diff --git a/hostapd/ctrl_iface.c b/hostapd/ctrl_iface.c index 54b17dc93..7d97484a1 100644 --- a/hostapd/ctrl_iface.c +++ b/hostapd/ctrl_iface.c @@ -1955,6 +1955,9 @@ static void hostapd_ctrl_iface_receive(int sock, void *eloop_ctx, } else if (os_strncmp(buf, "DISASSOCIATE ", 13) == 0) { if (hostapd_ctrl_iface_disassociate(hapd, buf + 13)) reply_len = -1; + } else if (os_strcmp(buf, "STOP_AP") == 0) { + if (hostapd_ctrl_iface_stop_ap(hapd)) + reply_len = -1; #ifdef CONFIG_IEEE80211W #ifdef NEED_AP_MLME } else if (os_strncmp(buf, "SA_QUERY ", 9) == 0) { diff --git a/src/ap/ap_drv_ops.h b/src/ap/ap_drv_ops.h index c133be754..1c8069506 100644 --- a/src/ap/ap_drv_ops.h +++ b/src/ap/ap_drv_ops.h @@ -335,4 +335,11 @@ static inline int hostapd_drv_vendor_cmd(struct hostapd_data *hapd, data_len, buf); } +static inline int hostapd_drv_stop_ap(struct hostapd_data *hapd) +{ + if (hapd->driver == NULL || hapd->driver->stop_ap == NULL) + return 0; + return hapd->driver->stop_ap(hapd->drv_priv); +} + #endif /* AP_DRV_OPS */ diff --git a/src/ap/ctrl_iface_ap.c b/src/ap/ctrl_iface_ap.c index 8c84e3ef1..41ab98827 100644 --- a/src/ap/ctrl_iface_ap.c +++ b/src/ap/ctrl_iface_ap.c @@ -537,3 +537,9 @@ int hostapd_parse_csa_settings(const char *pos, return 0; } + + +int hostapd_ctrl_iface_stop_ap(struct hostapd_data *hapd) +{ + return hostapd_drv_stop_ap(hapd); +} diff --git a/src/ap/ctrl_iface_ap.h b/src/ap/ctrl_iface_ap.h index ee58b4c96..e5297d03e 100644 --- a/src/ap/ctrl_iface_ap.h +++ b/src/ap/ctrl_iface_ap.h @@ -23,6 +23,6 @@ int hostapd_ctrl_iface_status(struct hostapd_data *hapd, char *buf, size_t buflen); int hostapd_parse_csa_settings(const char *pos, struct csa_settings *settings); - +int hostapd_ctrl_iface_stop_ap(struct hostapd_data *hapd); #endif /* CTRL_IFACE_AP_H */ diff --git a/wpa_supplicant/ap.c b/wpa_supplicant/ap.c index 65532e3cb..fca2137c6 100644 --- a/wpa_supplicant/ap.c +++ b/wpa_supplicant/ap.c @@ -1238,3 +1238,14 @@ int wpas_ap_wps_add_nfc_pw(struct wpa_supplicant *wpa_s, u16 pw_id, pw ? wpabuf_len(pw) : 0, 1); } #endif /* CONFIG_WPS_NFC */ + + +int wpas_ap_stop_ap(struct wpa_supplicant *wpa_s) +{ + struct hostapd_data *hapd; + + if (!wpa_s->ap_iface) + return -1; + hapd = wpa_s->ap_iface->bss[0]; + return hostapd_ctrl_iface_stop_ap(hapd); +} diff --git a/wpa_supplicant/ap.h b/wpa_supplicant/ap.h index 4d80c7a7c..6a1183424 100644 --- a/wpa_supplicant/ap.h +++ b/wpa_supplicant/ap.h @@ -80,4 +80,6 @@ void wpa_supplicant_conf_ap_ht(struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid, struct hostapd_config *conf); +int wpas_ap_stop_ap(struct wpa_supplicant *wpa_s); + #endif /* AP_H */ diff --git a/wpa_supplicant/ctrl_iface.c b/wpa_supplicant/ctrl_iface.c index 7a77a7f19..c4a457748 100644 --- a/wpa_supplicant/ctrl_iface.c +++ b/wpa_supplicant/ctrl_iface.c @@ -8278,6 +8278,9 @@ char * wpa_supplicant_ctrl_iface_process(struct wpa_supplicant *wpa_s, } else if (os_strncmp(buf, "CHAN_SWITCH ", 12) == 0) { if (ap_ctrl_iface_chanswitch(wpa_s, buf + 12)) reply_len = -1; + } else if (os_strcmp(buf, "STOP_AP") == 0) { + if (wpas_ap_stop_ap(wpa_s)) + reply_len = -1; #endif /* CONFIG_AP */ } else if (os_strcmp(buf, "SUSPEND") == 0) { wpas_notify_suspend(wpa_s->global);