]> git.ipfire.org Git - thirdparty/hostap.git/blame - wpa_supplicant/wpa_supplicant.c
FILS: Allow eap_peer_get_erp_info() to be called without config
[thirdparty/hostap.git] / wpa_supplicant / wpa_supplicant.c
CommitLineData
6fc6879b
JM
1/*
2 * WPA Supplicant
6774c6a9 3 * Copyright (c) 2003-2017, Jouni Malinen <j@w1.fi>
6fc6879b 4 *
0f3d578e
JM
5 * This software may be distributed under the terms of the BSD license.
6 * See README for more details.
6fc6879b
JM
7 *
8 * This file implements functions for registering and unregistering
9 * %wpa_supplicant interfaces. In addition, this file contains number of
10 * functions for managing network connections.
11 */
12
13#include "includes.h"
2e997eec
RM
14#ifdef CONFIG_MATCH_IFACE
15#include <net/if.h>
16#include <fnmatch.h>
17#endif /* CONFIG_MATCH_IFACE */
6fc6879b
JM
18
19#include "common.h"
d47fa330 20#include "crypto/random.h"
7d232e23 21#include "crypto/sha1.h"
6fc6879b
JM
22#include "eapol_supp/eapol_supp_sm.h"
23#include "eap_peer/eap.h"
ec7b97ab 24#include "eap_peer/eap_proxy.h"
3ec97afe 25#include "eap_server/eap_methods.h"
3acb5005 26#include "rsn_supp/wpa.h"
6fc6879b 27#include "eloop.h"
6fc6879b 28#include "config.h"
306ae225 29#include "utils/ext_password.h"
6fc6879b
JM
30#include "l2_packet/l2_packet.h"
31#include "wpa_supplicant_i.h"
2d5b792d 32#include "driver_i.h"
6fc6879b 33#include "ctrl_iface.h"
6fc6879b 34#include "pcsc_funcs.h"
90973fb2 35#include "common/version.h"
3acb5005
JM
36#include "rsn_supp/preauth.h"
37#include "rsn_supp/pmksa_cache.h"
90973fb2 38#include "common/wpa_ctrl.h"
90973fb2 39#include "common/ieee802_11_defs.h"
6b8b0774 40#include "common/hw_features_common.h"
461d39af 41#include "common/gas_server.h"
72044390 42#include "p2p/p2p.h"
b36a3a65 43#include "fst/fst.h"
6fc6879b
JM
44#include "blacklist.h"
45#include "wpas_glue.h"
116654ce 46#include "wps_supplicant.h"
11ef8d35 47#include "ibss_rsn.h"
c2a04078 48#include "sme.h"
04ea7b79 49#include "gas_query.h"
1f1b62a0 50#include "ap.h"
b22128ef 51#include "p2p_supplicant.h"
9675ce35 52#include "wifi_display.h"
8bac466b 53#include "notify.h"
60b94c98 54#include "bgscan.h"
7c865c68 55#include "autoscan.h"
83922c2d 56#include "bss.h"
9ba9fa07 57#include "scan.h"
24f6497c 58#include "offchannel.h"
cb418324 59#include "hs20_supplicant.h"
e27d20bb 60#include "wnm_sta.h"
dd10abcc 61#include "wpas_kay.h"
603a3f34 62#include "mesh.h"
be27e185 63#include "dpp_supplicant.h"
a39b040b
SB
64#ifdef CONFIG_MESH
65#include "ap/ap_config.h"
66#include "ap/hostapd.h"
67#endif /* CONFIG_MESH */
6fc6879b 68
8b423edb 69const char *const wpa_supplicant_version =
6fc6879b 70"wpa_supplicant v" VERSION_STR "\n"
6774c6a9 71"Copyright (c) 2003-2017, Jouni Malinen <j@w1.fi> and contributors";
6fc6879b 72
8b423edb 73const char *const wpa_supplicant_license =
331f89ff
JM
74"This software may be distributed under the terms of the BSD license.\n"
75"See README for more details.\n"
6fc6879b
JM
76#ifdef EAP_TLS_OPENSSL
77"\nThis product includes software developed by the OpenSSL Project\n"
78"for use in the OpenSSL Toolkit (http://www.openssl.org/)\n"
79#endif /* EAP_TLS_OPENSSL */
80;
81
82#ifndef CONFIG_NO_STDOUT_DEBUG
83/* Long text divided into parts in order to fit in C89 strings size limits. */
8b423edb 84const char *const wpa_supplicant_full_license1 =
331f89ff 85"";
8b423edb 86const char *const wpa_supplicant_full_license2 =
331f89ff 87"This software may be distributed under the terms of the BSD license.\n"
6fc6879b
JM
88"\n"
89"Redistribution and use in source and binary forms, with or without\n"
90"modification, are permitted provided that the following conditions are\n"
91"met:\n"
92"\n";
8b423edb 93const char *const wpa_supplicant_full_license3 =
6fc6879b
JM
94"1. Redistributions of source code must retain the above copyright\n"
95" notice, this list of conditions and the following disclaimer.\n"
96"\n"
97"2. Redistributions in binary form must reproduce the above copyright\n"
98" notice, this list of conditions and the following disclaimer in the\n"
99" documentation and/or other materials provided with the distribution.\n"
100"\n";
8b423edb 101const char *const wpa_supplicant_full_license4 =
6fc6879b
JM
102"3. Neither the name(s) of the above-listed copyright holder(s) nor the\n"
103" names of its contributors may be used to endorse or promote products\n"
104" derived from this software without specific prior written permission.\n"
105"\n"
106"THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n"
107"\"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n"
108"LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\n"
109"A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\n";
8b423edb 110const char *const wpa_supplicant_full_license5 =
6fc6879b
JM
111"OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\n"
112"SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\n"
113"LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\n"
114"DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\n"
115"THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n"
116"(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\n"
117"OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
118"\n";
119#endif /* CONFIG_NO_STDOUT_DEBUG */
120
b04854ce
AP
121
122static void wpa_bss_tmp_disallow_timeout(void *eloop_ctx, void *timeout_ctx);
123
124
6fc6879b 125/* Configure default/group WEP keys for static WEP */
0194fedb 126int wpa_set_wep_keys(struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid)
6fc6879b
JM
127{
128 int i, set = 0;
129
130 for (i = 0; i < NUM_WEP_KEYS; i++) {
131 if (ssid->wep_key_len[i] == 0)
132 continue;
133
134 set = 1;
0382097e 135 wpa_drv_set_key(wpa_s, WPA_ALG_WEP, NULL,
da64c266 136 i, i == ssid->wep_tx_keyidx, NULL, 0,
6fc6879b
JM
137 ssid->wep_key[i], ssid->wep_key_len[i]);
138 }
139
140 return set;
141}
142
143
6ea1f413
JM
144int wpa_supplicant_set_wpa_none_key(struct wpa_supplicant *wpa_s,
145 struct wpa_ssid *ssid)
6fc6879b
JM
146{
147 u8 key[32];
148 size_t keylen;
71934751 149 enum wpa_alg alg;
6fc6879b 150 u8 seq[6] = { 0 };
658da804 151 int ret;
6fc6879b
JM
152
153 /* IBSS/WPA-None uses only one key (Group) for both receiving and
154 * sending unicast and multicast packets. */
155
d7dcba70 156 if (ssid->mode != WPAS_MODE_IBSS) {
f049052b
BG
157 wpa_msg(wpa_s, MSG_INFO, "WPA: Invalid mode %d (not "
158 "IBSS/ad-hoc) for WPA-None", ssid->mode);
6fc6879b
JM
159 return -1;
160 }
161
162 if (!ssid->psk_set) {
f049052b
BG
163 wpa_msg(wpa_s, MSG_INFO, "WPA: No PSK configured for "
164 "WPA-None");
6fc6879b
JM
165 return -1;
166 }
167
168 switch (wpa_s->group_cipher) {
169 case WPA_CIPHER_CCMP:
170 os_memcpy(key, ssid->psk, 16);
171 keylen = 16;
172 alg = WPA_ALG_CCMP;
173 break;
eb7719ff
JM
174 case WPA_CIPHER_GCMP:
175 os_memcpy(key, ssid->psk, 16);
176 keylen = 16;
177 alg = WPA_ALG_GCMP;
178 break;
6fc6879b
JM
179 case WPA_CIPHER_TKIP:
180 /* WPA-None uses the same Michael MIC key for both TX and RX */
181 os_memcpy(key, ssid->psk, 16 + 8);
182 os_memcpy(key + 16 + 8, ssid->psk + 16, 8);
183 keylen = 32;
184 alg = WPA_ALG_TKIP;
185 break;
186 default:
f049052b
BG
187 wpa_msg(wpa_s, MSG_INFO, "WPA: Invalid group cipher %d for "
188 "WPA-None", wpa_s->group_cipher);
6fc6879b
JM
189 return -1;
190 }
191
192 /* TODO: should actually remember the previously used seq#, both for TX
193 * and RX from each STA.. */
194
658da804
JM
195 ret = wpa_drv_set_key(wpa_s, alg, NULL, 0, 1, seq, 6, key, keylen);
196 os_memset(key, 0, sizeof(key));
197 return ret;
6fc6879b
JM
198}
199
200
201static void wpa_supplicant_timeout(void *eloop_ctx, void *timeout_ctx)
202{
203 struct wpa_supplicant *wpa_s = eloop_ctx;
204 const u8 *bssid = wpa_s->bssid;
04e3d815
MK
205 if (!is_zero_ether_addr(wpa_s->pending_bssid) &&
206 (wpa_s->wpa_state == WPA_AUTHENTICATING ||
207 wpa_s->wpa_state == WPA_ASSOCIATING))
6fc6879b
JM
208 bssid = wpa_s->pending_bssid;
209 wpa_msg(wpa_s, MSG_INFO, "Authentication with " MACSTR " timed out.",
210 MAC2STR(bssid));
211 wpa_blacklist_add(wpa_s, bssid);
212 wpa_sm_notify_disassoc(wpa_s->wpa);
07783eaa 213 wpa_supplicant_deauthenticate(wpa_s, WLAN_REASON_DEAUTH_LEAVING);
6fc6879b 214 wpa_s->reassociate = 1;
48b84f18
BG
215
216 /*
217 * If we timed out, the AP or the local radio may be busy.
218 * So, wait a second until scanning again.
219 */
220 wpa_supplicant_req_scan(wpa_s, 1, 0);
6fc6879b
JM
221}
222
223
224/**
225 * wpa_supplicant_req_auth_timeout - Schedule a timeout for authentication
226 * @wpa_s: Pointer to wpa_supplicant data
227 * @sec: Number of seconds after which to time out authentication
228 * @usec: Number of microseconds after which to time out authentication
229 *
230 * This function is used to schedule a timeout for the current authentication
231 * attempt.
232 */
233void wpa_supplicant_req_auth_timeout(struct wpa_supplicant *wpa_s,
234 int sec, int usec)
235{
a2a535f8 236 if (wpa_s->conf->ap_scan == 0 &&
c2a04078 237 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED))
6fc6879b
JM
238 return;
239
f049052b 240 wpa_dbg(wpa_s, MSG_DEBUG, "Setting authentication timeout: %d sec "
6fc6879b
JM
241 "%d usec", sec, usec);
242 eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL);
243 eloop_register_timeout(sec, usec, wpa_supplicant_timeout, wpa_s, NULL);
244}
245
246
247/**
248 * wpa_supplicant_cancel_auth_timeout - Cancel authentication timeout
249 * @wpa_s: Pointer to wpa_supplicant data
250 *
251 * This function is used to cancel authentication timeout scheduled with
252 * wpa_supplicant_req_auth_timeout() and it is called when authentication has
253 * been completed.
254 */
255void wpa_supplicant_cancel_auth_timeout(struct wpa_supplicant *wpa_s)
256{
f049052b 257 wpa_dbg(wpa_s, MSG_DEBUG, "Cancelling authentication timeout");
6fc6879b
JM
258 eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL);
259 wpa_blacklist_del(wpa_s, wpa_s->bssid);
260}
261
262
263/**
264 * wpa_supplicant_initiate_eapol - Configure EAPOL state machine
265 * @wpa_s: Pointer to wpa_supplicant data
266 *
267 * This function is used to configure EAPOL state machine based on the selected
268 * authentication mode.
269 */
270void wpa_supplicant_initiate_eapol(struct wpa_supplicant *wpa_s)
271{
272#ifdef IEEE8021X_EAPOL
273 struct eapol_config eapol_conf;
274 struct wpa_ssid *ssid = wpa_s->current_ssid;
275
53895c3b 276#ifdef CONFIG_IBSS_RSN
d7dcba70 277 if (ssid->mode == WPAS_MODE_IBSS &&
53895c3b
JM
278 wpa_s->key_mgmt != WPA_KEY_MGMT_NONE &&
279 wpa_s->key_mgmt != WPA_KEY_MGMT_WPA_NONE) {
280 /*
281 * RSN IBSS authentication is per-STA and we can disable the
282 * per-BSSID EAPOL authentication.
283 */
284 eapol_sm_notify_portControl(wpa_s->eapol, ForceAuthorized);
285 eapol_sm_notify_eap_success(wpa_s->eapol, TRUE);
286 eapol_sm_notify_eap_fail(wpa_s->eapol, FALSE);
287 return;
288 }
289#endif /* CONFIG_IBSS_RSN */
290
0a40ec6a
JM
291 eapol_sm_notify_eap_success(wpa_s->eapol, FALSE);
292 eapol_sm_notify_eap_fail(wpa_s->eapol, FALSE);
293
6fc6879b
JM
294 if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE ||
295 wpa_s->key_mgmt == WPA_KEY_MGMT_WPA_NONE)
296 eapol_sm_notify_portControl(wpa_s->eapol, ForceAuthorized);
297 else
298 eapol_sm_notify_portControl(wpa_s->eapol, Auto);
299
300 os_memset(&eapol_conf, 0, sizeof(eapol_conf));
301 if (wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) {
302 eapol_conf.accept_802_1x_keys = 1;
303 eapol_conf.required_keys = 0;
304 if (ssid->eapol_flags & EAPOL_FLAG_REQUIRE_KEY_UNICAST) {
305 eapol_conf.required_keys |= EAPOL_REQUIRE_KEY_UNICAST;
306 }
307 if (ssid->eapol_flags & EAPOL_FLAG_REQUIRE_KEY_BROADCAST) {
308 eapol_conf.required_keys |=
309 EAPOL_REQUIRE_KEY_BROADCAST;
310 }
311
a2a535f8 312 if (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED)
6fc6879b 313 eapol_conf.required_keys = 0;
6fc6879b 314 }
a2a535f8 315 eapol_conf.fast_reauth = wpa_s->conf->fast_reauth;
6fc6879b 316 eapol_conf.workaround = ssid->eap_workaround;
56586197
JM
317 eapol_conf.eap_disabled =
318 !wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) &&
ad08c363
JM
319 wpa_s->key_mgmt != WPA_KEY_MGMT_IEEE8021X_NO_WPA &&
320 wpa_s->key_mgmt != WPA_KEY_MGMT_WPS;
a5d44ac0 321 eapol_conf.external_sim = wpa_s->conf->external_sim;
3f7ac058
JS
322
323#ifdef CONFIG_WPS
324 if (wpa_s->key_mgmt == WPA_KEY_MGMT_WPS) {
325 eapol_conf.wps |= EAPOL_LOCAL_WPS_IN_USE;
326 if (wpa_s->current_bss) {
327 struct wpabuf *ie;
328 ie = wpa_bss_get_vendor_ie_multi(wpa_s->current_bss,
329 WPS_IE_VENDOR_TYPE);
330 if (ie) {
331 if (wps_is_20(ie))
332 eapol_conf.wps |=
333 EAPOL_PEER_IS_WPS20_AP;
334 wpabuf_free(ie);
335 }
336 }
337 }
338#endif /* CONFIG_WPS */
339
6fc6879b 340 eapol_sm_notify_config(wpa_s->eapol, &ssid->eap, &eapol_conf);
dd10abcc 341
ad51731a
SD
342#ifdef CONFIG_MACSEC
343 if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE && ssid->mka_psk_set)
344 ieee802_1x_create_preshared_mka(wpa_s, ssid);
345 else
346 ieee802_1x_alloc_kay_sm(wpa_s, ssid);
347#endif /* CONFIG_MACSEC */
cd3153a9 348#endif /* IEEE8021X_EAPOL */
6fc6879b
JM
349}
350
351
352/**
353 * wpa_supplicant_set_non_wpa_policy - Set WPA parameters to non-WPA mode
354 * @wpa_s: Pointer to wpa_supplicant data
355 * @ssid: Configuration data for the network
356 *
357 * This function is used to configure WPA state machine and related parameters
358 * to a mode where WPA is not enabled. This is called as part of the
359 * authentication configuration when the selected network does not use WPA.
360 */
361void wpa_supplicant_set_non_wpa_policy(struct wpa_supplicant *wpa_s,
362 struct wpa_ssid *ssid)
363{
364 int i;
365
ad08c363
JM
366 if (ssid->key_mgmt & WPA_KEY_MGMT_WPS)
367 wpa_s->key_mgmt = WPA_KEY_MGMT_WPS;
368 else if (ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_NO_WPA)
6fc6879b
JM
369 wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X_NO_WPA;
370 else
371 wpa_s->key_mgmt = WPA_KEY_MGMT_NONE;
372 wpa_sm_set_ap_wpa_ie(wpa_s->wpa, NULL, 0);
373 wpa_sm_set_ap_rsn_ie(wpa_s->wpa, NULL, 0);
374 wpa_sm_set_assoc_wpa_ie(wpa_s->wpa, NULL, 0);
375 wpa_s->pairwise_cipher = WPA_CIPHER_NONE;
376 wpa_s->group_cipher = WPA_CIPHER_NONE;
377 wpa_s->mgmt_group_cipher = 0;
378
379 for (i = 0; i < NUM_WEP_KEYS; i++) {
380 if (ssid->wep_key_len[i] > 5) {
381 wpa_s->pairwise_cipher = WPA_CIPHER_WEP104;
382 wpa_s->group_cipher = WPA_CIPHER_WEP104;
383 break;
384 } else if (ssid->wep_key_len[i] > 0) {
385 wpa_s->pairwise_cipher = WPA_CIPHER_WEP40;
386 wpa_s->group_cipher = WPA_CIPHER_WEP40;
387 break;
388 }
389 }
390
391 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_RSN_ENABLED, 0);
392 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_KEY_MGMT, wpa_s->key_mgmt);
393 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_PAIRWISE,
394 wpa_s->pairwise_cipher);
395 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_GROUP, wpa_s->group_cipher);
396#ifdef CONFIG_IEEE80211W
397 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_MGMT_GROUP,
398 wpa_s->mgmt_group_cipher);
399#endif /* CONFIG_IEEE80211W */
400
401 pmksa_cache_clear_current(wpa_s->wpa);
402}
403
404
6979582c 405void free_hw_features(struct wpa_supplicant *wpa_s)
6bf731e8
CL
406{
407 int i;
408 if (wpa_s->hw.modes == NULL)
409 return;
410
411 for (i = 0; i < wpa_s->hw.num_modes; i++) {
412 os_free(wpa_s->hw.modes[i].channels);
413 os_free(wpa_s->hw.modes[i].rates);
414 }
415
416 os_free(wpa_s->hw.modes);
417 wpa_s->hw.modes = NULL;
418}
419
420
dd599908
AS
421static void free_bss_tmp_disallowed(struct wpa_supplicant *wpa_s)
422{
423 struct wpa_bss_tmp_disallowed *bss, *prev;
424
425 dl_list_for_each_safe(bss, prev, &wpa_s->bss_tmp_disallowed,
426 struct wpa_bss_tmp_disallowed, list) {
b04854ce 427 eloop_cancel_timeout(wpa_bss_tmp_disallow_timeout, wpa_s, bss);
dd599908
AS
428 dl_list_del(&bss->list);
429 os_free(bss);
430 }
431}
432
433
5732b770
JM
434void wpas_flush_fils_hlp_req(struct wpa_supplicant *wpa_s)
435{
436 struct fils_hlp_req *req;
437
438 while ((req = dl_list_first(&wpa_s->fils_hlp_req, struct fils_hlp_req,
439 list)) != NULL) {
440 dl_list_del(&req->list);
441 wpabuf_free(req->pkt);
442 os_free(req);
443 }
444}
445
446
6fc6879b
JM
447static void wpa_supplicant_cleanup(struct wpa_supplicant *wpa_s)
448{
86bd36f0
JM
449 int i;
450
60b94c98 451 bgscan_deinit(wpa_s);
7c865c68 452 autoscan_deinit(wpa_s);
6fc6879b
JM
453 scard_deinit(wpa_s->scard);
454 wpa_s->scard = NULL;
455 wpa_sm_set_scard_ctx(wpa_s->wpa, NULL);
456 eapol_sm_register_scard_ctx(wpa_s->eapol, NULL);
457 l2_packet_deinit(wpa_s->l2);
458 wpa_s->l2 = NULL;
459 if (wpa_s->l2_br) {
460 l2_packet_deinit(wpa_s->l2_br);
461 wpa_s->l2_br = NULL;
462 }
4a6cc862
JM
463#ifdef CONFIG_TESTING_OPTIONS
464 l2_packet_deinit(wpa_s->l2_test);
465 wpa_s->l2_test = NULL;
c06fca04
JM
466 os_free(wpa_s->get_pref_freq_list_override);
467 wpa_s->get_pref_freq_list_override = NULL;
daa40960
JM
468 wpabuf_free(wpa_s->last_assoc_req_wpa_ie);
469 wpa_s->last_assoc_req_wpa_ie = NULL;
4a6cc862 470#endif /* CONFIG_TESTING_OPTIONS */
6fc6879b 471
6fc6879b 472 if (wpa_s->conf != NULL) {
8e56d189
JM
473 struct wpa_ssid *ssid;
474 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next)
475 wpas_notify_network_removed(wpa_s, ssid);
6fc6879b
JM
476 }
477
478 os_free(wpa_s->confname);
479 wpa_s->confname = NULL;
480
e6304cad
DS
481 os_free(wpa_s->confanother);
482 wpa_s->confanother = NULL;
483
6fc6879b
JM
484 wpa_sm_set_eapol(wpa_s->wpa, NULL);
485 eapol_sm_deinit(wpa_s->eapol);
486 wpa_s->eapol = NULL;
487
488 rsn_preauth_deinit(wpa_s->wpa);
489
281ff0aa
GP
490#ifdef CONFIG_TDLS
491 wpa_tdls_deinit(wpa_s->wpa);
492#endif /* CONFIG_TDLS */
493
8c42b369 494 wmm_ac_clear_saved_tspecs(wpa_s);
6fc6879b
JM
495 pmksa_candidate_free(wpa_s->wpa);
496 wpa_sm_deinit(wpa_s->wpa);
497 wpa_s->wpa = NULL;
498 wpa_blacklist_clear(wpa_s);
499
83922c2d 500 wpa_bss_deinit(wpa_s);
6fc6879b 501
831770bf 502 wpa_supplicant_cancel_delayed_sched_scan(wpa_s);
6fc6879b
JM
503 wpa_supplicant_cancel_scan(wpa_s);
504 wpa_supplicant_cancel_auth_timeout(wpa_s);
01a17491
JM
505 eloop_cancel_timeout(wpa_supplicant_stop_countermeasures, wpa_s, NULL);
506#ifdef CONFIG_DELAYED_MIC_ERROR_REPORT
507 eloop_cancel_timeout(wpa_supplicant_delayed_mic_error_report,
508 wpa_s, NULL);
509#endif /* CONFIG_DELAYED_MIC_ERROR_REPORT */
6fc6879b 510
9bd566a3
AS
511 eloop_cancel_timeout(wpas_network_reenabled, wpa_s, NULL);
512
116654ce 513 wpas_wps_deinit(wpa_s);
11ef8d35 514
1ff73338
JM
515 wpabuf_free(wpa_s->pending_eapol_rx);
516 wpa_s->pending_eapol_rx = NULL;
517
11ef8d35
JM
518#ifdef CONFIG_IBSS_RSN
519 ibss_rsn_deinit(wpa_s->ibss_rsn);
520 wpa_s->ibss_rsn = NULL;
521#endif /* CONFIG_IBSS_RSN */
c2a04078 522
e29853bb 523 sme_deinit(wpa_s);
2d5b792d
JM
524
525#ifdef CONFIG_AP
526 wpa_supplicant_ap_deinit(wpa_s);
527#endif /* CONFIG_AP */
b22128ef 528
b22128ef 529 wpas_p2p_deinit(wpa_s);
f47d639d 530
24f6497c
JM
531#ifdef CONFIG_OFFCHANNEL
532 offchannel_deinit(wpa_s);
533#endif /* CONFIG_OFFCHANNEL */
534
a4cba8f1
LC
535 wpa_supplicant_cancel_sched_scan(wpa_s);
536
f47d639d
JM
537 os_free(wpa_s->next_scan_freqs);
538 wpa_s->next_scan_freqs = NULL;
fee52342
JM
539
540 os_free(wpa_s->manual_scan_freqs);
541 wpa_s->manual_scan_freqs = NULL;
88a44755
JM
542 os_free(wpa_s->select_network_scan_freqs);
543 wpa_s->select_network_scan_freqs = NULL;
04ea7b79 544
d3c9c35f
DS
545 os_free(wpa_s->manual_sched_scan_freqs);
546 wpa_s->manual_sched_scan_freqs = NULL;
547
56c76fa5
IP
548 wpas_mac_addr_rand_scan_clear(wpa_s, MAC_ADDR_RAND_ALL);
549
57e832de
IP
550 /*
551 * Need to remove any pending gas-query radio work before the
552 * gas_query_deinit() call because gas_query::work has not yet been set
553 * for works that have not been started. gas_query_free() will be unable
554 * to cancel such pending radio works and once the pending gas-query
555 * radio work eventually gets removed, the deinit notification call to
556 * gas_query_start_cb() would result in dereferencing freed memory.
557 */
558 if (wpa_s->radio)
559 radio_remove_works(wpa_s, "gas-query", 0);
04ea7b79
JM
560 gas_query_deinit(wpa_s->gas);
561 wpa_s->gas = NULL;
461d39af
JM
562 gas_server_deinit(wpa_s->gas_server);
563 wpa_s->gas_server = NULL;
6bf731e8
CL
564
565 free_hw_features(wpa_s);
d445a5cd 566
dd10abcc
HW
567 ieee802_1x_dealloc_kay_sm(wpa_s);
568
d445a5cd
JM
569 os_free(wpa_s->bssid_filter);
570 wpa_s->bssid_filter = NULL;
b6668734 571
6407f413
JM
572 os_free(wpa_s->disallow_aps_bssid);
573 wpa_s->disallow_aps_bssid = NULL;
574 os_free(wpa_s->disallow_aps_ssid);
575 wpa_s->disallow_aps_ssid = NULL;
576
b6668734 577 wnm_bss_keep_alive_deinit(wpa_s);
e27d20bb
VK
578#ifdef CONFIG_WNM
579 wnm_deallocate_memory(wpa_s);
580#endif /* CONFIG_WNM */
306ae225
JM
581
582 ext_password_deinit(wpa_s->ext_pw);
583 wpa_s->ext_pw = NULL;
b1f12296
JM
584
585 wpabuf_free(wpa_s->last_gas_resp);
b6a9590b
JM
586 wpa_s->last_gas_resp = NULL;
587 wpabuf_free(wpa_s->prev_gas_resp);
588 wpa_s->prev_gas_resp = NULL;
a297201d
JM
589
590 os_free(wpa_s->last_scan_res);
591 wpa_s->last_scan_res = NULL;
b572df86
JM
592
593#ifdef CONFIG_HS20
ece4ac5f
MG
594 if (wpa_s->drv_priv)
595 wpa_drv_configure_frame_filters(wpa_s, 0);
fb2ac53d 596 hs20_deinit(wpa_s);
b572df86 597#endif /* CONFIG_HS20 */
86bd36f0
JM
598
599 for (i = 0; i < NUM_VENDOR_ELEM_FRAMES; i++) {
600 wpabuf_free(wpa_s->vendor_elem[i]);
601 wpa_s->vendor_elem[i] = NULL;
602 }
3882a708
JM
603
604 wmm_ac_notify_disassoc(wpa_s);
32c02261
AS
605
606 wpa_s->sched_scan_plans_num = 0;
607 os_free(wpa_s->sched_scan_plans);
608 wpa_s->sched_scan_plans = NULL;
92c6e2e3
DS
609
610#ifdef CONFIG_MBO
611 wpa_s->non_pref_chan_num = 0;
612 os_free(wpa_s->non_pref_chan);
613 wpa_s->non_pref_chan = NULL;
614#endif /* CONFIG_MBO */
dd599908
AS
615
616 free_bss_tmp_disallowed(wpa_s);
4a742011
DS
617
618 wpabuf_free(wpa_s->lci);
619 wpa_s->lci = NULL;
76196ddb 620 wpas_clear_beacon_rep_data(wpa_s);
4d77d80e
MH
621
622#ifdef CONFIG_PMKSA_CACHE_EXTERNAL
623#ifdef CONFIG_MESH
624 {
625 struct external_pmksa_cache *entry;
626
627 while ((entry = dl_list_last(&wpa_s->mesh_external_pmksa_cache,
628 struct external_pmksa_cache,
629 list)) != NULL) {
630 dl_list_del(&entry->list);
631 os_free(entry->pmksa_cache);
632 os_free(entry);
633 }
634 }
635#endif /* CONFIG_MESH */
636#endif /* CONFIG_PMKSA_CACHE_EXTERNAL */
5732b770
JM
637
638 wpas_flush_fils_hlp_req(wpa_s);
c6c41f6e
JM
639
640 wpabuf_free(wpa_s->ric_ies);
641 wpa_s->ric_ies = NULL;
be27e185
JM
642
643#ifdef CONFIG_DPP
644 wpas_dpp_deinit(wpa_s);
645#endif /* CONFIG_DPP */
6fc6879b
JM
646}
647
648
649/**
650 * wpa_clear_keys - Clear keys configured for the driver
651 * @wpa_s: Pointer to wpa_supplicant data
652 * @addr: Previously used BSSID or %NULL if not available
653 *
654 * This function clears the encryption keys that has been previously configured
655 * for the driver.
656 */
657void wpa_clear_keys(struct wpa_supplicant *wpa_s, const u8 *addr)
658{
2f30cac3 659 int i, max;
6fc6879b 660
0e27f655 661#ifdef CONFIG_IEEE80211W
2f30cac3
JM
662 max = 6;
663#else /* CONFIG_IEEE80211W */
664 max = 4;
0e27f655 665#endif /* CONFIG_IEEE80211W */
2f30cac3
JM
666
667 /* MLME-DELETEKEYS.request */
668 for (i = 0; i < max; i++) {
669 if (wpa_s->keys_cleared & BIT(i))
670 continue;
671 wpa_drv_set_key(wpa_s, WPA_ALG_NONE, NULL, i, 0, NULL, 0,
672 NULL, 0);
673 }
674 if (!(wpa_s->keys_cleared & BIT(0)) && addr &&
675 !is_zero_ether_addr(addr)) {
6fc6879b
JM
676 wpa_drv_set_key(wpa_s, WPA_ALG_NONE, addr, 0, 0, NULL, 0, NULL,
677 0);
678 /* MLME-SETPROTECTION.request(None) */
679 wpa_drv_mlme_setprotection(
680 wpa_s, addr,
681 MLME_SETPROTECTION_PROTECT_TYPE_NONE,
682 MLME_SETPROTECTION_KEY_TYPE_PAIRWISE);
683 }
2f30cac3 684 wpa_s->keys_cleared = (u32) -1;
6fc6879b
JM
685}
686
687
688/**
689 * wpa_supplicant_state_txt - Get the connection state name as a text string
690 * @state: State (wpa_state; WPA_*)
691 * Returns: The state name as a printable text string
692 */
71934751 693const char * wpa_supplicant_state_txt(enum wpa_states state)
6fc6879b
JM
694{
695 switch (state) {
696 case WPA_DISCONNECTED:
697 return "DISCONNECTED";
698 case WPA_INACTIVE:
699 return "INACTIVE";
8401a6b0
JM
700 case WPA_INTERFACE_DISABLED:
701 return "INTERFACE_DISABLED";
6fc6879b
JM
702 case WPA_SCANNING:
703 return "SCANNING";
c2a04078
JM
704 case WPA_AUTHENTICATING:
705 return "AUTHENTICATING";
6fc6879b
JM
706 case WPA_ASSOCIATING:
707 return "ASSOCIATING";
708 case WPA_ASSOCIATED:
709 return "ASSOCIATED";
710 case WPA_4WAY_HANDSHAKE:
711 return "4WAY_HANDSHAKE";
712 case WPA_GROUP_HANDSHAKE:
713 return "GROUP_HANDSHAKE";
714 case WPA_COMPLETED:
715 return "COMPLETED";
716 default:
717 return "UNKNOWN";
718 }
719}
720
721
cfe53c9a
PS
722#ifdef CONFIG_BGSCAN
723
724static void wpa_supplicant_start_bgscan(struct wpa_supplicant *wpa_s)
725{
31392709
HD
726 const char *name;
727
728 if (wpa_s->current_ssid && wpa_s->current_ssid->bgscan)
729 name = wpa_s->current_ssid->bgscan;
730 else
731 name = wpa_s->conf->bgscan;
268043d5 732 if (name == NULL || name[0] == '\0')
31392709 733 return;
0096c427
JM
734 if (wpas_driver_bss_selection(wpa_s))
735 return;
cfe53c9a
PS
736 if (wpa_s->current_ssid == wpa_s->bgscan_ssid)
737 return;
aa109830
DS
738#ifdef CONFIG_P2P
739 if (wpa_s->p2p_group_interface != NOT_P2P_GROUP_INTERFACE)
740 return;
741#endif /* CONFIG_P2P */
cfe53c9a
PS
742
743 bgscan_deinit(wpa_s);
31392709
HD
744 if (wpa_s->current_ssid) {
745 if (bgscan_init(wpa_s, wpa_s->current_ssid, name)) {
cfe53c9a
PS
746 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to initialize "
747 "bgscan");
748 /*
749 * Live without bgscan; it is only used as a roaming
750 * optimization, so the initial connection is not
751 * affected.
752 */
6409b7a7
YD
753 } else {
754 struct wpa_scan_results *scan_res;
cfe53c9a 755 wpa_s->bgscan_ssid = wpa_s->current_ssid;
6409b7a7
YD
756 scan_res = wpa_supplicant_get_scan_results(wpa_s, NULL,
757 0);
758 if (scan_res) {
759 bgscan_notify_scan(wpa_s, scan_res);
760 wpa_scan_results_free(scan_res);
761 }
762 }
cfe53c9a
PS
763 } else
764 wpa_s->bgscan_ssid = NULL;
765}
766
767
768static void wpa_supplicant_stop_bgscan(struct wpa_supplicant *wpa_s)
769{
770 if (wpa_s->bgscan_ssid != NULL) {
771 bgscan_deinit(wpa_s);
772 wpa_s->bgscan_ssid = NULL;
773 }
774}
775
776#endif /* CONFIG_BGSCAN */
777
778
7c865c68
TB
779static void wpa_supplicant_start_autoscan(struct wpa_supplicant *wpa_s)
780{
99218999 781 if (autoscan_init(wpa_s, 0))
7c865c68
TB
782 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to initialize autoscan");
783}
784
785
786static void wpa_supplicant_stop_autoscan(struct wpa_supplicant *wpa_s)
787{
788 autoscan_deinit(wpa_s);
789}
790
791
c3d12238
JM
792void wpa_supplicant_reinit_autoscan(struct wpa_supplicant *wpa_s)
793{
794 if (wpa_s->wpa_state == WPA_DISCONNECTED ||
795 wpa_s->wpa_state == WPA_SCANNING) {
796 autoscan_deinit(wpa_s);
797 wpa_supplicant_start_autoscan(wpa_s);
798 }
799}
800
801
6fc6879b
JM
802/**
803 * wpa_supplicant_set_state - Set current connection state
804 * @wpa_s: Pointer to wpa_supplicant data
805 * @state: The new connection state
806 *
807 * This function is called whenever the connection state changes, e.g.,
808 * association is completed for WPA/WPA2 4-Way Handshake is started.
809 */
71934751
JM
810void wpa_supplicant_set_state(struct wpa_supplicant *wpa_s,
811 enum wpa_states state)
6fc6879b 812{
27f43d8d
MH
813 enum wpa_states old_state = wpa_s->wpa_state;
814
f049052b
BG
815 wpa_dbg(wpa_s, MSG_DEBUG, "State: %s -> %s",
816 wpa_supplicant_state_txt(wpa_s->wpa_state),
817 wpa_supplicant_state_txt(state));
6fc6879b 818
5ddd07cb
AS
819 if (state == WPA_INTERFACE_DISABLED) {
820 /* Assure normal scan when interface is restored */
821 wpa_s->normal_scans = 0;
822 }
823
0cf24fda 824 if (state == WPA_COMPLETED) {
6ac4b15e 825 wpas_connect_work_done(wpa_s);
0cf24fda
LC
826 /* Reinitialize normal_scan counter */
827 wpa_s->normal_scans = 0;
828 }
6ac4b15e 829
07c1e987
MS
830#ifdef CONFIG_P2P
831 /*
832 * P2PS client has to reply to Probe Request frames received on the
833 * group operating channel. Enable Probe Request frame reporting for
834 * P2P connected client in case p2p_cli_probe configuration property is
835 * set to 1.
836 */
837 if (wpa_s->conf->p2p_cli_probe && wpa_s->current_ssid &&
838 wpa_s->current_ssid->mode == WPAS_MODE_INFRA &&
839 wpa_s->current_ssid->p2p_group) {
840 if (state == WPA_COMPLETED && !wpa_s->p2p_cli_probe) {
841 wpa_dbg(wpa_s, MSG_DEBUG,
842 "P2P: Enable CLI Probe Request RX reporting");
843 wpa_s->p2p_cli_probe =
844 wpa_drv_probe_req_report(wpa_s, 1) >= 0;
845 } else if (state != WPA_COMPLETED && wpa_s->p2p_cli_probe) {
846 wpa_dbg(wpa_s, MSG_DEBUG,
847 "P2P: Disable CLI Probe Request RX reporting");
848 wpa_s->p2p_cli_probe = 0;
849 wpa_drv_probe_req_report(wpa_s, 0);
850 }
851 }
852#endif /* CONFIG_P2P */
853
cb8564b1
DW
854 if (state != WPA_SCANNING)
855 wpa_supplicant_notify_scanning(wpa_s, 0);
856
6fc6879b 857 if (state == WPA_COMPLETED && wpa_s->new_connection) {
6fc6879b 858 struct wpa_ssid *ssid = wpa_s->current_ssid;
da6a28ba
VK
859 int fils_hlp_sent = 0;
860
861#ifdef CONFIG_SME
862 if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_SME) &&
863 wpa_auth_alg_fils(wpa_s->sme.auth_alg))
864 fils_hlp_sent = 1;
865#endif /* CONFIG_SME */
866 if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_SME) &&
867 wpa_auth_alg_fils(wpa_s->auth_alg))
868 fils_hlp_sent = 1;
869
7d37a357 870#if defined(CONFIG_CTRL_IFACE) || !defined(CONFIG_NO_STDOUT_DEBUG)
6fc6879b 871 wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_CONNECTED "- Connection to "
da6a28ba 872 MACSTR " completed [id=%d id_str=%s%s]",
1cfc6787 873 MAC2STR(wpa_s->bssid),
6fc6879b 874 ssid ? ssid->id : -1,
da6a28ba
VK
875 ssid && ssid->id_str ? ssid->id_str : "",
876 fils_hlp_sent ? " FILS_HLP_SENT" : "");
6fc6879b 877#endif /* CONFIG_CTRL_IFACE || !CONFIG_NO_STDOUT_DEBUG */
00e5e3d5 878 wpas_clear_temp_disabled(wpa_s, ssid, 1);
a20a3616 879 wpa_blacklist_clear(wpa_s);
f1a52633 880 wpa_s->extra_blacklist_count = 0;
6fc6879b 881 wpa_s->new_connection = 0;
6fc6879b 882 wpa_drv_set_operstate(wpa_s, 1);
99ac2913
FF
883#ifndef IEEE8021X_EAPOL
884 wpa_drv_set_supp_port(wpa_s, 1);
885#endif /* IEEE8021X_EAPOL */
17a4734d 886 wpa_s->after_wps = 0;
4d9fb08d 887 wpa_s->known_wps_freq = 0;
b22128ef 888 wpas_p2p_completed(wpa_s);
c3701c66
RM
889
890 sme_sched_obss_scan(wpa_s, 1);
6fc6879b
JM
891 } else if (state == WPA_DISCONNECTED || state == WPA_ASSOCIATING ||
892 state == WPA_ASSOCIATED) {
893 wpa_s->new_connection = 1;
894 wpa_drv_set_operstate(wpa_s, 0);
99ac2913
FF
895#ifndef IEEE8021X_EAPOL
896 wpa_drv_set_supp_port(wpa_s, 0);
897#endif /* IEEE8021X_EAPOL */
c3701c66 898 sme_sched_obss_scan(wpa_s, 0);
6fc6879b
JM
899 }
900 wpa_s->wpa_state = state;
27f43d8d 901
cfe53c9a
PS
902#ifdef CONFIG_BGSCAN
903 if (state == WPA_COMPLETED)
904 wpa_supplicant_start_bgscan(wpa_s);
37271232 905 else if (state < WPA_ASSOCIATED)
cfe53c9a
PS
906 wpa_supplicant_stop_bgscan(wpa_s);
907#endif /* CONFIG_BGSCAN */
908
7c865c68
TB
909 if (state == WPA_AUTHENTICATING)
910 wpa_supplicant_stop_autoscan(wpa_s);
911
912 if (state == WPA_DISCONNECTED || state == WPA_INACTIVE)
913 wpa_supplicant_start_autoscan(wpa_s);
914
fecc2bb5
EP
915 if (old_state >= WPA_ASSOCIATED && wpa_s->wpa_state < WPA_ASSOCIATED)
916 wmm_ac_notify_disassoc(wpa_s);
917
5bbf9f10 918 if (wpa_s->wpa_state != old_state) {
27f43d8d 919 wpas_notify_state_changed(wpa_s, wpa_s->wpa_state, old_state);
5bbf9f10 920
e3bd6e9d
IP
921 /*
922 * Notify the P2P Device interface about a state change in one
923 * of the interfaces.
924 */
925 wpas_p2p_indicate_state_change(wpa_s);
e3bd6e9d 926
5bbf9f10
PS
927 if (wpa_s->wpa_state == WPA_COMPLETED ||
928 old_state == WPA_COMPLETED)
929 wpas_notify_auth_changed(wpa_s);
930 }
6fc6879b
JM
931}
932
933
1a1bf008
JM
934void wpa_supplicant_terminate_proc(struct wpa_global *global)
935{
936 int pending = 0;
937#ifdef CONFIG_WPS
938 struct wpa_supplicant *wpa_s = global->ifaces;
939 while (wpa_s) {
ab41595f 940 struct wpa_supplicant *next = wpa_s->next;
5516ed32
EA
941 if (wpas_wps_terminate_pending(wpa_s) == 1)
942 pending = 1;
20625e97
JM
943#ifdef CONFIG_P2P
944 if (wpa_s->p2p_group_interface != NOT_P2P_GROUP_INTERFACE ||
945 (wpa_s->current_ssid && wpa_s->current_ssid->p2p_group))
946 wpas_p2p_disconnect(wpa_s);
947#endif /* CONFIG_P2P */
ab41595f 948 wpa_s = next;
1a1bf008
JM
949 }
950#endif /* CONFIG_WPS */
951 if (pending)
952 return;
953 eloop_terminate();
954}
955
956
0456ea16 957static void wpa_supplicant_terminate(int sig, void *signal_ctx)
6fc6879b 958{
0456ea16 959 struct wpa_global *global = signal_ctx;
1a1bf008 960 wpa_supplicant_terminate_proc(global);
6fc6879b
JM
961}
962
963
b22128ef 964void wpa_supplicant_clear_status(struct wpa_supplicant *wpa_s)
6fc6879b 965{
71934751 966 enum wpa_states old_state = wpa_s->wpa_state;
27f43d8d 967
6fc6879b
JM
968 wpa_s->pairwise_cipher = 0;
969 wpa_s->group_cipher = 0;
970 wpa_s->mgmt_group_cipher = 0;
971 wpa_s->key_mgmt = 0;
8401a6b0 972 if (wpa_s->wpa_state != WPA_INTERFACE_DISABLED)
99218999 973 wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED);
27f43d8d
MH
974
975 if (wpa_s->wpa_state != old_state)
976 wpas_notify_state_changed(wpa_s, wpa_s->wpa_state, old_state);
6fc6879b
JM
977}
978
979
980/**
981 * wpa_supplicant_reload_configuration - Reload configuration data
982 * @wpa_s: Pointer to wpa_supplicant data
983 * Returns: 0 on success or -1 if configuration parsing failed
984 *
985 * This function can be used to request that the configuration data is reloaded
986 * (e.g., after configuration file change). This function is reloading
987 * configuration only for one interface, so this may need to be called multiple
988 * times if %wpa_supplicant is controlling multiple interfaces and all
989 * interfaces need reconfiguration.
990 */
991int wpa_supplicant_reload_configuration(struct wpa_supplicant *wpa_s)
992{
993 struct wpa_config *conf;
994 int reconf_ctrl;
8bac466b
JM
995 int old_ap_scan;
996
6fc6879b
JM
997 if (wpa_s->confname == NULL)
998 return -1;
e6304cad 999 conf = wpa_config_read(wpa_s->confname, NULL);
6fc6879b
JM
1000 if (conf == NULL) {
1001 wpa_msg(wpa_s, MSG_ERROR, "Failed to parse the configuration "
1002 "file '%s' - exiting", wpa_s->confname);
1003 return -1;
1004 }
e6304cad
DS
1005 wpa_config_read(wpa_s->confanother, conf);
1006
611aea7d 1007 conf->changed_parameters = (unsigned int) -1;
6fc6879b
JM
1008
1009 reconf_ctrl = !!conf->ctrl_interface != !!wpa_s->conf->ctrl_interface
1010 || (conf->ctrl_interface && wpa_s->conf->ctrl_interface &&
1011 os_strcmp(conf->ctrl_interface,
1012 wpa_s->conf->ctrl_interface) != 0);
1013
1014 if (reconf_ctrl && wpa_s->ctrl_iface) {
1015 wpa_supplicant_ctrl_iface_deinit(wpa_s->ctrl_iface);
1016 wpa_s->ctrl_iface = NULL;
1017 }
1018
1019 eapol_sm_invalidate_cached_session(wpa_s->eapol);
7b7ce8aa 1020 if (wpa_s->current_ssid) {
e66bcedd
JM
1021 if (wpa_s->wpa_state >= WPA_AUTHENTICATING)
1022 wpa_s->own_disconnect_req = 1;
7b7ce8aa
JM
1023 wpa_supplicant_deauthenticate(wpa_s,
1024 WLAN_REASON_DEAUTH_LEAVING);
1025 }
8bac466b 1026
6fc6879b
JM
1027 /*
1028 * TODO: should notify EAPOL SM about changes in opensc_engine_path,
07e2de31 1029 * pkcs11_engine_path, pkcs11_module_path, openssl_ciphers.
6fc6879b 1030 */
a1ea1b45 1031 if (wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) ||
567da5bb
JM
1032 wpa_s->key_mgmt == WPA_KEY_MGMT_OWE ||
1033 wpa_s->key_mgmt == WPA_KEY_MGMT_DPP) {
6fc6879b
JM
1034 /*
1035 * Clear forced success to clear EAP state for next
1036 * authentication.
1037 */
1038 eapol_sm_notify_eap_success(wpa_s->eapol, FALSE);
1039 }
1040 eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
1041 wpa_sm_set_config(wpa_s->wpa, NULL);
d8a790b9 1042 wpa_sm_pmksa_cache_flush(wpa_s->wpa, NULL);
6fc6879b
JM
1043 wpa_sm_set_fast_reauth(wpa_s->wpa, wpa_s->conf->fast_reauth);
1044 rsn_preauth_deinit(wpa_s->wpa);
8bac466b
JM
1045
1046 old_ap_scan = wpa_s->conf->ap_scan;
6fc6879b
JM
1047 wpa_config_free(wpa_s->conf);
1048 wpa_s->conf = conf;
8bac466b
JM
1049 if (old_ap_scan != wpa_s->conf->ap_scan)
1050 wpas_notify_ap_scan_changed(wpa_s);
1051
6fc6879b
JM
1052 if (reconf_ctrl)
1053 wpa_s->ctrl_iface = wpa_supplicant_ctrl_iface_init(wpa_s);
1054
611aea7d
JM
1055 wpa_supplicant_update_config(wpa_s);
1056
6fc6879b 1057 wpa_supplicant_clear_status(wpa_s);
349493bd 1058 if (wpa_supplicant_enabled_networks(wpa_s)) {
43a38635
JM
1059 wpa_s->reassociate = 1;
1060 wpa_supplicant_req_scan(wpa_s, 0, 0);
1061 }
f049052b 1062 wpa_dbg(wpa_s, MSG_DEBUG, "Reconfiguration completed");
6fc6879b
JM
1063 return 0;
1064}
1065
1066
0456ea16 1067static void wpa_supplicant_reconfig(int sig, void *signal_ctx)
6fc6879b 1068{
0456ea16 1069 struct wpa_global *global = signal_ctx;
6fc6879b 1070 struct wpa_supplicant *wpa_s;
6fc6879b 1071 for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next) {
f049052b
BG
1072 wpa_dbg(wpa_s, MSG_DEBUG, "Signal %d received - reconfiguring",
1073 sig);
6fc6879b 1074 if (wpa_supplicant_reload_configuration(wpa_s) < 0) {
1a1bf008 1075 wpa_supplicant_terminate_proc(global);
6fc6879b
JM
1076 }
1077 }
1248e584
LR
1078
1079 if (wpa_debug_reopen_file() < 0) {
1080 /* Ignore errors since we cannot really do much to fix this */
1081 wpa_printf(MSG_DEBUG, "Could not reopen debug log file");
1082 }
6fc6879b
JM
1083}
1084
1085
6fc6879b
JM
1086static int wpa_supplicant_suites_from_ai(struct wpa_supplicant *wpa_s,
1087 struct wpa_ssid *ssid,
1088 struct wpa_ie_data *ie)
1089{
1090 int ret = wpa_sm_parse_own_wpa_ie(wpa_s->wpa, ie);
1091 if (ret) {
1092 if (ret == -2) {
1093 wpa_msg(wpa_s, MSG_INFO, "WPA: Failed to parse WPA IE "
1094 "from association info");
1095 }
1096 return -1;
1097 }
1098
f049052b
BG
1099 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Using WPA IE from AssocReq to set "
1100 "cipher suites");
6fc6879b
JM
1101 if (!(ie->group_cipher & ssid->group_cipher)) {
1102 wpa_msg(wpa_s, MSG_INFO, "WPA: Driver used disabled group "
1103 "cipher 0x%x (mask 0x%x) - reject",
1104 ie->group_cipher, ssid->group_cipher);
1105 return -1;
1106 }
1107 if (!(ie->pairwise_cipher & ssid->pairwise_cipher)) {
1108 wpa_msg(wpa_s, MSG_INFO, "WPA: Driver used disabled pairwise "
1109 "cipher 0x%x (mask 0x%x) - reject",
1110 ie->pairwise_cipher, ssid->pairwise_cipher);
1111 return -1;
1112 }
1113 if (!(ie->key_mgmt & ssid->key_mgmt)) {
1114 wpa_msg(wpa_s, MSG_INFO, "WPA: Driver used disabled key "
1115 "management 0x%x (mask 0x%x) - reject",
1116 ie->key_mgmt, ssid->key_mgmt);
1117 return -1;
1118 }
1119
1120#ifdef CONFIG_IEEE80211W
0b60b0aa 1121 if (!(ie->capabilities & WPA_CAPABILITY_MFPC) &&
3f56a2b7 1122 wpas_get_ssid_pmf(wpa_s, ssid) == MGMT_FRAME_PROTECTION_REQUIRED) {
6fc6879b
JM
1123 wpa_msg(wpa_s, MSG_INFO, "WPA: Driver associated with an AP "
1124 "that does not support management frame protection - "
1125 "reject");
1126 return -1;
1127 }
1128#endif /* CONFIG_IEEE80211W */
1129
1130 return 0;
1131}
1132
1133
1134/**
1135 * wpa_supplicant_set_suites - Set authentication and encryption parameters
1136 * @wpa_s: Pointer to wpa_supplicant data
1137 * @bss: Scan results for the selected BSS, or %NULL if not available
1138 * @ssid: Configuration data for the selected network
1139 * @wpa_ie: Buffer for the WPA/RSN IE
1140 * @wpa_ie_len: Maximum wpa_ie buffer size on input. This is changed to be the
1141 * used buffer length in case the functions returns success.
1142 * Returns: 0 on success or -1 on failure
1143 *
1144 * This function is used to configure authentication and encryption parameters
1145 * based on the network configuration and scan result for the selected BSS (if
1146 * available).
1147 */
1148int wpa_supplicant_set_suites(struct wpa_supplicant *wpa_s,
6fa81a3b 1149 struct wpa_bss *bss, struct wpa_ssid *ssid,
6fc6879b
JM
1150 u8 *wpa_ie, size_t *wpa_ie_len)
1151{
1152 struct wpa_ie_data ie;
1153 int sel, proto;
df0f01d9 1154 const u8 *bss_wpa, *bss_rsn, *bss_osen;
6fc6879b
JM
1155
1156 if (bss) {
6fa81a3b
JM
1157 bss_wpa = wpa_bss_get_vendor_ie(bss, WPA_IE_VENDOR_TYPE);
1158 bss_rsn = wpa_bss_get_ie(bss, WLAN_EID_RSN);
df0f01d9 1159 bss_osen = wpa_bss_get_vendor_ie(bss, OSEN_IE_VENDOR_TYPE);
6fc6879b 1160 } else
df0f01d9 1161 bss_wpa = bss_rsn = bss_osen = NULL;
6fc6879b
JM
1162
1163 if (bss_rsn && (ssid->proto & WPA_PROTO_RSN) &&
1164 wpa_parse_wpa_ie(bss_rsn, 2 + bss_rsn[1], &ie) == 0 &&
1165 (ie.group_cipher & ssid->group_cipher) &&
1166 (ie.pairwise_cipher & ssid->pairwise_cipher) &&
1167 (ie.key_mgmt & ssid->key_mgmt)) {
f049052b 1168 wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using IEEE 802.11i/D9.0");
6fc6879b
JM
1169 proto = WPA_PROTO_RSN;
1170 } else if (bss_wpa && (ssid->proto & WPA_PROTO_WPA) &&
267ac3bc 1171 wpa_parse_wpa_ie(bss_wpa, 2 + bss_wpa[1], &ie) == 0 &&
6fc6879b
JM
1172 (ie.group_cipher & ssid->group_cipher) &&
1173 (ie.pairwise_cipher & ssid->pairwise_cipher) &&
1174 (ie.key_mgmt & ssid->key_mgmt)) {
f049052b 1175 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using IEEE 802.11i/D3.0");
6fc6879b 1176 proto = WPA_PROTO_WPA;
df0f01d9
JM
1177#ifdef CONFIG_HS20
1178 } else if (bss_osen && (ssid->proto & WPA_PROTO_OSEN)) {
1179 wpa_dbg(wpa_s, MSG_DEBUG, "HS 2.0: using OSEN");
1180 /* TODO: parse OSEN element */
137ff332 1181 os_memset(&ie, 0, sizeof(ie));
df0f01d9
JM
1182 ie.group_cipher = WPA_CIPHER_CCMP;
1183 ie.pairwise_cipher = WPA_CIPHER_CCMP;
1184 ie.key_mgmt = WPA_KEY_MGMT_OSEN;
1185 proto = WPA_PROTO_OSEN;
1186#endif /* CONFIG_HS20 */
6fc6879b
JM
1187 } else if (bss) {
1188 wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select WPA/RSN");
267ac3bc
JM
1189 wpa_dbg(wpa_s, MSG_DEBUG,
1190 "WPA: ssid proto=0x%x pairwise_cipher=0x%x group_cipher=0x%x key_mgmt=0x%x",
1191 ssid->proto, ssid->pairwise_cipher, ssid->group_cipher,
1192 ssid->key_mgmt);
1193 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: BSS " MACSTR " ssid='%s'%s%s%s",
1194 MAC2STR(bss->bssid),
1195 wpa_ssid_txt(bss->ssid, bss->ssid_len),
1196 bss_wpa ? " WPA" : "",
1197 bss_rsn ? " RSN" : "",
1198 bss_osen ? " OSEN" : "");
1199 if (bss_rsn) {
1200 wpa_hexdump(MSG_DEBUG, "RSN", bss_rsn, 2 + bss_rsn[1]);
1201 if (wpa_parse_wpa_ie(bss_rsn, 2 + bss_rsn[1], &ie)) {
1202 wpa_dbg(wpa_s, MSG_DEBUG,
1203 "Could not parse RSN element");
1204 } else {
1205 wpa_dbg(wpa_s, MSG_DEBUG,
1206 "RSN: pairwise_cipher=0x%x group_cipher=0x%x key_mgmt=0x%x",
1207 ie.pairwise_cipher, ie.group_cipher,
1208 ie.key_mgmt);
1209 }
1210 }
1211 if (bss_wpa) {
1212 wpa_hexdump(MSG_DEBUG, "WPA", bss_wpa, 2 + bss_wpa[1]);
1213 if (wpa_parse_wpa_ie(bss_wpa, 2 + bss_wpa[1], &ie)) {
1214 wpa_dbg(wpa_s, MSG_DEBUG,
1215 "Could not parse WPA element");
1216 } else {
1217 wpa_dbg(wpa_s, MSG_DEBUG,
1218 "WPA: pairwise_cipher=0x%x group_cipher=0x%x key_mgmt=0x%x",
1219 ie.pairwise_cipher, ie.group_cipher,
1220 ie.key_mgmt);
1221 }
1222 }
6fc6879b
JM
1223 return -1;
1224 } else {
df0f01d9
JM
1225 if (ssid->proto & WPA_PROTO_OSEN)
1226 proto = WPA_PROTO_OSEN;
1227 else if (ssid->proto & WPA_PROTO_RSN)
6fc6879b
JM
1228 proto = WPA_PROTO_RSN;
1229 else
1230 proto = WPA_PROTO_WPA;
1231 if (wpa_supplicant_suites_from_ai(wpa_s, ssid, &ie) < 0) {
1232 os_memset(&ie, 0, sizeof(ie));
1233 ie.group_cipher = ssid->group_cipher;
1234 ie.pairwise_cipher = ssid->pairwise_cipher;
1235 ie.key_mgmt = ssid->key_mgmt;
1236#ifdef CONFIG_IEEE80211W
61a56c14
JM
1237 ie.mgmt_group_cipher = 0;
1238 if (ssid->ieee80211w != NO_MGMT_FRAME_PROTECTION) {
1239 if (ssid->group_mgmt_cipher &
1240 WPA_CIPHER_BIP_GMAC_256)
1241 ie.mgmt_group_cipher =
1242 WPA_CIPHER_BIP_GMAC_256;
1243 else if (ssid->group_mgmt_cipher &
1244 WPA_CIPHER_BIP_CMAC_256)
1245 ie.mgmt_group_cipher =
1246 WPA_CIPHER_BIP_CMAC_256;
1247 else if (ssid->group_mgmt_cipher &
1248 WPA_CIPHER_BIP_GMAC_128)
1249 ie.mgmt_group_cipher =
1250 WPA_CIPHER_BIP_GMAC_128;
1251 else
1252 ie.mgmt_group_cipher =
1253 WPA_CIPHER_AES_128_CMAC;
1254 }
6fc6879b 1255#endif /* CONFIG_IEEE80211W */
f049052b
BG
1256 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Set cipher suites "
1257 "based on configuration");
6fc6879b
JM
1258 } else
1259 proto = ie.proto;
1260 }
1261
f049052b
BG
1262 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Selected cipher suites: group %d "
1263 "pairwise %d key_mgmt %d proto %d",
1264 ie.group_cipher, ie.pairwise_cipher, ie.key_mgmt, proto);
6fc6879b
JM
1265#ifdef CONFIG_IEEE80211W
1266 if (ssid->ieee80211w) {
f049052b
BG
1267 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Selected mgmt group cipher %d",
1268 ie.mgmt_group_cipher);
6fc6879b
JM
1269 }
1270#endif /* CONFIG_IEEE80211W */
1271
64fa840a 1272 wpa_s->wpa_proto = proto;
6fc6879b
JM
1273 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_PROTO, proto);
1274 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_RSN_ENABLED,
df0f01d9 1275 !!(ssid->proto & (WPA_PROTO_RSN | WPA_PROTO_OSEN)));
6fc6879b
JM
1276
1277 if (bss || !wpa_s->ap_ies_from_associnfo) {
1278 if (wpa_sm_set_ap_wpa_ie(wpa_s->wpa, bss_wpa,
1279 bss_wpa ? 2 + bss_wpa[1] : 0) ||
1280 wpa_sm_set_ap_rsn_ie(wpa_s->wpa, bss_rsn,
1281 bss_rsn ? 2 + bss_rsn[1] : 0))
1282 return -1;
1283 }
1284
9e68742e
JM
1285#ifdef CONFIG_NO_WPA
1286 wpa_s->group_cipher = WPA_CIPHER_NONE;
1287 wpa_s->pairwise_cipher = WPA_CIPHER_NONE;
1288#else /* CONFIG_NO_WPA */
6fc6879b 1289 sel = ie.group_cipher & ssid->group_cipher;
edbd2a19
JM
1290 wpa_s->group_cipher = wpa_pick_group_cipher(sel);
1291 if (wpa_s->group_cipher < 0) {
f049052b
BG
1292 wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select group "
1293 "cipher");
6fc6879b
JM
1294 return -1;
1295 }
edbd2a19
JM
1296 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using GTK %s",
1297 wpa_cipher_txt(wpa_s->group_cipher));
6fc6879b
JM
1298
1299 sel = ie.pairwise_cipher & ssid->pairwise_cipher;
edbd2a19
JM
1300 wpa_s->pairwise_cipher = wpa_pick_pairwise_cipher(sel, 1);
1301 if (wpa_s->pairwise_cipher < 0) {
f049052b
BG
1302 wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select pairwise "
1303 "cipher");
6fc6879b
JM
1304 return -1;
1305 }
edbd2a19
JM
1306 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using PTK %s",
1307 wpa_cipher_txt(wpa_s->pairwise_cipher));
9e68742e 1308#endif /* CONFIG_NO_WPA */
6fc6879b
JM
1309
1310 sel = ie.key_mgmt & ssid->key_mgmt;
c10347f2
JM
1311#ifdef CONFIG_SAE
1312 if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_SAE))
1313 sel &= ~(WPA_KEY_MGMT_SAE | WPA_KEY_MGMT_FT_SAE);
1314#endif /* CONFIG_SAE */
6fc6879b 1315 if (0) {
5e3b5197
JM
1316#ifdef CONFIG_SUITEB192
1317 } else if (sel & WPA_KEY_MGMT_IEEE8021X_SUITE_B_192) {
1318 wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X_SUITE_B_192;
1319 wpa_dbg(wpa_s, MSG_DEBUG,
1320 "WPA: using KEY_MGMT 802.1X with Suite B (192-bit)");
1321#endif /* CONFIG_SUITEB192 */
1322#ifdef CONFIG_SUITEB
666497c8
JM
1323 } else if (sel & WPA_KEY_MGMT_IEEE8021X_SUITE_B) {
1324 wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X_SUITE_B;
1325 wpa_dbg(wpa_s, MSG_DEBUG,
1326 "WPA: using KEY_MGMT 802.1X with Suite B");
5e3b5197 1327#endif /* CONFIG_SUITEB */
b8ae56e4
JM
1328#ifdef CONFIG_FILS
1329#ifdef CONFIG_IEEE80211R
1330 } else if (sel & WPA_KEY_MGMT_FT_FILS_SHA384) {
1331 wpa_s->key_mgmt = WPA_KEY_MGMT_FT_FILS_SHA384;
1332 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FT-FILS-SHA384");
1333 } else if (sel & WPA_KEY_MGMT_FT_FILS_SHA256) {
1334 wpa_s->key_mgmt = WPA_KEY_MGMT_FT_FILS_SHA256;
1335 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FT-FILS-SHA256");
1336#endif /* CONFIG_IEEE80211R */
1337 } else if (sel & WPA_KEY_MGMT_FILS_SHA384) {
1338 wpa_s->key_mgmt = WPA_KEY_MGMT_FILS_SHA384;
1339 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FILS-SHA384");
1340 } else if (sel & WPA_KEY_MGMT_FILS_SHA256) {
1341 wpa_s->key_mgmt = WPA_KEY_MGMT_FILS_SHA256;
1342 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FILS-SHA256");
1343#endif /* CONFIG_FILS */
6fc6879b
JM
1344#ifdef CONFIG_IEEE80211R
1345 } else if (sel & WPA_KEY_MGMT_FT_IEEE8021X) {
1346 wpa_s->key_mgmt = WPA_KEY_MGMT_FT_IEEE8021X;
f049052b 1347 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FT/802.1X");
6fc6879b
JM
1348 } else if (sel & WPA_KEY_MGMT_FT_PSK) {
1349 wpa_s->key_mgmt = WPA_KEY_MGMT_FT_PSK;
f049052b 1350 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FT/PSK");
6fc6879b 1351#endif /* CONFIG_IEEE80211R */
c10347f2
JM
1352#ifdef CONFIG_SAE
1353 } else if (sel & WPA_KEY_MGMT_SAE) {
1354 wpa_s->key_mgmt = WPA_KEY_MGMT_SAE;
1355 wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using KEY_MGMT SAE");
1356 } else if (sel & WPA_KEY_MGMT_FT_SAE) {
1357 wpa_s->key_mgmt = WPA_KEY_MGMT_FT_SAE;
1358 wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using KEY_MGMT FT/SAE");
1359#endif /* CONFIG_SAE */
56586197
JM
1360#ifdef CONFIG_IEEE80211W
1361 } else if (sel & WPA_KEY_MGMT_IEEE8021X_SHA256) {
1362 wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X_SHA256;
f049052b 1363 wpa_dbg(wpa_s, MSG_DEBUG,
56586197
JM
1364 "WPA: using KEY_MGMT 802.1X with SHA256");
1365 } else if (sel & WPA_KEY_MGMT_PSK_SHA256) {
1366 wpa_s->key_mgmt = WPA_KEY_MGMT_PSK_SHA256;
f049052b 1367 wpa_dbg(wpa_s, MSG_DEBUG,
56586197
JM
1368 "WPA: using KEY_MGMT PSK with SHA256");
1369#endif /* CONFIG_IEEE80211W */
6fc6879b
JM
1370 } else if (sel & WPA_KEY_MGMT_IEEE8021X) {
1371 wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X;
f049052b 1372 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT 802.1X");
6fc6879b
JM
1373 } else if (sel & WPA_KEY_MGMT_PSK) {
1374 wpa_s->key_mgmt = WPA_KEY_MGMT_PSK;
f049052b 1375 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT WPA-PSK");
6fc6879b
JM
1376 } else if (sel & WPA_KEY_MGMT_WPA_NONE) {
1377 wpa_s->key_mgmt = WPA_KEY_MGMT_WPA_NONE;
f049052b 1378 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT WPA-NONE");
df0f01d9
JM
1379#ifdef CONFIG_HS20
1380 } else if (sel & WPA_KEY_MGMT_OSEN) {
1381 wpa_s->key_mgmt = WPA_KEY_MGMT_OSEN;
1382 wpa_dbg(wpa_s, MSG_DEBUG, "HS 2.0: using KEY_MGMT OSEN");
1383#endif /* CONFIG_HS20 */
a1ea1b45
JM
1384#ifdef CONFIG_OWE
1385 } else if (sel & WPA_KEY_MGMT_OWE) {
1386 wpa_s->key_mgmt = WPA_KEY_MGMT_OWE;
1387 wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using KEY_MGMT OWE");
1388#endif /* CONFIG_OWE */
567da5bb
JM
1389#ifdef CONFIG_DPP
1390 } else if (sel & WPA_KEY_MGMT_DPP) {
1391 wpa_s->key_mgmt = WPA_KEY_MGMT_DPP;
1392 wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using KEY_MGMT DPP");
1393#endif /* CONFIG_DPP */
6fc6879b 1394 } else {
f049052b
BG
1395 wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select "
1396 "authenticated key management type");
6fc6879b
JM
1397 return -1;
1398 }
1399
1400 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_KEY_MGMT, wpa_s->key_mgmt);
1401 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_PAIRWISE,
1402 wpa_s->pairwise_cipher);
1403 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_GROUP, wpa_s->group_cipher);
1404
1405#ifdef CONFIG_IEEE80211W
1406 sel = ie.mgmt_group_cipher;
61a56c14
JM
1407 if (ssid->group_mgmt_cipher)
1408 sel &= ssid->group_mgmt_cipher;
3f56a2b7 1409 if (wpas_get_ssid_pmf(wpa_s, ssid) == NO_MGMT_FRAME_PROTECTION ||
0b60b0aa 1410 !(ie.capabilities & WPA_CAPABILITY_MFPC))
6fc6879b
JM
1411 sel = 0;
1412 if (sel & WPA_CIPHER_AES_128_CMAC) {
1413 wpa_s->mgmt_group_cipher = WPA_CIPHER_AES_128_CMAC;
f049052b 1414 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher "
6fc6879b 1415 "AES-128-CMAC");
8dd9f9cd
JM
1416 } else if (sel & WPA_CIPHER_BIP_GMAC_128) {
1417 wpa_s->mgmt_group_cipher = WPA_CIPHER_BIP_GMAC_128;
1418 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher "
1419 "BIP-GMAC-128");
1420 } else if (sel & WPA_CIPHER_BIP_GMAC_256) {
1421 wpa_s->mgmt_group_cipher = WPA_CIPHER_BIP_GMAC_256;
1422 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher "
1423 "BIP-GMAC-256");
1424 } else if (sel & WPA_CIPHER_BIP_CMAC_256) {
1425 wpa_s->mgmt_group_cipher = WPA_CIPHER_BIP_CMAC_256;
1426 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher "
1427 "BIP-CMAC-256");
6fc6879b
JM
1428 } else {
1429 wpa_s->mgmt_group_cipher = 0;
f049052b 1430 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: not using MGMT group cipher");
6fc6879b
JM
1431 }
1432 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_MGMT_GROUP,
1433 wpa_s->mgmt_group_cipher);
62d49803 1434 wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_MFP,
3f56a2b7 1435 wpas_get_ssid_pmf(wpa_s, ssid));
6fc6879b
JM
1436#endif /* CONFIG_IEEE80211W */
1437
1438 if (wpa_sm_set_assoc_wpa_ie_default(wpa_s->wpa, wpa_ie, wpa_ie_len)) {
f049052b 1439 wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to generate WPA IE");
6fc6879b
JM
1440 return -1;
1441 }
1442
0bf927a0 1443 if (wpa_key_mgmt_wpa_psk(ssid->key_mgmt)) {
a52410c2
JM
1444 int psk_set = 0;
1445
1446 if (ssid->psk_set) {
70c93963
MH
1447 wpa_sm_set_pmk(wpa_s->wpa, ssid->psk, PMK_LEN, NULL,
1448 NULL);
a52410c2
JM
1449 psk_set = 1;
1450 }
a34ca59e
JM
1451
1452 if (wpa_key_mgmt_sae(ssid->key_mgmt) && ssid->sae_password)
1453 psk_set = 1;
1454
7d232e23
ZC
1455#ifndef CONFIG_NO_PBKDF2
1456 if (bss && ssid->bssid_set && ssid->ssid_len == 0 &&
1457 ssid->passphrase) {
1458 u8 psk[PMK_LEN];
986de33d
JM
1459 pbkdf2_sha1(ssid->passphrase, bss->ssid, bss->ssid_len,
1460 4096, psk, PMK_LEN);
7d232e23
ZC
1461 wpa_hexdump_key(MSG_MSGDUMP, "PSK (from passphrase)",
1462 psk, PMK_LEN);
70c93963 1463 wpa_sm_set_pmk(wpa_s->wpa, psk, PMK_LEN, NULL, NULL);
a52410c2 1464 psk_set = 1;
e886c88e 1465 os_memset(psk, 0, sizeof(psk));
7d232e23
ZC
1466 }
1467#endif /* CONFIG_NO_PBKDF2 */
9173b16f
JM
1468#ifdef CONFIG_EXT_PASSWORD
1469 if (ssid->ext_psk) {
1470 struct wpabuf *pw = ext_password_get(wpa_s->ext_pw,
1471 ssid->ext_psk);
1472 char pw_str[64 + 1];
1473 u8 psk[PMK_LEN];
1474
1475 if (pw == NULL) {
1476 wpa_msg(wpa_s, MSG_INFO, "EXT PW: No PSK "
1477 "found from external storage");
1478 return -1;
1479 }
1480
1481 if (wpabuf_len(pw) < 8 || wpabuf_len(pw) > 64) {
1482 wpa_msg(wpa_s, MSG_INFO, "EXT PW: Unexpected "
1483 "PSK length %d in external storage",
1484 (int) wpabuf_len(pw));
1485 ext_password_free(pw);
1486 return -1;
1487 }
1488
1489 os_memcpy(pw_str, wpabuf_head(pw), wpabuf_len(pw));
1490 pw_str[wpabuf_len(pw)] = '\0';
1491
1492#ifndef CONFIG_NO_PBKDF2
1493 if (wpabuf_len(pw) >= 8 && wpabuf_len(pw) < 64 && bss)
1494 {
986de33d
JM
1495 pbkdf2_sha1(pw_str, bss->ssid, bss->ssid_len,
1496 4096, psk, PMK_LEN);
9173b16f
JM
1497 os_memset(pw_str, 0, sizeof(pw_str));
1498 wpa_hexdump_key(MSG_MSGDUMP, "PSK (from "
1499 "external passphrase)",
1500 psk, PMK_LEN);
70c93963
MH
1501 wpa_sm_set_pmk(wpa_s->wpa, psk, PMK_LEN, NULL,
1502 NULL);
a52410c2 1503 psk_set = 1;
e886c88e 1504 os_memset(psk, 0, sizeof(psk));
9173b16f
JM
1505 } else
1506#endif /* CONFIG_NO_PBKDF2 */
1507 if (wpabuf_len(pw) == 2 * PMK_LEN) {
1508 if (hexstr2bin(pw_str, psk, PMK_LEN) < 0) {
1509 wpa_msg(wpa_s, MSG_INFO, "EXT PW: "
1510 "Invalid PSK hex string");
1511 os_memset(pw_str, 0, sizeof(pw_str));
1512 ext_password_free(pw);
1513 return -1;
1514 }
70c93963
MH
1515 wpa_sm_set_pmk(wpa_s->wpa, psk, PMK_LEN, NULL,
1516 NULL);
a52410c2 1517 psk_set = 1;
e886c88e 1518 os_memset(psk, 0, sizeof(psk));
9173b16f
JM
1519 } else {
1520 wpa_msg(wpa_s, MSG_INFO, "EXT PW: No suitable "
1521 "PSK available");
1522 os_memset(pw_str, 0, sizeof(pw_str));
1523 ext_password_free(pw);
1524 return -1;
1525 }
1526
1527 os_memset(pw_str, 0, sizeof(pw_str));
1528 ext_password_free(pw);
1529 }
1530#endif /* CONFIG_EXT_PASSWORD */
a52410c2
JM
1531
1532 if (!psk_set) {
1533 wpa_msg(wpa_s, MSG_INFO,
1534 "No PSK available for association");
1535 return -1;
1536 }
675112df
JM
1537#ifdef CONFIG_OWE
1538 } else if (wpa_s->key_mgmt == WPA_KEY_MGMT_OWE) {
1539 /* OWE Diffie-Hellman exchange in (Re)Association
1540 * Request/Response frames set the PMK, so do not override it
1541 * here. */
1542#endif /* CONFIG_OWE */
7d232e23 1543 } else
6fc6879b
JM
1544 wpa_sm_set_pmk_from_pmksa(wpa_s->wpa);
1545
1546 return 0;
1547}
1548
1549
8cd6b7bc 1550static void wpas_ext_capab_byte(struct wpa_supplicant *wpa_s, u8 *pos, int idx)
03e47c9c 1551{
8cd6b7bc 1552 *pos = 0x00;
03e47c9c 1553
8cd6b7bc
JB
1554 switch (idx) {
1555 case 0: /* Bits 0-7 */
1556 break;
1557 case 1: /* Bits 8-15 */
1558 break;
1559 case 2: /* Bits 16-23 */
1560#ifdef CONFIG_WNM
1561 *pos |= 0x02; /* Bit 17 - WNM-Sleep Mode */
1562 *pos |= 0x08; /* Bit 19 - BSS Transition */
1563#endif /* CONFIG_WNM */
1564 break;
1565 case 3: /* Bits 24-31 */
1566#ifdef CONFIG_WNM
1567 *pos |= 0x02; /* Bit 25 - SSID List */
1568#endif /* CONFIG_WNM */
03e47c9c 1569#ifdef CONFIG_INTERWORKING
8cd6b7bc
JB
1570 if (wpa_s->conf->interworking)
1571 *pos |= 0x80; /* Bit 31 - Interworking */
03e47c9c 1572#endif /* CONFIG_INTERWORKING */
8cd6b7bc
JB
1573 break;
1574 case 4: /* Bits 32-39 */
56f5af48 1575#ifdef CONFIG_INTERWORKING
429dd9af
JM
1576 if (wpa_s->drv_flags / WPA_DRIVER_FLAGS_QOS_MAPPING)
1577 *pos |= 0x01; /* Bit 32 - QoS Map */
56f5af48 1578#endif /* CONFIG_INTERWORKING */
8cd6b7bc
JB
1579 break;
1580 case 5: /* Bits 40-47 */
95a3ea94
JM
1581#ifdef CONFIG_HS20
1582 if (wpa_s->conf->hs20)
1583 *pos |= 0x40; /* Bit 46 - WNM-Notification */
1584#endif /* CONFIG_HS20 */
92c6e2e3
DS
1585#ifdef CONFIG_MBO
1586 *pos |= 0x40; /* Bit 46 - WNM-Notification */
1587#endif /* CONFIG_MBO */
8cd6b7bc
JB
1588 break;
1589 case 6: /* Bits 48-55 */
1590 break;
d1723c55
LD
1591 case 7: /* Bits 56-63 */
1592 break;
1593 case 8: /* Bits 64-71 */
1594 if (wpa_s->conf->ftm_responder)
1595 *pos |= 0x40; /* Bit 70 - FTM responder */
1596 if (wpa_s->conf->ftm_initiator)
1597 *pos |= 0x80; /* Bit 71 - FTM initiator */
1598 break;
e4d2ce1b
JM
1599 case 9: /* Bits 72-79 */
1600#ifdef CONFIG_FILS
1601 *pos |= 0x01;
1602#endif /* CONFIG_FILS */
1603 break;
8cd6b7bc
JB
1604 }
1605}
03e47c9c 1606
03e47c9c 1607
0bbaa9b9 1608int wpas_build_ext_capab(struct wpa_supplicant *wpa_s, u8 *buf, size_t buflen)
8cd6b7bc
JB
1609{
1610 u8 *pos = buf;
e4d2ce1b 1611 u8 len = 10, i;
8cd6b7bc
JB
1612
1613 if (len < wpa_s->extended_capa_len)
1614 len = wpa_s->extended_capa_len;
0bbaa9b9
JM
1615 if (buflen < (size_t) len + 2) {
1616 wpa_printf(MSG_INFO,
1617 "Not enough room for building extended capabilities element");
1618 return -1;
1619 }
03e47c9c
JM
1620
1621 *pos++ = WLAN_EID_EXT_CAPAB;
8cd6b7bc
JB
1622 *pos++ = len;
1623 for (i = 0; i < len; i++, pos++) {
1624 wpas_ext_capab_byte(wpa_s, pos, i);
1625
1626 if (i < wpa_s->extended_capa_len) {
1627 *pos &= ~wpa_s->extended_capa_mask[i];
1628 *pos |= wpa_s->extended_capa[i];
1629 }
1630 }
03e47c9c 1631
3db5439a
JM
1632 while (len > 0 && buf[1 + len] == 0) {
1633 len--;
1634 buf[1] = len;
1635 }
1636 if (len == 0)
1637 return 0;
1638
1639 return 2 + len;
03e47c9c
JM
1640}
1641
1642
6ac4b15e
JM
1643static int wpas_valid_bss(struct wpa_supplicant *wpa_s,
1644 struct wpa_bss *test_bss)
1645{
1646 struct wpa_bss *bss;
1647
1648 dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
1649 if (bss == test_bss)
1650 return 1;
1651 }
1652
1653 return 0;
1654}
1655
1656
1657static int wpas_valid_ssid(struct wpa_supplicant *wpa_s,
1658 struct wpa_ssid *test_ssid)
1659{
1660 struct wpa_ssid *ssid;
1661
1662 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) {
1663 if (ssid == test_ssid)
1664 return 1;
1665 }
1666
1667 return 0;
1668}
1669
1670
1671int wpas_valid_bss_ssid(struct wpa_supplicant *wpa_s, struct wpa_bss *test_bss,
1672 struct wpa_ssid *test_ssid)
1673{
1674 if (test_bss && !wpas_valid_bss(wpa_s, test_bss))
1675 return 0;
1676
1677 return test_ssid == NULL || wpas_valid_ssid(wpa_s, test_ssid);
1678}
1679
1680
1681void wpas_connect_work_free(struct wpa_connect_work *cwork)
1682{
1683 if (cwork == NULL)
1684 return;
1685 os_free(cwork);
1686}
1687
1688
1689void wpas_connect_work_done(struct wpa_supplicant *wpa_s)
1690{
1691 struct wpa_connect_work *cwork;
1692 struct wpa_radio_work *work = wpa_s->connect_work;
1693
1694 if (!work)
1695 return;
1696
1697 wpa_s->connect_work = NULL;
1698 cwork = work->ctx;
1699 work->ctx = NULL;
1700 wpas_connect_work_free(cwork);
1701 radio_work_done(work);
1702}
1703
1704
a313d17d 1705int wpas_update_random_addr(struct wpa_supplicant *wpa_s, int style)
c267753b
JM
1706{
1707 struct os_reltime now;
1708 u8 addr[ETH_ALEN];
1709
1710 os_get_reltime(&now);
a313d17d
JM
1711 if (wpa_s->last_mac_addr_style == style &&
1712 wpa_s->last_mac_addr_change.sec != 0 &&
c267753b
JM
1713 !os_reltime_expired(&now, &wpa_s->last_mac_addr_change,
1714 wpa_s->conf->rand_addr_lifetime)) {
1715 wpa_msg(wpa_s, MSG_DEBUG,
1716 "Previously selected random MAC address has not yet expired");
1717 return 0;
1718 }
1719
a313d17d
JM
1720 switch (style) {
1721 case 1:
1722 if (random_mac_addr(addr) < 0)
1723 return -1;
1724 break;
1725 case 2:
1726 os_memcpy(addr, wpa_s->perm_addr, ETH_ALEN);
1727 if (random_mac_addr_keep_oui(addr) < 0)
1728 return -1;
1729 break;
1730 default:
c267753b 1731 return -1;
a313d17d 1732 }
c267753b
JM
1733
1734 if (wpa_drv_set_mac_addr(wpa_s, addr) < 0) {
1735 wpa_msg(wpa_s, MSG_INFO,
1736 "Failed to set random MAC address");
1737 return -1;
1738 }
1739
1740 os_get_reltime(&wpa_s->last_mac_addr_change);
1741 wpa_s->mac_addr_changed = 1;
a313d17d 1742 wpa_s->last_mac_addr_style = style;
c267753b
JM
1743
1744 if (wpa_supplicant_update_mac_addr(wpa_s) < 0) {
1745 wpa_msg(wpa_s, MSG_INFO,
1746 "Could not update MAC address information");
1747 return -1;
1748 }
1749
1750 wpa_msg(wpa_s, MSG_DEBUG, "Using random MAC address " MACSTR,
1751 MAC2STR(addr));
1752
1753 return 0;
1754}
1755
1756
1757int wpas_update_random_addr_disassoc(struct wpa_supplicant *wpa_s)
1758{
1759 if (wpa_s->wpa_state >= WPA_AUTHENTICATING ||
1760 !wpa_s->conf->preassoc_mac_addr)
1761 return 0;
1762
a313d17d 1763 return wpas_update_random_addr(wpa_s, wpa_s->conf->preassoc_mac_addr);
c267753b
JM
1764}
1765
1766
6ac4b15e
JM
1767static void wpas_start_assoc_cb(struct wpa_radio_work *work, int deinit);
1768
6fc6879b
JM
1769/**
1770 * wpa_supplicant_associate - Request association
1771 * @wpa_s: Pointer to wpa_supplicant data
1772 * @bss: Scan results for the selected BSS, or %NULL if not available
1773 * @ssid: Configuration data for the selected network
1774 *
1775 * This function is used to request %wpa_supplicant to associate with a BSS.
1776 */
1777void wpa_supplicant_associate(struct wpa_supplicant *wpa_s,
6fa81a3b 1778 struct wpa_bss *bss, struct wpa_ssid *ssid)
6fc6879b 1779{
6ac4b15e 1780 struct wpa_connect_work *cwork;
a313d17d
JM
1781 int rand_style;
1782
a8412ec9
JM
1783 wpa_s->own_disconnect_req = 0;
1784
e7160bd8
JM
1785 /*
1786 * If we are starting a new connection, any previously pending EAPOL
1787 * RX cannot be valid anymore.
1788 */
1789 wpabuf_free(wpa_s->pending_eapol_rx);
1790 wpa_s->pending_eapol_rx = NULL;
1791
a313d17d
JM
1792 if (ssid->mac_addr == -1)
1793 rand_style = wpa_s->conf->mac_addr;
1794 else
1795 rand_style = ssid->mac_addr;
6fc6879b 1796
8c42b369
EP
1797 wmm_ac_clear_saved_tspecs(wpa_s);
1798 wpa_s->reassoc_same_bss = 0;
6a5ee810 1799 wpa_s->reassoc_same_ess = 0;
daa40960
JM
1800#ifdef CONFIG_TESTING_OPTIONS
1801 wpa_s->testing_resend_assoc = 0;
1802#endif /* CONFIG_TESTING_OPTIONS */
8c42b369 1803
c267753b
JM
1804 if (wpa_s->last_ssid == ssid) {
1805 wpa_dbg(wpa_s, MSG_DEBUG, "Re-association to the same ESS");
6a5ee810 1806 wpa_s->reassoc_same_ess = 1;
8c42b369
EP
1807 if (wpa_s->current_bss && wpa_s->current_bss == bss) {
1808 wmm_ac_save_tspecs(wpa_s);
1809 wpa_s->reassoc_same_bss = 1;
1810 }
5d30f927
BR
1811 }
1812
1813 if (rand_style > 0 && !wpa_s->reassoc_same_ess) {
a313d17d 1814 if (wpas_update_random_addr(wpa_s, rand_style) < 0)
c267753b
JM
1815 return;
1816 wpa_sm_pmksa_cache_flush(wpa_s->wpa, ssid);
5d30f927 1817 } else if (rand_style == 0 && wpa_s->mac_addr_changed) {
c267753b
JM
1818 if (wpa_drv_set_mac_addr(wpa_s, NULL) < 0) {
1819 wpa_msg(wpa_s, MSG_INFO,
1820 "Could not restore permanent MAC address");
1821 return;
1822 }
1823 wpa_s->mac_addr_changed = 0;
1824 if (wpa_supplicant_update_mac_addr(wpa_s) < 0) {
1825 wpa_msg(wpa_s, MSG_INFO,
1826 "Could not update MAC address information");
1827 return;
1828 }
1829 wpa_msg(wpa_s, MSG_DEBUG, "Using permanent MAC address");
1830 }
1831 wpa_s->last_ssid = ssid;
1832
78177a00
JM
1833#ifdef CONFIG_IBSS_RSN
1834 ibss_rsn_deinit(wpa_s->ibss_rsn);
1835 wpa_s->ibss_rsn = NULL;
81a10a94
JM
1836#else /* CONFIG_IBSS_RSN */
1837 if (ssid->mode == WPAS_MODE_IBSS &&
1838 !(ssid->key_mgmt & (WPA_KEY_MGMT_NONE | WPA_KEY_MGMT_WPA_NONE))) {
1839 wpa_msg(wpa_s, MSG_INFO,
1840 "IBSS RSN not supported in the build");
1841 return;
1842 }
78177a00
JM
1843#endif /* CONFIG_IBSS_RSN */
1844
2c5d725c
JM
1845 if (ssid->mode == WPAS_MODE_AP || ssid->mode == WPAS_MODE_P2P_GO ||
1846 ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION) {
1581b38b
JM
1847#ifdef CONFIG_AP
1848 if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_AP)) {
f049052b
BG
1849 wpa_msg(wpa_s, MSG_INFO, "Driver does not support AP "
1850 "mode");
1581b38b
JM
1851 return;
1852 }
8c981d17
DW
1853 if (wpa_supplicant_create_ap(wpa_s, ssid) < 0) {
1854 wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED);
b2b688d1
VKE
1855 if (ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)
1856 wpas_p2p_ap_setup_failed(wpa_s);
8c981d17
DW
1857 return;
1858 }
8f770587 1859 wpa_s->current_bss = bss;
1581b38b 1860#else /* CONFIG_AP */
f049052b
BG
1861 wpa_msg(wpa_s, MSG_ERROR, "AP mode support not included in "
1862 "the build");
1581b38b
JM
1863#endif /* CONFIG_AP */
1864 return;
1865 }
1866
603a3f34
JL
1867 if (ssid->mode == WPAS_MODE_MESH) {
1868#ifdef CONFIG_MESH
1869 if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_MESH)) {
1870 wpa_msg(wpa_s, MSG_INFO,
1871 "Driver does not support mesh mode");
1872 return;
1873 }
1874 if (bss)
1875 ssid->frequency = bss->freq;
1876 if (wpa_supplicant_join_mesh(wpa_s, ssid) < 0) {
1877 wpa_msg(wpa_s, MSG_ERROR, "Could not join mesh");
1878 return;
1879 }
1880 wpa_s->current_bss = bss;
6174de66
JM
1881 wpa_msg(wpa_s, MSG_INFO, MESH_GROUP_STARTED "ssid=\"%s\" id=%d",
1882 wpa_ssid_txt(ssid->ssid, ssid->ssid_len),
1883 ssid->id);
89e9cd25 1884 wpas_notify_mesh_group_started(wpa_s, ssid);
603a3f34
JL
1885#else /* CONFIG_MESH */
1886 wpa_msg(wpa_s, MSG_ERROR,
1887 "mesh mode support not included in the build");
1888#endif /* CONFIG_MESH */
1889 return;
1890 }
1891
2efc6720
JM
1892 /*
1893 * Set WPA state machine configuration to match the selected network now
1894 * so that the information is available before wpas_start_assoc_cb()
1895 * gets called. This is needed at least for RSN pre-authentication where
1896 * candidate APs are added to a list based on scan result processing
1897 * before completion of the first association.
1898 */
1899 wpa_supplicant_rsn_supp_set_config(wpa_s, ssid);
1900
a0d5c56f
JM
1901#ifdef CONFIG_DPP
1902 if (wpas_dpp_check_connect(wpa_s, ssid, bss) != 0)
1903 return;
1904#endif /* CONFIG_DPP */
1905
52c9e6f3 1906#ifdef CONFIG_TDLS
95cb2d88
JM
1907 if (bss)
1908 wpa_tdls_ap_ies(wpa_s->wpa, (const u8 *) (bss + 1),
1909 bss->ie_len);
52c9e6f3
JM
1910#endif /* CONFIG_TDLS */
1911
5cc4d64b
JM
1912 if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_SME) &&
1913 ssid->mode == IEEE80211_MODE_INFRA) {
c2a04078
JM
1914 sme_authenticate(wpa_s, bss, ssid);
1915 return;
1916 }
1917
6ac4b15e
JM
1918 if (wpa_s->connect_work) {
1919 wpa_dbg(wpa_s, MSG_DEBUG, "Reject wpa_supplicant_associate() call since connect_work exist");
1920 return;
1921 }
1922
f0e30c84
JM
1923 if (radio_work_pending(wpa_s, "connect")) {
1924 wpa_dbg(wpa_s, MSG_DEBUG, "Reject wpa_supplicant_associate() call since pending work exist");
1925 return;
1926 }
1927
a1836de6
JM
1928#ifdef CONFIG_SME
1929 if (ssid->mode == WPAS_MODE_IBSS || ssid->mode == WPAS_MODE_MESH) {
1930 /* Clear possibly set auth_alg, if any, from last attempt. */
1931 wpa_s->sme.auth_alg = WPA_AUTH_ALG_OPEN;
1932 }
1933#endif /* CONFIG_SME */
1934
4ead7cfd
KV
1935 wpas_abort_ongoing_scan(wpa_s);
1936
6ac4b15e
JM
1937 cwork = os_zalloc(sizeof(*cwork));
1938 if (cwork == NULL)
1939 return;
1940
1941 cwork->bss = bss;
1942 cwork->ssid = ssid;
1943
1944 if (radio_add_work(wpa_s, bss ? bss->freq : 0, "connect", 1,
1945 wpas_start_assoc_cb, cwork) < 0) {
1946 os_free(cwork);
1947 }
1948}
1949
1950
98479dc9
JD
1951static int bss_is_ibss(struct wpa_bss *bss)
1952{
1953 return (bss->caps & (IEEE80211_CAP_ESS | IEEE80211_CAP_IBSS)) ==
1954 IEEE80211_CAP_IBSS;
1955}
1956
1957
a65efbfb
PO
1958static int drv_supports_vht(struct wpa_supplicant *wpa_s,
1959 const struct wpa_ssid *ssid)
1960{
1961 enum hostapd_hw_mode hw_mode;
1962 struct hostapd_hw_modes *mode = NULL;
1963 u8 channel;
1964 int i;
1965
a65efbfb
PO
1966 hw_mode = ieee80211_freq_to_chan(ssid->frequency, &channel);
1967 if (hw_mode == NUM_HOSTAPD_MODES)
1968 return 0;
1969 for (i = 0; wpa_s->hw.modes && i < wpa_s->hw.num_modes; i++) {
1970 if (wpa_s->hw.modes[i].mode == hw_mode) {
1971 mode = &wpa_s->hw.modes[i];
1972 break;
1973 }
1974 }
1975
1976 if (!mode)
1977 return 0;
1978
1979 return mode->vht_capab != 0;
1980}
1981
1982
54fe48b9
JM
1983void ibss_mesh_setup_freq(struct wpa_supplicant *wpa_s,
1984 const struct wpa_ssid *ssid,
1985 struct hostapd_freq_params *freq)
1830817e
JD
1986{
1987 enum hostapd_hw_mode hw_mode;
1988 struct hostapd_hw_modes *mode = NULL;
6b8b0774
JD
1989 int ht40plus[] = { 36, 44, 52, 60, 100, 108, 116, 124, 132, 149, 157,
1990 184, 192 };
563ee183 1991 int vht80[] = { 36, 52, 100, 116, 132, 149 };
6b8b0774 1992 struct hostapd_channel_data *pri_chan = NULL, *sec_chan = NULL;
1830817e 1993 u8 channel;
98479dc9 1994 int i, chan_idx, ht40 = -1, res, obss_scan = 1;
0f29bc68 1995 unsigned int j, k;
563ee183 1996 struct hostapd_freq_params vht_freq;
0f29bc68
AK
1997 int chwidth, seg0, seg1;
1998 u32 vht_caps = 0;
1830817e
JD
1999
2000 freq->freq = ssid->frequency;
2001
98479dc9
JD
2002 for (j = 0; j < wpa_s->last_scan_res_used; j++) {
2003 struct wpa_bss *bss = wpa_s->last_scan_res[j];
2004
2005 if (ssid->mode != WPAS_MODE_IBSS)
2006 break;
2007
2008 /* Don't adjust control freq in case of fixed_freq */
2009 if (ssid->fixed_freq)
2010 break;
2011
2012 if (!bss_is_ibss(bss))
2013 continue;
2014
2015 if (ssid->ssid_len == bss->ssid_len &&
2016 os_memcmp(ssid->ssid, bss->ssid, bss->ssid_len) == 0) {
2017 wpa_printf(MSG_DEBUG,
2018 "IBSS already found in scan results, adjust control freq: %d",
2019 bss->freq);
2020 freq->freq = bss->freq;
2021 obss_scan = 0;
2022 break;
2023 }
2024 }
2025
1830817e
JD
2026 /* For IBSS check HT_IBSS flag */
2027 if (ssid->mode == WPAS_MODE_IBSS &&
2028 !(wpa_s->drv_flags & WPA_DRIVER_FLAGS_HT_IBSS))
2029 return;
2030
d9a9bc04
JD
2031 if (wpa_s->group_cipher == WPA_CIPHER_WEP40 ||
2032 wpa_s->group_cipher == WPA_CIPHER_WEP104 ||
2033 wpa_s->pairwise_cipher == WPA_CIPHER_TKIP) {
2034 wpa_printf(MSG_DEBUG,
2035 "IBSS: WEP/TKIP detected, do not try to enable HT");
2036 return;
2037 }
2038
98479dc9 2039 hw_mode = ieee80211_freq_to_chan(freq->freq, &channel);
1830817e
JD
2040 for (i = 0; wpa_s->hw.modes && i < wpa_s->hw.num_modes; i++) {
2041 if (wpa_s->hw.modes[i].mode == hw_mode) {
2042 mode = &wpa_s->hw.modes[i];
2043 break;
2044 }
2045 }
2046
2047 if (!mode)
2048 return;
2049
3388e7b9
MH
2050#ifdef CONFIG_HT_OVERRIDES
2051 if (ssid->disable_ht) {
2052 freq->ht_enabled = 0;
2053 return;
2054 }
2055#endif /* CONFIG_HT_OVERRIDES */
2056
1830817e 2057 freq->ht_enabled = ht_supported(mode);
6b8b0774
JD
2058 if (!freq->ht_enabled)
2059 return;
2060
2061 /* Setup higher BW only for 5 GHz */
2062 if (mode->mode != HOSTAPD_MODE_IEEE80211A)
2063 return;
2064
2065 for (chan_idx = 0; chan_idx < mode->num_channels; chan_idx++) {
2066 pri_chan = &mode->channels[chan_idx];
2067 if (pri_chan->chan == channel)
2068 break;
2069 pri_chan = NULL;
2070 }
2071 if (!pri_chan)
2072 return;
2073
2074 /* Check primary channel flags */
2075 if (pri_chan->flag & (HOSTAPD_CHAN_DISABLED | HOSTAPD_CHAN_NO_IR))
2076 return;
2077
05aed438
MH
2078#ifdef CONFIG_HT_OVERRIDES
2079 if (ssid->disable_ht40)
2080 return;
2081#endif /* CONFIG_HT_OVERRIDES */
2082
6b8b0774
JD
2083 /* Check/setup HT40+/HT40- */
2084 for (j = 0; j < ARRAY_SIZE(ht40plus); j++) {
2085 if (ht40plus[j] == channel) {
2086 ht40 = 1;
2087 break;
2088 }
2089 }
2090
2091 /* Find secondary channel */
2092 for (i = 0; i < mode->num_channels; i++) {
2093 sec_chan = &mode->channels[i];
2094 if (sec_chan->chan == channel + ht40 * 4)
2095 break;
2096 sec_chan = NULL;
2097 }
2098 if (!sec_chan)
2099 return;
2100
2101 /* Check secondary channel flags */
2102 if (sec_chan->flag & (HOSTAPD_CHAN_DISABLED | HOSTAPD_CHAN_NO_IR))
2103 return;
2104
2105 freq->channel = pri_chan->chan;
2106
ecba4509 2107 if (ht40 == -1) {
6b8b0774
JD
2108 if (!(pri_chan->flag & HOSTAPD_CHAN_HT40MINUS))
2109 return;
ecba4509 2110 } else {
6b8b0774
JD
2111 if (!(pri_chan->flag & HOSTAPD_CHAN_HT40PLUS))
2112 return;
6b8b0774 2113 }
ecba4509 2114 freq->sec_channel_offset = ht40;
6b8b0774 2115
ecba4509 2116 if (obss_scan) {
6b8b0774
JD
2117 struct wpa_scan_results *scan_res;
2118
2119 scan_res = wpa_supplicant_get_scan_results(wpa_s, NULL, 0);
2120 if (scan_res == NULL) {
2121 /* Back to HT20 */
2122 freq->sec_channel_offset = 0;
2123 return;
2124 }
2125
2126 res = check_40mhz_5g(mode, scan_res, pri_chan->chan,
2127 sec_chan->chan);
2128 switch (res) {
2129 case 0:
2130 /* Back to HT20 */
2131 freq->sec_channel_offset = 0;
2132 break;
2133 case 1:
2134 /* Configuration allowed */
2135 break;
2136 case 2:
2137 /* Switch pri/sec channels */
2138 freq->freq = hw_get_freq(mode, sec_chan->chan);
2139 freq->sec_channel_offset = -freq->sec_channel_offset;
2140 freq->channel = sec_chan->chan;
2141 break;
2142 default:
2143 freq->sec_channel_offset = 0;
2144 break;
2145 }
2146
2147 wpa_scan_results_free(scan_res);
2148 }
2149
2150 wpa_printf(MSG_DEBUG,
2151 "IBSS/mesh: setup freq channel %d, sec_channel_offset %d",
2152 freq->channel, freq->sec_channel_offset);
563ee183 2153
a65efbfb 2154 if (!drv_supports_vht(wpa_s, ssid))
563ee183
JD
2155 return;
2156
2157 /* For IBSS check VHT_IBSS flag */
a65efbfb
PO
2158 if (ssid->mode == WPAS_MODE_IBSS &&
2159 !(wpa_s->drv_flags & WPA_DRIVER_FLAGS_VHT_IBSS))
563ee183
JD
2160 return;
2161
2162 vht_freq = *freq;
2163
b301f54e
JM
2164#ifdef CONFIG_VHT_OVERRIDES
2165 if (ssid->disable_vht) {
2166 freq->vht_enabled = 0;
2167 return;
2168 }
2169#endif /* CONFIG_VHT_OVERRIDES */
2170
563ee183
JD
2171 vht_freq.vht_enabled = vht_supported(mode);
2172 if (!vht_freq.vht_enabled)
2173 return;
2174
2175 /* setup center_freq1, bandwidth */
2176 for (j = 0; j < ARRAY_SIZE(vht80); j++) {
2177 if (freq->channel >= vht80[j] &&
2178 freq->channel < vht80[j] + 16)
2179 break;
2180 }
2181
2182 if (j == ARRAY_SIZE(vht80))
2183 return;
2184
2185 for (i = vht80[j]; i < vht80[j] + 16; i += 4) {
2186 struct hostapd_channel_data *chan;
2187
2188 chan = hw_get_channel_chan(mode, i, NULL);
2189 if (!chan)
2190 return;
2191
2192 /* Back to HT configuration if channel not usable */
2193 if (chan->flag & (HOSTAPD_CHAN_DISABLED | HOSTAPD_CHAN_NO_IR))
2194 return;
2195 }
2196
0f29bc68
AK
2197 chwidth = VHT_CHANWIDTH_80MHZ;
2198 seg0 = vht80[j] + 6;
2199 seg1 = 0;
2200
2201 if (ssid->max_oper_chwidth == VHT_CHANWIDTH_80P80MHZ) {
2202 /* setup center_freq2, bandwidth */
2203 for (k = 0; k < ARRAY_SIZE(vht80); k++) {
2204 /* Only accept 80 MHz segments separated by a gap */
2205 if (j == k || abs(vht80[j] - vht80[k]) == 16)
2206 continue;
2207 for (i = vht80[k]; i < vht80[k] + 16; i += 4) {
2208 struct hostapd_channel_data *chan;
2209
2210 chan = hw_get_channel_chan(mode, i, NULL);
2211 if (!chan)
2212 continue;
2213
2214 if (chan->flag & (HOSTAPD_CHAN_DISABLED |
2215 HOSTAPD_CHAN_NO_IR |
2216 HOSTAPD_CHAN_RADAR))
2217 continue;
2218
2219 /* Found a suitable second segment for 80+80 */
2220 chwidth = VHT_CHANWIDTH_80P80MHZ;
2221 vht_caps |=
2222 VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ;
2223 seg1 = vht80[k] + 6;
2224 }
2225
2226 if (chwidth == VHT_CHANWIDTH_80P80MHZ)
2227 break;
2228 }
331f0774
JM
2229 } else if (ssid->max_oper_chwidth == VHT_CHANWIDTH_160MHZ) {
2230 if (freq->freq == 5180) {
2231 chwidth = VHT_CHANWIDTH_160MHZ;
2232 vht_caps |= VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
2233 seg0 = 50;
2234 } else if (freq->freq == 5520) {
2235 chwidth = VHT_CHANWIDTH_160MHZ;
2236 vht_caps |= VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
2237 seg0 = 114;
2238 }
0f29bc68
AK
2239 }
2240
563ee183
JD
2241 if (hostapd_set_freq_params(&vht_freq, mode->mode, freq->freq,
2242 freq->channel, freq->ht_enabled,
2243 vht_freq.vht_enabled,
2244 freq->sec_channel_offset,
0f29bc68 2245 chwidth, seg0, seg1, vht_caps) != 0)
563ee183
JD
2246 return;
2247
2248 *freq = vht_freq;
2249
2250 wpa_printf(MSG_DEBUG, "IBSS: VHT setup freq cf1 %d, cf2 %d, bw %d",
2251 freq->center_freq1, freq->center_freq2, freq->bandwidth);
1830817e
JD
2252}
2253
2254
a38090b1
VK
2255#ifdef CONFIG_FILS
2256static size_t wpas_add_fils_hlp_req(struct wpa_supplicant *wpa_s, u8 *ie_buf,
2257 size_t ie_buf_len)
2258{
2259 struct fils_hlp_req *req;
2260 size_t rem_len, hdr_len, hlp_len, len, ie_len = 0;
2261 const u8 *pos;
2262 u8 *buf = ie_buf;
2263
2264 dl_list_for_each(req, &wpa_s->fils_hlp_req, struct fils_hlp_req,
2265 list) {
2266 rem_len = ie_buf_len - ie_len;
2267 pos = wpabuf_head(req->pkt);
2268 hdr_len = 1 + 2 * ETH_ALEN + 6;
2269 hlp_len = wpabuf_len(req->pkt);
2270
2271 if (rem_len < 2 + hdr_len + hlp_len) {
2272 wpa_printf(MSG_ERROR,
2273 "FILS: Cannot fit HLP - rem_len=%lu to_fill=%lu",
2274 (unsigned long) rem_len,
2275 (unsigned long) (2 + hdr_len + hlp_len));
2276 break;
2277 }
2278
2279 len = (hdr_len + hlp_len) > 255 ? 255 : hdr_len + hlp_len;
2280 /* Element ID */
2281 *buf++ = WLAN_EID_EXTENSION;
2282 /* Length */
2283 *buf++ = len;
2284 /* Element ID Extension */
2285 *buf++ = WLAN_EID_EXT_FILS_HLP_CONTAINER;
2286 /* Destination MAC address */
2287 os_memcpy(buf, req->dst, ETH_ALEN);
2288 buf += ETH_ALEN;
2289 /* Source MAC address */
2290 os_memcpy(buf, wpa_s->own_addr, ETH_ALEN);
2291 buf += ETH_ALEN;
2292 /* LLC/SNAP Header */
2293 os_memcpy(buf, "\xaa\xaa\x03\x00\x00\x00", 6);
2294 buf += 6;
2295 /* HLP Packet */
2296 os_memcpy(buf, pos, len - hdr_len);
2297 buf += len - hdr_len;
2298 pos += len - hdr_len;
2299
2300 hlp_len -= len - hdr_len;
2301 ie_len += 2 + len;
2302 rem_len -= 2 + len;
2303
2304 while (hlp_len) {
2305 len = (hlp_len > 255) ? 255 : hlp_len;
2306 if (rem_len < 2 + len)
2307 break;
2308 *buf++ = WLAN_EID_FRAGMENT;
2309 *buf++ = len;
2310 os_memcpy(buf, pos, len);
2311 buf += len;
2312 pos += len;
2313
2314 hlp_len -= len;
2315 ie_len += 2 + len;
2316 rem_len -= 2 + len;
2317 }
2318 }
2319
2320 return ie_len;
2321}
2322#endif /* CONFIG_FILS */
2323
2324
6ac4b15e
JM
2325static void wpas_start_assoc_cb(struct wpa_radio_work *work, int deinit)
2326{
2327 struct wpa_connect_work *cwork = work->ctx;
2328 struct wpa_bss *bss = cwork->bss;
2329 struct wpa_ssid *ssid = cwork->ssid;
2330 struct wpa_supplicant *wpa_s = work->wpa_s;
1e6780bd 2331 u8 *wpa_ie;
10970465 2332 size_t max_wpa_ie_len = 500;
6ac4b15e
JM
2333 size_t wpa_ie_len;
2334 int use_crypt, ret, i, bssid_changed;
2335 int algs = WPA_AUTH_ALG_OPEN;
61a56c14 2336 unsigned int cipher_pairwise, cipher_group, cipher_group_mgmt;
6ac4b15e
JM
2337 struct wpa_driver_associate_params params;
2338 int wep_keys_set = 0;
2339 int assoc_failed = 0;
2340 struct wpa_ssid *old_ssid;
6a5ee810 2341 u8 prev_bssid[ETH_ALEN];
6ac4b15e
JM
2342#ifdef CONFIG_HT_OVERRIDES
2343 struct ieee80211_ht_capabilities htcaps;
2344 struct ieee80211_ht_capabilities htcaps_mask;
2345#endif /* CONFIG_HT_OVERRIDES */
6aa1cd4e
PS
2346#ifdef CONFIG_VHT_OVERRIDES
2347 struct ieee80211_vht_capabilities vhtcaps;
2348 struct ieee80211_vht_capabilities vhtcaps_mask;
2349#endif /* CONFIG_VHT_OVERRIDES */
8b0a6dba
VK
2350#ifdef CONFIG_FILS
2351 const u8 *realm, *username, *rrk;
2352 size_t realm_len, username_len, rrk_len;
2353 u16 next_seq_num;
b377ec25 2354 struct fils_hlp_req *req;
8b0a6dba 2355#endif /* CONFIG_FILS */
6ac4b15e
JM
2356
2357 if (deinit) {
b3253ebb
AO
2358 if (work->started) {
2359 wpa_s->connect_work = NULL;
2360
2361 /* cancel possible auth. timeout */
2362 eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s,
2363 NULL);
2364 }
6ac4b15e
JM
2365 wpas_connect_work_free(cwork);
2366 return;
2367 }
2368
2369 wpa_s->connect_work = work;
2370
6108536d
HW
2371 if (cwork->bss_removed || !wpas_valid_bss_ssid(wpa_s, bss, ssid) ||
2372 wpas_network_disabled(wpa_s, ssid)) {
6ac4b15e
JM
2373 wpa_dbg(wpa_s, MSG_DEBUG, "BSS/SSID entry for association not valid anymore - drop connection attempt");
2374 wpas_connect_work_done(wpa_s);
2375 return;
2376 }
2377
6a5ee810 2378 os_memcpy(prev_bssid, wpa_s->bssid, ETH_ALEN);
0c80427d 2379 os_memset(&params, 0, sizeof(params));
6fc6879b 2380 wpa_s->reassociate = 0;
c60ba9f7 2381 wpa_s->eap_expected_failure = 0;
76d81b32
JM
2382 if (bss &&
2383 (!wpas_driver_bss_selection(wpa_s) || wpas_wps_searching(wpa_s))) {
6fc6879b 2384#ifdef CONFIG_IEEE80211R
6fa81a3b 2385 const u8 *ie, *md = NULL;
6fc6879b 2386#endif /* CONFIG_IEEE80211R */
6fc6879b
JM
2387 wpa_msg(wpa_s, MSG_INFO, "Trying to associate with " MACSTR
2388 " (SSID='%s' freq=%d MHz)", MAC2STR(bss->bssid),
6fa81a3b 2389 wpa_ssid_txt(bss->ssid, bss->ssid_len), bss->freq);
8bac466b 2390 bssid_changed = !is_zero_ether_addr(wpa_s->bssid);
6fc6879b
JM
2391 os_memset(wpa_s->bssid, 0, ETH_ALEN);
2392 os_memcpy(wpa_s->pending_bssid, bss->bssid, ETH_ALEN);
8bac466b
JM
2393 if (bssid_changed)
2394 wpas_notify_bssid_changed(wpa_s);
6fc6879b 2395#ifdef CONFIG_IEEE80211R
6fa81a3b 2396 ie = wpa_bss_get_ie(bss, WLAN_EID_MOBILITY_DOMAIN);
6fc6879b
JM
2397 if (ie && ie[1] >= MOBILITY_DOMAIN_ID_LEN)
2398 md = ie + 2;
e7846b68 2399 wpa_sm_set_ft_params(wpa_s->wpa, ie, ie ? 2 + ie[1] : 0);
91a05482
JM
2400 if (md) {
2401 /* Prepare for the next transition */
76b7981d 2402 wpa_ft_prepare_auth_request(wpa_s->wpa, ie);
91a05482 2403 }
6fc6879b 2404#endif /* CONFIG_IEEE80211R */
24c23d1b
JM
2405#ifdef CONFIG_WPS
2406 } else if ((ssid->ssid == NULL || ssid->ssid_len == 0) &&
2407 wpa_s->conf->ap_scan == 2 &&
2408 (ssid->key_mgmt & WPA_KEY_MGMT_WPS)) {
2409 /* Use ap_scan==1 style network selection to find the network
2410 */
74656400 2411 wpas_connect_work_done(wpa_s);
4115303b 2412 wpa_s->scan_req = MANUAL_SCAN_REQ;
24c23d1b
JM
2413 wpa_s->reassociate = 1;
2414 wpa_supplicant_req_scan(wpa_s, 0, 0);
2415 return;
2416#endif /* CONFIG_WPS */
6fc6879b
JM
2417 } else {
2418 wpa_msg(wpa_s, MSG_INFO, "Trying to associate with SSID '%s'",
2419 wpa_ssid_txt(ssid->ssid, ssid->ssid_len));
04e3d815
MK
2420 if (bss)
2421 os_memcpy(wpa_s->pending_bssid, bss->bssid, ETH_ALEN);
2422 else
2423 os_memset(wpa_s->pending_bssid, 0, ETH_ALEN);
6fc6879b 2424 }
0d0f7ecb
MS
2425 if (!wpa_s->pno)
2426 wpa_supplicant_cancel_sched_scan(wpa_s);
2427
6fc6879b
JM
2428 wpa_supplicant_cancel_scan(wpa_s);
2429
2430 /* Starting new association, so clear the possibly used WPA IE from the
2431 * previous association. */
2432 wpa_sm_set_assoc_wpa_ie(wpa_s->wpa, NULL, 0);
2433
8b0a6dba 2434#ifdef CONFIG_FILS
b377ec25
VK
2435 dl_list_for_each(req, &wpa_s->fils_hlp_req, struct fils_hlp_req,
2436 list) {
2437 max_wpa_ie_len += 3 + 2 * ETH_ALEN + 6 + wpabuf_len(req->pkt) +
2438 2 + 2 * wpabuf_len(req->pkt) / 255;
8b0a6dba
VK
2439 }
2440#endif /* CONFIG_FILS */
8b0a6dba 2441
1e6780bd
VK
2442 wpa_ie = os_malloc(max_wpa_ie_len);
2443 if (!wpa_ie) {
2444 wpa_printf(MSG_ERROR,
2445 "Failed to allocate connect IE buffer for %lu bytes",
2446 (unsigned long) max_wpa_ie_len);
2447 wpas_connect_work_done(wpa_s);
2448 return;
2449 }
2450
6fa81a3b
JM
2451 if (bss && (wpa_bss_get_vendor_ie(bss, WPA_IE_VENDOR_TYPE) ||
2452 wpa_bss_get_ie(bss, WLAN_EID_RSN)) &&
0bf927a0 2453 wpa_key_mgmt_wpa(ssid->key_mgmt)) {
6fc6879b 2454 int try_opportunistic;
79f3121b
VK
2455 const u8 *cache_id = NULL;
2456
6e202021
JM
2457 try_opportunistic = (ssid->proactive_key_caching < 0 ?
2458 wpa_s->conf->okc :
2459 ssid->proactive_key_caching) &&
6fc6879b 2460 (ssid->proto & WPA_PROTO_RSN);
79f3121b
VK
2461#ifdef CONFIG_FILS
2462 if (wpa_key_mgmt_fils(ssid->key_mgmt))
2463 cache_id = wpa_bss_get_fils_cache_id(bss);
2464#endif /* CONFIG_FILS */
6fc6879b 2465 if (pmksa_cache_set_current(wpa_s->wpa, NULL, bss->bssid,
79f3121b
VK
2466 ssid, try_opportunistic,
2467 cache_id) == 0)
ba422613 2468 eapol_sm_notify_pmkid_attempt(wpa_s->eapol);
1e6780bd 2469 wpa_ie_len = max_wpa_ie_len;
6fc6879b
JM
2470 if (wpa_supplicant_set_suites(wpa_s, bss, ssid,
2471 wpa_ie, &wpa_ie_len)) {
f049052b
BG
2472 wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to set WPA "
2473 "key management and encryption suites");
74656400 2474 wpas_connect_work_done(wpa_s);
1e6780bd 2475 os_free(wpa_ie);
6fc6879b
JM
2476 return;
2477 }
a3f7e518
JM
2478 } else if ((ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_NO_WPA) && bss &&
2479 wpa_key_mgmt_wpa_ieee8021x(ssid->key_mgmt)) {
2480 /*
2481 * Both WPA and non-WPA IEEE 802.1X enabled in configuration -
2482 * use non-WPA since the scan results did not indicate that the
2483 * AP is using WPA or WPA2.
2484 */
2485 wpa_supplicant_set_non_wpa_policy(wpa_s, ssid);
2486 wpa_ie_len = 0;
2487 wpa_s->wpa_proto = 0;
0bf927a0 2488 } else if (wpa_key_mgmt_wpa_any(ssid->key_mgmt)) {
1e6780bd 2489 wpa_ie_len = max_wpa_ie_len;
6fc6879b
JM
2490 if (wpa_supplicant_set_suites(wpa_s, NULL, ssid,
2491 wpa_ie, &wpa_ie_len)) {
f049052b
BG
2492 wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to set WPA "
2493 "key management and encryption suites (no "
2494 "scan results)");
74656400 2495 wpas_connect_work_done(wpa_s);
1e6780bd 2496 os_free(wpa_ie);
6fc6879b
JM
2497 return;
2498 }
ad08c363
JM
2499#ifdef CONFIG_WPS
2500 } else if (ssid->key_mgmt & WPA_KEY_MGMT_WPS) {
b01c18a8
JM
2501 struct wpabuf *wps_ie;
2502 wps_ie = wps_build_assoc_req_ie(wpas_wps_get_req_type(ssid));
1e6780bd 2503 if (wps_ie && wpabuf_len(wps_ie) <= max_wpa_ie_len) {
ad08c363
JM
2504 wpa_ie_len = wpabuf_len(wps_ie);
2505 os_memcpy(wpa_ie, wpabuf_head(wps_ie), wpa_ie_len);
24386985
JM
2506 } else
2507 wpa_ie_len = 0;
ad08c363
JM
2508 wpabuf_free(wps_ie);
2509 wpa_supplicant_set_non_wpa_policy(wpa_s, ssid);
0c80427d
JM
2510 if (!bss || (bss->caps & IEEE80211_CAP_PRIVACY))
2511 params.wps = WPS_MODE_PRIVACY;
2512 else
2513 params.wps = WPS_MODE_OPEN;
cf546f1a 2514 wpa_s->wpa_proto = 0;
ad08c363 2515#endif /* CONFIG_WPS */
6fc6879b
JM
2516 } else {
2517 wpa_supplicant_set_non_wpa_policy(wpa_s, ssid);
2518 wpa_ie_len = 0;
cf546f1a 2519 wpa_s->wpa_proto = 0;
6fc6879b
JM
2520 }
2521
b377ec25
VK
2522#ifdef IEEE8021X_EAPOL
2523 if (ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_NO_WPA) {
2524 if (ssid->leap) {
2525 if (ssid->non_leap == 0)
2526 algs = WPA_AUTH_ALG_LEAP;
2527 else
2528 algs |= WPA_AUTH_ALG_LEAP;
2529 }
2530 }
2531
2532#ifdef CONFIG_FILS
2533 /* Clear FILS association */
2534 wpa_sm_set_reset_fils_completed(wpa_s->wpa, 0);
2535
2536 if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_FILS_SK_OFFLOAD) &&
2537 ssid->eap.erp && wpa_key_mgmt_fils(wpa_s->key_mgmt) &&
2538 eapol_sm_get_erp_info(wpa_s->eapol, &ssid->eap, &username,
2539 &username_len, &realm, &realm_len,
2540 &next_seq_num, &rrk, &rrk_len) == 0) {
2541 algs = WPA_AUTH_ALG_FILS;
2542 params.fils_erp_username = username;
2543 params.fils_erp_username_len = username_len;
2544 params.fils_erp_realm = realm;
2545 params.fils_erp_realm_len = realm_len;
2546 params.fils_erp_next_seq_num = next_seq_num;
2547 params.fils_erp_rrk = rrk;
2548 params.fils_erp_rrk_len = rrk_len;
2549 }
2550#endif /* CONFIG_FILS */
2551#endif /* IEEE8021X_EAPOL */
2552
2553 wpa_dbg(wpa_s, MSG_DEBUG, "Automatic auth_alg selection: 0x%x", algs);
2554 if (ssid->auth_alg) {
2555 algs = ssid->auth_alg;
2556 wpa_dbg(wpa_s, MSG_DEBUG,
2557 "Overriding auth_alg selection: 0x%x", algs);
2558 }
2559
5f3a6aa0
JM
2560#ifdef CONFIG_P2P
2561 if (wpa_s->global->p2p) {
2562 u8 *pos;
2563 size_t len;
2564 int res;
5f3a6aa0 2565 pos = wpa_ie + wpa_ie_len;
1e6780bd 2566 len = max_wpa_ie_len - wpa_ie_len;
b8a8d677
JM
2567 res = wpas_p2p_assoc_req_ie(wpa_s, bss, pos, len,
2568 ssid->p2p_group);
5f3a6aa0
JM
2569 if (res >= 0)
2570 wpa_ie_len += res;
2571 }
72044390
JM
2572
2573 wpa_s->cross_connect_disallowed = 0;
2574 if (bss) {
2575 struct wpabuf *p2p;
2576 p2p = wpa_bss_get_vendor_ie_multi(bss, P2P_IE_VENDOR_TYPE);
2577 if (p2p) {
2578 wpa_s->cross_connect_disallowed =
2579 p2p_get_cross_connect_disallowed(p2p);
2580 wpabuf_free(p2p);
f049052b
BG
2581 wpa_dbg(wpa_s, MSG_DEBUG, "P2P: WLAN AP %s cross "
2582 "connection",
2583 wpa_s->cross_connect_disallowed ?
2584 "disallows" : "allows");
72044390
JM
2585 }
2586 }
25ef8529
JM
2587
2588 os_memset(wpa_s->p2p_ip_addr_info, 0, sizeof(wpa_s->p2p_ip_addr_info));
5f3a6aa0
JM
2589#endif /* CONFIG_P2P */
2590
5e57ba25 2591 if (bss) {
065c029a 2592 wpa_ie_len += wpas_supp_op_class_ie(wpa_s, bss->freq,
2593 wpa_ie + wpa_ie_len,
1e6780bd 2594 max_wpa_ie_len -
065c029a 2595 wpa_ie_len);
5e57ba25 2596 }
5e57ba25 2597
8b3b803a
AH
2598 /*
2599 * Workaround: Add Extended Capabilities element only if the AP
2600 * included this element in Beacon/Probe Response frames. Some older
2601 * APs seem to have interoperability issues if this element is
2602 * included, so while the standard may require us to include the
2603 * element in all cases, it is justifiable to skip it to avoid
2604 * interoperability issues.
2605 */
cc9a2575
KV
2606 if (ssid->p2p_group)
2607 wpa_drv_get_ext_capa(wpa_s, WPA_IF_P2P_CLIENT);
2608 else
2609 wpa_drv_get_ext_capa(wpa_s, WPA_IF_STATION);
2610
8b3b803a 2611 if (!bss || wpa_bss_get_ie(bss, WLAN_EID_EXT_CAPAB)) {
0bbaa9b9 2612 u8 ext_capab[18];
8b3b803a 2613 int ext_capab_len;
0bbaa9b9
JM
2614 ext_capab_len = wpas_build_ext_capab(wpa_s, ext_capab,
2615 sizeof(ext_capab));
2c66c7d1
AA
2616 if (ext_capab_len > 0 &&
2617 wpa_ie_len + ext_capab_len <= max_wpa_ie_len) {
8b3b803a
AH
2618 u8 *pos = wpa_ie;
2619 if (wpa_ie_len > 0 && pos[0] == WLAN_EID_RSN)
2620 pos += 2 + pos[1];
2621 os_memmove(pos + ext_capab_len, pos,
2622 wpa_ie_len - (pos - wpa_ie));
2623 wpa_ie_len += ext_capab_len;
2624 os_memcpy(pos, ext_capab, ext_capab_len);
2625 }
92cbcf91 2626 }
92cbcf91 2627
c484b198
AS
2628#ifdef CONFIG_HS20
2629 if (is_hs20_network(wpa_s, ssid, bss)) {
2630 struct wpabuf *hs20;
2631
2632 hs20 = wpabuf_alloc(20);
2633 if (hs20) {
2634 int pps_mo_id = hs20_get_pps_mo_id(wpa_s, ssid);
2635 size_t len;
2636
2637 wpas_hs20_add_indication(hs20, pps_mo_id);
1e6780bd 2638 len = max_wpa_ie_len - wpa_ie_len;
c484b198
AS
2639 if (wpabuf_len(hs20) <= len) {
2640 os_memcpy(wpa_ie + wpa_ie_len,
2641 wpabuf_head(hs20), wpabuf_len(hs20));
2642 wpa_ie_len += wpabuf_len(hs20);
2643 }
2644 wpabuf_free(hs20);
ece4ac5f
MG
2645
2646 hs20_configure_frame_filters(wpa_s);
c484b198
AS
2647 }
2648 }
2649#endif /* CONFIG_HS20 */
2650
d29fa3a7
JM
2651 if (wpa_s->vendor_elem[VENDOR_ELEM_ASSOC_REQ]) {
2652 struct wpabuf *buf = wpa_s->vendor_elem[VENDOR_ELEM_ASSOC_REQ];
2653 size_t len;
2654
1e6780bd 2655 len = max_wpa_ie_len - wpa_ie_len;
d29fa3a7
JM
2656 if (wpabuf_len(buf) <= len) {
2657 os_memcpy(wpa_ie + wpa_ie_len,
2658 wpabuf_head(buf), wpabuf_len(buf));
2659 wpa_ie_len += wpabuf_len(buf);
2660 }
2661 }
2662
b36a3a65
AN
2663#ifdef CONFIG_FST
2664 if (wpa_s->fst_ies) {
2665 int fst_ies_len = wpabuf_len(wpa_s->fst_ies);
2666
1e6780bd 2667 if (wpa_ie_len + fst_ies_len <= max_wpa_ie_len) {
b36a3a65
AN
2668 os_memcpy(wpa_ie + wpa_ie_len,
2669 wpabuf_head(wpa_s->fst_ies), fst_ies_len);
2670 wpa_ie_len += fst_ies_len;
2671 }
2672 }
2673#endif /* CONFIG_FST */
2674
92c6e2e3 2675#ifdef CONFIG_MBO
065c029a 2676 if (bss && wpa_bss_get_vendor_ie(bss, MBO_IE_VENDOR_TYPE)) {
5e57ba25 2677 int len;
92c6e2e3 2678
5e57ba25 2679 len = wpas_mbo_ie(wpa_s, wpa_ie + wpa_ie_len,
1e6780bd 2680 max_wpa_ie_len - wpa_ie_len);
5e57ba25
AS
2681 if (len >= 0)
2682 wpa_ie_len += len;
92c6e2e3
DS
2683 }
2684#endif /* CONFIG_MBO */
2685
a38090b1
VK
2686#ifdef CONFIG_FILS
2687 if (algs == WPA_AUTH_ALG_FILS) {
2688 size_t len;
2689
2690 len = wpas_add_fils_hlp_req(wpa_s, wpa_ie + wpa_ie_len,
2691 max_wpa_ie_len - wpa_ie_len);
2692 wpa_ie_len += len;
2693 }
2694#endif /* CONFIG_FILS */
2695
10970465
JM
2696#ifdef CONFIG_OWE
2697 if (algs == WPA_AUTH_ALG_OPEN &&
2698 ssid->key_mgmt == WPA_KEY_MGMT_OWE) {
2699 struct wpabuf *owe_ie;
2700 u16 group = OWE_DH_GROUP;
2701
2702 if (ssid->owe_group)
2703 group = ssid->owe_group;
2704 owe_ie = owe_build_assoc_req(wpa_s->wpa, group);
2705 if (owe_ie &&
2706 wpabuf_len(owe_ie) <= max_wpa_ie_len - wpa_ie_len) {
2707 os_memcpy(wpa_ie + wpa_ie_len,
2708 wpabuf_head(owe_ie), wpabuf_len(owe_ie));
2709 wpa_ie_len += wpabuf_len(owe_ie);
2710 wpabuf_free(owe_ie);
2711 }
2712 }
2713#endif /* CONFIG_OWE */
2714
6fc6879b
JM
2715 wpa_clear_keys(wpa_s, bss ? bss->bssid : NULL);
2716 use_crypt = 1;
4848a38d
JM
2717 cipher_pairwise = wpa_s->pairwise_cipher;
2718 cipher_group = wpa_s->group_cipher;
61a56c14 2719 cipher_group_mgmt = wpa_s->mgmt_group_cipher;
6fc6879b
JM
2720 if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE ||
2721 wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) {
2722 if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE)
2723 use_crypt = 0;
2724 if (wpa_set_wep_keys(wpa_s, ssid)) {
2725 use_crypt = 1;
2726 wep_keys_set = 1;
2727 }
2728 }
ad08c363
JM
2729 if (wpa_s->key_mgmt == WPA_KEY_MGMT_WPS)
2730 use_crypt = 0;
6fc6879b
JM
2731
2732#ifdef IEEE8021X_EAPOL
2733 if (wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) {
2734 if ((ssid->eapol_flags &
2735 (EAPOL_FLAG_REQUIRE_KEY_UNICAST |
2736 EAPOL_FLAG_REQUIRE_KEY_BROADCAST)) == 0 &&
2737 !wep_keys_set) {
2738 use_crypt = 0;
2739 } else {
2740 /* Assume that dynamic WEP-104 keys will be used and
2741 * set cipher suites in order for drivers to expect
2742 * encryption. */
4848a38d 2743 cipher_pairwise = cipher_group = WPA_CIPHER_WEP104;
6fc6879b
JM
2744 }
2745 }
2746#endif /* IEEE8021X_EAPOL */
2747
2748 if (wpa_s->key_mgmt == WPA_KEY_MGMT_WPA_NONE) {
2749 /* Set the key before (and later after) association */
2750 wpa_supplicant_set_wpa_none_key(wpa_s, ssid);
2751 }
2752
6fc6879b 2753 wpa_supplicant_set_state(wpa_s, WPA_ASSOCIATING);
6fc6879b 2754 if (bss) {
6fa81a3b
JM
2755 params.ssid = bss->ssid;
2756 params.ssid_len = bss->ssid_len;
4b5b8a53
JM
2757 if (!wpas_driver_bss_selection(wpa_s) || ssid->bssid_set ||
2758 wpa_s->key_mgmt == WPA_KEY_MGMT_WPS) {
f15854d1
JM
2759 wpa_printf(MSG_DEBUG, "Limit connection to BSSID "
2760 MACSTR " freq=%u MHz based on scan results "
4b5b8a53 2761 "(bssid_set=%d wps=%d)",
f15854d1 2762 MAC2STR(bss->bssid), bss->freq,
4b5b8a53
JM
2763 ssid->bssid_set,
2764 wpa_s->key_mgmt == WPA_KEY_MGMT_WPS);
22628eca 2765 params.bssid = bss->bssid;
4ec68377 2766 params.freq.freq = bss->freq;
22628eca 2767 }
7ac7fd43
DS
2768 params.bssid_hint = bss->bssid;
2769 params.freq_hint = bss->freq;
b9074912 2770 params.pbss = bss_is_pbss(bss);
6fc6879b 2771 } else {
43a356b2
PK
2772 if (ssid->bssid_hint_set)
2773 params.bssid_hint = ssid->bssid_hint;
2774
6fc6879b
JM
2775 params.ssid = ssid->ssid;
2776 params.ssid_len = ssid->ssid_len;
90f14962 2777 params.pbss = (ssid->pbss != 2) ? ssid->pbss : 0;
6fc6879b 2778 }
9e2af29f
NC
2779
2780 if (ssid->mode == WPAS_MODE_IBSS && ssid->bssid_set &&
2781 wpa_s->conf->ap_scan == 2) {
2782 params.bssid = ssid->bssid;
2783 params.fixed_bssid = 1;
2784 }
2785
603a3f34
JL
2786 /* Initial frequency for IBSS/mesh */
2787 if ((ssid->mode == WPAS_MODE_IBSS || ssid->mode == WPAS_MODE_MESH) &&
1830817e
JD
2788 ssid->frequency > 0 && params.freq.freq == 0)
2789 ibss_mesh_setup_freq(wpa_s, ssid, &params.freq);
dc152f32 2790
8f05577d 2791 if (ssid->mode == WPAS_MODE_IBSS) {
4d9e6fba 2792 params.fixed_freq = ssid->fixed_freq;
8f05577d
JM
2793 if (ssid->beacon_int)
2794 params.beacon_int = ssid->beacon_int;
2795 else
2796 params.beacon_int = wpa_s->conf->beacon_int;
2797 }
2798
6fc6879b
JM
2799 params.wpa_ie = wpa_ie;
2800 params.wpa_ie_len = wpa_ie_len;
2801 params.pairwise_suite = cipher_pairwise;
2802 params.group_suite = cipher_group;
61a56c14 2803 params.mgmt_group_suite = cipher_group_mgmt;
4848a38d 2804 params.key_mgmt_suite = wpa_s->key_mgmt;
64fa840a 2805 params.wpa_proto = wpa_s->wpa_proto;
6fc6879b 2806 params.auth_alg = algs;
5538fc93 2807 wpa_s->auth_alg = params.auth_alg;
6fc6879b 2808 params.mode = ssid->mode;
1f6c0ab8 2809 params.bg_scan_period = ssid->bg_scan_period;
6fc6879b
JM
2810 for (i = 0; i < NUM_WEP_KEYS; i++) {
2811 if (ssid->wep_key_len[i])
2812 params.wep_key[i] = ssid->wep_key[i];
2813 params.wep_key_len[i] = ssid->wep_key_len[i];
2814 }
2815 params.wep_tx_keyidx = ssid->wep_tx_keyidx;
2816
c2a04078 2817 if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE) &&
4848a38d
JM
2818 (params.key_mgmt_suite == WPA_KEY_MGMT_PSK ||
2819 params.key_mgmt_suite == WPA_KEY_MGMT_FT_PSK)) {
6fc6879b
JM
2820 params.passphrase = ssid->passphrase;
2821 if (ssid->psk_set)
2822 params.psk = ssid->psk;
b41f2684
CL
2823 }
2824
2825 if (wpa_s->conf->key_mgmt_offload) {
2826 if (params.key_mgmt_suite == WPA_KEY_MGMT_IEEE8021X ||
666497c8 2827 params.key_mgmt_suite == WPA_KEY_MGMT_IEEE8021X_SHA256 ||
5e3b5197
JM
2828 params.key_mgmt_suite == WPA_KEY_MGMT_IEEE8021X_SUITE_B ||
2829 params.key_mgmt_suite == WPA_KEY_MGMT_IEEE8021X_SUITE_B_192)
b41f2684
CL
2830 params.req_key_mgmt_offload =
2831 ssid->proactive_key_caching < 0 ?
2832 wpa_s->conf->okc : ssid->proactive_key_caching;
2833 else
2834 params.req_key_mgmt_offload = 1;
2835
2836 if ((params.key_mgmt_suite == WPA_KEY_MGMT_PSK ||
2837 params.key_mgmt_suite == WPA_KEY_MGMT_PSK_SHA256 ||
2838 params.key_mgmt_suite == WPA_KEY_MGMT_FT_PSK) &&
2839 ssid->psk_set)
2840 params.psk = ssid->psk;
6fc6879b
JM
2841 }
2842
36b15723
JM
2843 params.drop_unencrypted = use_crypt;
2844
6fc6879b 2845#ifdef CONFIG_IEEE80211W
3f56a2b7 2846 params.mgmt_frame_protection = wpas_get_ssid_pmf(wpa_s, ssid);
62d49803 2847 if (params.mgmt_frame_protection != NO_MGMT_FRAME_PROTECTION && bss) {
6fa81a3b 2848 const u8 *rsn = wpa_bss_get_ie(bss, WLAN_EID_RSN);
97d3497e
JM
2849 struct wpa_ie_data ie;
2850 if (rsn && wpa_parse_wpa_ie(rsn, 2 + rsn[1], &ie) == 0 &&
2851 ie.capabilities &
2852 (WPA_CAPABILITY_MFPC | WPA_CAPABILITY_MFPR)) {
f049052b
BG
2853 wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Selected AP supports "
2854 "MFP: require MFP");
97d3497e
JM
2855 params.mgmt_frame_protection =
2856 MGMT_FRAME_PROTECTION_REQUIRED;
2857 }
2858 }
6fc6879b
JM
2859#endif /* CONFIG_IEEE80211W */
2860
ffad8858 2861 params.p2p = ssid->p2p_group;
6e3f4b89 2862
ba307f85
LD
2863 if (wpa_s->p2pdev->set_sta_uapsd)
2864 params.uapsd = wpa_s->p2pdev->sta_uapsd;
eea2fd9e
JM
2865 else
2866 params.uapsd = -1;
2867
80e8a5ee
BG
2868#ifdef CONFIG_HT_OVERRIDES
2869 os_memset(&htcaps, 0, sizeof(htcaps));
2870 os_memset(&htcaps_mask, 0, sizeof(htcaps_mask));
2871 params.htcaps = (u8 *) &htcaps;
2872 params.htcaps_mask = (u8 *) &htcaps_mask;
2873 wpa_supplicant_apply_ht_overrides(wpa_s, ssid, &params);
2874#endif /* CONFIG_HT_OVERRIDES */
6aa1cd4e
PS
2875#ifdef CONFIG_VHT_OVERRIDES
2876 os_memset(&vhtcaps, 0, sizeof(vhtcaps));
2877 os_memset(&vhtcaps_mask, 0, sizeof(vhtcaps_mask));
2878 params.vhtcaps = &vhtcaps;
2879 params.vhtcaps_mask = &vhtcaps_mask;
95ff3069 2880 wpa_supplicant_apply_vht_overrides(wpa_s, ssid, &params);
6aa1cd4e 2881#endif /* CONFIG_VHT_OVERRIDES */
80e8a5ee 2882
8567866d
JJ
2883#ifdef CONFIG_P2P
2884 /*
2885 * If multi-channel concurrency is not supported, check for any
2886 * frequency conflict. In case of any frequency conflict, remove the
2887 * least prioritized connection.
2888 */
2889 if (wpa_s->num_multichan_concurrent < 2) {
d0df6437
IP
2890 int freq, num;
2891 num = get_shared_radio_freqs(wpa_s, &freq, 1);
4ec68377 2892 if (num > 0 && freq > 0 && freq != params.freq.freq) {
d0df6437
IP
2893 wpa_printf(MSG_DEBUG,
2894 "Assoc conflicting freq found (%d != %d)",
4ec68377
JD
2895 freq, params.freq.freq);
2896 if (wpas_p2p_handle_frequency_conflicts(
74656400
SD
2897 wpa_s, params.freq.freq, ssid) < 0) {
2898 wpas_connect_work_done(wpa_s);
1e6780bd 2899 os_free(wpa_ie);
8567866d 2900 return;
74656400 2901 }
8567866d
JJ
2902 }
2903 }
2904#endif /* CONFIG_P2P */
2905
6a5ee810
JM
2906 if (wpa_s->reassoc_same_ess && !is_zero_ether_addr(prev_bssid) &&
2907 wpa_s->current_ssid)
2908 params.prev_bssid = prev_bssid;
2909
17fbb751 2910 ret = wpa_drv_associate(wpa_s, &params);
1e6780bd 2911 os_free(wpa_ie);
6fc6879b
JM
2912 if (ret < 0) {
2913 wpa_msg(wpa_s, MSG_INFO, "Association request to the driver "
2914 "failed");
871f4dd0
JM
2915 if (wpa_s->drv_flags & WPA_DRIVER_FLAGS_SANE_ERROR_CODES) {
2916 /*
2917 * The driver is known to mean what is saying, so we
2918 * can stop right here; the association will not
2919 * succeed.
2920 */
2921 wpas_connection_failed(wpa_s, wpa_s->pending_bssid);
c1c02342 2922 wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED);
871f4dd0
JM
2923 os_memset(wpa_s->pending_bssid, 0, ETH_ALEN);
2924 return;
2925 }
6fc6879b
JM
2926 /* try to continue anyway; new association will be tried again
2927 * after timeout */
2928 assoc_failed = 1;
2929 }
2930
2931 if (wpa_s->key_mgmt == WPA_KEY_MGMT_WPA_NONE) {
2932 /* Set the key after the association just in case association
2933 * cleared the previously configured key. */
2934 wpa_supplicant_set_wpa_none_key(wpa_s, ssid);
2935 /* No need to timeout authentication since there is no key
2936 * management. */
2937 wpa_supplicant_cancel_auth_timeout(wpa_s);
2938 wpa_supplicant_set_state(wpa_s, WPA_COMPLETED);
53895c3b 2939#ifdef CONFIG_IBSS_RSN
d7dcba70 2940 } else if (ssid->mode == WPAS_MODE_IBSS &&
53895c3b
JM
2941 wpa_s->key_mgmt != WPA_KEY_MGMT_NONE &&
2942 wpa_s->key_mgmt != WPA_KEY_MGMT_WPA_NONE) {
2943 /*
2944 * RSN IBSS authentication is per-STA and we can disable the
2945 * per-BSSID authentication.
2946 */
2947 wpa_supplicant_cancel_auth_timeout(wpa_s);
53895c3b 2948#endif /* CONFIG_IBSS_RSN */
6fc6879b
JM
2949 } else {
2950 /* Timeout for IEEE 802.11 authentication and association */
1d3c75b3
DW
2951 int timeout = 60;
2952
2953 if (assoc_failed) {
2954 /* give IBSS a bit more time */
d7dcba70 2955 timeout = ssid->mode == WPAS_MODE_IBSS ? 10 : 5;
1d3c75b3
DW
2956 } else if (wpa_s->conf->ap_scan == 1) {
2957 /* give IBSS a bit more time */
d7dcba70 2958 timeout = ssid->mode == WPAS_MODE_IBSS ? 20 : 10;
1d3c75b3 2959 }
6fc6879b
JM
2960 wpa_supplicant_req_auth_timeout(wpa_s, timeout, 0);
2961 }
2962
66562e9c
JM
2963 if (wep_keys_set &&
2964 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_SET_KEYS_AFTER_ASSOC)) {
6fc6879b
JM
2965 /* Set static WEP keys again */
2966 wpa_set_wep_keys(wpa_s, ssid);
2967 }
2968
2969 if (wpa_s->current_ssid && wpa_s->current_ssid != ssid) {
2970 /*
2971 * Do not allow EAP session resumption between different
2972 * network configurations.
2973 */
2974 eapol_sm_invalidate_cached_session(wpa_s->eapol);
2975 }
8bac466b 2976 old_ssid = wpa_s->current_ssid;
6fc6879b 2977 wpa_s->current_ssid = ssid;
ece4ac5f
MG
2978
2979 if (!wpas_driver_bss_selection(wpa_s) || ssid->bssid_set) {
4d3be9cd 2980 wpa_s->current_bss = bss;
ece4ac5f
MG
2981#ifdef CONFIG_HS20
2982 hs20_configure_frame_filters(wpa_s);
2983#endif /* CONFIG_HS20 */
2984 }
2985
6fc6879b
JM
2986 wpa_supplicant_rsn_supp_set_config(wpa_s, wpa_s->current_ssid);
2987 wpa_supplicant_initiate_eapol(wpa_s);
8bac466b
JM
2988 if (old_ssid != wpa_s->current_ssid)
2989 wpas_notify_network_changed(wpa_s);
6fc6879b
JM
2990}
2991
2992
09f58c09
JM
2993static void wpa_supplicant_clear_connection(struct wpa_supplicant *wpa_s,
2994 const u8 *addr)
2995{
2996 struct wpa_ssid *old_ssid;
2997
c155305f 2998 wpas_connect_work_done(wpa_s);
09f58c09 2999 wpa_clear_keys(wpa_s, addr);
09f58c09 3000 old_ssid = wpa_s->current_ssid;
0d30cc24 3001 wpa_supplicant_mark_disassoc(wpa_s);
09f58c09
JM
3002 wpa_sm_set_config(wpa_s->wpa, NULL);
3003 eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
3004 if (old_ssid != wpa_s->current_ssid)
3005 wpas_notify_network_changed(wpa_s);
3006 eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL);
3007}
3008
3009
6fc6879b
JM
3010/**
3011 * wpa_supplicant_deauthenticate - Deauthenticate the current connection
3012 * @wpa_s: Pointer to wpa_supplicant data
3013 * @reason_code: IEEE 802.11 reason code for the deauthenticate frame
3014 *
073ab58f 3015 * This function is used to request %wpa_supplicant to deauthenticate from the
6fc6879b
JM
3016 * current AP.
3017 */
3018void wpa_supplicant_deauthenticate(struct wpa_supplicant *wpa_s,
3019 int reason_code)
3020{
3021 u8 *addr = NULL;
ef48ff94 3022 union wpa_event_data event;
42d23547 3023 int zero_addr = 0;
8bac466b 3024
42d23547
JM
3025 wpa_dbg(wpa_s, MSG_DEBUG, "Request to deauthenticate - bssid=" MACSTR
3026 " pending_bssid=" MACSTR " reason=%d state=%s",
3027 MAC2STR(wpa_s->bssid), MAC2STR(wpa_s->pending_bssid),
3028 reason_code, wpa_supplicant_state_txt(wpa_s->wpa_state));
3029
04e3d815
MK
3030 if (!is_zero_ether_addr(wpa_s->pending_bssid) &&
3031 (wpa_s->wpa_state == WPA_AUTHENTICATING ||
3032 wpa_s->wpa_state == WPA_ASSOCIATING))
42d23547 3033 addr = wpa_s->pending_bssid;
04e3d815
MK
3034 else if (!is_zero_ether_addr(wpa_s->bssid))
3035 addr = wpa_s->bssid;
42d23547
JM
3036 else if (wpa_s->wpa_state == WPA_ASSOCIATING) {
3037 /*
3038 * When using driver-based BSS selection, we may not know the
3039 * BSSID with which we are currently trying to associate. We
3040 * need to notify the driver of this disconnection even in such
3041 * a case, so use the all zeros address here.
3042 */
6fc6879b 3043 addr = wpa_s->bssid;
42d23547
JM
3044 zero_addr = 1;
3045 }
3046
7b44ff2c
SD
3047#ifdef CONFIG_TDLS
3048 wpa_tdls_teardown_peers(wpa_s->wpa);
3049#endif /* CONFIG_TDLS */
3050
603a3f34
JL
3051#ifdef CONFIG_MESH
3052 if (wpa_s->ifmsh) {
a39b040b
SB
3053 struct mesh_conf *mconf;
3054
3055 mconf = wpa_s->ifmsh->mconf;
6174de66
JM
3056 wpa_msg(wpa_s, MSG_INFO, MESH_GROUP_REMOVED "%s",
3057 wpa_s->ifname);
a39b040b
SB
3058 wpas_notify_mesh_group_removed(wpa_s, mconf->meshid,
3059 mconf->meshid_len, reason_code);
603a3f34
JL
3060 wpa_supplicant_leave_mesh(wpa_s);
3061 }
3062#endif /* CONFIG_MESH */
3063
42d23547
JM
3064 if (addr) {
3065 wpa_drv_deauthenticate(wpa_s, addr, reason_code);
ef48ff94
JM
3066 os_memset(&event, 0, sizeof(event));
3067 event.deauth_info.reason_code = (u16) reason_code;
3068 event.deauth_info.locally_generated = 1;
3069 wpa_supplicant_event(wpa_s, EVENT_DEAUTH, &event);
42d23547
JM
3070 if (zero_addr)
3071 addr = NULL;
6fc6879b 3072 }
09f58c09
JM
3073
3074 wpa_supplicant_clear_connection(wpa_s, addr);
6fc6879b
JM
3075}
3076
dca1a511
DS
3077static void wpa_supplicant_enable_one_network(struct wpa_supplicant *wpa_s,
3078 struct wpa_ssid *ssid)
3079{
3080 if (!ssid || !ssid->disabled || ssid->disabled == 2)
3081 return;
3082
3083 ssid->disabled = 0;
3084 wpas_clear_temp_disabled(wpa_s, ssid, 1);
3085 wpas_notify_network_enabled_changed(wpa_s, ssid);
3086
3087 /*
3088 * Try to reassociate since there is no current configuration and a new
3089 * network was made available.
3090 */
d2592497 3091 if (!wpa_s->current_ssid && !wpa_s->disconnected)
dca1a511
DS
3092 wpa_s->reassociate = 1;
3093}
3094
6fc6879b 3095
d015bb05
RP
3096/**
3097 * wpa_supplicant_add_network - Add a new network
3098 * @wpa_s: wpa_supplicant structure for a network interface
3099 * Returns: The new network configuration or %NULL if operation failed
3100 *
3101 * This function performs the following operations:
3102 * 1. Adds a new network.
3103 * 2. Send network addition notification.
3104 * 3. Marks the network disabled.
3105 * 4. Set network default parameters.
3106 */
3107struct wpa_ssid * wpa_supplicant_add_network(struct wpa_supplicant *wpa_s)
3108{
3109 struct wpa_ssid *ssid;
3110
3111 ssid = wpa_config_add_network(wpa_s->conf);
3112 if (!ssid)
3113 return NULL;
3114 wpas_notify_network_added(wpa_s, ssid);
3115 ssid->disabled = 1;
3116 wpa_config_set_network_defaults(ssid);
3117
3118 return ssid;
3119}
3120
3121
3122/**
3123 * wpa_supplicant_remove_network - Remove a configured network based on id
3124 * @wpa_s: wpa_supplicant structure for a network interface
3125 * @id: Unique network id to search for
3126 * Returns: 0 on success, or -1 if the network was not found, -2 if the network
3127 * could not be removed
3128 *
3129 * This function performs the following operations:
3130 * 1. Removes the network.
3131 * 2. Send network removal notification.
3132 * 3. Update internal state machines.
3133 * 4. Stop any running sched scans.
3134 */
3135int wpa_supplicant_remove_network(struct wpa_supplicant *wpa_s, int id)
3136{
3137 struct wpa_ssid *ssid;
3138 int was_disabled;
3139
3140 ssid = wpa_config_get_network(wpa_s->conf, id);
3141 if (!ssid)
3142 return -1;
3143 wpas_notify_network_removed(wpa_s, ssid);
3144
3145 if (wpa_s->last_ssid == ssid)
3146 wpa_s->last_ssid = NULL;
3147
3148 if (ssid == wpa_s->current_ssid || !wpa_s->current_ssid) {
3149#ifdef CONFIG_SME
3150 wpa_s->sme.prev_bssid_set = 0;
3151#endif /* CONFIG_SME */
3152 /*
3153 * Invalidate the EAP session cache if the current or
3154 * previously used network is removed.
3155 */
3156 eapol_sm_invalidate_cached_session(wpa_s->eapol);
3157 }
3158
3159 if (ssid == wpa_s->current_ssid) {
3160 wpa_sm_set_config(wpa_s->wpa, NULL);
3161 eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
3162
3163 if (wpa_s->wpa_state >= WPA_AUTHENTICATING)
3164 wpa_s->own_disconnect_req = 1;
3165 wpa_supplicant_deauthenticate(wpa_s,
3166 WLAN_REASON_DEAUTH_LEAVING);
3167 }
3168
3169 was_disabled = ssid->disabled;
3170
3171 if (wpa_config_remove_network(wpa_s->conf, id) < 0)
3172 return -2;
3173
3174 if (!was_disabled && wpa_s->sched_scanning) {
3175 wpa_printf(MSG_DEBUG,
3176 "Stop ongoing sched_scan to remove network from filters");
3177 wpa_supplicant_cancel_sched_scan(wpa_s);
3178 wpa_supplicant_req_scan(wpa_s, 0, 0);
3179 }
3180
3181 return 0;
3182}
3183
3184
86b89452
WS
3185/**
3186 * wpa_supplicant_enable_network - Mark a configured network as enabled
3187 * @wpa_s: wpa_supplicant structure for a network interface
3188 * @ssid: wpa_ssid structure for a configured network or %NULL
3189 *
3190 * Enables the specified network or all networks if no network specified.
3191 */
3192void wpa_supplicant_enable_network(struct wpa_supplicant *wpa_s,
3193 struct wpa_ssid *ssid)
3194{
86b89452 3195 if (ssid == NULL) {
14f79078
JM
3196 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next)
3197 wpa_supplicant_enable_one_network(wpa_s, ssid);
dca1a511
DS
3198 } else
3199 wpa_supplicant_enable_one_network(wpa_s, ssid);
86b89452 3200
5a1d9d1a
JM
3201 if (wpa_s->reassociate && !wpa_s->disconnected &&
3202 (!wpa_s->current_ssid ||
3203 wpa_s->wpa_state == WPA_DISCONNECTED ||
3204 wpa_s->wpa_state == WPA_SCANNING)) {
dca1a511
DS
3205 if (wpa_s->sched_scanning) {
3206 wpa_printf(MSG_DEBUG, "Stop ongoing sched_scan to add "
3207 "new network to scan filters");
3208 wpa_supplicant_cancel_sched_scan(wpa_s);
3209 }
86b89452 3210
35d40309
JM
3211 if (wpa_supplicant_fast_associate(wpa_s) != 1) {
3212 wpa_s->scan_req = NORMAL_SCAN_REQ;
dad153d1 3213 wpa_supplicant_req_scan(wpa_s, 0, 0);
35d40309 3214 }
86b89452
WS
3215 }
3216}
3217
3218
3219/**
3220 * wpa_supplicant_disable_network - Mark a configured network as disabled
3221 * @wpa_s: wpa_supplicant structure for a network interface
3222 * @ssid: wpa_ssid structure for a configured network or %NULL
3223 *
3224 * Disables the specified network or all networks if no network specified.
3225 */
3226void wpa_supplicant_disable_network(struct wpa_supplicant *wpa_s,
3227 struct wpa_ssid *ssid)
3228{
3229 struct wpa_ssid *other_ssid;
3230 int was_disabled;
3231
3232 if (ssid == NULL) {
725fc39e
DS
3233 if (wpa_s->sched_scanning)
3234 wpa_supplicant_cancel_sched_scan(wpa_s);
3235
4dac0245
JM
3236 for (other_ssid = wpa_s->conf->ssid; other_ssid;
3237 other_ssid = other_ssid->next) {
86b89452 3238 was_disabled = other_ssid->disabled;
4dac0245
JM
3239 if (was_disabled == 2)
3240 continue; /* do not change persistent P2P group
3241 * data */
86b89452
WS
3242
3243 other_ssid->disabled = 1;
3244
3245 if (was_disabled != other_ssid->disabled)
3246 wpas_notify_network_enabled_changed(
3247 wpa_s, other_ssid);
86b89452 3248 }
0661163e
SD
3249 if (wpa_s->current_ssid) {
3250 if (wpa_s->wpa_state >= WPA_AUTHENTICATING)
3251 wpa_s->own_disconnect_req = 1;
07783eaa 3252 wpa_supplicant_deauthenticate(
86b89452 3253 wpa_s, WLAN_REASON_DEAUTH_LEAVING);
0661163e 3254 }
4dac0245 3255 } else if (ssid->disabled != 2) {
0661163e
SD
3256 if (ssid == wpa_s->current_ssid) {
3257 if (wpa_s->wpa_state >= WPA_AUTHENTICATING)
3258 wpa_s->own_disconnect_req = 1;
07783eaa 3259 wpa_supplicant_deauthenticate(
86b89452 3260 wpa_s, WLAN_REASON_DEAUTH_LEAVING);
0661163e 3261 }
86b89452
WS
3262
3263 was_disabled = ssid->disabled;
3264
3265 ssid->disabled = 1;
3266
725fc39e 3267 if (was_disabled != ssid->disabled) {
86b89452 3268 wpas_notify_network_enabled_changed(wpa_s, ssid);
725fc39e
DS
3269 if (wpa_s->sched_scanning) {
3270 wpa_printf(MSG_DEBUG, "Stop ongoing sched_scan "
3271 "to remove network from filters");
3272 wpa_supplicant_cancel_sched_scan(wpa_s);
3273 wpa_supplicant_req_scan(wpa_s, 0, 0);
3274 }
3275 }
86b89452
WS
3276 }
3277}
3278
3279
3280/**
3281 * wpa_supplicant_select_network - Attempt association with a network
3282 * @wpa_s: wpa_supplicant structure for a network interface
3283 * @ssid: wpa_ssid structure for a configured network or %NULL for any network
3284 */
3285void wpa_supplicant_select_network(struct wpa_supplicant *wpa_s,
3286 struct wpa_ssid *ssid)
3287{
3288
3289 struct wpa_ssid *other_ssid;
d93dfbd5 3290 int disconnected = 0;
86b89452 3291
d93dfbd5 3292 if (ssid && ssid != wpa_s->current_ssid && wpa_s->current_ssid) {
e66bcedd
JM
3293 if (wpa_s->wpa_state >= WPA_AUTHENTICATING)
3294 wpa_s->own_disconnect_req = 1;
07783eaa 3295 wpa_supplicant_deauthenticate(
86b89452 3296 wpa_s, WLAN_REASON_DEAUTH_LEAVING);
d93dfbd5
JM
3297 disconnected = 1;
3298 }
86b89452 3299
00e5e3d5
JM
3300 if (ssid)
3301 wpas_clear_temp_disabled(wpa_s, ssid, 1);
3302
86b89452
WS
3303 /*
3304 * Mark all other networks disabled or mark all networks enabled if no
3305 * network specified.
3306 */
4dac0245
JM
3307 for (other_ssid = wpa_s->conf->ssid; other_ssid;
3308 other_ssid = other_ssid->next) {
86b89452 3309 int was_disabled = other_ssid->disabled;
4dac0245
JM
3310 if (was_disabled == 2)
3311 continue; /* do not change persistent P2P group data */
86b89452
WS
3312
3313 other_ssid->disabled = ssid ? (ssid->id != other_ssid->id) : 0;
00e5e3d5
JM
3314 if (was_disabled && !other_ssid->disabled)
3315 wpas_clear_temp_disabled(wpa_s, other_ssid, 0);
86b89452
WS
3316
3317 if (was_disabled != other_ssid->disabled)
3318 wpas_notify_network_enabled_changed(wpa_s, other_ssid);
86b89452 3319 }
2a6f78fb 3320
d38c7be0
JM
3321 if (ssid && ssid == wpa_s->current_ssid && wpa_s->current_ssid &&
3322 wpa_s->wpa_state >= WPA_AUTHENTICATING) {
2a6f78fb
JJ
3323 /* We are already associated with the selected network */
3324 wpa_printf(MSG_DEBUG, "Already associated with the "
3325 "selected network - do nothing");
3326 return;
3327 }
3328
25a8f9e3 3329 if (ssid) {
96efeeb6 3330 wpa_s->current_ssid = ssid;
25a8f9e3 3331 eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
603a3f34
JL
3332 wpa_s->connect_without_scan =
3333 (ssid->mode == WPAS_MODE_MESH) ? ssid : NULL;
701f3961
AS
3334
3335 /*
3336 * Don't optimize next scan freqs since a new ESS has been
3337 * selected.
3338 */
3339 os_free(wpa_s->next_scan_freqs);
3340 wpa_s->next_scan_freqs = NULL;
603a3f34
JL
3341 } else {
3342 wpa_s->connect_without_scan = NULL;
25a8f9e3 3343 }
603a3f34 3344
86b89452
WS
3345 wpa_s->disconnected = 0;
3346 wpa_s->reassociate = 1;
cecdddc1 3347
e4a35f07 3348 if (wpa_s->connect_without_scan ||
35d40309
JM
3349 wpa_supplicant_fast_associate(wpa_s) != 1) {
3350 wpa_s->scan_req = NORMAL_SCAN_REQ;
be7ebd89 3351 wpas_scan_reset_sched_scan(wpa_s);
cecdddc1 3352 wpa_supplicant_req_scan(wpa_s, 0, disconnected ? 100000 : 0);
35d40309 3353 }
86b89452 3354
a1641d26
JM
3355 if (ssid)
3356 wpas_notify_network_selected(wpa_s, ssid);
86b89452
WS
3357}
3358
3359
bdec7ee5
MS
3360/**
3361 * wpas_set_pkcs11_engine_and_module_path - Set PKCS #11 engine and module path
3362 * @wpa_s: wpa_supplicant structure for a network interface
3363 * @pkcs11_engine_path: PKCS #11 engine path or NULL
3364 * @pkcs11_module_path: PKCS #11 module path or NULL
3365 * Returns: 0 on success; -1 on failure
3366 *
3367 * Sets the PKCS #11 engine and module path. Both have to be NULL or a valid
3368 * path. If resetting the EAPOL state machine with the new PKCS #11 engine and
3369 * module path fails the paths will be reset to the default value (NULL).
3370 */
3371int wpas_set_pkcs11_engine_and_module_path(struct wpa_supplicant *wpa_s,
3372 const char *pkcs11_engine_path,
3373 const char *pkcs11_module_path)
3374{
3375 char *pkcs11_engine_path_copy = NULL;
3376 char *pkcs11_module_path_copy = NULL;
3377
3378 if (pkcs11_engine_path != NULL) {
3379 pkcs11_engine_path_copy = os_strdup(pkcs11_engine_path);
3380 if (pkcs11_engine_path_copy == NULL)
3381 return -1;
3382 }
3383 if (pkcs11_module_path != NULL) {
3384 pkcs11_module_path_copy = os_strdup(pkcs11_module_path);
04c366cb 3385 if (pkcs11_module_path_copy == NULL) {
bdec7ee5
MS
3386 os_free(pkcs11_engine_path_copy);
3387 return -1;
3388 }
3389 }
3390
3391 os_free(wpa_s->conf->pkcs11_engine_path);
3392 os_free(wpa_s->conf->pkcs11_module_path);
3393 wpa_s->conf->pkcs11_engine_path = pkcs11_engine_path_copy;
3394 wpa_s->conf->pkcs11_module_path = pkcs11_module_path_copy;
3395
3396 wpa_sm_set_eapol(wpa_s->wpa, NULL);
3397 eapol_sm_deinit(wpa_s->eapol);
3398 wpa_s->eapol = NULL;
3399 if (wpa_supplicant_init_eapol(wpa_s)) {
3400 /* Error -> Reset paths to the default value (NULL) once. */
3401 if (pkcs11_engine_path != NULL && pkcs11_module_path != NULL)
3402 wpas_set_pkcs11_engine_and_module_path(wpa_s, NULL,
3403 NULL);
3404
3405 return -1;
3406 }
3407 wpa_sm_set_eapol(wpa_s->wpa, wpa_s->eapol);
3408
3409 return 0;
3410}
3411
3412
86b89452
WS
3413/**
3414 * wpa_supplicant_set_ap_scan - Set AP scan mode for interface
3415 * @wpa_s: wpa_supplicant structure for a network interface
3416 * @ap_scan: AP scan mode
3417 * Returns: 0 if succeed or -1 if ap_scan has an invalid value
3418 *
3419 */
3420int wpa_supplicant_set_ap_scan(struct wpa_supplicant *wpa_s, int ap_scan)
3421{
3422
3423 int old_ap_scan;
3424
3425 if (ap_scan < 0 || ap_scan > 2)
3426 return -1;
3427
8406cd35
JM
3428 if (ap_scan == 2 && os_strcmp(wpa_s->driver->name, "nl80211") == 0) {
3429 wpa_printf(MSG_INFO,
3430 "Note: nl80211 driver interface is not designed to be used with ap_scan=2; this can result in connection failures");
3431 }
3432
48f8e036
DS
3433#ifdef ANDROID
3434 if (ap_scan == 2 && ap_scan != wpa_s->conf->ap_scan &&
3435 wpa_s->wpa_state >= WPA_ASSOCIATING &&
3436 wpa_s->wpa_state < WPA_COMPLETED) {
3437 wpa_printf(MSG_ERROR, "ap_scan = %d (%d) rejected while "
3438 "associating", wpa_s->conf->ap_scan, ap_scan);
3439 return 0;
3440 }
3441#endif /* ANDROID */
3442
86b89452
WS
3443 old_ap_scan = wpa_s->conf->ap_scan;
3444 wpa_s->conf->ap_scan = ap_scan;
3445
3446 if (old_ap_scan != wpa_s->conf->ap_scan)
3447 wpas_notify_ap_scan_changed(wpa_s);
3448
3449 return 0;
3450}
3451
3452
78633c37
SL
3453/**
3454 * wpa_supplicant_set_bss_expiration_age - Set BSS entry expiration age
3455 * @wpa_s: wpa_supplicant structure for a network interface
3456 * @expire_age: Expiration age in seconds
3457 * Returns: 0 if succeed or -1 if expire_age has an invalid value
3458 *
3459 */
3460int wpa_supplicant_set_bss_expiration_age(struct wpa_supplicant *wpa_s,
3461 unsigned int bss_expire_age)
3462{
3463 if (bss_expire_age < 10) {
3464 wpa_msg(wpa_s, MSG_ERROR, "Invalid bss expiration age %u",
3465 bss_expire_age);
3466 return -1;
3467 }
3468 wpa_msg(wpa_s, MSG_DEBUG, "Setting bss expiration age: %d sec",
3469 bss_expire_age);
3470 wpa_s->conf->bss_expiration_age = bss_expire_age;
3471
3472 return 0;
3473}
3474
3475
3476/**
3477 * wpa_supplicant_set_bss_expiration_count - Set BSS entry expiration scan count
3478 * @wpa_s: wpa_supplicant structure for a network interface
3479 * @expire_count: number of scans after which an unseen BSS is reclaimed
3480 * Returns: 0 if succeed or -1 if expire_count has an invalid value
3481 *
3482 */
3483int wpa_supplicant_set_bss_expiration_count(struct wpa_supplicant *wpa_s,
3484 unsigned int bss_expire_count)
3485{
3486 if (bss_expire_count < 1) {
3487 wpa_msg(wpa_s, MSG_ERROR, "Invalid bss expiration count %u",
3488 bss_expire_count);
3489 return -1;
3490 }
3491 wpa_msg(wpa_s, MSG_DEBUG, "Setting bss expiration scan count: %u",
3492 bss_expire_count);
3493 wpa_s->conf->bss_expiration_scan_count = bss_expire_count;
3494
3495 return 0;
3496}
3497
3498
c6e86b63
MA
3499/**
3500 * wpa_supplicant_set_scan_interval - Set scan interval
3501 * @wpa_s: wpa_supplicant structure for a network interface
3502 * @scan_interval: scan interval in seconds
3503 * Returns: 0 if succeed or -1 if scan_interval has an invalid value
3504 *
3505 */
3506int wpa_supplicant_set_scan_interval(struct wpa_supplicant *wpa_s,
3507 int scan_interval)
3508{
3509 if (scan_interval < 0) {
3510 wpa_msg(wpa_s, MSG_ERROR, "Invalid scan interval %d",
3511 scan_interval);
3512 return -1;
3513 }
3514 wpa_msg(wpa_s, MSG_DEBUG, "Setting scan interval: %d sec",
3515 scan_interval);
9e737f08 3516 wpa_supplicant_update_scan_int(wpa_s, scan_interval);
c6e86b63
MA
3517
3518 return 0;
3519}
3520
3521
86b89452
WS
3522/**
3523 * wpa_supplicant_set_debug_params - Set global debug params
3524 * @global: wpa_global structure
3525 * @debug_level: debug level
3526 * @debug_timestamp: determines if show timestamp in debug data
3527 * @debug_show_keys: determines if show keys in debug data
3528 * Returns: 0 if succeed or -1 if debug_level has wrong value
3529 */
3530int wpa_supplicant_set_debug_params(struct wpa_global *global, int debug_level,
3531 int debug_timestamp, int debug_show_keys)
3532{
3533
3534 int old_level, old_timestamp, old_show_keys;
3535
3536 /* check for allowed debuglevels */
14dc0011
PS
3537 if (debug_level != MSG_EXCESSIVE &&
3538 debug_level != MSG_MSGDUMP &&
86b89452
WS
3539 debug_level != MSG_DEBUG &&
3540 debug_level != MSG_INFO &&
3541 debug_level != MSG_WARNING &&
3542 debug_level != MSG_ERROR)
3543 return -1;
3544
3545 old_level = wpa_debug_level;
3546 old_timestamp = wpa_debug_timestamp;
3547 old_show_keys = wpa_debug_show_keys;
3548
3549 wpa_debug_level = debug_level;
3550 wpa_debug_timestamp = debug_timestamp ? 1 : 0;
3551 wpa_debug_show_keys = debug_show_keys ? 1 : 0;
3552
db9133ac
WS
3553 if (wpa_debug_level != old_level)
3554 wpas_notify_debug_level_changed(global);
3555 if (wpa_debug_timestamp != old_timestamp)
3556 wpas_notify_debug_timestamp_changed(global);
3557 if (wpa_debug_show_keys != old_show_keys)
3558 wpas_notify_debug_show_keys_changed(global);
86b89452
WS
3559
3560 return 0;
3561}
3562
3563
e8b96490
JM
3564#ifdef CONFIG_OWE
3565static int owe_trans_ssid_match(struct wpa_supplicant *wpa_s, const u8 *bssid,
3566 const u8 *entry_ssid, size_t entry_ssid_len)
3567{
3568 const u8 *owe, *pos, *end;
3569 u8 ssid_len;
3570 struct wpa_bss *bss;
3571
3572 /* Check network profile SSID aganst the SSID in the
3573 * OWE Transition Mode element. */
3574
3575 bss = wpa_bss_get_bssid_latest(wpa_s, bssid);
3576 if (!bss)
3577 return 0;
3578
3579 owe = wpa_bss_get_vendor_ie(bss, OWE_IE_VENDOR_TYPE);
3580 if (!owe)
3581 return 0;
3582
3583 pos = owe + 6;
3584 end = owe + 2 + owe[1];
3585
3586 if (end - pos < ETH_ALEN + 1)
3587 return 0;
3588 pos += ETH_ALEN;
3589 ssid_len = *pos++;
3590 if (end - pos < ssid_len || ssid_len > SSID_MAX_LEN)
3591 return 0;
3592
3593 return entry_ssid_len == ssid_len &&
3594 os_memcmp(pos, entry_ssid, ssid_len) == 0;
3595}
3596#endif /* CONFIG_OWE */
3597
3598
6fc6879b
JM
3599/**
3600 * wpa_supplicant_get_ssid - Get a pointer to the current network structure
3601 * @wpa_s: Pointer to wpa_supplicant data
3602 * Returns: A pointer to the current network structure or %NULL on failure
3603 */
3604struct wpa_ssid * wpa_supplicant_get_ssid(struct wpa_supplicant *wpa_s)
3605{
3606 struct wpa_ssid *entry;
eaa8eefe 3607 u8 ssid[SSID_MAX_LEN];
6fc6879b
JM
3608 int res;
3609 size_t ssid_len;
3610 u8 bssid[ETH_ALEN];
3611 int wired;
3612
17fbb751
JM
3613 res = wpa_drv_get_ssid(wpa_s, ssid);
3614 if (res < 0) {
3615 wpa_msg(wpa_s, MSG_WARNING, "Could not read SSID from "
3616 "driver");
3617 return NULL;
6fc6879b 3618 }
17fbb751 3619 ssid_len = res;
6fc6879b 3620
17fbb751 3621 if (wpa_drv_get_bssid(wpa_s, bssid) < 0) {
f049052b
BG
3622 wpa_msg(wpa_s, MSG_WARNING, "Could not read BSSID from "
3623 "driver");
6fc6879b
JM
3624 return NULL;
3625 }
3626
c2a04078
JM
3627 wired = wpa_s->conf->ap_scan == 0 &&
3628 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED);
6fc6879b
JM
3629
3630 entry = wpa_s->conf->ssid;
3631 while (entry) {
349493bd 3632 if (!wpas_network_disabled(wpa_s, entry) &&
6fc6879b
JM
3633 ((ssid_len == entry->ssid_len &&
3634 os_memcmp(ssid, entry->ssid, ssid_len) == 0) || wired) &&
3635 (!entry->bssid_set ||
3636 os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0))
3637 return entry;
24c23d1b 3638#ifdef CONFIG_WPS
349493bd 3639 if (!wpas_network_disabled(wpa_s, entry) &&
24c23d1b
JM
3640 (entry->key_mgmt & WPA_KEY_MGMT_WPS) &&
3641 (entry->ssid == NULL || entry->ssid_len == 0) &&
3642 (!entry->bssid_set ||
3643 os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0))
3644 return entry;
3645#endif /* CONFIG_WPS */
7d232e23 3646
e8b96490
JM
3647#ifdef CONFIG_OWE
3648 if (!wpas_network_disabled(wpa_s, entry) &&
3649 owe_trans_ssid_match(wpa_s, bssid, entry->ssid,
3650 entry->ssid_len) &&
3651 (!entry->bssid_set ||
3652 os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0))
3653 return entry;
3654#endif /* CONFIG_OWE */
3655
349493bd 3656 if (!wpas_network_disabled(wpa_s, entry) && entry->bssid_set &&
7d232e23
ZC
3657 entry->ssid_len == 0 &&
3658 os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0)
3659 return entry;
3660
6fc6879b
JM
3661 entry = entry->next;
3662 }
3663
3664 return NULL;
3665}
3666
3667
7756114f
JM
3668static int select_driver(struct wpa_supplicant *wpa_s, int i)
3669{
3670 struct wpa_global *global = wpa_s->global;
3671
3672 if (wpa_drivers[i]->global_init && global->drv_priv[i] == NULL) {
45e3fc72 3673 global->drv_priv[i] = wpa_drivers[i]->global_init(global);
7756114f
JM
3674 if (global->drv_priv[i] == NULL) {
3675 wpa_printf(MSG_ERROR, "Failed to initialize driver "
3676 "'%s'", wpa_drivers[i]->name);
3677 return -1;
3678 }
3679 }
3680
3681 wpa_s->driver = wpa_drivers[i];
3682 wpa_s->global_drv_priv = global->drv_priv[i];
3683
3684 return 0;
3685}
3686
3687
6fc6879b
JM
3688static int wpa_supplicant_set_driver(struct wpa_supplicant *wpa_s,
3689 const char *name)
3690{
3691 int i;
362f781e 3692 size_t len;
74b1c84a 3693 const char *pos, *driver = name;
6fc6879b
JM
3694
3695 if (wpa_s == NULL)
3696 return -1;
3697
c5121837 3698 if (wpa_drivers[0] == NULL) {
f049052b
BG
3699 wpa_msg(wpa_s, MSG_ERROR, "No driver interfaces build into "
3700 "wpa_supplicant");
6fc6879b
JM
3701 return -1;
3702 }
3703
3704 if (name == NULL) {
3705 /* default to first driver in the list */
7756114f 3706 return select_driver(wpa_s, 0);
6fc6879b
JM
3707 }
3708
74b1c84a
SO
3709 do {
3710 pos = os_strchr(driver, ',');
3711 if (pos)
3712 len = pos - driver;
3713 else
3714 len = os_strlen(driver);
3715
3716 for (i = 0; wpa_drivers[i]; i++) {
3717 if (os_strlen(wpa_drivers[i]->name) == len &&
3718 os_strncmp(driver, wpa_drivers[i]->name, len) ==
0f4668ce
DW
3719 0) {
3720 /* First driver that succeeds wins */
3721 if (select_driver(wpa_s, i) == 0)
3722 return 0;
3723 }
6fc6879b 3724 }
74b1c84a
SO
3725
3726 driver = pos + 1;
3727 } while (pos);
6fc6879b 3728
f049052b 3729 wpa_msg(wpa_s, MSG_ERROR, "Unsupported driver '%s'", name);
6fc6879b
JM
3730 return -1;
3731}
3732
3733
a8e0505b
JM
3734/**
3735 * wpa_supplicant_rx_eapol - Deliver a received EAPOL frame to wpa_supplicant
3736 * @ctx: Context pointer (wpa_s); this is the ctx variable registered
3737 * with struct wpa_driver_ops::init()
3738 * @src_addr: Source address of the EAPOL frame
3739 * @buf: EAPOL data starting from the EAPOL header (i.e., no Ethernet header)
3740 * @len: Length of the EAPOL data
3741 *
3742 * This function is called for each received EAPOL frame. Most driver
3743 * interfaces rely on more generic OS mechanism for receiving frames through
3744 * l2_packet, but if such a mechanism is not available, the driver wrapper may
3745 * take care of received EAPOL frames and deliver them to the core supplicant
3746 * code by calling this function.
3747 */
6fc6879b
JM
3748void wpa_supplicant_rx_eapol(void *ctx, const u8 *src_addr,
3749 const u8 *buf, size_t len)
3750{
3751 struct wpa_supplicant *wpa_s = ctx;
3752
f049052b 3753 wpa_dbg(wpa_s, MSG_DEBUG, "RX EAPOL from " MACSTR, MAC2STR(src_addr));
6fc6879b
JM
3754 wpa_hexdump(MSG_MSGDUMP, "RX EAPOL", buf, len);
3755
02adead5
MK
3756#ifdef CONFIG_TESTING_OPTIONS
3757 if (wpa_s->ignore_auth_resp) {
3758 wpa_printf(MSG_INFO, "RX EAPOL - ignore_auth_resp active!");
3759 return;
3760 }
3761#endif /* CONFIG_TESTING_OPTIONS */
3762
3ab35a66
JM
3763 if (wpa_s->wpa_state < WPA_ASSOCIATED ||
3764 (wpa_s->last_eapol_matches_bssid &&
3765#ifdef CONFIG_AP
3766 !wpa_s->ap_iface &&
3767#endif /* CONFIG_AP */
3768 os_memcmp(src_addr, wpa_s->bssid, ETH_ALEN) != 0)) {
1ff73338
JM
3769 /*
3770 * There is possible race condition between receiving the
3771 * association event and the EAPOL frame since they are coming
3772 * through different paths from the driver. In order to avoid
3773 * issues in trying to process the EAPOL frame before receiving
3774 * association information, lets queue it for processing until
3ab35a66
JM
3775 * the association event is received. This may also be needed in
3776 * driver-based roaming case, so also use src_addr != BSSID as a
3777 * trigger if we have previously confirmed that the
3778 * Authenticator uses BSSID as the src_addr (which is not the
3779 * case with wired IEEE 802.1X).
1ff73338 3780 */
f049052b 3781 wpa_dbg(wpa_s, MSG_DEBUG, "Not associated - Delay processing "
3ab35a66
JM
3782 "of received EAPOL frame (state=%s bssid=" MACSTR ")",
3783 wpa_supplicant_state_txt(wpa_s->wpa_state),
3784 MAC2STR(wpa_s->bssid));
1ff73338
JM
3785 wpabuf_free(wpa_s->pending_eapol_rx);
3786 wpa_s->pending_eapol_rx = wpabuf_alloc_copy(buf, len);
3787 if (wpa_s->pending_eapol_rx) {
c2be937c 3788 os_get_reltime(&wpa_s->pending_eapol_rx_time);
1ff73338
JM
3789 os_memcpy(wpa_s->pending_eapol_rx_src, src_addr,
3790 ETH_ALEN);
3791 }
3792 return;
3793 }
3794
3ab35a66
JM
3795 wpa_s->last_eapol_matches_bssid =
3796 os_memcmp(src_addr, wpa_s->bssid, ETH_ALEN) == 0;
3797
db149ac9
JM
3798#ifdef CONFIG_AP
3799 if (wpa_s->ap_iface) {
3800 wpa_supplicant_ap_rx_eapol(wpa_s, src_addr, buf, len);
3801 return;
3802 }
3803#endif /* CONFIG_AP */
3804
6fc6879b 3805 if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE) {
f049052b
BG
3806 wpa_dbg(wpa_s, MSG_DEBUG, "Ignored received EAPOL frame since "
3807 "no key management is configured");
6fc6879b
JM
3808 return;
3809 }
3810
3811 if (wpa_s->eapol_received == 0 &&
c2a04078 3812 (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE) ||
56586197 3813 !wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) ||
9c972abb
JM
3814 wpa_s->wpa_state != WPA_COMPLETED) &&
3815 (wpa_s->current_ssid == NULL ||
3816 wpa_s->current_ssid->mode != IEEE80211_MODE_IBSS)) {
6fc6879b 3817 /* Timeout for completing IEEE 802.1X and WPA authentication */
5add4101
JM
3818 int timeout = 10;
3819
3820 if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) ||
3821 wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA ||
3822 wpa_s->key_mgmt == WPA_KEY_MGMT_WPS) {
3823 /* Use longer timeout for IEEE 802.1X/EAP */
3824 timeout = 70;
3825 }
3826
c7dafdf9 3827#ifdef CONFIG_WPS
5add4101
JM
3828 if (wpa_s->current_ssid && wpa_s->current_bss &&
3829 (wpa_s->current_ssid->key_mgmt & WPA_KEY_MGMT_WPS) &&
3830 eap_is_wps_pin_enrollee(&wpa_s->current_ssid->eap)) {
3831 /*
3832 * Use shorter timeout if going through WPS AP iteration
3833 * for PIN config method with an AP that does not
3834 * advertise Selected Registrar.
3835 */
3836 struct wpabuf *wps_ie;
3837
3838 wps_ie = wpa_bss_get_vendor_ie_multi(
3839 wpa_s->current_bss, WPS_IE_VENDOR_TYPE);
0ef1e290
JM
3840 if (wps_ie &&
3841 !wps_is_addr_authorized(wps_ie, wpa_s->own_addr, 1))
5add4101
JM
3842 timeout = 10;
3843 wpabuf_free(wps_ie);
3844 }
c7dafdf9 3845#endif /* CONFIG_WPS */
5add4101
JM
3846
3847 wpa_supplicant_req_auth_timeout(wpa_s, timeout, 0);
6fc6879b
JM
3848 }
3849 wpa_s->eapol_received++;
3850
3851 if (wpa_s->countermeasures) {
f049052b
BG
3852 wpa_msg(wpa_s, MSG_INFO, "WPA: Countermeasures - dropped "
3853 "EAPOL packet");
6fc6879b
JM
3854 return;
3855 }
3856
8be18440
JM
3857#ifdef CONFIG_IBSS_RSN
3858 if (wpa_s->current_ssid &&
d7dcba70 3859 wpa_s->current_ssid->mode == WPAS_MODE_IBSS) {
8be18440
JM
3860 ibss_rsn_rx_eapol(wpa_s->ibss_rsn, src_addr, buf, len);
3861 return;
3862 }
3863#endif /* CONFIG_IBSS_RSN */
3864
6fc6879b
JM
3865 /* Source address of the incoming EAPOL frame could be compared to the
3866 * current BSSID. However, it is possible that a centralized
3867 * Authenticator could be using another MAC address than the BSSID of
3868 * an AP, so just allow any address to be used for now. The replies are
3869 * still sent to the current BSSID (if available), though. */
3870
3871 os_memcpy(wpa_s->last_eapol_src, src_addr, ETH_ALEN);
56586197 3872 if (!wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) &&
a1ea1b45 3873 wpa_s->key_mgmt != WPA_KEY_MGMT_OWE &&
567da5bb 3874 wpa_s->key_mgmt != WPA_KEY_MGMT_DPP &&
6fc6879b
JM
3875 eapol_sm_rx_eapol(wpa_s->eapol, src_addr, buf, len) > 0)
3876 return;
3877 wpa_drv_poll(wpa_s);
c2a04078 3878 if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE))
6fc6879b 3879 wpa_sm_rx_eapol(wpa_s->wpa, src_addr, buf, len);
56586197 3880 else if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt)) {
6fc6879b
JM
3881 /*
3882 * Set portValid = TRUE here since we are going to skip 4-way
3883 * handshake processing which would normally set portValid. We
3884 * need this to allow the EAPOL state machines to be completed
3885 * without going through EAPOL-Key handshake.
3886 */
3887 eapol_sm_notify_portValid(wpa_s->eapol, TRUE);
3888 }
3889}
3890
3891
bfba8deb 3892int wpa_supplicant_update_mac_addr(struct wpa_supplicant *wpa_s)
6fc6879b 3893{
2961bfa8
JM
3894 if ((!wpa_s->p2p_mgmt ||
3895 !(wpa_s->drv_flags & WPA_DRIVER_FLAGS_DEDICATED_P2P_DEVICE)) &&
3896 !(wpa_s->drv_flags & WPA_DRIVER_FLAGS_P2P_DEDICATED_INTERFACE)) {
bfba8deb 3897 l2_packet_deinit(wpa_s->l2);
6fc6879b
JM
3898 wpa_s->l2 = l2_packet_init(wpa_s->ifname,
3899 wpa_drv_get_mac_addr(wpa_s),
3900 ETH_P_EAPOL,
3901 wpa_supplicant_rx_eapol, wpa_s, 0);
3902 if (wpa_s->l2 == NULL)
3903 return -1;
fdadd5fe
JM
3904 } else {
3905 const u8 *addr = wpa_drv_get_mac_addr(wpa_s);
3906 if (addr)
3907 os_memcpy(wpa_s->own_addr, addr, ETH_ALEN);
6fc6879b
JM
3908 }
3909
3910 if (wpa_s->l2 && l2_packet_get_own_addr(wpa_s->l2, wpa_s->own_addr)) {
f049052b 3911 wpa_msg(wpa_s, MSG_ERROR, "Failed to get own L2 address");
6fc6879b
JM
3912 return -1;
3913 }
3914
c267753b
JM
3915 wpa_sm_set_own_addr(wpa_s->wpa, wpa_s->own_addr);
3916
bfba8deb
JM
3917 return 0;
3918}
3919
3920
25f839c6
JM
3921static void wpa_supplicant_rx_eapol_bridge(void *ctx, const u8 *src_addr,
3922 const u8 *buf, size_t len)
3923{
3924 struct wpa_supplicant *wpa_s = ctx;
3925 const struct l2_ethhdr *eth;
3926
3927 if (len < sizeof(*eth))
3928 return;
3929 eth = (const struct l2_ethhdr *) buf;
3930
3931 if (os_memcmp(eth->h_dest, wpa_s->own_addr, ETH_ALEN) != 0 &&
3932 !(eth->h_dest[0] & 0x01)) {
3933 wpa_dbg(wpa_s, MSG_DEBUG, "RX EAPOL from " MACSTR " to " MACSTR
3934 " (bridge - not for this interface - ignore)",
3935 MAC2STR(src_addr), MAC2STR(eth->h_dest));
3936 return;
3937 }
3938
3939 wpa_dbg(wpa_s, MSG_DEBUG, "RX EAPOL from " MACSTR " to " MACSTR
3940 " (bridge)", MAC2STR(src_addr), MAC2STR(eth->h_dest));
3941 wpa_supplicant_rx_eapol(wpa_s, src_addr, buf + sizeof(*eth),
3942 len - sizeof(*eth));
3943}
3944
3945
bfba8deb
JM
3946/**
3947 * wpa_supplicant_driver_init - Initialize driver interface parameters
3948 * @wpa_s: Pointer to wpa_supplicant data
3949 * Returns: 0 on success, -1 on failure
3950 *
3951 * This function is called to initialize driver interface parameters.
3952 * wpa_drv_init() must have been called before this function to initialize the
3953 * driver interface.
3954 */
3955int wpa_supplicant_driver_init(struct wpa_supplicant *wpa_s)
3956{
3957 static int interface_count = 0;
3958
3959 if (wpa_supplicant_update_mac_addr(wpa_s) < 0)
3960 return -1;
3961
c68f6200
AS
3962 wpa_dbg(wpa_s, MSG_DEBUG, "Own MAC address: " MACSTR,
3963 MAC2STR(wpa_s->own_addr));
a313d17d 3964 os_memcpy(wpa_s->perm_addr, wpa_s->own_addr, ETH_ALEN);
c68f6200
AS
3965 wpa_sm_set_own_addr(wpa_s->wpa, wpa_s->own_addr);
3966
6fc6879b 3967 if (wpa_s->bridge_ifname[0]) {
f049052b
BG
3968 wpa_dbg(wpa_s, MSG_DEBUG, "Receiving packets from bridge "
3969 "interface '%s'", wpa_s->bridge_ifname);
e6dd8196
JM
3970 wpa_s->l2_br = l2_packet_init_bridge(
3971 wpa_s->bridge_ifname, wpa_s->ifname, wpa_s->own_addr,
3972 ETH_P_EAPOL, wpa_supplicant_rx_eapol_bridge, wpa_s, 1);
6fc6879b 3973 if (wpa_s->l2_br == NULL) {
f049052b
BG
3974 wpa_msg(wpa_s, MSG_ERROR, "Failed to open l2_packet "
3975 "connection for the bridge interface '%s'",
3976 wpa_s->bridge_ifname);
6fc6879b
JM
3977 return -1;
3978 }
3979 }
3980
8406cd35
JM
3981 if (wpa_s->conf->ap_scan == 2 &&
3982 os_strcmp(wpa_s->driver->name, "nl80211") == 0) {
3983 wpa_printf(MSG_INFO,
3984 "Note: nl80211 driver interface is not designed to be used with ap_scan=2; this can result in connection failures");
3985 }
3986
6fc6879b
JM
3987 wpa_clear_keys(wpa_s, NULL);
3988
3989 /* Make sure that TKIP countermeasures are not left enabled (could
3990 * happen if wpa_supplicant is killed during countermeasures. */
3991 wpa_drv_set_countermeasures(wpa_s, 0);
3992
f049052b 3993 wpa_dbg(wpa_s, MSG_DEBUG, "RSN: flushing PMKID list in the driver");
6fc6879b
JM
3994 wpa_drv_flush_pmkid(wpa_s);
3995
ba2a573c 3996 wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN;
b3aa456b
ES
3997 wpa_s->prev_scan_wildcard = 0;
3998
349493bd 3999 if (wpa_supplicant_enabled_networks(wpa_s)) {
a0e9d892
AS
4000 if (wpa_s->wpa_state == WPA_INTERFACE_DISABLED) {
4001 wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED);
4002 interface_count = 0;
4003 }
ee82e33d 4004#ifndef ANDROID
3a94adbf 4005 if (!wpa_s->p2p_mgmt &&
5d0d72a3
BG
4006 wpa_supplicant_delayed_sched_scan(wpa_s,
4007 interface_count % 3,
6a90053c 4008 100000))
5d0d72a3 4009 wpa_supplicant_req_scan(wpa_s, interface_count % 3,
a4cba8f1 4010 100000);
ee82e33d 4011#endif /* ANDROID */
74e259ec
JM
4012 interface_count++;
4013 } else
4014 wpa_supplicant_set_state(wpa_s, WPA_INACTIVE);
6fc6879b
JM
4015
4016 return 0;
4017}
4018
4019
4020static int wpa_supplicant_daemon(const char *pid_file)
4021{
4022 wpa_printf(MSG_DEBUG, "Daemonize..");
4023 return os_daemonize(pid_file);
4024}
4025
4026
1772d348
JM
4027static struct wpa_supplicant *
4028wpa_supplicant_alloc(struct wpa_supplicant *parent)
6fc6879b
JM
4029{
4030 struct wpa_supplicant *wpa_s;
4031
4032 wpa_s = os_zalloc(sizeof(*wpa_s));
4033 if (wpa_s == NULL)
4034 return NULL;
4115303b 4035 wpa_s->scan_req = INITIAL_SCAN_REQ;
67b9bd08 4036 wpa_s->scan_interval = 5;
c302f207 4037 wpa_s->new_connection = 1;
1772d348 4038 wpa_s->parent = parent ? parent : wpa_s;
ba307f85 4039 wpa_s->p2pdev = wpa_s->parent;
cbdf3507 4040 wpa_s->sched_scanning = 0;
6fc6879b 4041
dd599908 4042 dl_list_init(&wpa_s->bss_tmp_disallowed);
5732b770 4043 dl_list_init(&wpa_s->fils_hlp_req);
dd599908 4044
6fc6879b
JM
4045 return wpa_s;
4046}
4047
4048
80e8a5ee
BG
4049#ifdef CONFIG_HT_OVERRIDES
4050
4051static int wpa_set_htcap_mcs(struct wpa_supplicant *wpa_s,
4052 struct ieee80211_ht_capabilities *htcaps,
4053 struct ieee80211_ht_capabilities *htcaps_mask,
4054 const char *ht_mcs)
4055{
4056 /* parse ht_mcs into hex array */
4057 int i;
4058 const char *tmp = ht_mcs;
4059 char *end = NULL;
4060
4061 /* If ht_mcs is null, do not set anything */
4062 if (!ht_mcs)
4063 return 0;
4064
4065 /* This is what we are setting in the kernel */
4066 os_memset(&htcaps->supported_mcs_set, 0, IEEE80211_HT_MCS_MASK_LEN);
4067
4068 wpa_msg(wpa_s, MSG_DEBUG, "set_htcap, ht_mcs -:%s:-", ht_mcs);
4069
4070 for (i = 0; i < IEEE80211_HT_MCS_MASK_LEN; i++) {
30eddf35
JB
4071 long v;
4072
80e8a5ee 4073 errno = 0;
30eddf35
JB
4074 v = strtol(tmp, &end, 16);
4075
80e8a5ee
BG
4076 if (errno == 0) {
4077 wpa_msg(wpa_s, MSG_DEBUG,
4078 "htcap value[%i]: %ld end: %p tmp: %p",
4079 i, v, end, tmp);
4080 if (end == tmp)
4081 break;
4082
4083 htcaps->supported_mcs_set[i] = v;
4084 tmp = end;
4085 } else {
4086 wpa_msg(wpa_s, MSG_ERROR,
4087 "Failed to parse ht-mcs: %s, error: %s\n",
4088 ht_mcs, strerror(errno));
4089 return -1;
4090 }
4091 }
4092
4093 /*
4094 * If we were able to parse any values, then set mask for the MCS set.
4095 */
4096 if (i) {
4097 os_memset(&htcaps_mask->supported_mcs_set, 0xff,
4098 IEEE80211_HT_MCS_MASK_LEN - 1);
4099 /* skip the 3 reserved bits */
4100 htcaps_mask->supported_mcs_set[IEEE80211_HT_MCS_MASK_LEN - 1] =
4101 0x1f;
4102 }
4103
4104 return 0;
4105}
4106
4107
4108static int wpa_disable_max_amsdu(struct wpa_supplicant *wpa_s,
4109 struct ieee80211_ht_capabilities *htcaps,
4110 struct ieee80211_ht_capabilities *htcaps_mask,
4111 int disabled)
4112{
5bc28571 4113 le16 msk;
80e8a5ee
BG
4114
4115 wpa_msg(wpa_s, MSG_DEBUG, "set_disable_max_amsdu: %d", disabled);
4116
4117 if (disabled == -1)
4118 return 0;
4119
4120 msk = host_to_le16(HT_CAP_INFO_MAX_AMSDU_SIZE);
4121 htcaps_mask->ht_capabilities_info |= msk;
4122 if (disabled)
4123 htcaps->ht_capabilities_info &= msk;
4124 else
4125 htcaps->ht_capabilities_info |= msk;
4126
4127 return 0;
4128}
4129
4130
4131static int wpa_set_ampdu_factor(struct wpa_supplicant *wpa_s,
4132 struct ieee80211_ht_capabilities *htcaps,
4133 struct ieee80211_ht_capabilities *htcaps_mask,
4134 int factor)
4135{
4136 wpa_msg(wpa_s, MSG_DEBUG, "set_ampdu_factor: %d", factor);
4137
4138 if (factor == -1)
4139 return 0;
4140
4141 if (factor < 0 || factor > 3) {
4142 wpa_msg(wpa_s, MSG_ERROR, "ampdu_factor: %d out of range. "
4143 "Must be 0-3 or -1", factor);
4144 return -EINVAL;
4145 }
4146
4147 htcaps_mask->a_mpdu_params |= 0x3; /* 2 bits for factor */
4148 htcaps->a_mpdu_params &= ~0x3;
4149 htcaps->a_mpdu_params |= factor & 0x3;
4150
4151 return 0;
4152}
4153
4154
4155static int wpa_set_ampdu_density(struct wpa_supplicant *wpa_s,
4156 struct ieee80211_ht_capabilities *htcaps,
4157 struct ieee80211_ht_capabilities *htcaps_mask,
4158 int density)
4159{
4160 wpa_msg(wpa_s, MSG_DEBUG, "set_ampdu_density: %d", density);
4161
4162 if (density == -1)
4163 return 0;
4164
4165 if (density < 0 || density > 7) {
4166 wpa_msg(wpa_s, MSG_ERROR,
4167 "ampdu_density: %d out of range. Must be 0-7 or -1.",
4168 density);
4169 return -EINVAL;
4170 }
4171
4172 htcaps_mask->a_mpdu_params |= 0x1C;
4173 htcaps->a_mpdu_params &= ~(0x1C);
4174 htcaps->a_mpdu_params |= (density << 2) & 0x1C;
4175
4176 return 0;
4177}
4178
4179
4180static int wpa_set_disable_ht40(struct wpa_supplicant *wpa_s,
4181 struct ieee80211_ht_capabilities *htcaps,
4182 struct ieee80211_ht_capabilities *htcaps_mask,
4183 int disabled)
4184{
80e8a5ee
BG
4185 wpa_msg(wpa_s, MSG_DEBUG, "set_disable_ht40: %d", disabled);
4186
9eb5757a
MH
4187 set_disable_ht40(htcaps, disabled);
4188 set_disable_ht40(htcaps_mask, 0);
80e8a5ee
BG
4189
4190 return 0;
4191}
4192
4193
a90497f8
BG
4194static int wpa_set_disable_sgi(struct wpa_supplicant *wpa_s,
4195 struct ieee80211_ht_capabilities *htcaps,
4196 struct ieee80211_ht_capabilities *htcaps_mask,
4197 int disabled)
4198{
4199 /* Masking these out disables SGI */
5bc28571
JM
4200 le16 msk = host_to_le16(HT_CAP_INFO_SHORT_GI20MHZ |
4201 HT_CAP_INFO_SHORT_GI40MHZ);
a90497f8
BG
4202
4203 wpa_msg(wpa_s, MSG_DEBUG, "set_disable_sgi: %d", disabled);
4204
4205 if (disabled)
4206 htcaps->ht_capabilities_info &= ~msk;
4207 else
4208 htcaps->ht_capabilities_info |= msk;
4209
4210 htcaps_mask->ht_capabilities_info |= msk;
4211
4212 return 0;
4213}
4214
4215
39a5800f
PK
4216static int wpa_set_disable_ldpc(struct wpa_supplicant *wpa_s,
4217 struct ieee80211_ht_capabilities *htcaps,
4218 struct ieee80211_ht_capabilities *htcaps_mask,
4219 int disabled)
4220{
4221 /* Masking these out disables LDPC */
5bc28571 4222 le16 msk = host_to_le16(HT_CAP_INFO_LDPC_CODING_CAP);
39a5800f
PK
4223
4224 wpa_msg(wpa_s, MSG_DEBUG, "set_disable_ldpc: %d", disabled);
4225
4226 if (disabled)
4227 htcaps->ht_capabilities_info &= ~msk;
4228 else
4229 htcaps->ht_capabilities_info |= msk;
4230
4231 htcaps_mask->ht_capabilities_info |= msk;
4232
4233 return 0;
4234}
4235
4236
80e8a5ee
BG
4237void wpa_supplicant_apply_ht_overrides(
4238 struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid,
4239 struct wpa_driver_associate_params *params)
4240{
4241 struct ieee80211_ht_capabilities *htcaps;
4242 struct ieee80211_ht_capabilities *htcaps_mask;
4243
4244 if (!ssid)
4245 return;
4246
4247 params->disable_ht = ssid->disable_ht;
4248 if (!params->htcaps || !params->htcaps_mask)
4249 return;
4250
4251 htcaps = (struct ieee80211_ht_capabilities *) params->htcaps;
4252 htcaps_mask = (struct ieee80211_ht_capabilities *) params->htcaps_mask;
4253 wpa_set_htcap_mcs(wpa_s, htcaps, htcaps_mask, ssid->ht_mcs);
4254 wpa_disable_max_amsdu(wpa_s, htcaps, htcaps_mask,
4255 ssid->disable_max_amsdu);
4256 wpa_set_ampdu_factor(wpa_s, htcaps, htcaps_mask, ssid->ampdu_factor);
4257 wpa_set_ampdu_density(wpa_s, htcaps, htcaps_mask, ssid->ampdu_density);
4258 wpa_set_disable_ht40(wpa_s, htcaps, htcaps_mask, ssid->disable_ht40);
a90497f8 4259 wpa_set_disable_sgi(wpa_s, htcaps, htcaps_mask, ssid->disable_sgi);
39a5800f 4260 wpa_set_disable_ldpc(wpa_s, htcaps, htcaps_mask, ssid->disable_ldpc);
d41cc8cc
JM
4261
4262 if (ssid->ht40_intolerant) {
5bc28571 4263 le16 bit = host_to_le16(HT_CAP_INFO_40MHZ_INTOLERANT);
d41cc8cc
JM
4264 htcaps->ht_capabilities_info |= bit;
4265 htcaps_mask->ht_capabilities_info |= bit;
4266 }
80e8a5ee
BG
4267}
4268
4269#endif /* CONFIG_HT_OVERRIDES */
4270
4271
e9ee8dc3
JB
4272#ifdef CONFIG_VHT_OVERRIDES
4273void wpa_supplicant_apply_vht_overrides(
4274 struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid,
4275 struct wpa_driver_associate_params *params)
4276{
4277 struct ieee80211_vht_capabilities *vhtcaps;
4278 struct ieee80211_vht_capabilities *vhtcaps_mask;
4279
4280 if (!ssid)
4281 return;
4282
4283 params->disable_vht = ssid->disable_vht;
4284
4285 vhtcaps = (void *) params->vhtcaps;
4286 vhtcaps_mask = (void *) params->vhtcaps_mask;
4287
4288 if (!vhtcaps || !vhtcaps_mask)
4289 return;
4290
4d8d710f
JM
4291 vhtcaps->vht_capabilities_info = host_to_le32(ssid->vht_capa);
4292 vhtcaps_mask->vht_capabilities_info = host_to_le32(ssid->vht_capa_mask);
e9ee8dc3 4293
4f560cde
EP
4294#ifdef CONFIG_HT_OVERRIDES
4295 /* if max ampdu is <= 3, we have to make the HT cap the same */
b0f33467
JM
4296 if (ssid->vht_capa_mask & VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MAX) {
4297 int max_ampdu;
4298
4299 max_ampdu = (ssid->vht_capa &
4300 VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MAX) >>
4301 VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MAX_SHIFT;
4f560cde
EP
4302
4303 max_ampdu = max_ampdu < 3 ? max_ampdu : 3;
4304 wpa_set_ampdu_factor(wpa_s,
4305 (void *) params->htcaps,
4306 (void *) params->htcaps_mask,
4307 max_ampdu);
4308 }
4309#endif /* CONFIG_HT_OVERRIDES */
4310
e9ee8dc3
JB
4311#define OVERRIDE_MCS(i) \
4312 if (ssid->vht_tx_mcs_nss_ ##i >= 0) { \
4313 vhtcaps_mask->vht_supported_mcs_set.tx_map |= \
4d8d710f 4314 host_to_le16(3 << 2 * (i - 1)); \
e9ee8dc3 4315 vhtcaps->vht_supported_mcs_set.tx_map |= \
4d8d710f
JM
4316 host_to_le16(ssid->vht_tx_mcs_nss_ ##i << \
4317 2 * (i - 1)); \
e9ee8dc3
JB
4318 } \
4319 if (ssid->vht_rx_mcs_nss_ ##i >= 0) { \
4320 vhtcaps_mask->vht_supported_mcs_set.rx_map |= \
4d8d710f 4321 host_to_le16(3 << 2 * (i - 1)); \
e9ee8dc3 4322 vhtcaps->vht_supported_mcs_set.rx_map |= \
4d8d710f
JM
4323 host_to_le16(ssid->vht_rx_mcs_nss_ ##i << \
4324 2 * (i - 1)); \
e9ee8dc3
JB
4325 }
4326
4327 OVERRIDE_MCS(1);
4328 OVERRIDE_MCS(2);
4329 OVERRIDE_MCS(3);
4330 OVERRIDE_MCS(4);
4331 OVERRIDE_MCS(5);
4332 OVERRIDE_MCS(6);
4333 OVERRIDE_MCS(7);
4334 OVERRIDE_MCS(8);
4335}
4336#endif /* CONFIG_VHT_OVERRIDES */
4337
4338
f64adcd7
JM
4339static int pcsc_reader_init(struct wpa_supplicant *wpa_s)
4340{
4341#ifdef PCSC_FUNCS
4342 size_t len;
4343
4344 if (!wpa_s->conf->pcsc_reader)
4345 return 0;
4346
22cf7d73 4347 wpa_s->scard = scard_init(wpa_s->conf->pcsc_reader);
f64adcd7
JM
4348 if (!wpa_s->scard)
4349 return 1;
4350
4351 if (wpa_s->conf->pcsc_pin &&
4352 scard_set_pin(wpa_s->scard, wpa_s->conf->pcsc_pin) < 0) {
4353 scard_deinit(wpa_s->scard);
4354 wpa_s->scard = NULL;
4355 wpa_msg(wpa_s, MSG_ERROR, "PC/SC PIN validation failed");
4356 return -1;
4357 }
4358
4359 len = sizeof(wpa_s->imsi) - 1;
4360 if (scard_get_imsi(wpa_s->scard, wpa_s->imsi, &len)) {
4361 scard_deinit(wpa_s->scard);
4362 wpa_s->scard = NULL;
4363 wpa_msg(wpa_s, MSG_ERROR, "Could not read IMSI");
4364 return -1;
4365 }
4366 wpa_s->imsi[len] = '\0';
4367
4368 wpa_s->mnc_len = scard_get_mnc_len(wpa_s->scard);
4369
4370 wpa_printf(MSG_DEBUG, "SCARD: IMSI %s (MNC length %d)",
4371 wpa_s->imsi, wpa_s->mnc_len);
4372
4373 wpa_sm_set_scard_ctx(wpa_s->wpa, wpa_s->scard);
4374 eapol_sm_register_scard_ctx(wpa_s->eapol, wpa_s->scard);
4375#endif /* PCSC_FUNCS */
4376
4377 return 0;
4378}
4379
4380
306ae225
JM
4381int wpas_init_ext_pw(struct wpa_supplicant *wpa_s)
4382{
4383 char *val, *pos;
4384
4385 ext_password_deinit(wpa_s->ext_pw);
4386 wpa_s->ext_pw = NULL;
4387 eapol_sm_set_ext_pw_ctx(wpa_s->eapol, NULL);
4388
4389 if (!wpa_s->conf->ext_password_backend)
4390 return 0;
4391
4392 val = os_strdup(wpa_s->conf->ext_password_backend);
4393 if (val == NULL)
4394 return -1;
4395 pos = os_strchr(val, ':');
4396 if (pos)
4397 *pos++ = '\0';
4398
4399 wpa_printf(MSG_DEBUG, "EXT PW: Initialize backend '%s'", val);
4400
4401 wpa_s->ext_pw = ext_password_init(val, pos);
4402 os_free(val);
4403 if (wpa_s->ext_pw == NULL) {
4404 wpa_printf(MSG_DEBUG, "EXT PW: Failed to initialize backend");
4405 return -1;
4406 }
4407 eapol_sm_set_ext_pw_ctx(wpa_s->eapol, wpa_s->ext_pw);
4408
4409 return 0;
4410}
4411
4412
b36a3a65
AN
4413#ifdef CONFIG_FST
4414
4415static const u8 * wpas_fst_get_bssid_cb(void *ctx)
4416{
4417 struct wpa_supplicant *wpa_s = ctx;
4418
4419 return (is_zero_ether_addr(wpa_s->bssid) ||
4420 wpa_s->wpa_state != WPA_COMPLETED) ? NULL : wpa_s->bssid;
4421}
4422
4423
4424static void wpas_fst_get_channel_info_cb(void *ctx,
4425 enum hostapd_hw_mode *hw_mode,
4426 u8 *channel)
4427{
4428 struct wpa_supplicant *wpa_s = ctx;
4429
4430 if (wpa_s->current_bss) {
4431 *hw_mode = ieee80211_freq_to_chan(wpa_s->current_bss->freq,
4432 channel);
4433 } else if (wpa_s->hw.num_modes) {
4434 *hw_mode = wpa_s->hw.modes[0].mode;
4435 } else {
4436 WPA_ASSERT(0);
4437 *hw_mode = 0;
4438 }
4439}
4440
4441
4442static int wpas_fst_get_hw_modes(void *ctx, struct hostapd_hw_modes **modes)
4443{
4444 struct wpa_supplicant *wpa_s = ctx;
4445
4446 *modes = wpa_s->hw.modes;
4447 return wpa_s->hw.num_modes;
4448}
4449
4450
84bcb4e7 4451static void wpas_fst_set_ies_cb(void *ctx, const struct wpabuf *fst_ies)
b36a3a65
AN
4452{
4453 struct wpa_supplicant *wpa_s = ctx;
4454
b7a07937 4455 wpa_hexdump_buf(MSG_DEBUG, "FST: Set IEs", fst_ies);
b36a3a65
AN
4456 wpa_s->fst_ies = fst_ies;
4457}
4458
4459
4460static int wpas_fst_send_action_cb(void *ctx, const u8 *da, struct wpabuf *data)
4461{
4462 struct wpa_supplicant *wpa_s = ctx;
4463
0da35523
JM
4464 if (os_memcmp(wpa_s->bssid, da, ETH_ALEN) != 0) {
4465 wpa_printf(MSG_INFO, "FST:%s:bssid=" MACSTR " != da=" MACSTR,
4466 __func__, MAC2STR(wpa_s->bssid), MAC2STR(da));
4467 return -1;
4468 }
b36a3a65 4469 return wpa_drv_send_action(wpa_s, wpa_s->assoc_freq, 0, wpa_s->bssid,
0da35523
JM
4470 wpa_s->own_addr, wpa_s->bssid,
4471 wpabuf_head(data), wpabuf_len(data),
b36a3a65
AN
4472 0);
4473}
4474
4475
a0f04da5 4476static const struct wpabuf * wpas_fst_get_mb_ie_cb(void *ctx, const u8 *addr)
b36a3a65
AN
4477{
4478 struct wpa_supplicant *wpa_s = ctx;
4479
4480 WPA_ASSERT(os_memcmp(wpa_s->bssid, addr, ETH_ALEN) == 0);
4481 return wpa_s->received_mb_ies;
4482}
4483
4484
4485static void wpas_fst_update_mb_ie_cb(void *ctx, const u8 *addr,
4486 const u8 *buf, size_t size)
4487{
4488 struct wpa_supplicant *wpa_s = ctx;
4489 struct mb_ies_info info;
4490
4491 WPA_ASSERT(os_memcmp(wpa_s->bssid, addr, ETH_ALEN) == 0);
4492
4493 if (!mb_ies_info_by_ies(&info, buf, size)) {
4494 wpabuf_free(wpa_s->received_mb_ies);
4495 wpa_s->received_mb_ies = mb_ies_by_info(&info);
4496 }
4497}
4498
4499
39cdd3a0
JM
4500static const u8 * wpas_fst_get_peer_first(void *ctx,
4501 struct fst_get_peer_ctx **get_ctx,
4502 Boolean mb_only)
b36a3a65
AN
4503{
4504 struct wpa_supplicant *wpa_s = ctx;
4505
4506 *get_ctx = NULL;
4507 if (!is_zero_ether_addr(wpa_s->bssid))
4508 return (wpa_s->received_mb_ies || !mb_only) ?
4509 wpa_s->bssid : NULL;
4510 return NULL;
4511}
4512
4513
39cdd3a0
JM
4514static const u8 * wpas_fst_get_peer_next(void *ctx,
4515 struct fst_get_peer_ctx **get_ctx,
4516 Boolean mb_only)
b36a3a65
AN
4517{
4518 return NULL;
4519}
4520
4521void fst_wpa_supplicant_fill_iface_obj(struct wpa_supplicant *wpa_s,
4522 struct fst_wpa_obj *iface_obj)
4523{
4524 iface_obj->ctx = wpa_s;
4525 iface_obj->get_bssid = wpas_fst_get_bssid_cb;
4526 iface_obj->get_channel_info = wpas_fst_get_channel_info_cb;
4527 iface_obj->get_hw_modes = wpas_fst_get_hw_modes;
4528 iface_obj->set_ies = wpas_fst_set_ies_cb;
4529 iface_obj->send_action = wpas_fst_send_action_cb;
4530 iface_obj->get_mb_ie = wpas_fst_get_mb_ie_cb;
4531 iface_obj->update_mb_ie = wpas_fst_update_mb_ie_cb;
4532 iface_obj->get_peer_first = wpas_fst_get_peer_first;
4533 iface_obj->get_peer_next = wpas_fst_get_peer_next;
4534}
4535#endif /* CONFIG_FST */
4536
a520bf4a 4537static int wpas_set_wowlan_triggers(struct wpa_supplicant *wpa_s,
6cbdb0c5 4538 const struct wpa_driver_capa *capa)
e4fa8b12 4539{
88cb27c7
DS
4540 struct wowlan_triggers *triggers;
4541 int ret = 0;
e4fa8b12
EP
4542
4543 if (!wpa_s->conf->wowlan_triggers)
4544 return 0;
4545
88cb27c7
DS
4546 triggers = wpa_get_wowlan_triggers(wpa_s->conf->wowlan_triggers, capa);
4547 if (triggers) {
4548 ret = wpa_drv_wowlan(wpa_s, triggers);
4549 os_free(triggers);
e4fa8b12 4550 }
e4fa8b12
EP
4551 return ret;
4552}
4553
4554
2b6e9f91 4555enum wpa_radio_work_band wpas_freq_to_band(int freq)
e903d32d
KV
4556{
4557 if (freq < 3000)
4558 return BAND_2_4_GHZ;
4559 if (freq > 50000)
4560 return BAND_60_GHZ;
4561 return BAND_5_GHZ;
4562}
4563
4564
2b6e9f91 4565unsigned int wpas_get_bands(struct wpa_supplicant *wpa_s, const int *freqs)
e903d32d
KV
4566{
4567 int i;
4568 unsigned int band = 0;
4569
4570 if (freqs) {
4571 /* freqs are specified for the radio work */
4572 for (i = 0; freqs[i]; i++)
4573 band |= wpas_freq_to_band(freqs[i]);
4574 } else {
4575 /*
4576 * freqs are not specified, implies all
4577 * the supported freqs by HW
4578 */
4579 for (i = 0; i < wpa_s->hw.num_modes; i++) {
4580 if (wpa_s->hw.modes[i].num_channels != 0) {
4581 if (wpa_s->hw.modes[i].mode ==
4582 HOSTAPD_MODE_IEEE80211B ||
4583 wpa_s->hw.modes[i].mode ==
4584 HOSTAPD_MODE_IEEE80211G)
4585 band |= BAND_2_4_GHZ;
4586 else if (wpa_s->hw.modes[i].mode ==
4587 HOSTAPD_MODE_IEEE80211A)
4588 band |= BAND_5_GHZ;
4589 else if (wpa_s->hw.modes[i].mode ==
4590 HOSTAPD_MODE_IEEE80211AD)
4591 band |= BAND_60_GHZ;
4592 else if (wpa_s->hw.modes[i].mode ==
4593 HOSTAPD_MODE_IEEE80211ANY)
4594 band = BAND_2_4_GHZ | BAND_5_GHZ |
4595 BAND_60_GHZ;
4596 }
4597 }
4598 }
4599
4600 return band;
4601}
4602
4603
202dec2a
JM
4604static struct wpa_radio * radio_add_interface(struct wpa_supplicant *wpa_s,
4605 const char *rn)
4606{
4607 struct wpa_supplicant *iface = wpa_s->global->ifaces;
4608 struct wpa_radio *radio;
4609
4610 while (rn && iface) {
4611 radio = iface->radio;
4612 if (radio && os_strcmp(rn, radio->name) == 0) {
4613 wpa_printf(MSG_DEBUG, "Add interface %s to existing radio %s",
4614 wpa_s->ifname, rn);
4615 dl_list_add(&radio->ifaces, &wpa_s->radio_list);
4616 return radio;
4617 }
b154a24e
TB
4618
4619 iface = iface->next;
202dec2a
JM
4620 }
4621
4622 wpa_printf(MSG_DEBUG, "Add interface %s to a new radio %s",
4623 wpa_s->ifname, rn ? rn : "N/A");
4624 radio = os_zalloc(sizeof(*radio));
4625 if (radio == NULL)
4626 return NULL;
4627
4628 if (rn)
4629 os_strlcpy(radio->name, rn, sizeof(radio->name));
4630 dl_list_init(&radio->ifaces);
b1ae396f 4631 dl_list_init(&radio->work);
202dec2a
JM
4632 dl_list_add(&radio->ifaces, &wpa_s->radio_list);
4633
4634 return radio;
4635}
4636
4637
b1ae396f
JM
4638static void radio_work_free(struct wpa_radio_work *work)
4639{
d12a51b5
JM
4640 if (work->wpa_s->scan_work == work) {
4641 /* This should not really happen. */
4642 wpa_dbg(work->wpa_s, MSG_INFO, "Freeing radio work '%s'@%p (started=%d) that is marked as scan_work",
4643 work->type, work, work->started);
4644 work->wpa_s->scan_work = NULL;
4645 }
4646
1b5d4714
JM
4647#ifdef CONFIG_P2P
4648 if (work->wpa_s->p2p_scan_work == work) {
4649 /* This should not really happen. */
4650 wpa_dbg(work->wpa_s, MSG_INFO, "Freeing radio work '%s'@%p (started=%d) that is marked as p2p_scan_work",
4651 work->type, work, work->started);
4652 work->wpa_s->p2p_scan_work = NULL;
4653 }
4654#endif /* CONFIG_P2P */
4655
e903d32d
KV
4656 if (work->started) {
4657 work->wpa_s->radio->num_active_works--;
4658 wpa_dbg(work->wpa_s, MSG_DEBUG,
4659 "radio_work_free('%s'@%p: num_active_works --> %u",
4660 work->type, work,
4661 work->wpa_s->radio->num_active_works);
4662 }
4663
b1ae396f
JM
4664 dl_list_del(&work->list);
4665 os_free(work);
4666}
4667
4668
4c6f450c
JM
4669static int radio_work_is_connect(struct wpa_radio_work *work)
4670{
4671 return os_strcmp(work->type, "sme-connect") == 0 ||
4672 os_strcmp(work->type, "connect") == 0;
4673}
4674
4675
85b6b6b6
SD
4676static int radio_work_is_scan(struct wpa_radio_work *work)
4677{
4678 return os_strcmp(work->type, "scan") == 0 ||
4679 os_strcmp(work->type, "p2p-scan") == 0;
4680}
4681
4682
e903d32d
KV
4683static struct wpa_radio_work * radio_work_get_next_work(struct wpa_radio *radio)
4684{
4685 struct wpa_radio_work *active_work = NULL;
4686 struct wpa_radio_work *tmp;
4687
4688 /* Get the active work to know the type and band. */
4689 dl_list_for_each(tmp, &radio->work, struct wpa_radio_work, list) {
4690 if (tmp->started) {
4691 active_work = tmp;
4692 break;
4693 }
4694 }
4695
4696 if (!active_work) {
4697 /* No active work, start one */
4698 radio->num_active_works = 0;
4699 dl_list_for_each(tmp, &radio->work, struct wpa_radio_work,
4700 list) {
4701 if (os_strcmp(tmp->type, "scan") == 0 &&
4702 radio->external_scan_running &&
4703 (((struct wpa_driver_scan_params *)
4704 tmp->ctx)->only_new_results ||
4705 tmp->wpa_s->clear_driver_scan_cache))
4706 continue;
4707 return tmp;
4708 }
4709 return NULL;
4710 }
4711
4c6f450c 4712 if (radio_work_is_connect(active_work)) {
e903d32d
KV
4713 /*
4714 * If the active work is either connect or sme-connect,
4715 * do not parallelize them with other radio works.
4716 */
4717 wpa_dbg(active_work->wpa_s, MSG_DEBUG,
4718 "Do not parallelize radio work with %s",
4719 active_work->type);
4720 return NULL;
4721 }
4722
4723 dl_list_for_each(tmp, &radio->work, struct wpa_radio_work, list) {
4724 if (tmp->started)
4725 continue;
4726
4727 /*
4728 * If connect or sme-connect are enqueued, parallelize only
4729 * those operations ahead of them in the queue.
4730 */
4c6f450c 4731 if (radio_work_is_connect(tmp))
e903d32d
KV
4732 break;
4733
85b6b6b6
SD
4734 /* Serialize parallel scan and p2p_scan operations on the same
4735 * interface since the driver_nl80211 mechanism for tracking
4736 * scan cookies does not yet have support for this. */
4737 if (active_work->wpa_s == tmp->wpa_s &&
4738 radio_work_is_scan(active_work) &&
4739 radio_work_is_scan(tmp)) {
4740 wpa_dbg(active_work->wpa_s, MSG_DEBUG,
4741 "Do not start work '%s' when another work '%s' is already scheduled",
4742 tmp->type, active_work->type);
4743 continue;
4744 }
e903d32d
KV
4745 /*
4746 * Check that the radio works are distinct and
4747 * on different bands.
4748 */
4749 if (os_strcmp(active_work->type, tmp->type) != 0 &&
4750 (active_work->bands != tmp->bands)) {
4751 /*
4752 * If a scan has to be scheduled through nl80211 scan
4753 * interface and if an external scan is already running,
4754 * do not schedule the scan since it is likely to get
4755 * rejected by kernel.
4756 */
4757 if (os_strcmp(tmp->type, "scan") == 0 &&
4758 radio->external_scan_running &&
4759 (((struct wpa_driver_scan_params *)
4760 tmp->ctx)->only_new_results ||
4761 tmp->wpa_s->clear_driver_scan_cache))
4762 continue;
4763
4764 wpa_dbg(active_work->wpa_s, MSG_DEBUG,
4765 "active_work:%s new_work:%s",
4766 active_work->type, tmp->type);
4767 return tmp;
4768 }
4769 }
4770
4771 /* Did not find a radio work to schedule in parallel. */
4772 return NULL;
4773}
4774
4775
b1ae396f
JM
4776static void radio_start_next_work(void *eloop_ctx, void *timeout_ctx)
4777{
4778 struct wpa_radio *radio = eloop_ctx;
4779 struct wpa_radio_work *work;
4780 struct os_reltime now, diff;
6428d0a7 4781 struct wpa_supplicant *wpa_s;
b1ae396f
JM
4782
4783 work = dl_list_first(&radio->work, struct wpa_radio_work, list);
e903d32d
KV
4784 if (work == NULL) {
4785 radio->num_active_works = 0;
b1ae396f 4786 return;
e903d32d 4787 }
b1ae396f 4788
6428d0a7
JM
4789 wpa_s = dl_list_first(&radio->ifaces, struct wpa_supplicant,
4790 radio_list);
e903d32d
KV
4791
4792 if (!(wpa_s &&
4793 wpa_s->drv_flags & WPA_DRIVER_FLAGS_OFFCHANNEL_SIMULTANEOUS)) {
4794 if (work->started)
4795 return; /* already started and still in progress */
4796
4797 if (wpa_s && wpa_s->radio->external_scan_running) {
4798 wpa_printf(MSG_DEBUG, "Delay radio work start until externally triggered scan completes");
4799 return;
4800 }
4801 } else {
4802 work = NULL;
4803 if (radio->num_active_works < MAX_ACTIVE_WORKS) {
4804 /* get the work to schedule next */
4805 work = radio_work_get_next_work(radio);
4806 }
4807 if (!work)
4808 return;
6428d0a7
JM
4809 }
4810
e903d32d 4811 wpa_s = work->wpa_s;
b1ae396f
JM
4812 os_get_reltime(&now);
4813 os_reltime_sub(&now, &work->time, &diff);
e903d32d
KV
4814 wpa_dbg(wpa_s, MSG_DEBUG,
4815 "Starting radio work '%s'@%p after %ld.%06ld second wait",
b1ae396f
JM
4816 work->type, work, diff.sec, diff.usec);
4817 work->started = 1;
4818 work->time = now;
e903d32d
KV
4819 radio->num_active_works++;
4820
b1ae396f 4821 work->cb(work, 0);
e903d32d
KV
4822
4823 if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_OFFCHANNEL_SIMULTANEOUS) &&
4824 radio->num_active_works < MAX_ACTIVE_WORKS)
4825 radio_work_check_next(wpa_s);
b1ae396f
JM
4826}
4827
4828
b3253ebb
AO
4829/*
4830 * This function removes both started and pending radio works running on
4831 * the provided interface's radio.
4832 * Prior to the removal of the radio work, its callback (cb) is called with
4833 * deinit set to be 1. Each work's callback is responsible for clearing its
4834 * internal data and restoring to a correct state.
4835 * @wpa_s: wpa_supplicant data
4836 * @type: type of works to be removed
4837 * @remove_all: 1 to remove all the works on this radio, 0 to remove only
4838 * this interface's works.
4839 */
4840void radio_remove_works(struct wpa_supplicant *wpa_s,
4841 const char *type, int remove_all)
b1ae396f
JM
4842{
4843 struct wpa_radio_work *work, *tmp;
4844 struct wpa_radio *radio = wpa_s->radio;
4845
4846 dl_list_for_each_safe(work, tmp, &radio->work, struct wpa_radio_work,
4847 list) {
b3253ebb 4848 if (type && os_strcmp(type, work->type) != 0)
b1ae396f 4849 continue;
b3253ebb
AO
4850
4851 /* skip other ifaces' works */
4852 if (!remove_all && work->wpa_s != wpa_s)
b1ae396f 4853 continue;
b3253ebb
AO
4854
4855 wpa_dbg(wpa_s, MSG_DEBUG, "Remove radio work '%s'@%p%s",
4856 work->type, work, work->started ? " (started)" : "");
b1ae396f
JM
4857 work->cb(work, 1);
4858 radio_work_free(work);
4859 }
b3253ebb
AO
4860
4861 /* in case we removed the started work */
4862 radio_work_check_next(wpa_s);
b1ae396f
JM
4863}
4864
4865
202dec2a
JM
4866static void radio_remove_interface(struct wpa_supplicant *wpa_s)
4867{
4868 struct wpa_radio *radio = wpa_s->radio;
4869
4870 if (!radio)
4871 return;
4872
4873 wpa_printf(MSG_DEBUG, "Remove interface %s from radio %s",
4874 wpa_s->ifname, radio->name);
4875 dl_list_del(&wpa_s->radio_list);
c46235aa
AO
4876 radio_remove_works(wpa_s, NULL, 0);
4877 wpa_s->radio = NULL;
4878 if (!dl_list_empty(&radio->ifaces))
202dec2a
JM
4879 return; /* Interfaces remain for this radio */
4880
4881 wpa_printf(MSG_DEBUG, "Remove radio %s", radio->name);
b1ae396f 4882 eloop_cancel_timeout(radio_start_next_work, radio, NULL);
202dec2a
JM
4883 os_free(radio);
4884}
4885
4886
6428d0a7 4887void radio_work_check_next(struct wpa_supplicant *wpa_s)
b1ae396f
JM
4888{
4889 struct wpa_radio *radio = wpa_s->radio;
4890
4891 if (dl_list_empty(&radio->work))
4892 return;
e3745228
JM
4893 if (wpa_s->ext_work_in_progress) {
4894 wpa_printf(MSG_DEBUG,
4895 "External radio work in progress - delay start of pending item");
4896 return;
4897 }
b1ae396f
JM
4898 eloop_cancel_timeout(radio_start_next_work, radio, NULL);
4899 eloop_register_timeout(0, 0, radio_start_next_work, radio, NULL);
4900}
4901
4902
4903/**
4904 * radio_add_work - Add a radio work item
4905 * @wpa_s: Pointer to wpa_supplicant data
4906 * @freq: Frequency of the offchannel operation in MHz or 0
4907 * @type: Unique identifier for each type of work
4908 * @next: Force as the next work to be executed
4909 * @cb: Callback function for indicating when radio is available
4910 * @ctx: Context pointer for the work (work->ctx in cb())
4911 * Returns: 0 on success, -1 on failure
4912 *
4913 * This function is used to request time for an operation that requires
4914 * exclusive radio control. Once the radio is available, the registered callback
4915 * function will be called. radio_work_done() must be called once the exclusive
4916 * radio operation has been completed, so that the radio is freed for other
4917 * operations. The special case of deinit=1 is used to free the context data
4918 * during interface removal. That does not allow the callback function to start
4919 * the radio operation, i.e., it must free any resources allocated for the radio
4920 * work and return.
4921 *
4922 * The @freq parameter can be used to indicate a single channel on which the
4923 * offchannel operation will occur. This may allow multiple radio work
4924 * operations to be performed in parallel if they apply for the same channel.
4925 * Setting this to 0 indicates that the work item may use multiple channels or
4926 * requires exclusive control of the radio.
4927 */
4928int radio_add_work(struct wpa_supplicant *wpa_s, unsigned int freq,
4929 const char *type, int next,
4930 void (*cb)(struct wpa_radio_work *work, int deinit),
4931 void *ctx)
4932{
e903d32d 4933 struct wpa_radio *radio = wpa_s->radio;
b1ae396f
JM
4934 struct wpa_radio_work *work;
4935 int was_empty;
4936
4937 work = os_zalloc(sizeof(*work));
4938 if (work == NULL)
4939 return -1;
4940 wpa_dbg(wpa_s, MSG_DEBUG, "Add radio work '%s'@%p", type, work);
4941 os_get_reltime(&work->time);
4942 work->freq = freq;
4943 work->type = type;
4944 work->wpa_s = wpa_s;
4945 work->cb = cb;
4946 work->ctx = ctx;
4947
e903d32d
KV
4948 if (freq)
4949 work->bands = wpas_freq_to_band(freq);
4950 else if (os_strcmp(type, "scan") == 0 ||
4951 os_strcmp(type, "p2p-scan") == 0)
4952 work->bands = wpas_get_bands(wpa_s,
4953 ((struct wpa_driver_scan_params *)
4954 ctx)->freqs);
4955 else
4956 work->bands = wpas_get_bands(wpa_s, NULL);
4957
b1ae396f
JM
4958 was_empty = dl_list_empty(&wpa_s->radio->work);
4959 if (next)
4960 dl_list_add(&wpa_s->radio->work, &work->list);
4961 else
4962 dl_list_add_tail(&wpa_s->radio->work, &work->list);
4963 if (was_empty) {
4964 wpa_dbg(wpa_s, MSG_DEBUG, "First radio work item in the queue - schedule start immediately");
4965 radio_work_check_next(wpa_s);
e903d32d
KV
4966 } else if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_OFFCHANNEL_SIMULTANEOUS)
4967 && radio->num_active_works < MAX_ACTIVE_WORKS) {
4968 wpa_dbg(wpa_s, MSG_DEBUG,
4969 "Try to schedule a radio work (num_active_works=%u)",
4970 radio->num_active_works);
4971 radio_work_check_next(wpa_s);
b1ae396f
JM
4972 }
4973
4974 return 0;
4975}
4976
4977
4978/**
4979 * radio_work_done - Indicate that a radio work item has been completed
4980 * @work: Completed work
4981 *
4982 * This function is called once the callback function registered with
4983 * radio_add_work() has completed its work.
4984 */
4985void radio_work_done(struct wpa_radio_work *work)
4986{
4987 struct wpa_supplicant *wpa_s = work->wpa_s;
4988 struct os_reltime now, diff;
1f965e62 4989 unsigned int started = work->started;
b1ae396f
JM
4990
4991 os_get_reltime(&now);
4992 os_reltime_sub(&now, &work->time, &diff);
1f965e62
JM
4993 wpa_dbg(wpa_s, MSG_DEBUG, "Radio work '%s'@%p %s in %ld.%06ld seconds",
4994 work->type, work, started ? "done" : "canceled",
4995 diff.sec, diff.usec);
b1ae396f 4996 radio_work_free(work);
1f965e62
JM
4997 if (started)
4998 radio_work_check_next(wpa_s);
b1ae396f
JM
4999}
5000
5001
a7f5271d
JM
5002struct wpa_radio_work *
5003radio_work_pending(struct wpa_supplicant *wpa_s, const char *type)
f0e30c84
JM
5004{
5005 struct wpa_radio_work *work;
5006 struct wpa_radio *radio = wpa_s->radio;
5007
5008 dl_list_for_each(work, &radio->work, struct wpa_radio_work, list) {
5009 if (work->wpa_s == wpa_s && os_strcmp(work->type, type) == 0)
a7f5271d 5010 return work;
f0e30c84
JM
5011 }
5012
a7f5271d 5013 return NULL;
f0e30c84
JM
5014}
5015
5016
73c00fd7
JM
5017static int wpas_init_driver(struct wpa_supplicant *wpa_s,
5018 struct wpa_interface *iface)
5019{
202dec2a 5020 const char *ifname, *driver, *rn;
73c00fd7
JM
5021
5022 driver = iface->driver;
5023next_driver:
5024 if (wpa_supplicant_set_driver(wpa_s, driver) < 0)
5025 return -1;
5026
5027 wpa_s->drv_priv = wpa_drv_init(wpa_s, wpa_s->ifname);
5028 if (wpa_s->drv_priv == NULL) {
5029 const char *pos;
5030 pos = driver ? os_strchr(driver, ',') : NULL;
5031 if (pos) {
5032 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to initialize "
5033 "driver interface - try next driver wrapper");
5034 driver = pos + 1;
5035 goto next_driver;
5036 }
5037 wpa_msg(wpa_s, MSG_ERROR, "Failed to initialize driver "
5038 "interface");
5039 return -1;
5040 }
5041 if (wpa_drv_set_param(wpa_s, wpa_s->conf->driver_param) < 0) {
5042 wpa_msg(wpa_s, MSG_ERROR, "Driver interface rejected "
5043 "driver_param '%s'", wpa_s->conf->driver_param);
5044 return -1;
5045 }
5046
5047 ifname = wpa_drv_get_ifname(wpa_s);
5048 if (ifname && os_strcmp(ifname, wpa_s->ifname) != 0) {
5049 wpa_dbg(wpa_s, MSG_DEBUG, "Driver interface replaced "
5050 "interface name with '%s'", ifname);
5051 os_strlcpy(wpa_s->ifname, ifname, sizeof(wpa_s->ifname));
5052 }
5053
95bf699f 5054 rn = wpa_driver_get_radio_name(wpa_s);
202dec2a
JM
5055 if (rn && rn[0] == '\0')
5056 rn = NULL;
5057
5058 wpa_s->radio = radio_add_interface(wpa_s, rn);
5059 if (wpa_s->radio == NULL)
5060 return -1;
5061
73c00fd7
JM
5062 return 0;
5063}
5064
5065
461d39af
JM
5066#ifdef CONFIG_GAS_SERVER
5067
5068static void wpas_gas_server_tx_status(struct wpa_supplicant *wpa_s,
5069 unsigned int freq, const u8 *dst,
5070 const u8 *src, const u8 *bssid,
5071 const u8 *data, size_t data_len,
5072 enum offchannel_send_action_result result)
5073{
5074 wpa_printf(MSG_DEBUG, "GAS: TX status: freq=%u dst=" MACSTR
5075 " result=%s",
5076 freq, MAC2STR(dst),
5077 result == OFFCHANNEL_SEND_ACTION_SUCCESS ? "SUCCESS" :
5078 (result == OFFCHANNEL_SEND_ACTION_NO_ACK ? "no-ACK" :
5079 "FAILED"));
5080 gas_server_tx_status(wpa_s->gas_server, dst, data, data_len,
5081 result == OFFCHANNEL_SEND_ACTION_SUCCESS);
5082}
5083
5084
5085static void wpas_gas_server_tx(void *ctx, int freq, const u8 *da,
5086 struct wpabuf *buf, unsigned int wait_time)
5087{
5088 struct wpa_supplicant *wpa_s = ctx;
5089 const u8 broadcast[ETH_ALEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
5090
5091 if (wait_time > wpa_s->max_remain_on_chan)
5092 wait_time = wpa_s->max_remain_on_chan;
5093
5094 offchannel_send_action(wpa_s, freq, da, wpa_s->own_addr, broadcast,
5095 wpabuf_head(buf), wpabuf_len(buf),
5096 wait_time, wpas_gas_server_tx_status, 0);
5097}
5098
5099#endif /* CONFIG_GAS_SERVER */
5100
6fc6879b
JM
5101static int wpa_supplicant_init_iface(struct wpa_supplicant *wpa_s,
5102 struct wpa_interface *iface)
5103{
362f781e 5104 struct wpa_driver_capa capa;
6cbdb0c5 5105 int capa_res;
aa56e36d 5106 u8 dfs_domain;
362f781e 5107
6fc6879b
JM
5108 wpa_printf(MSG_DEBUG, "Initializing interface '%s' conf '%s' driver "
5109 "'%s' ctrl_interface '%s' bridge '%s'", iface->ifname,
5110 iface->confname ? iface->confname : "N/A",
5111 iface->driver ? iface->driver : "default",
5112 iface->ctrl_interface ? iface->ctrl_interface : "N/A",
5113 iface->bridge_ifname ? iface->bridge_ifname : "N/A");
5114
6fc6879b
JM
5115 if (iface->confname) {
5116#ifdef CONFIG_BACKEND_FILE
5117 wpa_s->confname = os_rel2abs_path(iface->confname);
5118 if (wpa_s->confname == NULL) {
5119 wpa_printf(MSG_ERROR, "Failed to get absolute path "
5120 "for configuration file '%s'.",
5121 iface->confname);
5122 return -1;
5123 }
5124 wpa_printf(MSG_DEBUG, "Configuration file '%s' -> '%s'",
5125 iface->confname, wpa_s->confname);
5126#else /* CONFIG_BACKEND_FILE */
5127 wpa_s->confname = os_strdup(iface->confname);
5128#endif /* CONFIG_BACKEND_FILE */
e6304cad 5129 wpa_s->conf = wpa_config_read(wpa_s->confname, NULL);
6fc6879b
JM
5130 if (wpa_s->conf == NULL) {
5131 wpa_printf(MSG_ERROR, "Failed to read or parse "
5132 "configuration '%s'.", wpa_s->confname);
5133 return -1;
5134 }
e6304cad
DS
5135 wpa_s->confanother = os_rel2abs_path(iface->confanother);
5136 wpa_config_read(wpa_s->confanother, wpa_s->conf);
6fc6879b
JM
5137
5138 /*
5139 * Override ctrl_interface and driver_param if set on command
5140 * line.
5141 */
5142 if (iface->ctrl_interface) {
5143 os_free(wpa_s->conf->ctrl_interface);
5144 wpa_s->conf->ctrl_interface =
5145 os_strdup(iface->ctrl_interface);
5146 }
5147
5148 if (iface->driver_param) {
5149 os_free(wpa_s->conf->driver_param);
5150 wpa_s->conf->driver_param =
5151 os_strdup(iface->driver_param);
5152 }
78f79fe5
JM
5153
5154 if (iface->p2p_mgmt && !iface->ctrl_interface) {
5155 os_free(wpa_s->conf->ctrl_interface);
5156 wpa_s->conf->ctrl_interface = NULL;
5157 }
6fc6879b
JM
5158 } else
5159 wpa_s->conf = wpa_config_alloc_empty(iface->ctrl_interface,
5160 iface->driver_param);
5161
5162 if (wpa_s->conf == NULL) {
5163 wpa_printf(MSG_ERROR, "\nNo configuration found.");
5164 return -1;
5165 }
5166
5167 if (iface->ifname == NULL) {
5168 wpa_printf(MSG_ERROR, "\nInterface name is required.");
5169 return -1;
5170 }
5171 if (os_strlen(iface->ifname) >= sizeof(wpa_s->ifname)) {
5172 wpa_printf(MSG_ERROR, "\nToo long interface name '%s'.",
5173 iface->ifname);
5174 return -1;
5175 }
5176 os_strlcpy(wpa_s->ifname, iface->ifname, sizeof(wpa_s->ifname));
5177
5178 if (iface->bridge_ifname) {
5179 if (os_strlen(iface->bridge_ifname) >=
5180 sizeof(wpa_s->bridge_ifname)) {
5181 wpa_printf(MSG_ERROR, "\nToo long bridge interface "
5182 "name '%s'.", iface->bridge_ifname);
5183 return -1;
5184 }
5185 os_strlcpy(wpa_s->bridge_ifname, iface->bridge_ifname,
5186 sizeof(wpa_s->bridge_ifname));
5187 }
5188
6fc6879b
JM
5189 /* RSNA Supplicant Key Management - INITIALIZE */
5190 eapol_sm_notify_portEnabled(wpa_s->eapol, FALSE);
5191 eapol_sm_notify_portValid(wpa_s->eapol, FALSE);
5192
5193 /* Initialize driver interface and register driver event handler before
5194 * L2 receive handler so that association events are processed before
5195 * EAPOL-Key packets if both become available for the same select()
5196 * call. */
73c00fd7 5197 if (wpas_init_driver(wpa_s, iface) < 0)
362f781e
JM
5198 return -1;
5199
6fc6879b
JM
5200 if (wpa_supplicant_init_wpa(wpa_s) < 0)
5201 return -1;
5202
5203 wpa_sm_set_ifname(wpa_s->wpa, wpa_s->ifname,
5204 wpa_s->bridge_ifname[0] ? wpa_s->bridge_ifname :
5205 NULL);
5206 wpa_sm_set_fast_reauth(wpa_s->wpa, wpa_s->conf->fast_reauth);
5207
5208 if (wpa_s->conf->dot11RSNAConfigPMKLifetime &&
5209 wpa_sm_set_param(wpa_s->wpa, RSNA_PMK_LIFETIME,
5210 wpa_s->conf->dot11RSNAConfigPMKLifetime)) {
f049052b
BG
5211 wpa_msg(wpa_s, MSG_ERROR, "Invalid WPA parameter value for "
5212 "dot11RSNAConfigPMKLifetime");
6fc6879b
JM
5213 return -1;
5214 }
5215
5216 if (wpa_s->conf->dot11RSNAConfigPMKReauthThreshold &&
5217 wpa_sm_set_param(wpa_s->wpa, RSNA_PMK_REAUTH_THRESHOLD,
5218 wpa_s->conf->dot11RSNAConfigPMKReauthThreshold)) {
f049052b 5219 wpa_msg(wpa_s, MSG_ERROR, "Invalid WPA parameter value for "
6fc6879b
JM
5220 "dot11RSNAConfigPMKReauthThreshold");
5221 return -1;
5222 }
5223
5224 if (wpa_s->conf->dot11RSNAConfigSATimeout &&
5225 wpa_sm_set_param(wpa_s->wpa, RSNA_SA_TIMEOUT,
5226 wpa_s->conf->dot11RSNAConfigSATimeout)) {
f049052b
BG
5227 wpa_msg(wpa_s, MSG_ERROR, "Invalid WPA parameter value for "
5228 "dot11RSNAConfigSATimeout");
6fc6879b
JM
5229 return -1;
5230 }
5231
6bf731e8
CL
5232 wpa_s->hw.modes = wpa_drv_get_hw_feature_data(wpa_s,
5233 &wpa_s->hw.num_modes,
aa56e36d
VT
5234 &wpa_s->hw.flags,
5235 &dfs_domain);
a1b790eb
JM
5236 if (wpa_s->hw.modes) {
5237 u16 i;
5238
5239 for (i = 0; i < wpa_s->hw.num_modes; i++) {
5240 if (wpa_s->hw.modes[i].vht_capab) {
5241 wpa_s->hw_capab = CAPAB_VHT;
5242 break;
5243 }
5244
5245 if (wpa_s->hw.modes[i].ht_capab &
5246 HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET)
5247 wpa_s->hw_capab = CAPAB_HT40;
5248 else if (wpa_s->hw.modes[i].ht_capab &&
5249 wpa_s->hw_capab == CAPAB_NO_HT_VHT)
5250 wpa_s->hw_capab = CAPAB_HT;
5251 }
5252 }
6bf731e8 5253
6cbdb0c5
JM
5254 capa_res = wpa_drv_get_capa(wpa_s, &capa);
5255 if (capa_res == 0) {
c58ab8f2 5256 wpa_s->drv_capa_known = 1;
814782b9 5257 wpa_s->drv_flags = capa.flags;
349493bd 5258 wpa_s->drv_enc = capa.enc;
04ee647d 5259 wpa_s->drv_smps_modes = capa.smps_modes;
f936b73c 5260 wpa_s->drv_rrm_flags = capa.rrm_flags;
4f73d88a 5261 wpa_s->probe_resp_offloads = capa.probe_resp_offloads;
814782b9 5262 wpa_s->max_scan_ssids = capa.max_scan_ssids;
cbdf3507 5263 wpa_s->max_sched_scan_ssids = capa.max_sched_scan_ssids;
32c02261
AS
5264 wpa_s->max_sched_scan_plans = capa.max_sched_scan_plans;
5265 wpa_s->max_sched_scan_plan_interval =
5266 capa.max_sched_scan_plan_interval;
5267 wpa_s->max_sched_scan_plan_iterations =
5268 capa.max_sched_scan_plan_iterations;
cbdf3507 5269 wpa_s->sched_scan_supported = capa.sched_scan_supported;
b59e6f26 5270 wpa_s->max_match_sets = capa.max_match_sets;
814782b9 5271 wpa_s->max_remain_on_chan = capa.max_remain_on_chan;
c4ea4c5c 5272 wpa_s->max_stations = capa.max_stations;
8cd6b7bc
JB
5273 wpa_s->extended_capa = capa.extended_capa;
5274 wpa_s->extended_capa_mask = capa.extended_capa_mask;
5275 wpa_s->extended_capa_len = capa.extended_capa_len;
4752147d
IP
5276 wpa_s->num_multichan_concurrent =
5277 capa.num_multichan_concurrent;
471cd6e1 5278 wpa_s->wmm_ac_supported = capa.wmm_ac_supported;
56c76fa5
IP
5279
5280 if (capa.mac_addr_rand_scan_supported)
5281 wpa_s->mac_addr_rand_supported |= MAC_ADDR_RAND_SCAN;
5282 if (wpa_s->sched_scan_supported &&
5283 capa.mac_addr_rand_sched_scan_supported)
5284 wpa_s->mac_addr_rand_supported |=
5285 (MAC_ADDR_RAND_SCHED_SCAN | MAC_ADDR_RAND_PNO);
814782b9
JM
5286 }
5287 if (wpa_s->max_remain_on_chan == 0)
5288 wpa_s->max_remain_on_chan = 1000;
5289
c68f6200
AS
5290 /*
5291 * Only take p2p_mgmt parameters when P2P Device is supported.
5292 * Doing it here as it determines whether l2_packet_init() will be done
5293 * during wpa_supplicant_driver_init().
5294 */
5295 if (wpa_s->drv_flags & WPA_DRIVER_FLAGS_DEDICATED_P2P_DEVICE)
5296 wpa_s->p2p_mgmt = iface->p2p_mgmt;
5297 else
5298 iface->p2p_mgmt = 1;
5299
4752147d
IP
5300 if (wpa_s->num_multichan_concurrent == 0)
5301 wpa_s->num_multichan_concurrent = 1;
5302
6fc6879b
JM
5303 if (wpa_supplicant_driver_init(wpa_s) < 0)
5304 return -1;
5305
281ff0aa 5306#ifdef CONFIG_TDLS
1c42b42f
JM
5307 if ((!iface->p2p_mgmt ||
5308 !(wpa_s->drv_flags &
5309 WPA_DRIVER_FLAGS_DEDICATED_P2P_DEVICE)) &&
5310 wpa_tdls_init(wpa_s->wpa))
281ff0aa
GP
5311 return -1;
5312#endif /* CONFIG_TDLS */
5313
315ce40a
JM
5314 if (wpa_s->conf->country[0] && wpa_s->conf->country[1] &&
5315 wpa_drv_set_country(wpa_s, wpa_s->conf->country)) {
f049052b 5316 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to set country");
6d158490
LR
5317 return -1;
5318 }
5319
b36a3a65
AN
5320#ifdef CONFIG_FST
5321 if (wpa_s->conf->fst_group_id) {
5322 struct fst_iface_cfg cfg;
5323 struct fst_wpa_obj iface_obj;
5324
5325 fst_wpa_supplicant_fill_iface_obj(wpa_s, &iface_obj);
5326 os_strlcpy(cfg.group_id, wpa_s->conf->fst_group_id,
5327 sizeof(cfg.group_id));
5328 cfg.priority = wpa_s->conf->fst_priority;
5329 cfg.llt = wpa_s->conf->fst_llt;
5330
5331 wpa_s->fst = fst_attach(wpa_s->ifname, wpa_s->own_addr,
5332 &iface_obj, &cfg);
5333 if (!wpa_s->fst) {
5334 wpa_msg(wpa_s, MSG_ERROR,
5335 "FST: Cannot attach iface %s to group %s",
5336 wpa_s->ifname, cfg.group_id);
5337 return -1;
5338 }
5339 }
5340#endif /* CONFIG_FST */
5341
116654ce
JM
5342 if (wpas_wps_init(wpa_s))
5343 return -1;
5344
461d39af
JM
5345#ifdef CONFIG_GAS_SERVER
5346 wpa_s->gas_server = gas_server_init(wpa_s, wpas_gas_server_tx);
5347 if (!wpa_s->gas_server) {
5348 wpa_printf(MSG_ERROR, "Failed to initialize GAS server");
5349 return -1;
5350 }
5351#endif /* CONFIG_GAS_SERVER */
5352
be27e185
JM
5353#ifdef CONFIG_DPP
5354 if (wpas_dpp_init(wpa_s) < 0)
5355 return -1;
5356#endif /* CONFIG_DPP */
5357
6fc6879b
JM
5358 if (wpa_supplicant_init_eapol(wpa_s) < 0)
5359 return -1;
5360 wpa_sm_set_eapol(wpa_s->wpa, wpa_s->eapol);
5361
5362 wpa_s->ctrl_iface = wpa_supplicant_ctrl_iface_init(wpa_s);
5363 if (wpa_s->ctrl_iface == NULL) {
5364 wpa_printf(MSG_ERROR,
5365 "Failed to initialize control interface '%s'.\n"
5366 "You may have another wpa_supplicant process "
5367 "already running or the file was\n"
5368 "left by an unclean termination of wpa_supplicant "
5369 "in which case you will need\n"
5370 "to manually remove this file before starting "
5371 "wpa_supplicant again.\n",
5372 wpa_s->conf->ctrl_interface);
5373 return -1;
5374 }
5375
04ea7b79
JM
5376 wpa_s->gas = gas_query_init(wpa_s);
5377 if (wpa_s->gas == NULL) {
5378 wpa_printf(MSG_ERROR, "Failed to initialize GAS query");
5379 return -1;
5380 }
5381
c68f6200 5382 if (iface->p2p_mgmt && wpas_p2p_init(wpa_s->global, wpa_s) < 0) {
f049052b 5383 wpa_msg(wpa_s, MSG_ERROR, "Failed to init P2P");
b22128ef
JM
5384 return -1;
5385 }
b22128ef 5386
83922c2d
JM
5387 if (wpa_bss_init(wpa_s) < 0)
5388 return -1;
83922c2d 5389
4d77d80e
MH
5390#ifdef CONFIG_PMKSA_CACHE_EXTERNAL
5391#ifdef CONFIG_MESH
5392 dl_list_init(&wpa_s->mesh_external_pmksa_cache);
5393#endif /* CONFIG_MESH */
5394#endif /* CONFIG_PMKSA_CACHE_EXTERNAL */
5395
e4fa8b12
EP
5396 /*
5397 * Set Wake-on-WLAN triggers, if configured.
5398 * Note: We don't restore/remove the triggers on shutdown (it doesn't
5399 * have effect anyway when the interface is down).
5400 */
6cbdb0c5 5401 if (capa_res == 0 && wpas_set_wowlan_triggers(wpa_s, &capa) < 0)
e4fa8b12
EP
5402 return -1;
5403
ec7b97ab
JM
5404#ifdef CONFIG_EAP_PROXY
5405{
5406 size_t len;
b5db6e5d
VK
5407 wpa_s->mnc_len = eapol_sm_get_eap_proxy_imsi(wpa_s->eapol, -1,
5408 wpa_s->imsi, &len);
ec7b97ab
JM
5409 if (wpa_s->mnc_len > 0) {
5410 wpa_s->imsi[len] = '\0';
5411 wpa_printf(MSG_DEBUG, "eap_proxy: IMSI %s (MNC length %d)",
5412 wpa_s->imsi, wpa_s->mnc_len);
5413 } else {
5414 wpa_printf(MSG_DEBUG, "eap_proxy: IMSI not available");
5415 }
5416}
5417#endif /* CONFIG_EAP_PROXY */
5418
f64adcd7
JM
5419 if (pcsc_reader_init(wpa_s) < 0)
5420 return -1;
5421
306ae225
JM
5422 if (wpas_init_ext_pw(wpa_s) < 0)
5423 return -1;
5424
b361d580
AK
5425 wpas_rrm_reset(wpa_s);
5426
32c02261
AS
5427 wpas_sched_scan_plans_set(wpa_s, wpa_s->conf->sched_scan_plans);
5428
ca9968a0
JM
5429#ifdef CONFIG_HS20
5430 hs20_init(wpa_s);
5431#endif /* CONFIG_HS20 */
92c6e2e3 5432#ifdef CONFIG_MBO
332aadb8
AP
5433 if (wpa_s->conf->oce) {
5434 if ((wpa_s->conf->oce & OCE_STA) &&
5435 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_OCE_STA))
5436 wpa_s->enable_oce = OCE_STA;
5437 if ((wpa_s->conf->oce & OCE_STA_CFON) &&
5438 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_OCE_STA_CFON)) {
5439 /* TODO: Need to add STA-CFON support */
5440 wpa_printf(MSG_ERROR,
5441 "OCE STA-CFON feature is not yet supported");
5442 }
5443 }
92c6e2e3
DS
5444 wpas_mbo_update_non_pref_chan(wpa_s, wpa_s->conf->non_pref_chan);
5445#endif /* CONFIG_MBO */
ca9968a0 5446
cc9985d1 5447 wpa_supplicant_set_default_scan_ies(wpa_s);
5448
6fc6879b
JM
5449 return 0;
5450}
5451
5452
2ee055b3 5453static void wpa_supplicant_deinit_iface(struct wpa_supplicant *wpa_s,
df509539 5454 int notify, int terminate)
6fc6879b 5455{
26fc96e8
JM
5456 struct wpa_global *global = wpa_s->global;
5457 struct wpa_supplicant *iface, *prev;
5458
5459 if (wpa_s == wpa_s->parent)
5460 wpas_p2p_group_remove(wpa_s, "*");
5461
5462 iface = global->ifaces;
5463 while (iface) {
96a26ab7
LD
5464 if (iface->p2pdev == wpa_s)
5465 iface->p2pdev = iface->parent;
26fc96e8
JM
5466 if (iface == wpa_s || iface->parent != wpa_s) {
5467 iface = iface->next;
5468 continue;
5469 }
5470 wpa_printf(MSG_DEBUG,
5471 "Remove remaining child interface %s from parent %s",
5472 iface->ifname, wpa_s->ifname);
5473 prev = iface;
5474 iface = iface->next;
5475 wpa_supplicant_remove_iface(global, prev, terminate);
5476 }
5477
e679f140 5478 wpa_s->disconnected = 1;
6fc6879b
JM
5479 if (wpa_s->drv_priv) {
5480 wpa_supplicant_deauthenticate(wpa_s,
5481 WLAN_REASON_DEAUTH_LEAVING);
5482
6fc6879b
JM
5483 wpa_drv_set_countermeasures(wpa_s, 0);
5484 wpa_clear_keys(wpa_s, NULL);
5485 }
5486
8e56d189 5487 wpa_supplicant_cleanup(wpa_s);
bd10d938 5488 wpas_p2p_deinit_iface(wpa_s);
ab28911d 5489
1f965e62 5490 wpas_ctrl_radio_work_flush(wpa_s);
202dec2a
JM
5491 radio_remove_interface(wpa_s);
5492
b36a3a65
AN
5493#ifdef CONFIG_FST
5494 if (wpa_s->fst) {
5495 fst_detach(wpa_s->fst);
5496 wpa_s->fst = NULL;
5497 }
5498 if (wpa_s->received_mb_ies) {
5499 wpabuf_free(wpa_s->received_mb_ies);
5500 wpa_s->received_mb_ies = NULL;
5501 }
5502#endif /* CONFIG_FST */
5503
6fc6879b
JM
5504 if (wpa_s->drv_priv)
5505 wpa_drv_deinit(wpa_s);
2523ff6e
DS
5506
5507 if (notify)
5508 wpas_notify_iface_removed(wpa_s);
f0811516
DS
5509
5510 if (terminate)
5511 wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_TERMINATING);
5512
5513 if (wpa_s->ctrl_iface) {
5514 wpa_supplicant_ctrl_iface_deinit(wpa_s->ctrl_iface);
5515 wpa_s->ctrl_iface = NULL;
5516 }
5517
603a3f34
JL
5518#ifdef CONFIG_MESH
5519 if (wpa_s->ifmsh) {
5520 wpa_supplicant_mesh_iface_deinit(wpa_s, wpa_s->ifmsh);
5521 wpa_s->ifmsh = NULL;
5522 }
5523#endif /* CONFIG_MESH */
5524
f0811516
DS
5525 if (wpa_s->conf != NULL) {
5526 wpa_config_free(wpa_s->conf);
5527 wpa_s->conf = NULL;
5528 }
18e00b5e 5529
a80651d0
KV
5530 os_free(wpa_s->ssids_from_scan_req);
5531
18e00b5e 5532 os_free(wpa_s);
6fc6879b
JM
5533}
5534
5535
2e997eec
RM
5536#ifdef CONFIG_MATCH_IFACE
5537
5538/**
5539 * wpa_supplicant_match_iface - Match an interface description to a name
5540 * @global: Pointer to global data from wpa_supplicant_init()
5541 * @ifname: Name of the interface to match
5542 * Returns: Pointer to the created interface description or %NULL on failure
5543 */
5544struct wpa_interface * wpa_supplicant_match_iface(struct wpa_global *global,
5545 const char *ifname)
5546{
5547 int i;
5548 struct wpa_interface *iface, *miface;
5549
5550 for (i = 0; i < global->params.match_iface_count; i++) {
5551 miface = &global->params.match_ifaces[i];
5552 if (!miface->ifname ||
5553 fnmatch(miface->ifname, ifname, 0) == 0) {
5554 iface = os_zalloc(sizeof(*iface));
5555 if (!iface)
5556 return NULL;
5557 *iface = *miface;
5558 iface->ifname = ifname;
5559 return iface;
5560 }
5561 }
5562
5563 return NULL;
5564}
5565
5566
5567/**
5568 * wpa_supplicant_match_existing - Match existing interfaces
5569 * @global: Pointer to global data from wpa_supplicant_init()
5570 * Returns: 0 on success, -1 on failure
5571 */
5572static int wpa_supplicant_match_existing(struct wpa_global *global)
5573{
5574 struct if_nameindex *ifi, *ifp;
5575 struct wpa_supplicant *wpa_s;
5576 struct wpa_interface *iface;
5577
5578 ifp = if_nameindex();
5579 if (!ifp) {
5580 wpa_printf(MSG_ERROR, "if_nameindex: %s", strerror(errno));
5581 return -1;
5582 }
5583
5584 for (ifi = ifp; ifi->if_name; ifi++) {
5585 wpa_s = wpa_supplicant_get_iface(global, ifi->if_name);
5586 if (wpa_s)
5587 continue;
5588 iface = wpa_supplicant_match_iface(global, ifi->if_name);
5589 if (iface) {
5590 wpa_s = wpa_supplicant_add_iface(global, iface, NULL);
5591 os_free(iface);
5592 if (wpa_s)
5593 wpa_s->matched = 1;
5594 }
5595 }
5596
5597 if_freenameindex(ifp);
5598 return 0;
5599}
5600
5601#endif /* CONFIG_MATCH_IFACE */
5602
5603
6fc6879b
JM
5604/**
5605 * wpa_supplicant_add_iface - Add a new network interface
5606 * @global: Pointer to global data from wpa_supplicant_init()
5607 * @iface: Interface configuration options
1772d348 5608 * @parent: Parent interface or %NULL to assign new interface as parent
6fc6879b
JM
5609 * Returns: Pointer to the created interface or %NULL on failure
5610 *
5611 * This function is used to add new network interfaces for %wpa_supplicant.
5612 * This can be called before wpa_supplicant_run() to add interfaces before the
5613 * main event loop has been started. In addition, new interfaces can be added
5614 * dynamically while %wpa_supplicant is already running. This could happen,
5615 * e.g., when a hotplug network adapter is inserted.
5616 */
5617struct wpa_supplicant * wpa_supplicant_add_iface(struct wpa_global *global,
1772d348
JM
5618 struct wpa_interface *iface,
5619 struct wpa_supplicant *parent)
6fc6879b
JM
5620{
5621 struct wpa_supplicant *wpa_s;
d27df100 5622 struct wpa_interface t_iface;
8e56d189 5623 struct wpa_ssid *ssid;
6fc6879b
JM
5624
5625 if (global == NULL || iface == NULL)
5626 return NULL;
5627
1772d348 5628 wpa_s = wpa_supplicant_alloc(parent);
6fc6879b
JM
5629 if (wpa_s == NULL)
5630 return NULL;
5631
d8222ae3
JM
5632 wpa_s->global = global;
5633
d27df100
JM
5634 t_iface = *iface;
5635 if (global->params.override_driver) {
5636 wpa_printf(MSG_DEBUG, "Override interface parameter: driver "
5637 "('%s' -> '%s')",
5638 iface->driver, global->params.override_driver);
5639 t_iface.driver = global->params.override_driver;
5640 }
5641 if (global->params.override_ctrl_interface) {
5642 wpa_printf(MSG_DEBUG, "Override interface parameter: "
5643 "ctrl_interface ('%s' -> '%s')",
5644 iface->ctrl_interface,
5645 global->params.override_ctrl_interface);
5646 t_iface.ctrl_interface =
5647 global->params.override_ctrl_interface;
5648 }
5649 if (wpa_supplicant_init_iface(wpa_s, &t_iface)) {
6fc6879b
JM
5650 wpa_printf(MSG_DEBUG, "Failed to add interface %s",
5651 iface->ifname);
df509539 5652 wpa_supplicant_deinit_iface(wpa_s, 0, 0);
6fc6879b
JM
5653 return NULL;
5654 }
5655
21efc940
TB
5656 if (iface->p2p_mgmt == 0) {
5657 /* Notify the control interfaces about new iface */
5658 if (wpas_notify_iface_added(wpa_s)) {
5659 wpa_supplicant_deinit_iface(wpa_s, 1, 0);
5660 return NULL;
5661 }
1bd3f426 5662
21efc940
TB
5663 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next)
5664 wpas_notify_network_added(wpa_s, ssid);
5665 }
8e56d189 5666
6fc6879b
JM
5667 wpa_s->next = global->ifaces;
5668 global->ifaces = wpa_s;
5669
f049052b 5670 wpa_dbg(wpa_s, MSG_DEBUG, "Added interface %s", wpa_s->ifname);
99218999 5671 wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED);
6fc6879b 5672
c3c4b3ed
JM
5673#ifdef CONFIG_P2P
5674 if (wpa_s->global->p2p == NULL &&
74802c09 5675 !wpa_s->global->p2p_disabled && !wpa_s->conf->p2p_disabled &&
c3c4b3ed 5676 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_DEDICATED_P2P_DEVICE) &&
f43c1ae7
IP
5677 wpas_p2p_add_p2pdev_interface(
5678 wpa_s, wpa_s->global->params.conf_p2p_dev) < 0) {
c3c4b3ed
JM
5679 wpa_printf(MSG_INFO,
5680 "P2P: Failed to enable P2P Device interface");
5681 /* Try to continue without. P2P will be disabled. */
5682 }
5683#endif /* CONFIG_P2P */
5684
6fc6879b
JM
5685 return wpa_s;
5686}
5687
5688
5689/**
5690 * wpa_supplicant_remove_iface - Remove a network interface
5691 * @global: Pointer to global data from wpa_supplicant_init()
5692 * @wpa_s: Pointer to the network interface to be removed
5693 * Returns: 0 if interface was removed, -1 if interface was not found
5694 *
5695 * This function can be used to dynamically remove network interfaces from
5696 * %wpa_supplicant, e.g., when a hotplug network adapter is ejected. In
5697 * addition, this function is used to remove all remaining interfaces when
5698 * %wpa_supplicant is terminated.
5699 */
5700int wpa_supplicant_remove_iface(struct wpa_global *global,
df509539
DS
5701 struct wpa_supplicant *wpa_s,
5702 int terminate)
6fc6879b
JM
5703{
5704 struct wpa_supplicant *prev;
5b78493f
MH
5705#ifdef CONFIG_MESH
5706 unsigned int mesh_if_created = wpa_s->mesh_if_created;
5707 char *ifname = NULL;
9b170991 5708 struct wpa_supplicant *parent = wpa_s->parent;
5b78493f 5709#endif /* CONFIG_MESH */
6fc6879b
JM
5710
5711 /* Remove interface from the global list of interfaces */
5712 prev = global->ifaces;
5713 if (prev == wpa_s) {
5714 global->ifaces = wpa_s->next;
5715 } else {
5716 while (prev && prev->next != wpa_s)
5717 prev = prev->next;
5718 if (prev == NULL)
5719 return -1;
5720 prev->next = wpa_s->next;
5721 }
5722
f049052b 5723 wpa_dbg(wpa_s, MSG_DEBUG, "Removing interface %s", wpa_s->ifname);
6fc6879b 5724
5b78493f
MH
5725#ifdef CONFIG_MESH
5726 if (mesh_if_created) {
5727 ifname = os_strdup(wpa_s->ifname);
5728 if (ifname == NULL) {
5729 wpa_dbg(wpa_s, MSG_ERROR,
5730 "mesh: Failed to malloc ifname");
5731 return -1;
5732 }
5733 }
5734#endif /* CONFIG_MESH */
5735
b22128ef
JM
5736 if (global->p2p_group_formation == wpa_s)
5737 global->p2p_group_formation = NULL;
dbca75f8
JM
5738 if (global->p2p_invite_group == wpa_s)
5739 global->p2p_invite_group = NULL;
df509539 5740 wpa_supplicant_deinit_iface(wpa_s, 1, terminate);
6fc6879b 5741
5b78493f
MH
5742#ifdef CONFIG_MESH
5743 if (mesh_if_created) {
9b170991 5744 wpa_drv_if_remove(parent, WPA_IF_MESH, ifname);
5b78493f
MH
5745 os_free(ifname);
5746 }
5747#endif /* CONFIG_MESH */
5748
6fc6879b
JM
5749 return 0;
5750}
5751
5752
cf83fb0b
PS
5753/**
5754 * wpa_supplicant_get_eap_mode - Get the current EAP mode
5755 * @wpa_s: Pointer to the network interface
5756 * Returns: Pointer to the eap mode or the string "UNKNOWN" if not found
5757 */
5758const char * wpa_supplicant_get_eap_mode(struct wpa_supplicant *wpa_s)
5759{
5760 const char *eapol_method;
5761
5762 if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) == 0 &&
5763 wpa_s->key_mgmt != WPA_KEY_MGMT_IEEE8021X_NO_WPA) {
5764 return "NO-EAP";
5765 }
5766
5767 eapol_method = eapol_sm_get_method_name(wpa_s->eapol);
5768 if (eapol_method == NULL)
5769 return "UNKNOWN-EAP";
5770
5771 return eapol_method;
5772}
5773
5774
6fc6879b
JM
5775/**
5776 * wpa_supplicant_get_iface - Get a new network interface
5777 * @global: Pointer to global data from wpa_supplicant_init()
5778 * @ifname: Interface name
5779 * Returns: Pointer to the interface or %NULL if not found
5780 */
5781struct wpa_supplicant * wpa_supplicant_get_iface(struct wpa_global *global,
5782 const char *ifname)
5783{
5784 struct wpa_supplicant *wpa_s;
5785
5786 for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next) {
5787 if (os_strcmp(wpa_s->ifname, ifname) == 0)
5788 return wpa_s;
5789 }
5790 return NULL;
5791}
5792
5793
50b16da1 5794#ifndef CONFIG_NO_WPA_MSG
4f1495ae
BG
5795static const char * wpa_supplicant_msg_ifname_cb(void *ctx)
5796{
5797 struct wpa_supplicant *wpa_s = ctx;
5798 if (wpa_s == NULL)
5799 return NULL;
5800 return wpa_s->ifname;
5801}
50b16da1 5802#endif /* CONFIG_NO_WPA_MSG */
4f1495ae
BG
5803
5804
8c0d0ff2
JM
5805#ifndef WPA_SUPPLICANT_CLEANUP_INTERVAL
5806#define WPA_SUPPLICANT_CLEANUP_INTERVAL 10
5807#endif /* WPA_SUPPLICANT_CLEANUP_INTERVAL */
5808
5809/* Periodic cleanup tasks */
5810static void wpas_periodic(void *eloop_ctx, void *timeout_ctx)
5811{
5812 struct wpa_global *global = eloop_ctx;
5813 struct wpa_supplicant *wpa_s;
5814
5815 eloop_register_timeout(WPA_SUPPLICANT_CLEANUP_INTERVAL, 0,
5816 wpas_periodic, global, NULL);
5817
5818#ifdef CONFIG_P2P
5819 if (global->p2p)
5820 p2p_expire_peers(global->p2p);
5821#endif /* CONFIG_P2P */
5822
3188aaba 5823 for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next) {
8c0d0ff2 5824 wpa_bss_flush_by_age(wpa_s, wpa_s->conf->bss_expiration_age);
3188aaba
JM
5825#ifdef CONFIG_AP
5826 ap_periodic(wpa_s);
5827#endif /* CONFIG_AP */
5828 }
8c0d0ff2
JM
5829}
5830
5831
6fc6879b
JM
5832/**
5833 * wpa_supplicant_init - Initialize %wpa_supplicant
5834 * @params: Parameters for %wpa_supplicant
5835 * Returns: Pointer to global %wpa_supplicant data, or %NULL on failure
5836 *
5837 * This function is used to initialize %wpa_supplicant. After successful
5838 * initialization, the returned data pointer can be used to add and remove
5839 * network interfaces, and eventually, to deinitialize %wpa_supplicant.
5840 */
5841struct wpa_global * wpa_supplicant_init(struct wpa_params *params)
5842{
5843 struct wpa_global *global;
ac305589 5844 int ret, i;
6fc6879b
JM
5845
5846 if (params == NULL)
5847 return NULL;
5848
39e7d718
JM
5849#ifdef CONFIG_DRIVER_NDIS
5850 {
5851 void driver_ndis_init_ops(void);
5852 driver_ndis_init_ops();
5853 }
5854#endif /* CONFIG_DRIVER_NDIS */
5855
50b16da1 5856#ifndef CONFIG_NO_WPA_MSG
4f1495ae 5857 wpa_msg_register_ifname_cb(wpa_supplicant_msg_ifname_cb);
50b16da1 5858#endif /* CONFIG_NO_WPA_MSG */
4f1495ae 5859
f4637fe0
JM
5860 if (params->wpa_debug_file_path)
5861 wpa_debug_open_file(params->wpa_debug_file_path);
5862 else
5863 wpa_debug_setup_stdout();
daa70d49
SL
5864 if (params->wpa_debug_syslog)
5865 wpa_debug_open_syslog();
4f68895e
JB
5866 if (params->wpa_debug_tracing) {
5867 ret = wpa_debug_open_linux_tracing();
5868 if (ret) {
5869 wpa_printf(MSG_ERROR,
5870 "Failed to enable trace logging");
5871 return NULL;
5872 }
5873 }
6fc6879b 5874
12760815 5875 ret = eap_register_methods();
6fc6879b
JM
5876 if (ret) {
5877 wpa_printf(MSG_ERROR, "Failed to register EAP methods");
5878 if (ret == -2)
5879 wpa_printf(MSG_ERROR, "Two or more EAP methods used "
5880 "the same EAP type.");
5881 return NULL;
5882 }
5883
5884 global = os_zalloc(sizeof(*global));
5885 if (global == NULL)
5886 return NULL;
b22128ef
JM
5887 dl_list_init(&global->p2p_srv_bonjour);
5888 dl_list_init(&global->p2p_srv_upnp);
6fc6879b
JM
5889 global->params.daemonize = params->daemonize;
5890 global->params.wait_for_monitor = params->wait_for_monitor;
5891 global->params.dbus_ctrl_interface = params->dbus_ctrl_interface;
5892 if (params->pid_file)
5893 global->params.pid_file = os_strdup(params->pid_file);
5894 if (params->ctrl_interface)
5895 global->params.ctrl_interface =
5896 os_strdup(params->ctrl_interface);
29257565
JM
5897 if (params->ctrl_interface_group)
5898 global->params.ctrl_interface_group =
5899 os_strdup(params->ctrl_interface_group);
d27df100
JM
5900 if (params->override_driver)
5901 global->params.override_driver =
5902 os_strdup(params->override_driver);
5903 if (params->override_ctrl_interface)
5904 global->params.override_ctrl_interface =
5905 os_strdup(params->override_ctrl_interface);
2e997eec
RM
5906#ifdef CONFIG_MATCH_IFACE
5907 global->params.match_iface_count = params->match_iface_count;
5908 if (params->match_iface_count) {
5909 global->params.match_ifaces =
5910 os_calloc(params->match_iface_count,
5911 sizeof(struct wpa_interface));
5912 os_memcpy(global->params.match_ifaces,
5913 params->match_ifaces,
5914 params->match_iface_count *
5915 sizeof(struct wpa_interface));
5916 }
5917#endif /* CONFIG_MATCH_IFACE */
d4e59795
G
5918#ifdef CONFIG_P2P
5919 if (params->conf_p2p_dev)
5920 global->params.conf_p2p_dev =
5921 os_strdup(params->conf_p2p_dev);
5922#endif /* CONFIG_P2P */
6fc6879b
JM
5923 wpa_debug_level = global->params.wpa_debug_level =
5924 params->wpa_debug_level;
5925 wpa_debug_show_keys = global->params.wpa_debug_show_keys =
5926 params->wpa_debug_show_keys;
5927 wpa_debug_timestamp = global->params.wpa_debug_timestamp =
5928 params->wpa_debug_timestamp;
5929
f19858f5
JM
5930 wpa_printf(MSG_DEBUG, "wpa_supplicant v" VERSION_STR);
5931
0456ea16 5932 if (eloop_init()) {
6fc6879b
JM
5933 wpa_printf(MSG_ERROR, "Failed to initialize event loop");
5934 wpa_supplicant_deinit(global);
5935 return NULL;
5936 }
5937
38e24575 5938 random_init(params->entropy_file);
d47fa330 5939
6fc6879b
JM
5940 global->ctrl_iface = wpa_supplicant_global_ctrl_iface_init(global);
5941 if (global->ctrl_iface == NULL) {
5942 wpa_supplicant_deinit(global);
5943 return NULL;
5944 }
5945
dc461de4
WS
5946 if (wpas_notify_supplicant_initialized(global)) {
5947 wpa_supplicant_deinit(global);
5948 return NULL;
6fc6879b
JM
5949 }
5950
c5121837 5951 for (i = 0; wpa_drivers[i]; i++)
ac305589
JM
5952 global->drv_count++;
5953 if (global->drv_count == 0) {
5954 wpa_printf(MSG_ERROR, "No drivers enabled");
5955 wpa_supplicant_deinit(global);
5956 return NULL;
5957 }
faebdeaa 5958 global->drv_priv = os_calloc(global->drv_count, sizeof(void *));
ac305589
JM
5959 if (global->drv_priv == NULL) {
5960 wpa_supplicant_deinit(global);
5961 return NULL;
5962 }
ac305589 5963
9675ce35
JM
5964#ifdef CONFIG_WIFI_DISPLAY
5965 if (wifi_display_init(global) < 0) {
5966 wpa_printf(MSG_ERROR, "Failed to initialize Wi-Fi Display");
5967 wpa_supplicant_deinit(global);
5968 return NULL;
5969 }
5970#endif /* CONFIG_WIFI_DISPLAY */
5971
8c0d0ff2
JM
5972 eloop_register_timeout(WPA_SUPPLICANT_CLEANUP_INTERVAL, 0,
5973 wpas_periodic, global, NULL);
5974
6fc6879b
JM
5975 return global;
5976}
5977
5978
5979/**
5980 * wpa_supplicant_run - Run the %wpa_supplicant main event loop
5981 * @global: Pointer to global data from wpa_supplicant_init()
5982 * Returns: 0 after successful event loop run, -1 on failure
5983 *
5984 * This function starts the main event loop and continues running as long as
5985 * there are any remaining events. In most cases, this function is running as
5986 * long as the %wpa_supplicant process in still in use.
5987 */
5988int wpa_supplicant_run(struct wpa_global *global)
5989{
5990 struct wpa_supplicant *wpa_s;
5991
5992 if (global->params.daemonize &&
2e69bdd1
RM
5993 (wpa_supplicant_daemon(global->params.pid_file) ||
5994 eloop_sock_requeue()))
6fc6879b
JM
5995 return -1;
5996
2e997eec
RM
5997#ifdef CONFIG_MATCH_IFACE
5998 if (wpa_supplicant_match_existing(global))
5999 return -1;
6000#endif
6001
6fc6879b
JM
6002 if (global->params.wait_for_monitor) {
6003 for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next)
ede77701 6004 if (wpa_s->ctrl_iface && !wpa_s->p2p_mgmt)
6fc6879b
JM
6005 wpa_supplicant_ctrl_iface_wait(
6006 wpa_s->ctrl_iface);
6007 }
6008
0456ea16
JM
6009 eloop_register_signal_terminate(wpa_supplicant_terminate, global);
6010 eloop_register_signal_reconfig(wpa_supplicant_reconfig, global);
6fc6879b
JM
6011
6012 eloop_run();
6013
6014 return 0;
6015}
6016
6017
6018/**
6019 * wpa_supplicant_deinit - Deinitialize %wpa_supplicant
6020 * @global: Pointer to global data from wpa_supplicant_init()
6021 *
6022 * This function is called to deinitialize %wpa_supplicant and to free all
6023 * allocated resources. Remaining network interfaces will also be removed.
6024 */
6025void wpa_supplicant_deinit(struct wpa_global *global)
6026{
ac305589
JM
6027 int i;
6028
6fc6879b
JM
6029 if (global == NULL)
6030 return;
6031
8c0d0ff2
JM
6032 eloop_cancel_timeout(wpas_periodic, global, NULL);
6033
9675ce35
JM
6034#ifdef CONFIG_WIFI_DISPLAY
6035 wifi_display_deinit(global);
6036#endif /* CONFIG_WIFI_DISPLAY */
b22128ef 6037
6fc6879b 6038 while (global->ifaces)
df509539 6039 wpa_supplicant_remove_iface(global, global->ifaces, 1);
6fc6879b
JM
6040
6041 if (global->ctrl_iface)
6042 wpa_supplicant_global_ctrl_iface_deinit(global->ctrl_iface);
dc461de4
WS
6043
6044 wpas_notify_supplicant_deinitialized(global);
6fc6879b
JM
6045
6046 eap_peer_unregister_methods();
3ec97afe
JM
6047#ifdef CONFIG_AP
6048 eap_server_unregister_methods();
6049#endif /* CONFIG_AP */
6fc6879b 6050
c5121837 6051 for (i = 0; wpa_drivers[i] && global->drv_priv; i++) {
ac305589
JM
6052 if (!global->drv_priv[i])
6053 continue;
c5121837 6054 wpa_drivers[i]->global_deinit(global->drv_priv[i]);
ac305589
JM
6055 }
6056 os_free(global->drv_priv);
6057
d47fa330
JM
6058 random_deinit();
6059
6fc6879b
JM
6060 eloop_destroy();
6061
6062 if (global->params.pid_file) {
6063 os_daemonize_terminate(global->params.pid_file);
6064 os_free(global->params.pid_file);
6065 }
6066 os_free(global->params.ctrl_interface);
29257565 6067 os_free(global->params.ctrl_interface_group);
d27df100
JM
6068 os_free(global->params.override_driver);
6069 os_free(global->params.override_ctrl_interface);
2e997eec
RM
6070#ifdef CONFIG_MATCH_IFACE
6071 os_free(global->params.match_ifaces);
6072#endif /* CONFIG_MATCH_IFACE */
d4e59795
G
6073#ifdef CONFIG_P2P
6074 os_free(global->params.conf_p2p_dev);
6075#endif /* CONFIG_P2P */
6fc6879b 6076
af8a827b 6077 os_free(global->p2p_disallow_freq.range);
253f2e37 6078 os_free(global->p2p_go_avoid_freq.range);
01a57fe4 6079 os_free(global->add_psk);
6f3bc72b 6080
6fc6879b 6081 os_free(global);
daa70d49 6082 wpa_debug_close_syslog();
6fc6879b 6083 wpa_debug_close_file();
4f68895e 6084 wpa_debug_close_linux_tracing();
6fc6879b 6085}
611aea7d
JM
6086
6087
6088void wpa_supplicant_update_config(struct wpa_supplicant *wpa_s)
6089{
849b5dc7
JM
6090 if ((wpa_s->conf->changed_parameters & CFG_CHANGED_COUNTRY) &&
6091 wpa_s->conf->country[0] && wpa_s->conf->country[1]) {
6092 char country[3];
6093 country[0] = wpa_s->conf->country[0];
6094 country[1] = wpa_s->conf->country[1];
6095 country[2] = '\0';
6096 if (wpa_drv_set_country(wpa_s, country) < 0) {
6097 wpa_printf(MSG_ERROR, "Failed to set country code "
6098 "'%s'", country);
6099 }
6100 }
6101
306ae225
JM
6102 if (wpa_s->conf->changed_parameters & CFG_CHANGED_EXT_PW_BACKEND)
6103 wpas_init_ext_pw(wpa_s);
6104
bea48f77
JM
6105 if (wpa_s->conf->changed_parameters & CFG_CHANGED_SCHED_SCAN_PLANS)
6106 wpas_sched_scan_plans_set(wpa_s, wpa_s->conf->sched_scan_plans);
6107
3c7863f8
LD
6108 if (wpa_s->conf->changed_parameters & CFG_CHANGED_WOWLAN_TRIGGERS) {
6109 struct wpa_driver_capa capa;
6110 int res = wpa_drv_get_capa(wpa_s, &capa);
6111
6112 if (res == 0 && wpas_set_wowlan_triggers(wpa_s, &capa) < 0)
6113 wpa_printf(MSG_ERROR,
6114 "Failed to update wowlan_triggers to '%s'",
6115 wpa_s->conf->wowlan_triggers);
6116 }
6117
611aea7d
JM
6118#ifdef CONFIG_WPS
6119 wpas_wps_update_config(wpa_s);
6120#endif /* CONFIG_WPS */
b22128ef 6121 wpas_p2p_update_config(wpa_s);
611aea7d
JM
6122 wpa_s->conf->changed_parameters = 0;
6123}
2f9c6aa6
JM
6124
6125
e1117c1c 6126void add_freq(int *freqs, int *num_freqs, int freq)
0fb337c1
JM
6127{
6128 int i;
6129
6130 for (i = 0; i < *num_freqs; i++) {
6131 if (freqs[i] == freq)
6132 return;
6133 }
6134
6135 freqs[*num_freqs] = freq;
6136 (*num_freqs)++;
6137}
6138
6139
6140static int * get_bss_freqs_in_ess(struct wpa_supplicant *wpa_s)
6141{
6142 struct wpa_bss *bss, *cbss;
6143 const int max_freqs = 10;
6144 int *freqs;
6145 int num_freqs = 0;
6146
faebdeaa 6147 freqs = os_calloc(max_freqs + 1, sizeof(int));
0fb337c1
JM
6148 if (freqs == NULL)
6149 return NULL;
6150
6151 cbss = wpa_s->current_bss;
6152
6153 dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
6154 if (bss == cbss)
6155 continue;
6156 if (bss->ssid_len == cbss->ssid_len &&
6157 os_memcmp(bss->ssid, cbss->ssid, bss->ssid_len) == 0 &&
6158 wpa_blacklist_get(wpa_s, bss->bssid) == NULL) {
6159 add_freq(freqs, &num_freqs, bss->freq);
6160 if (num_freqs == max_freqs)
6161 break;
6162 }
6163 }
6164
6165 if (num_freqs == 0) {
6166 os_free(freqs);
6167 freqs = NULL;
6168 }
6169
6170 return freqs;
6171}
6172
6173
6174void wpas_connection_failed(struct wpa_supplicant *wpa_s, const u8 *bssid)
6175{
6176 int timeout;
6177 int count;
6178 int *freqs = NULL;
6179
6ac4b15e
JM
6180 wpas_connect_work_done(wpa_s);
6181
5fd9fb27
JM
6182 /*
6183 * Remove possible authentication timeout since the connection failed.
6184 */
6185 eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL);
6186
c2805909
JM
6187 /*
6188 * There is no point in blacklisting the AP if this event is
6189 * generated based on local request to disconnect.
6190 */
6191 if (wpa_s->own_disconnect_req) {
6192 wpa_s->own_disconnect_req = 0;
6193 wpa_dbg(wpa_s, MSG_DEBUG,
6194 "Ignore connection failure due to local request to disconnect");
6195 return;
6196 }
0cdb93fe 6197 if (wpa_s->disconnected) {
0cdb93fe
JM
6198 wpa_dbg(wpa_s, MSG_DEBUG, "Ignore connection failure "
6199 "indication since interface has been put into "
6200 "disconnected state");
6201 return;
6202 }
6203
0fb337c1
JM
6204 /*
6205 * Add the failed BSSID into the blacklist and speed up next scan
6206 * attempt if there could be other APs that could accept association.
6207 * The current blacklist count indicates how many times we have tried
6208 * connecting to this AP and multiple attempts mean that other APs are
6209 * either not available or has already been tried, so that we can start
6210 * increasing the delay here to avoid constant scanning.
6211 */
6212 count = wpa_blacklist_add(wpa_s, bssid);
6213 if (count == 1 && wpa_s->current_bss) {
6214 /*
6215 * This BSS was not in the blacklist before. If there is
6216 * another BSS available for the same ESS, we should try that
6217 * next. Otherwise, we may as well try this one once more
6218 * before allowing other, likely worse, ESSes to be considered.
6219 */
6220 freqs = get_bss_freqs_in_ess(wpa_s);
6221 if (freqs) {
f049052b
BG
6222 wpa_dbg(wpa_s, MSG_DEBUG, "Another BSS in this ESS "
6223 "has been seen; try it next");
0fb337c1
JM
6224 wpa_blacklist_add(wpa_s, bssid);
6225 /*
6226 * On the next scan, go through only the known channels
6227 * used in this ESS based on previous scans to speed up
6228 * common load balancing use case.
6229 */
6230 os_free(wpa_s->next_scan_freqs);
6231 wpa_s->next_scan_freqs = freqs;
6232 }
6233 }
6234
f1a52633
JM
6235 /*
6236 * Add previous failure count in case the temporary blacklist was
6237 * cleared due to no other BSSes being available.
6238 */
6239 count += wpa_s->extra_blacklist_count;
6240
dd579704
JM
6241 if (count > 3 && wpa_s->current_ssid) {
6242 wpa_printf(MSG_DEBUG, "Continuous association failures - "
6243 "consider temporary network disabling");
b19c098e 6244 wpas_auth_failed(wpa_s, "CONN_FAILED");
dd579704
JM
6245 }
6246
0fb337c1
JM
6247 switch (count) {
6248 case 1:
6249 timeout = 100;
6250 break;
6251 case 2:
6252 timeout = 500;
6253 break;
6254 case 3:
6255 timeout = 1000;
6256 break;
f1a52633 6257 case 4:
0fb337c1 6258 timeout = 5000;
f1a52633
JM
6259 break;
6260 default:
6261 timeout = 10000;
6262 break;
0fb337c1
JM
6263 }
6264
f1a52633
JM
6265 wpa_dbg(wpa_s, MSG_DEBUG, "Blacklist count %d --> request scan in %d "
6266 "ms", count, timeout);
6267
0fb337c1
JM
6268 /*
6269 * TODO: if more than one possible AP is available in scan results,
6270 * could try the other ones before requesting a new scan.
6271 */
6272 wpa_supplicant_req_scan(wpa_s, timeout / 1000,
6273 1000 * (timeout % 1000));
6274}
22628eca
JM
6275
6276
6277int wpas_driver_bss_selection(struct wpa_supplicant *wpa_s)
6278{
6279 return wpa_s->conf->ap_scan == 2 ||
6280 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_BSS_SELECTION);
6281}
d2118814
JM
6282
6283
6284#if defined(CONFIG_CTRL_IFACE) || defined(CONFIG_CTRL_IFACE_DBUS_NEW)
6285int wpa_supplicant_ctrl_iface_ctrl_rsp_handle(struct wpa_supplicant *wpa_s,
6286 struct wpa_ssid *ssid,
6287 const char *field,
6288 const char *value)
6289{
6290#ifdef IEEE8021X_EAPOL
6291 struct eap_peer_config *eap = &ssid->eap;
6292
6293 wpa_printf(MSG_DEBUG, "CTRL_IFACE: response handle field=%s", field);
6294 wpa_hexdump_ascii_key(MSG_DEBUG, "CTRL_IFACE: response value",
6295 (const u8 *) value, os_strlen(value));
6296
6297 switch (wpa_supplicant_ctrl_req_from_string(field)) {
6298 case WPA_CTRL_REQ_EAP_IDENTITY:
6299 os_free(eap->identity);
6300 eap->identity = (u8 *) os_strdup(value);
6301 eap->identity_len = os_strlen(value);
6302 eap->pending_req_identity = 0;
6303 if (ssid == wpa_s->current_ssid)
6304 wpa_s->reassociate = 1;
6305 break;
6306 case WPA_CTRL_REQ_EAP_PASSWORD:
19c48da0 6307 bin_clear_free(eap->password, eap->password_len);
d2118814
JM
6308 eap->password = (u8 *) os_strdup(value);
6309 eap->password_len = os_strlen(value);
6310 eap->pending_req_password = 0;
6311 if (ssid == wpa_s->current_ssid)
6312 wpa_s->reassociate = 1;
6313 break;
6314 case WPA_CTRL_REQ_EAP_NEW_PASSWORD:
19c48da0 6315 bin_clear_free(eap->new_password, eap->new_password_len);
d2118814
JM
6316 eap->new_password = (u8 *) os_strdup(value);
6317 eap->new_password_len = os_strlen(value);
6318 eap->pending_req_new_password = 0;
6319 if (ssid == wpa_s->current_ssid)
6320 wpa_s->reassociate = 1;
6321 break;
6322 case WPA_CTRL_REQ_EAP_PIN:
19c48da0 6323 str_clear_free(eap->pin);
d2118814
JM
6324 eap->pin = os_strdup(value);
6325 eap->pending_req_pin = 0;
6326 if (ssid == wpa_s->current_ssid)
6327 wpa_s->reassociate = 1;
6328 break;
6329 case WPA_CTRL_REQ_EAP_OTP:
19c48da0 6330 bin_clear_free(eap->otp, eap->otp_len);
d2118814
JM
6331 eap->otp = (u8 *) os_strdup(value);
6332 eap->otp_len = os_strlen(value);
6333 os_free(eap->pending_req_otp);
6334 eap->pending_req_otp = NULL;
6335 eap->pending_req_otp_len = 0;
6336 break;
6337 case WPA_CTRL_REQ_EAP_PASSPHRASE:
19c48da0
JM
6338 str_clear_free(eap->private_key_passwd);
6339 eap->private_key_passwd = os_strdup(value);
d2118814
JM
6340 eap->pending_req_passphrase = 0;
6341 if (ssid == wpa_s->current_ssid)
6342 wpa_s->reassociate = 1;
6343 break;
a5d44ac0 6344 case WPA_CTRL_REQ_SIM:
19c48da0 6345 str_clear_free(eap->external_sim_resp);
a5d44ac0 6346 eap->external_sim_resp = os_strdup(value);
ed9b1c16 6347 eap->pending_req_sim = 0;
a5d44ac0 6348 break;
a52410c2
JM
6349 case WPA_CTRL_REQ_PSK_PASSPHRASE:
6350 if (wpa_config_set(ssid, "psk", value, 0) < 0)
6351 return -1;
6352 ssid->mem_only_psk = 1;
6353 if (ssid->passphrase)
6354 wpa_config_update_psk(ssid);
6355 if (wpa_s->wpa_state == WPA_SCANNING && !wpa_s->scanning)
6356 wpa_supplicant_req_scan(wpa_s, 0, 0);
6357 break;
3c108b75
JM
6358 case WPA_CTRL_REQ_EXT_CERT_CHECK:
6359 if (eap->pending_ext_cert_check != PENDING_CHECK)
6360 return -1;
6361 if (os_strcmp(value, "good") == 0)
6362 eap->pending_ext_cert_check = EXT_CERT_CHECK_GOOD;
6363 else if (os_strcmp(value, "bad") == 0)
6364 eap->pending_ext_cert_check = EXT_CERT_CHECK_BAD;
6365 else
6366 return -1;
6367 break;
d2118814
JM
6368 default:
6369 wpa_printf(MSG_DEBUG, "CTRL_IFACE: Unknown field '%s'", field);
6370 return -1;
6371 }
6372
6373 return 0;
6374#else /* IEEE8021X_EAPOL */
6375 wpa_printf(MSG_DEBUG, "CTRL_IFACE: IEEE 802.1X not included");
6376 return -1;
6377#endif /* IEEE8021X_EAPOL */
6378}
6379#endif /* CONFIG_CTRL_IFACE || CONFIG_CTRL_IFACE_DBUS_NEW */
349493bd
JM
6380
6381
6382int wpas_network_disabled(struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid)
6383{
6384 int i;
6385 unsigned int drv_enc;
6386
44b9ea5b
JM
6387 if (wpa_s->p2p_mgmt)
6388 return 1; /* no normal network profiles on p2p_mgmt interface */
6389
349493bd
JM
6390 if (ssid == NULL)
6391 return 1;
6392
6393 if (ssid->disabled)
6394 return 1;
6395
9feadba1 6396 if (wpa_s->drv_capa_known)
349493bd
JM
6397 drv_enc = wpa_s->drv_enc;
6398 else
6399 drv_enc = (unsigned int) -1;
6400
6401 for (i = 0; i < NUM_WEP_KEYS; i++) {
6402 size_t len = ssid->wep_key_len[i];
6403 if (len == 0)
6404 continue;
6405 if (len == 5 && (drv_enc & WPA_DRIVER_CAPA_ENC_WEP40))
6406 continue;
6407 if (len == 13 && (drv_enc & WPA_DRIVER_CAPA_ENC_WEP104))
6408 continue;
6409 if (len == 16 && (drv_enc & WPA_DRIVER_CAPA_ENC_WEP128))
6410 continue;
6411 return 1; /* invalid WEP key */
6412 }
6413
9173b16f 6414 if (wpa_key_mgmt_wpa_psk(ssid->key_mgmt) && !ssid->psk_set &&
a52410c2 6415 (!ssid->passphrase || ssid->ssid_len != 0) && !ssid->ext_psk &&
a34ca59e 6416 !(wpa_key_mgmt_sae(ssid->key_mgmt) && ssid->sae_password) &&
a52410c2 6417 !ssid->mem_only_psk)
2518aad3
JM
6418 return 1;
6419
349493bd
JM
6420 return 0;
6421}
b9cfc09a
JJ
6422
6423
3f56a2b7
JM
6424int wpas_get_ssid_pmf(struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid)
6425{
6426#ifdef CONFIG_IEEE80211W
6427 if (ssid == NULL || ssid->ieee80211w == MGMT_FRAME_PROTECTION_DEFAULT) {
6428 if (wpa_s->conf->pmf == MGMT_FRAME_PROTECTION_OPTIONAL &&
6429 !(wpa_s->drv_enc & WPA_DRIVER_CAPA_ENC_BIP)) {
6430 /*
6431 * Driver does not support BIP -- ignore pmf=1 default
6432 * since the connection with PMF would fail and the
6433 * configuration does not require PMF to be enabled.
6434 */
6435 return NO_MGMT_FRAME_PROTECTION;
6436 }
6437
22950049
JM
6438 if (ssid &&
6439 (ssid->key_mgmt &
6440 ~(WPA_KEY_MGMT_NONE | WPA_KEY_MGMT_WPS |
6441 WPA_KEY_MGMT_IEEE8021X_NO_WPA)) == 0) {
6442 /*
6443 * Do not use the default PMF value for non-RSN networks
6444 * since PMF is available only with RSN and pmf=2
6445 * configuration would otherwise prevent connections to
6446 * all open networks.
6447 */
6448 return NO_MGMT_FRAME_PROTECTION;
6449 }
6450
3f56a2b7
JM
6451 return wpa_s->conf->pmf;
6452 }
6453
6454 return ssid->ieee80211w;
6455#else /* CONFIG_IEEE80211W */
6456 return NO_MGMT_FRAME_PROTECTION;
6457#endif /* CONFIG_IEEE80211W */
6458}
6459
6460
b9cfc09a
JJ
6461int wpas_is_p2p_prioritized(struct wpa_supplicant *wpa_s)
6462{
6463 if (wpa_s->global->conc_pref == WPA_CONC_PREF_P2P)
6464 return 1;
6465 if (wpa_s->global->conc_pref == WPA_CONC_PREF_STA)
6466 return 0;
6467 return -1;
6468}
00e5e3d5
JM
6469
6470
b19c098e 6471void wpas_auth_failed(struct wpa_supplicant *wpa_s, char *reason)
00e5e3d5
JM
6472{
6473 struct wpa_ssid *ssid = wpa_s->current_ssid;
6474 int dur;
4e1eae1d 6475 struct os_reltime now;
00e5e3d5
JM
6476
6477 if (ssid == NULL) {
6478 wpa_printf(MSG_DEBUG, "Authentication failure but no known "
6479 "SSID block");
6480 return;
6481 }
6482
6483 if (ssid->key_mgmt == WPA_KEY_MGMT_WPS)
6484 return;
6485
6486 ssid->auth_failures++;
cbf41ca7
SL
6487
6488#ifdef CONFIG_P2P
6489 if (ssid->p2p_group &&
6490 (wpa_s->p2p_in_provisioning || wpa_s->show_group_started)) {
6491 /*
6492 * Skip the wait time since there is a short timeout on the
6493 * connection to a P2P group.
6494 */
6495 return;
6496 }
6497#endif /* CONFIG_P2P */
6498
00e5e3d5
JM
6499 if (ssid->auth_failures > 50)
6500 dur = 300;
00e5e3d5 6501 else if (ssid->auth_failures > 10)
8a77f1be 6502 dur = 120;
00e5e3d5 6503 else if (ssid->auth_failures > 5)
8a77f1be
JM
6504 dur = 90;
6505 else if (ssid->auth_failures > 3)
6506 dur = 60;
6507 else if (ssid->auth_failures > 2)
00e5e3d5
JM
6508 dur = 30;
6509 else if (ssid->auth_failures > 1)
6510 dur = 20;
6511 else
6512 dur = 10;
6513
8a77f1be
JM
6514 if (ssid->auth_failures > 1 &&
6515 wpa_key_mgmt_wpa_ieee8021x(ssid->key_mgmt))
6516 dur += os_random() % (ssid->auth_failures * 10);
6517
4e1eae1d 6518 os_get_reltime(&now);
00e5e3d5
JM
6519 if (now.sec + dur <= ssid->disabled_until.sec)
6520 return;
6521
6522 ssid->disabled_until.sec = now.sec + dur;
6523
6524 wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_TEMP_DISABLED
b19c098e 6525 "id=%d ssid=\"%s\" auth_failures=%u duration=%d reason=%s",
00e5e3d5 6526 ssid->id, wpa_ssid_txt(ssid->ssid, ssid->ssid_len),
b19c098e 6527 ssid->auth_failures, dur, reason);
00e5e3d5
JM
6528}
6529
6530
6531void wpas_clear_temp_disabled(struct wpa_supplicant *wpa_s,
6532 struct wpa_ssid *ssid, int clear_failures)
6533{
6534 if (ssid == NULL)
6535 return;
6536
6537 if (ssid->disabled_until.sec) {
6538 wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_REENABLED
6539 "id=%d ssid=\"%s\"",
6540 ssid->id, wpa_ssid_txt(ssid->ssid, ssid->ssid_len));
6541 }
6542 ssid->disabled_until.sec = 0;
6543 ssid->disabled_until.usec = 0;
6544 if (clear_failures)
6545 ssid->auth_failures = 0;
6546}
6407f413
JM
6547
6548
6549int disallowed_bssid(struct wpa_supplicant *wpa_s, const u8 *bssid)
6550{
6551 size_t i;
6552
6553 if (wpa_s->disallow_aps_bssid == NULL)
6554 return 0;
6555
6556 for (i = 0; i < wpa_s->disallow_aps_bssid_count; i++) {
6557 if (os_memcmp(wpa_s->disallow_aps_bssid + i * ETH_ALEN,
6558 bssid, ETH_ALEN) == 0)
6559 return 1;
6560 }
6561
6562 return 0;
6563}
6564
6565
6566int disallowed_ssid(struct wpa_supplicant *wpa_s, const u8 *ssid,
6567 size_t ssid_len)
6568{
6569 size_t i;
6570
6571 if (wpa_s->disallow_aps_ssid == NULL || ssid == NULL)
6572 return 0;
6573
6574 for (i = 0; i < wpa_s->disallow_aps_ssid_count; i++) {
6575 struct wpa_ssid_value *s = &wpa_s->disallow_aps_ssid[i];
6576 if (ssid_len == s->ssid_len &&
6577 os_memcmp(ssid, s->ssid, ssid_len) == 0)
6578 return 1;
6579 }
6580
6581 return 0;
6582}
9796a86c
JM
6583
6584
6585/**
6586 * wpas_request_connection - Request a new connection
6587 * @wpa_s: Pointer to the network interface
6588 *
6589 * This function is used to request a new connection to be found. It will mark
6590 * the interface to allow reassociation and request a new scan to find a
6591 * suitable network to connect to.
6592 */
6593void wpas_request_connection(struct wpa_supplicant *wpa_s)
6594{
6595 wpa_s->normal_scans = 0;
5214f4fa 6596 wpa_s->scan_req = NORMAL_SCAN_REQ;
9796a86c
JM
6597 wpa_supplicant_reinit_autoscan(wpa_s);
6598 wpa_s->extra_blacklist_count = 0;
6599 wpa_s->disconnected = 0;
6600 wpa_s->reassociate = 1;
5e24beae
MH
6601
6602 if (wpa_supplicant_fast_associate(wpa_s) != 1)
6603 wpa_supplicant_req_scan(wpa_s, 0, 0);
0c5f01fd
B
6604 else
6605 wpa_s->reattach = 0;
9796a86c 6606}
36b9883d
DG
6607
6608
5f040be4
RP
6609/**
6610 * wpas_request_disconnection - Request disconnection
6611 * @wpa_s: Pointer to the network interface
6612 *
6613 * This function is used to request disconnection from the currently connected
6614 * network. This will stop any ongoing scans and initiate deauthentication.
6615 */
6616void wpas_request_disconnection(struct wpa_supplicant *wpa_s)
6617{
6618#ifdef CONFIG_SME
6619 wpa_s->sme.prev_bssid_set = 0;
6620#endif /* CONFIG_SME */
6621 wpa_s->reassociate = 0;
6622 wpa_s->disconnected = 1;
6623 wpa_supplicant_cancel_sched_scan(wpa_s);
6624 wpa_supplicant_cancel_scan(wpa_s);
6625 wpa_supplicant_deauthenticate(wpa_s, WLAN_REASON_DEAUTH_LEAVING);
6626 eloop_cancel_timeout(wpas_network_reenabled, wpa_s, NULL);
6627}
6628
6629
a0c90bb0
IP
6630void dump_freq_data(struct wpa_supplicant *wpa_s, const char *title,
6631 struct wpa_used_freq_data *freqs_data,
6632 unsigned int len)
6633{
6634 unsigned int i;
6635
6636 wpa_dbg(wpa_s, MSG_DEBUG, "Shared frequencies (len=%u): %s",
6637 len, title);
6638 for (i = 0; i < len; i++) {
6639 struct wpa_used_freq_data *cur = &freqs_data[i];
6640 wpa_dbg(wpa_s, MSG_DEBUG, "freq[%u]: %d, flags=0x%X",
6641 i, cur->freq, cur->flags);
6642 }
6643}
6644
6645
53c5dfc2
IP
6646/*
6647 * Find the operating frequencies of any of the virtual interfaces that
a0c90bb0
IP
6648 * are using the same radio as the current interface, and in addition, get
6649 * information about the interface types that are using the frequency.
53c5dfc2 6650 */
a0c90bb0
IP
6651int get_shared_radio_freqs_data(struct wpa_supplicant *wpa_s,
6652 struct wpa_used_freq_data *freqs_data,
6653 unsigned int len)
53c5dfc2 6654{
53c5dfc2
IP
6655 struct wpa_supplicant *ifs;
6656 u8 bssid[ETH_ALEN];
6657 int freq;
6658 unsigned int idx = 0, i;
6659
217cf499
JM
6660 wpa_dbg(wpa_s, MSG_DEBUG,
6661 "Determining shared radio frequencies (max len %u)", len);
a0c90bb0 6662 os_memset(freqs_data, 0, sizeof(struct wpa_used_freq_data) * len);
53c5dfc2 6663
0ad3b9c4
JM
6664 dl_list_for_each(ifs, &wpa_s->radio->ifaces, struct wpa_supplicant,
6665 radio_list) {
a0c90bb0
IP
6666 if (idx == len)
6667 break;
6668
53c5dfc2
IP
6669 if (ifs->current_ssid == NULL || ifs->assoc_freq == 0)
6670 continue;
6671
6672 if (ifs->current_ssid->mode == WPAS_MODE_AP ||
241c3333
MH
6673 ifs->current_ssid->mode == WPAS_MODE_P2P_GO ||
6674 ifs->current_ssid->mode == WPAS_MODE_MESH)
53c5dfc2
IP
6675 freq = ifs->current_ssid->frequency;
6676 else if (wpa_drv_get_bssid(ifs, bssid) == 0)
6677 freq = ifs->assoc_freq;
6678 else
6679 continue;
6680
6681 /* Hold only distinct freqs */
6682 for (i = 0; i < idx; i++)
a0c90bb0 6683 if (freqs_data[i].freq == freq)
53c5dfc2
IP
6684 break;
6685
6686 if (i == idx)
a0c90bb0
IP
6687 freqs_data[idx++].freq = freq;
6688
6689 if (ifs->current_ssid->mode == WPAS_MODE_INFRA) {
22264b3c 6690 freqs_data[i].flags |= ifs->current_ssid->p2p_group ?
a0c90bb0
IP
6691 WPA_FREQ_USED_BY_P2P_CLIENT :
6692 WPA_FREQ_USED_BY_INFRA_STATION;
6693 }
53c5dfc2 6694 }
217cf499 6695
a0c90bb0 6696 dump_freq_data(wpa_s, "completed iteration", freqs_data, idx);
53c5dfc2
IP
6697 return idx;
6698}
a0c90bb0
IP
6699
6700
6701/*
6702 * Find the operating frequencies of any of the virtual interfaces that
6703 * are using the same radio as the current interface.
6704 */
6705int get_shared_radio_freqs(struct wpa_supplicant *wpa_s,
6706 int *freq_array, unsigned int len)
6707{
6708 struct wpa_used_freq_data *freqs_data;
6709 int num, i;
6710
6711 os_memset(freq_array, 0, sizeof(int) * len);
6712
6713 freqs_data = os_calloc(len, sizeof(struct wpa_used_freq_data));
6714 if (!freqs_data)
6715 return -1;
6716
6717 num = get_shared_radio_freqs_data(wpa_s, freqs_data, len);
6718 for (i = 0; i < num; i++)
6719 freq_array[i] = freqs_data[i].freq;
6720
6721 os_free(freqs_data);
6722
6723 return num;
6724}
b361d580
AK
6725
6726
af041f99
AA
6727struct wpa_supplicant *
6728wpas_vendor_elem(struct wpa_supplicant *wpa_s, enum wpa_vendor_elem_frame frame)
6729{
6730 switch (frame) {
6731#ifdef CONFIG_P2P
6732 case VENDOR_ELEM_PROBE_REQ_P2P:
6733 case VENDOR_ELEM_PROBE_RESP_P2P:
6734 case VENDOR_ELEM_PROBE_RESP_P2P_GO:
6735 case VENDOR_ELEM_BEACON_P2P_GO:
6736 case VENDOR_ELEM_P2P_PD_REQ:
6737 case VENDOR_ELEM_P2P_PD_RESP:
6738 case VENDOR_ELEM_P2P_GO_NEG_REQ:
6739 case VENDOR_ELEM_P2P_GO_NEG_RESP:
6740 case VENDOR_ELEM_P2P_GO_NEG_CONF:
6741 case VENDOR_ELEM_P2P_INV_REQ:
6742 case VENDOR_ELEM_P2P_INV_RESP:
6743 case VENDOR_ELEM_P2P_ASSOC_REQ:
6744 case VENDOR_ELEM_P2P_ASSOC_RESP:
ba307f85 6745 return wpa_s->p2pdev;
af041f99
AA
6746#endif /* CONFIG_P2P */
6747 default:
6748 return wpa_s;
6749 }
6750}
6751
6752
6753void wpas_vendor_elem_update(struct wpa_supplicant *wpa_s)
6754{
6755 unsigned int i;
6756 char buf[30];
6757
6758 wpa_printf(MSG_DEBUG, "Update vendor elements");
6759
6760 for (i = 0; i < NUM_VENDOR_ELEM_FRAMES; i++) {
6761 if (wpa_s->vendor_elem[i]) {
6762 int res;
6763
6764 res = os_snprintf(buf, sizeof(buf), "frame[%u]", i);
6765 if (!os_snprintf_error(sizeof(buf), res)) {
6766 wpa_hexdump_buf(MSG_DEBUG, buf,
6767 wpa_s->vendor_elem[i]);
6768 }
6769 }
6770 }
6771
6772#ifdef CONFIG_P2P
6773 if (wpa_s->parent == wpa_s &&
6774 wpa_s->global->p2p &&
6775 !wpa_s->global->p2p_disabled)
6776 p2p_set_vendor_elems(wpa_s->global->p2p, wpa_s->vendor_elem);
6777#endif /* CONFIG_P2P */
6778}
6779
6780
6781int wpas_vendor_elem_remove(struct wpa_supplicant *wpa_s, int frame,
6782 const u8 *elem, size_t len)
6783{
6784 u8 *ie, *end;
6785
6786 ie = wpabuf_mhead_u8(wpa_s->vendor_elem[frame]);
6787 end = ie + wpabuf_len(wpa_s->vendor_elem[frame]);
6788
6789 for (; ie + 1 < end; ie += 2 + ie[1]) {
6790 if (ie + len > end)
6791 break;
6792 if (os_memcmp(ie, elem, len) != 0)
6793 continue;
6794
6795 if (wpabuf_len(wpa_s->vendor_elem[frame]) == len) {
6796 wpabuf_free(wpa_s->vendor_elem[frame]);
6797 wpa_s->vendor_elem[frame] = NULL;
6798 } else {
6799 os_memmove(ie, ie + len, end - (ie + len));
6800 wpa_s->vendor_elem[frame]->used -= len;
6801 }
6802 wpas_vendor_elem_update(wpa_s);
6803 return 0;
6804 }
6805
6806 return -1;
6807}
ea69d973
AS
6808
6809
6810struct hostapd_hw_modes * get_mode(struct hostapd_hw_modes *modes,
6811 u16 num_modes, enum hostapd_hw_mode mode)
6812{
6813 u16 i;
6814
6815 for (i = 0; i < num_modes; i++) {
6816 if (modes[i].mode == mode)
6817 return &modes[i];
6818 }
6819
6820 return NULL;
6821}
dd599908
AS
6822
6823
6824static struct
6825wpa_bss_tmp_disallowed * wpas_get_disallowed_bss(struct wpa_supplicant *wpa_s,
6826 const u8 *bssid)
6827{
6828 struct wpa_bss_tmp_disallowed *bss;
6829
6830 dl_list_for_each(bss, &wpa_s->bss_tmp_disallowed,
6831 struct wpa_bss_tmp_disallowed, list) {
6832 if (os_memcmp(bssid, bss->bssid, ETH_ALEN) == 0)
6833 return bss;
6834 }
6835
6836 return NULL;
6837}
6838
6839
b04854ce
AP
6840static int wpa_set_driver_tmp_disallow_list(struct wpa_supplicant *wpa_s)
6841{
6842 struct wpa_bss_tmp_disallowed *tmp;
6843 unsigned int num_bssid = 0;
6844 u8 *bssids;
6845 int ret;
6846
6847 bssids = os_malloc(dl_list_len(&wpa_s->bss_tmp_disallowed) * ETH_ALEN);
6848 if (!bssids)
6849 return -1;
6850 dl_list_for_each(tmp, &wpa_s->bss_tmp_disallowed,
6851 struct wpa_bss_tmp_disallowed, list) {
6852 os_memcpy(&bssids[num_bssid * ETH_ALEN], tmp->bssid,
6853 ETH_ALEN);
6854 num_bssid++;
6855 }
6856 ret = wpa_drv_set_bssid_blacklist(wpa_s, num_bssid, bssids);
6857 os_free(bssids);
6858 return ret;
6859}
6860
6861
6862static void wpa_bss_tmp_disallow_timeout(void *eloop_ctx, void *timeout_ctx)
6863{
6864 struct wpa_supplicant *wpa_s = eloop_ctx;
6865 struct wpa_bss_tmp_disallowed *tmp, *bss = timeout_ctx;
6866
6867 /* Make sure the bss is not already freed */
6868 dl_list_for_each(tmp, &wpa_s->bss_tmp_disallowed,
6869 struct wpa_bss_tmp_disallowed, list) {
6870 if (bss == tmp) {
6871 dl_list_del(&tmp->list);
6872 os_free(tmp);
6873 wpa_set_driver_tmp_disallow_list(wpa_s);
6874 break;
6875 }
6876 }
6877}
6878
6879
dd599908
AS
6880void wpa_bss_tmp_disallow(struct wpa_supplicant *wpa_s, const u8 *bssid,
6881 unsigned int sec)
6882{
6883 struct wpa_bss_tmp_disallowed *bss;
dd599908
AS
6884
6885 bss = wpas_get_disallowed_bss(wpa_s, bssid);
6886 if (bss) {
b04854ce
AP
6887 eloop_cancel_timeout(wpa_bss_tmp_disallow_timeout, wpa_s, bss);
6888 eloop_register_timeout(sec, 0, wpa_bss_tmp_disallow_timeout,
6889 wpa_s, bss);
dd599908
AS
6890 return;
6891 }
6892
6893 bss = os_malloc(sizeof(*bss));
6894 if (!bss) {
6895 wpa_printf(MSG_DEBUG,
6896 "Failed to allocate memory for temp disallow BSS");
6897 return;
6898 }
6899
dd599908
AS
6900 os_memcpy(bss->bssid, bssid, ETH_ALEN);
6901 dl_list_add(&wpa_s->bss_tmp_disallowed, &bss->list);
b04854ce
AP
6902 wpa_set_driver_tmp_disallow_list(wpa_s);
6903 eloop_register_timeout(sec, 0, wpa_bss_tmp_disallow_timeout,
6904 wpa_s, bss);
dd599908
AS
6905}
6906
6907
6908int wpa_is_bss_tmp_disallowed(struct wpa_supplicant *wpa_s, const u8 *bssid)
6909{
d010048c 6910 struct wpa_bss_tmp_disallowed *bss = NULL, *tmp, *prev;
dd599908 6911
d010048c
JM
6912 dl_list_for_each_safe(tmp, prev, &wpa_s->bss_tmp_disallowed,
6913 struct wpa_bss_tmp_disallowed, list) {
d010048c
JM
6914 if (os_memcmp(bssid, tmp->bssid, ETH_ALEN) == 0) {
6915 bss = tmp;
6916 break;
6917 }
6918 }
dd599908
AS
6919 if (!bss)
6920 return 0;
6921
d010048c 6922 return 1;
dd599908 6923}