wpa_s, NULL);
#endif /* CONFIG_DELAYED_MIC_ERROR_REPORT */
+ eloop_cancel_timeout(wpas_network_reenabled, wpa_s, NULL);
+
wpas_wps_deinit(wpa_s);
wpabuf_free(wpa_s->pending_eapol_rx);
eapol_sm_invalidate_cached_session(wpa_s->eapol);
if (wpa_s->current_ssid) {
+ wpa_s->own_disconnect_req = 1;
wpa_supplicant_deauthenticate(wpa_s,
WLAN_REASON_DEAUTH_LEAVING);
}
vht_freq.vht_enabled,
freq->sec_channel_offset,
VHT_CHANWIDTH_80MHZ,
- vht80[i] + 6, 0, 0) != 0)
+ vht80[j] + 6, 0, 0) != 0)
return;
*freq = vht_freq;
int disconnected = 0;
if (ssid && ssid != wpa_s->current_ssid && wpa_s->current_ssid) {
+ wpa_s->own_disconnect_req = 1;
wpa_supplicant_deauthenticate(
wpa_s, WLAN_REASON_DEAUTH_LEAVING);
disconnected = 1;
eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
wpa_s->connect_without_scan =
(ssid->mode == WPAS_MODE_MESH) ? ssid : NULL;
+
+ /*
+ * Don't optimize next scan freqs since a new ESS has been
+ * selected.
+ */
+ os_free(wpa_s->next_scan_freqs);
+ wpa_s->next_scan_freqs = NULL;
} else {
wpa_s->connect_without_scan = NULL;
}
}
-static struct wpa_supplicant * wpa_supplicant_alloc(void)
+static struct wpa_supplicant *
+wpa_supplicant_alloc(struct wpa_supplicant *parent)
{
struct wpa_supplicant *wpa_s;
wpa_s->scan_req = INITIAL_SCAN_REQ;
wpa_s->scan_interval = 5;
wpa_s->new_connection = 1;
- wpa_s->parent = wpa_s;
+ wpa_s->parent = parent ? parent : wpa_s;
wpa_s->sched_scanning = 0;
return wpa_s;
wpa_s->hw.modes = wpa_drv_get_hw_feature_data(wpa_s,
&wpa_s->hw.num_modes,
&wpa_s->hw.flags);
+ if (wpa_s->hw.modes) {
+ u16 i;
+
+ for (i = 0; i < wpa_s->hw.num_modes; i++) {
+ if (wpa_s->hw.modes[i].vht_capab) {
+ wpa_s->hw_capab = CAPAB_VHT;
+ break;
+ }
+
+ if (wpa_s->hw.modes[i].ht_capab &
+ HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET)
+ wpa_s->hw_capab = CAPAB_HT40;
+ else if (wpa_s->hw.modes[i].ht_capab &&
+ wpa_s->hw_capab == CAPAB_NO_HT_VHT)
+ wpa_s->hw_capab = CAPAB_HT;
+ }
+ }
capa_res = wpa_drv_get_capa(wpa_s, &capa);
if (capa_res == 0) {
* wpa_supplicant_add_iface - Add a new network interface
* @global: Pointer to global data from wpa_supplicant_init()
* @iface: Interface configuration options
+ * @parent: Parent interface or %NULL to assign new interface as parent
* Returns: Pointer to the created interface or %NULL on failure
*
* This function is used to add new network interfaces for %wpa_supplicant.
* e.g., when a hotplug network adapter is inserted.
*/
struct wpa_supplicant * wpa_supplicant_add_iface(struct wpa_global *global,
- struct wpa_interface *iface)
+ struct wpa_interface *iface,
+ struct wpa_supplicant *parent)
{
struct wpa_supplicant *wpa_s;
struct wpa_interface t_iface;
if (global == NULL || iface == NULL)
return NULL;
- wpa_s = wpa_supplicant_alloc();
+ wpa_s = wpa_supplicant_alloc(parent);
if (wpa_s == NULL)
return NULL;
*/
eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL);
+ /*
+ * There is no point in blacklisting the AP if this event is
+ * generated based on local request to disconnect.
+ */
+ if (wpa_s->own_disconnect_req) {
+ wpa_s->own_disconnect_req = 0;
+ wpa_dbg(wpa_s, MSG_DEBUG,
+ "Ignore connection failure due to local request to disconnect");
+ return;
+ }
if (wpa_s->disconnected) {
- /*
- * There is no point in blacklisting the AP if this event is
- * generated based on local request to disconnect.
- */
wpa_dbg(wpa_s, MSG_DEBUG, "Ignore connection failure "
"indication since interface has been put into "
"disconnected state");
int i;
unsigned int drv_enc;
+ if (wpa_s->p2p_mgmt)
+ return 1; /* no normal network profiles on p2p_mgmt interface */
+
if (ssid == NULL)
return 1;
if (ssid->disabled)
return 1;
- if (wpa_s && wpa_s->drv_capa_known)
+ if (wpa_s->drv_capa_known)
drv_enc = wpa_s->drv_enc;
else
drv_enc = (unsigned int) -1;