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