18d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* 28d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * WPA Supplicant 3fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * Copyright (c) 2003-2014, Jouni Malinen <j@w1.fi> 48d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 5c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt * This software may be distributed under the terms of the BSD license. 6c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt * See README for more details. 78d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 88d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This file implements functions for registering and unregistering 98d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * %wpa_supplicant interfaces. In addition, this file contains number of 108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * functions for managing network connections. 118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "includes.h" 148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "common.h" 168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "crypto/random.h" 171f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#include "crypto/sha1.h" 188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "eapol_supp/eapol_supp_sm.h" 198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "eap_peer/eap.h" 2034af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt#include "eap_peer/eap_proxy.h" 218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "eap_server/eap_methods.h" 228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "rsn_supp/wpa.h" 238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "eloop.h" 248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "config.h" 2561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "utils/ext_password.h" 268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "l2_packet/l2_packet.h" 278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "wpa_supplicant_i.h" 288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "driver_i.h" 298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "ctrl_iface.h" 308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "pcsc_funcs.h" 318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "common/version.h" 328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "rsn_supp/preauth.h" 338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "rsn_supp/pmksa_cache.h" 348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "common/wpa_ctrl.h" 358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "common/ieee802_11_defs.h" 368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "p2p/p2p.h" 378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "blacklist.h" 388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "wpas_glue.h" 398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "wps_supplicant.h" 408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "ibss_rsn.h" 418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "sme.h" 421f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#include "gas_query.h" 438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "ap.h" 448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "p2p_supplicant.h" 4561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "wifi_display.h" 468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "notify.h" 478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "bgscan.h" 4804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#include "autoscan.h" 498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "bss.h" 508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "scan.h" 511f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#include "offchannel.h" 5204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#include "hs20_supplicant.h" 5344c957860ca714a86357591f39aff0bfa904c743Dmitry Shmidt#include "wnm_sta.h" 545a1480c7c46c4236d93bfd303dde32062bee04acDmitry Shmidt#include "wpas_kay.h" 558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char *wpa_supplicant_version = 578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"wpa_supplicant v" VERSION_STR "\n" 58fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt"Copyright (c) 2003-2014, Jouni Malinen <j@w1.fi> and contributors"; 598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char *wpa_supplicant_license = 61c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt"This software may be distributed under the terms of the BSD license.\n" 62c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt"See README for more details.\n" 638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef EAP_TLS_OPENSSL 648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\nThis product includes software developed by the OpenSSL Project\n" 658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"for use in the OpenSSL Toolkit (http://www.openssl.org/)\n" 668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* EAP_TLS_OPENSSL */ 678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt; 688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifndef CONFIG_NO_STDOUT_DEBUG 708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* Long text divided into parts in order to fit in C89 strings size limits. */ 718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char *wpa_supplicant_full_license1 = 72c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt""; 738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char *wpa_supplicant_full_license2 = 74c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt"This software may be distributed under the terms of the BSD license.\n" 758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\n" 768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"Redistribution and use in source and binary forms, with or without\n" 778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"modification, are permitted provided that the following conditions are\n" 788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"met:\n" 798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\n"; 808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char *wpa_supplicant_full_license3 = 818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"1. Redistributions of source code must retain the above copyright\n" 828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt" notice, this list of conditions and the following disclaimer.\n" 838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\n" 848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"2. Redistributions in binary form must reproduce the above copyright\n" 858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt" notice, this list of conditions and the following disclaimer in the\n" 868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt" documentation and/or other materials provided with the distribution.\n" 878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\n"; 888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char *wpa_supplicant_full_license4 = 898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"3. Neither the name(s) of the above-listed copyright holder(s) nor the\n" 908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt" names of its contributors may be used to endorse or promote products\n" 918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt" derived from this software without specific prior written permission.\n" 928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\n" 938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n" 948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n" 958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\n" 968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\n"; 978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char *wpa_supplicant_full_license5 = 988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\n" 998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\n" 1008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\n" 1018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\n" 1028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n" 1038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\n" 1048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n" 1058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"\n"; 1068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NO_STDOUT_DEBUG */ 1078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1080207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidtstruct wowlan_triggers *wpa_get_wowlan_triggers(const char *wowlan_triggers, 1090207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt struct wpa_driver_capa *capa); 1100207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt 1118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* Configure default/group WEP keys for static WEP */ 1128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_set_wep_keys(struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid) 1138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i, set = 0; 1158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < NUM_WEP_KEYS; i++) { 1178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->wep_key_len[i] == 0) 1188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 1198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt set = 1; 1218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_key(wpa_s, WPA_ALG_WEP, NULL, 1228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt i, i == ssid->wep_tx_keyidx, NULL, 0, 1238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid->wep_key[i], ssid->wep_key_len[i]); 1248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return set; 1278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13051b6ea882f234c14cd1fe1332a3840cf61fafccaDmitry Shmidtint wpa_supplicant_set_wpa_none_key(struct wpa_supplicant *wpa_s, 13151b6ea882f234c14cd1fe1332a3840cf61fafccaDmitry Shmidt struct wpa_ssid *ssid) 1328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 key[32]; 1348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t keylen; 1358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt enum wpa_alg alg; 1368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 seq[6] = { 0 }; 1378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* IBSS/WPA-None uses only one key (Group) for both receiving and 1398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * sending unicast and multicast packets. */ 1408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->mode != WPAS_MODE_IBSS) { 1428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Invalid mode %d (not " 1438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "IBSS/ad-hoc) for WPA-None", ssid->mode); 1448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 1458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!ssid->psk_set) { 1488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: No PSK configured for " 1498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "WPA-None"); 1508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 1518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt switch (wpa_s->group_cipher) { 1548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_CIPHER_CCMP: 1558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(key, ssid->psk, 16); 1568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt keylen = 16; 1578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt alg = WPA_ALG_CCMP; 1588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 15961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt case WPA_CIPHER_GCMP: 16061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt os_memcpy(key, ssid->psk, 16); 16161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt keylen = 16; 16261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt alg = WPA_ALG_GCMP; 16361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt break; 1648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_CIPHER_TKIP: 1658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* WPA-None uses the same Michael MIC key for both TX and RX */ 1668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(key, ssid->psk, 16 + 8); 1678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(key + 16 + 8, ssid->psk + 16, 8); 1688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt keylen = 32; 1698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt alg = WPA_ALG_TKIP; 1708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 1718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt default: 1728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Invalid group cipher %d for " 1738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "WPA-None", wpa_s->group_cipher); 1748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 1758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* TODO: should actually remember the previously used seq#, both for TX 1788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * and RX from each STA.. */ 1798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return wpa_drv_set_key(wpa_s, alg, NULL, 0, 1, seq, 6, key, keylen); 1818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_timeout(void *eloop_ctx, void *timeout_ctx) 1858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s = eloop_ctx; 1878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *bssid = wpa_s->bssid; 1888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (is_zero_ether_addr(bssid)) 1898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bssid = wpa_s->pending_bssid; 1908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "Authentication with " MACSTR " timed out.", 1918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt MAC2STR(bssid)); 1928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_blacklist_add(wpa_s, bssid); 1938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_notify_disassoc(wpa_s->wpa); 194d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_supplicant_deauthenticate(wpa_s, WLAN_REASON_DEAUTH_LEAVING); 1958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->reassociate = 1; 1968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 1988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * If we timed out, the AP or the local radio may be busy. 1998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * So, wait a second until scanning again. 2008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_req_scan(wpa_s, 1, 0); 2028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 2068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_req_auth_timeout - Schedule a timeout for authentication 2078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 2088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @sec: Number of seconds after which to time out authentication 2098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @usec: Number of microseconds after which to time out authentication 2108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 2118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to schedule a timeout for the current authentication 2128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * attempt. 2138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_req_auth_timeout(struct wpa_supplicant *wpa_s, 2158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int sec, int usec) 2168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 21768d0e3ed07847339aedfac8e02f50db68c702e52Dmitry Shmidt if (wpa_s->conf->ap_scan == 0 && 2188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED)) 2198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 2208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Setting authentication timeout: %d sec " 2228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "%d usec", sec, usec); 2238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL); 2248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_register_timeout(sec, usec, wpa_supplicant_timeout, wpa_s, NULL); 2258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 2298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_cancel_auth_timeout - Cancel authentication timeout 2308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 2318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 2328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to cancel authentication timeout scheduled with 2338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_req_auth_timeout() and it is called when authentication has 2348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * been completed. 2358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_cancel_auth_timeout(struct wpa_supplicant *wpa_s) 2378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Cancelling authentication timeout"); 2398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL); 2408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_blacklist_del(wpa_s, wpa_s->bssid); 2418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 2458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_initiate_eapol - Configure EAPOL state machine 2468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 2478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 2488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to configure EAPOL state machine based on the selected 2498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * authentication mode. 2508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_initiate_eapol(struct wpa_supplicant *wpa_s) 2528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef IEEE8021X_EAPOL 2548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct eapol_config eapol_conf; 2558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid = wpa_s->current_ssid; 2568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IBSS_RSN 2588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->mode == WPAS_MODE_IBSS && 2598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt != WPA_KEY_MGMT_NONE && 2608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt != WPA_KEY_MGMT_WPA_NONE) { 2618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 2628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * RSN IBSS authentication is per-STA and we can disable the 2638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * per-BSSID EAPOL authentication. 2648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_portControl(wpa_s->eapol, ForceAuthorized); 2668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_eap_success(wpa_s->eapol, TRUE); 2678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_eap_fail(wpa_s->eapol, FALSE); 2688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 2698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IBSS_RSN */ 2718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_eap_success(wpa_s->eapol, FALSE); 2738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_eap_fail(wpa_s->eapol, FALSE); 2748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE || 2768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt == WPA_KEY_MGMT_WPA_NONE) 2778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_portControl(wpa_s->eapol, ForceAuthorized); 2788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 2798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_portControl(wpa_s->eapol, Auto); 2808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memset(&eapol_conf, 0, sizeof(eapol_conf)); 2828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) { 2838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_conf.accept_802_1x_keys = 1; 2848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_conf.required_keys = 0; 2858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->eapol_flags & EAPOL_FLAG_REQUIRE_KEY_UNICAST) { 2868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_conf.required_keys |= EAPOL_REQUIRE_KEY_UNICAST; 2878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->eapol_flags & EAPOL_FLAG_REQUIRE_KEY_BROADCAST) { 2898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_conf.required_keys |= 2908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt EAPOL_REQUIRE_KEY_BROADCAST; 2918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 29368d0e3ed07847339aedfac8e02f50db68c702e52Dmitry Shmidt if (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED) 2948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_conf.required_keys = 0; 2958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 29668d0e3ed07847339aedfac8e02f50db68c702e52Dmitry Shmidt eapol_conf.fast_reauth = wpa_s->conf->fast_reauth; 2978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_conf.workaround = ssid->eap_workaround; 2988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_conf.eap_disabled = 2998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt !wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) && 3008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt != WPA_KEY_MGMT_IEEE8021X_NO_WPA && 3018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt != WPA_KEY_MGMT_WPS; 302051af73b8f8014eff33330aead0f36944b3403e6Dmitry Shmidt eapol_conf.external_sim = wpa_s->conf->external_sim; 303661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt eapol_conf.wps = wpa_s->key_mgmt == WPA_KEY_MGMT_WPS; 3048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_config(wpa_s->eapol, &ssid->eap, &eapol_conf); 3058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* IEEE8021X_EAPOL */ 3065a1480c7c46c4236d93bfd303dde32062bee04acDmitry Shmidt 3075a1480c7c46c4236d93bfd303dde32062bee04acDmitry Shmidt ieee802_1x_alloc_kay_sm(wpa_s, ssid); 3088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 3128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_set_non_wpa_policy - Set WPA parameters to non-WPA mode 3138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 3148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid: Configuration data for the network 3158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 3168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to configure WPA state machine and related parameters 3178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * to a mode where WPA is not enabled. This is called as part of the 3188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * authentication configuration when the selected network does not use WPA. 3198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 3208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_set_non_wpa_policy(struct wpa_supplicant *wpa_s, 3218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid) 3228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 3248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->key_mgmt & WPA_KEY_MGMT_WPS) 3268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_WPS; 3278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_NO_WPA) 3288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X_NO_WPA; 3298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 3308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_NONE; 3318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_ap_wpa_ie(wpa_s->wpa, NULL, 0); 3328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_ap_rsn_ie(wpa_s->wpa, NULL, 0); 3338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_assoc_wpa_ie(wpa_s->wpa, NULL, 0); 3348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pairwise_cipher = WPA_CIPHER_NONE; 3358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->group_cipher = WPA_CIPHER_NONE; 3368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->mgmt_group_cipher = 0; 3378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < NUM_WEP_KEYS; i++) { 3398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->wep_key_len[i] > 5) { 3408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pairwise_cipher = WPA_CIPHER_WEP104; 3418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->group_cipher = WPA_CIPHER_WEP104; 3428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 3438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (ssid->wep_key_len[i] > 0) { 3448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pairwise_cipher = WPA_CIPHER_WEP40; 3458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->group_cipher = WPA_CIPHER_WEP40; 3468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 3478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_RSN_ENABLED, 0); 3518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_KEY_MGMT, wpa_s->key_mgmt); 3528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_PAIRWISE, 3538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pairwise_cipher); 3548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_GROUP, wpa_s->group_cipher); 3558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 3568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_MGMT_GROUP, 3578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->mgmt_group_cipher); 3588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 3598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pmksa_cache_clear_current(wpa_s->wpa); 3618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36404949598a23f501be6eec21697465fd46a28840aDmitry Shmidtvoid free_hw_features(struct wpa_supplicant *wpa_s) 3651f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt{ 3661f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt int i; 3671f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpa_s->hw.modes == NULL) 3681f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return; 3691f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 3701f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt for (i = 0; i < wpa_s->hw.num_modes; i++) { 3711f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt os_free(wpa_s->hw.modes[i].channels); 3721f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt os_free(wpa_s->hw.modes[i].rates); 3731f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 3741f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 3751f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt os_free(wpa_s->hw.modes); 3761f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->hw.modes = NULL; 3771f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt} 3781f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 3791f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 3808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_cleanup(struct wpa_supplicant *wpa_s) 3818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3822e67f06149ff649fb6f8782bad041d3d9124685eDmitry Shmidt int i; 3832e67f06149ff649fb6f8782bad041d3d9124685eDmitry Shmidt 3848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bgscan_deinit(wpa_s); 38504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt autoscan_deinit(wpa_s); 3868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt scard_deinit(wpa_s->scard); 3878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->scard = NULL; 3888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_scard_ctx(wpa_s->wpa, NULL); 3898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_register_scard_ctx(wpa_s->eapol, NULL); 3908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt l2_packet_deinit(wpa_s->l2); 3918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->l2 = NULL; 3928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->l2_br) { 3938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt l2_packet_deinit(wpa_s->l2_br); 3948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->l2_br = NULL; 3958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->conf != NULL) { 3988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid; 3998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) 4008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_removed(wpa_s, ssid); 4018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 4028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(wpa_s->confname); 4048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->confname = NULL; 4058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4065d1c8ad11de48ba5e449e83e1e5dcd844e9c35d1Jouni Malinen os_free(wpa_s->confanother); 4075d1c8ad11de48ba5e449e83e1e5dcd844e9c35d1Jouni Malinen wpa_s->confanother = NULL; 4085d1c8ad11de48ba5e449e83e1e5dcd844e9c35d1Jouni Malinen 4098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_eapol(wpa_s->wpa, NULL); 4108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_deinit(wpa_s->eapol); 4118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->eapol = NULL; 4128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt rsn_preauth_deinit(wpa_s->wpa); 4148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_TDLS 4168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_tdls_deinit(wpa_s->wpa); 4178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_TDLS */ 4188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pmksa_candidate_free(wpa_s->wpa); 4208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_deinit(wpa_s->wpa); 4218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->wpa = NULL; 4228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_blacklist_clear(wpa_s); 4238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_bss_deinit(wpa_s); 4258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 426c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt wpa_supplicant_cancel_delayed_sched_scan(wpa_s); 4278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_cancel_scan(wpa_s); 4288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_cancel_auth_timeout(wpa_s); 4291f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt eloop_cancel_timeout(wpa_supplicant_stop_countermeasures, wpa_s, NULL); 4301f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#ifdef CONFIG_DELAYED_MIC_ERROR_REPORT 4311f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt eloop_cancel_timeout(wpa_supplicant_delayed_mic_error_report, 4321f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s, NULL); 4331f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#endif /* CONFIG_DELAYED_MIC_ERROR_REPORT */ 4348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_wps_deinit(wpa_s); 4368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_free(wpa_s->pending_eapol_rx); 4388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pending_eapol_rx = NULL; 4398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IBSS_RSN 4418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ibss_rsn_deinit(wpa_s->ibss_rsn); 4428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->ibss_rsn = NULL; 4438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IBSS_RSN */ 4448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sme_deinit(wpa_s); 4468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_AP 4488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_ap_deinit(wpa_s); 4498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_AP */ 4508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_p2p_deinit(wpa_s); 4528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4531f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#ifdef CONFIG_OFFCHANNEL 4541f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt offchannel_deinit(wpa_s); 4551f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#endif /* CONFIG_OFFCHANNEL */ 4561f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 4571f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_supplicant_cancel_sched_scan(wpa_s); 4581f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 4598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(wpa_s->next_scan_freqs); 4608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->next_scan_freqs = NULL; 4611f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 462fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_free(wpa_s->manual_scan_freqs); 463fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s->manual_scan_freqs = NULL; 464fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 465d11f019d62a42a8fc4c4d1f2ec17cf35b0763153Dmitry Shmidt os_free(wpa_s->manual_sched_scan_freqs); 466d11f019d62a42a8fc4c4d1f2ec17cf35b0763153Dmitry Shmidt wpa_s->manual_sched_scan_freqs = NULL; 467d11f019d62a42a8fc4c4d1f2ec17cf35b0763153Dmitry Shmidt 4681f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt gas_query_deinit(wpa_s->gas); 4691f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->gas = NULL; 4701f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 4711f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt free_hw_features(wpa_s); 47204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 4735a1480c7c46c4236d93bfd303dde32062bee04acDmitry Shmidt ieee802_1x_dealloc_kay_sm(wpa_s); 4745a1480c7c46c4236d93bfd303dde32062bee04acDmitry Shmidt 47504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt os_free(wpa_s->bssid_filter); 47604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->bssid_filter = NULL; 47704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 478d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt os_free(wpa_s->disallow_aps_bssid); 479d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->disallow_aps_bssid = NULL; 480d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt os_free(wpa_s->disallow_aps_ssid); 481d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->disallow_aps_ssid = NULL; 482d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 48304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wnm_bss_keep_alive_deinit(wpa_s); 48444c957860ca714a86357591f39aff0bfa904c743Dmitry Shmidt#ifdef CONFIG_WNM 48544c957860ca714a86357591f39aff0bfa904c743Dmitry Shmidt wnm_deallocate_memory(wpa_s); 48644c957860ca714a86357591f39aff0bfa904c743Dmitry Shmidt#endif /* CONFIG_WNM */ 48761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 48861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ext_password_deinit(wpa_s->ext_pw); 48961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_s->ext_pw = NULL; 49061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 49161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_free(wpa_s->last_gas_resp); 492fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s->last_gas_resp = NULL; 493fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpabuf_free(wpa_s->prev_gas_resp); 494fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s->prev_gas_resp = NULL; 4959bce59c7fef20e34a05f04d1e33a4076083dca0cDmitry Shmidt 4969bce59c7fef20e34a05f04d1e33a4076083dca0cDmitry Shmidt os_free(wpa_s->last_scan_res); 4979bce59c7fef20e34a05f04d1e33a4076083dca0cDmitry Shmidt wpa_s->last_scan_res = NULL; 498f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt 499f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#ifdef CONFIG_HS20 500684785c7f4e58498603a9a5ce26f933cc2557ebdDmitry Shmidt hs20_deinit(wpa_s); 501f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#endif /* CONFIG_HS20 */ 5022e67f06149ff649fb6f8782bad041d3d9124685eDmitry Shmidt 5032e67f06149ff649fb6f8782bad041d3d9124685eDmitry Shmidt for (i = 0; i < NUM_VENDOR_ELEM_FRAMES; i++) { 5042e67f06149ff649fb6f8782bad041d3d9124685eDmitry Shmidt wpabuf_free(wpa_s->vendor_elem[i]); 5052e67f06149ff649fb6f8782bad041d3d9124685eDmitry Shmidt wpa_s->vendor_elem[i] = NULL; 5062e67f06149ff649fb6f8782bad041d3d9124685eDmitry Shmidt } 5078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 5118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_clear_keys - Clear keys configured for the driver 5128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 5138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @addr: Previously used BSSID or %NULL if not available 5148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 5158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function clears the encryption keys that has been previously configured 5168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * for the driver. 5178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 5188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_clear_keys(struct wpa_supplicant *wpa_s, const u8 *addr) 5198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 520fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt int i, max; 5218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 523fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt max = 6; 524fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt#else /* CONFIG_IEEE80211W */ 525fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt max = 4; 5268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 527fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 528fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt /* MLME-DELETEKEYS.request */ 529fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt for (i = 0; i < max; i++) { 530fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (wpa_s->keys_cleared & BIT(i)) 531fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt continue; 532fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_drv_set_key(wpa_s, WPA_ALG_NONE, NULL, i, 0, NULL, 0, 533fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt NULL, 0); 534fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 535fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (!(wpa_s->keys_cleared & BIT(0)) && addr && 536fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt !is_zero_ether_addr(addr)) { 5378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_key(wpa_s, WPA_ALG_NONE, addr, 0, 0, NULL, 0, NULL, 5388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 0); 5398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* MLME-SETPROTECTION.request(None) */ 5408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_mlme_setprotection( 5418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s, addr, 5428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt MLME_SETPROTECTION_PROTECT_TYPE_NONE, 5438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt MLME_SETPROTECTION_KEY_TYPE_PAIRWISE); 5448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 545fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s->keys_cleared = (u32) -1; 5468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 5508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_state_txt - Get the connection state name as a text string 5518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @state: State (wpa_state; WPA_*) 5528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: The state name as a printable text string 5538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 5548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char * wpa_supplicant_state_txt(enum wpa_states state) 5558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 5568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt switch (state) { 5578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_DISCONNECTED: 5588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "DISCONNECTED"; 5598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_INACTIVE: 5608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "INACTIVE"; 5618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_INTERFACE_DISABLED: 5628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "INTERFACE_DISABLED"; 5638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_SCANNING: 5648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "SCANNING"; 5658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_AUTHENTICATING: 5668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "AUTHENTICATING"; 5678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_ASSOCIATING: 5688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "ASSOCIATING"; 5698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_ASSOCIATED: 5708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "ASSOCIATED"; 5718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_4WAY_HANDSHAKE: 5728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "4WAY_HANDSHAKE"; 5738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_GROUP_HANDSHAKE: 5748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "GROUP_HANDSHAKE"; 5758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case WPA_COMPLETED: 5768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "COMPLETED"; 5778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt default: 5788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "UNKNOWN"; 5798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 5808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_BGSCAN 5848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_start_bgscan(struct wpa_supplicant *wpa_s) 5868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 587b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt const char *name; 588b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt 589b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt if (wpa_s->current_ssid && wpa_s->current_ssid->bgscan) 590b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt name = wpa_s->current_ssid->bgscan; 591b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt else 592b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt name = wpa_s->conf->bgscan; 593a38abf9af7bec7e89dbfb39ac7bb77223fe47c72Dmitry Shmidt if (name == NULL || name[0] == '\0') 594b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt return; 5951f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpas_driver_bss_selection(wpa_s)) 5961f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return; 5978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->current_ssid == wpa_s->bgscan_ssid) 5988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 599a38abf9af7bec7e89dbfb39ac7bb77223fe47c72Dmitry Shmidt#ifdef CONFIG_P2P 600a38abf9af7bec7e89dbfb39ac7bb77223fe47c72Dmitry Shmidt if (wpa_s->p2p_group_interface != NOT_P2P_GROUP_INTERFACE) 601a38abf9af7bec7e89dbfb39ac7bb77223fe47c72Dmitry Shmidt return; 602a38abf9af7bec7e89dbfb39ac7bb77223fe47c72Dmitry Shmidt#endif /* CONFIG_P2P */ 6038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bgscan_deinit(wpa_s); 605b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt if (wpa_s->current_ssid) { 606b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt if (bgscan_init(wpa_s, wpa_s->current_ssid, name)) { 6078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Failed to initialize " 6088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "bgscan"); 6098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 6108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Live without bgscan; it is only used as a roaming 6118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * optimization, so the initial connection is not 6128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * affected. 6138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 61461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } else { 61561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt struct wpa_scan_results *scan_res; 6168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->bgscan_ssid = wpa_s->current_ssid; 61761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt scan_res = wpa_supplicant_get_scan_results(wpa_s, NULL, 61861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 0); 61961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (scan_res) { 62061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt bgscan_notify_scan(wpa_s, scan_res); 62161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_scan_results_free(scan_res); 62261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 62361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 6248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else 6258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->bgscan_ssid = NULL; 6268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_stop_bgscan(struct wpa_supplicant *wpa_s) 6308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->bgscan_ssid != NULL) { 6328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bgscan_deinit(wpa_s); 6338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->bgscan_ssid = NULL; 6348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 6358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_BGSCAN */ 6388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 64004949598a23f501be6eec21697465fd46a28840aDmitry Shmidtstatic void wpa_supplicant_start_autoscan(struct wpa_supplicant *wpa_s) 64104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 64204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (autoscan_init(wpa_s, 0)) 64304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Failed to initialize autoscan"); 64404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 64504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 64604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 64704949598a23f501be6eec21697465fd46a28840aDmitry Shmidtstatic void wpa_supplicant_stop_autoscan(struct wpa_supplicant *wpa_s) 64804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 64904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt autoscan_deinit(wpa_s); 65004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 65104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 65204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 65304949598a23f501be6eec21697465fd46a28840aDmitry Shmidtvoid wpa_supplicant_reinit_autoscan(struct wpa_supplicant *wpa_s) 65404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 65504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (wpa_s->wpa_state == WPA_DISCONNECTED || 65604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->wpa_state == WPA_SCANNING) { 65704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt autoscan_deinit(wpa_s); 65804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_start_autoscan(wpa_s); 65904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 66004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 66104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 66204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 6638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 6648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_set_state - Set current connection state 6658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 6668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @state: The new connection state 6678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 6688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is called whenever the connection state changes, e.g., 6698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * association is completed for WPA/WPA2 4-Way Handshake is started. 6708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 6718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_set_state(struct wpa_supplicant *wpa_s, 6728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt enum wpa_states state) 6738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt enum wpa_states old_state = wpa_s->wpa_state; 6758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "State: %s -> %s", 6778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_state_txt(wpa_s->wpa_state), 6788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_state_txt(state)); 6798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6809e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt if (state == WPA_INTERFACE_DISABLED) { 6819e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt /* Assure normal scan when interface is restored */ 6829e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt wpa_s->normal_scans = 0; 6839e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt } 6849e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt 685f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt if (state == WPA_COMPLETED) { 686fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpas_connect_work_done(wpa_s); 687f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt /* Reinitialize normal_scan counter */ 688f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt wpa_s->normal_scans = 0; 689f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt } 690fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 6918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (state != WPA_SCANNING) 6928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_notify_scanning(wpa_s, 0); 6938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (state == WPA_COMPLETED && wpa_s->new_connection) { 6958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid = wpa_s->current_ssid; 696700a137ab366edc72e371da68ba187b4717ee660Dmitry Shmidt#if defined(CONFIG_CTRL_IFACE) || !defined(CONFIG_NO_STDOUT_DEBUG) 6978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_CONNECTED "- Connection to " 6988f0dbf4c846369f18f4571cd997a6b4538d4e5dbDmitry Shmidt MACSTR " completed [id=%d id_str=%s]", 699f86232838cf712377867cb42417c1613ab5dc425Dmitry Shmidt MAC2STR(wpa_s->bssid), 7008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid ? ssid->id : -1, 7018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid && ssid->id_str ? ssid->id_str : ""); 7028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_CTRL_IFACE || !CONFIG_NO_STDOUT_DEBUG */ 70361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpas_clear_temp_disabled(wpa_s, ssid, 1); 704d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->extra_blacklist_count = 0; 7058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->new_connection = 0; 7068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_operstate(wpa_s, 1); 7078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifndef IEEE8021X_EAPOL 7088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_supp_port(wpa_s, 1); 7098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* IEEE8021X_EAPOL */ 7108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->after_wps = 0; 71168d0e3ed07847339aedfac8e02f50db68c702e52Dmitry Shmidt wpa_s->known_wps_freq = 0; 7128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_p2p_completed(wpa_s); 71304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 71404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt sme_sched_obss_scan(wpa_s, 1); 7158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (state == WPA_DISCONNECTED || state == WPA_ASSOCIATING || 7168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt state == WPA_ASSOCIATED) { 7178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->new_connection = 1; 7188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_operstate(wpa_s, 0); 7198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifndef IEEE8021X_EAPOL 7208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_supp_port(wpa_s, 0); 7218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* IEEE8021X_EAPOL */ 72204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt sme_sched_obss_scan(wpa_s, 0); 7238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 7248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->wpa_state = state; 7258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_BGSCAN 7278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (state == WPA_COMPLETED) 7288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_start_bgscan(wpa_s); 729fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt else if (state < WPA_ASSOCIATED) 7308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_stop_bgscan(wpa_s); 7318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_BGSCAN */ 7328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 73304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (state == WPA_AUTHENTICATING) 73404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_stop_autoscan(wpa_s); 73504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 73604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (state == WPA_DISCONNECTED || state == WPA_INACTIVE) 73704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_start_autoscan(wpa_s); 73804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 7398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->wpa_state != old_state) { 7408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_state_changed(wpa_s, wpa_s->wpa_state, old_state); 7418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 74243cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt /* 74343cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt * Notify the P2P Device interface about a state change in one 74443cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt * of the interfaces. 74543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt */ 74643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt wpas_p2p_indicate_state_change(wpa_s); 74743cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 7488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->wpa_state == WPA_COMPLETED || 7498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_state == WPA_COMPLETED) 7508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_auth_changed(wpa_s); 7518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 7528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 7538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_terminate_proc(struct wpa_global *global) 7568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 7578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int pending = 0; 7588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_WPS 7598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s = global->ifaces; 7608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (wpa_s) { 761fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_supplicant *next = wpa_s->next; 7626dc03bd757d3befd2c03a543a402338db03914d6Dmitry Shmidt if (wpas_wps_terminate_pending(wpa_s) == 1) 7636dc03bd757d3befd2c03a543a402338db03914d6Dmitry Shmidt pending = 1; 7645605286c30e1701491bd3af974ae423727750eddDmitry Shmidt#ifdef CONFIG_P2P 7655605286c30e1701491bd3af974ae423727750eddDmitry Shmidt if (wpa_s->p2p_group_interface != NOT_P2P_GROUP_INTERFACE || 7665605286c30e1701491bd3af974ae423727750eddDmitry Shmidt (wpa_s->current_ssid && wpa_s->current_ssid->p2p_group)) 7675605286c30e1701491bd3af974ae423727750eddDmitry Shmidt wpas_p2p_disconnect(wpa_s); 7685605286c30e1701491bd3af974ae423727750eddDmitry Shmidt#endif /* CONFIG_P2P */ 769fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s = next; 7708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 7718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_WPS */ 7728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pending) 7738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 7748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_terminate(); 7758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 7768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_terminate(int sig, void *signal_ctx) 7798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 7808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_global *global = signal_ctx; 7818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_terminate_proc(global); 7828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 7838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_clear_status(struct wpa_supplicant *wpa_s) 7868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 7878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt enum wpa_states old_state = wpa_s->wpa_state; 7888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pairwise_cipher = 0; 7908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->group_cipher = 0; 7918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->mgmt_group_cipher = 0; 7928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = 0; 7938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->wpa_state != WPA_INTERFACE_DISABLED) 79404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED); 7958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->wpa_state != old_state) 7978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_state_changed(wpa_s, wpa_s->wpa_state, old_state); 7988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 7998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 8028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_reload_configuration - Reload configuration data 8038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 8048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 on success or -1 if configuration parsing failed 8058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 8068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function can be used to request that the configuration data is reloaded 8078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * (e.g., after configuration file change). This function is reloading 8088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * configuration only for one interface, so this may need to be called multiple 8098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * times if %wpa_supplicant is controlling multiple interfaces and all 8108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * interfaces need reconfiguration. 8118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 8128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_reload_configuration(struct wpa_supplicant *wpa_s) 8138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 8148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_config *conf; 8158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int reconf_ctrl; 8168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int old_ap_scan; 8178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->confname == NULL) 8198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 82064f47c5c24428834677459e048420f86e3514c20Dmitry Shmidt conf = wpa_config_read(wpa_s->confname, NULL); 8218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (conf == NULL) { 8228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Failed to parse the configuration " 8238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "file '%s' - exiting", wpa_s->confname); 8248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 8258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 82664f47c5c24428834677459e048420f86e3514c20Dmitry Shmidt wpa_config_read(wpa_s->confanother, conf); 82764f47c5c24428834677459e048420f86e3514c20Dmitry Shmidt 8288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt conf->changed_parameters = (unsigned int) -1; 8298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt reconf_ctrl = !!conf->ctrl_interface != !!wpa_s->conf->ctrl_interface 8318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt || (conf->ctrl_interface && wpa_s->conf->ctrl_interface && 8328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strcmp(conf->ctrl_interface, 8338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->ctrl_interface) != 0); 8348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (reconf_ctrl && wpa_s->ctrl_iface) { 8368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_ctrl_iface_deinit(wpa_s->ctrl_iface); 8378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->ctrl_iface = NULL; 8388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_invalidate_cached_session(wpa_s->eapol); 8411f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpa_s->current_ssid) { 8421f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_supplicant_deauthenticate(wpa_s, 8431f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt WLAN_REASON_DEAUTH_LEAVING); 8441f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 8458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 8478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * TODO: should notify EAPOL SM about changes in opensc_engine_path, 8488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * pkcs11_engine_path, pkcs11_module_path. 8498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 8508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt)) { 8518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 8528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Clear forced success to clear EAP state for next 8538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * authentication. 8548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 8558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_eap_success(wpa_s->eapol, FALSE); 8568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_config(wpa_s->eapol, NULL, NULL); 8588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_config(wpa_s->wpa, NULL); 8591f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_sm_pmksa_cache_flush(wpa_s->wpa, NULL); 8608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_fast_reauth(wpa_s->wpa, wpa_s->conf->fast_reauth); 8618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt rsn_preauth_deinit(wpa_s->wpa); 8628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_ap_scan = wpa_s->conf->ap_scan; 8648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_config_free(wpa_s->conf); 8658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf = conf; 8668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (old_ap_scan != wpa_s->conf->ap_scan) 8678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_ap_scan_changed(wpa_s); 8688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (reconf_ctrl) 8708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->ctrl_iface = wpa_supplicant_ctrl_iface_init(wpa_s); 8718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_update_config(wpa_s); 8738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_clear_status(wpa_s); 87504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (wpa_supplicant_enabled_networks(wpa_s)) { 8768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->reassociate = 1; 8778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_req_scan(wpa_s, 0, 0); 8788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Reconfiguration completed"); 8808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 8818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 8828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_reconfig(int sig, void *signal_ctx) 8858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 8868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_global *global = signal_ctx; 8878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s; 8888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next) { 8898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Signal %d received - reconfiguring", 8908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sig); 8918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_reload_configuration(wpa_s) < 0) { 8928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_terminate_proc(global); 8938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 8968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int wpa_supplicant_suites_from_ai(struct wpa_supplicant *wpa_s, 8998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid, 9008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ie_data *ie) 9018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 9028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int ret = wpa_sm_parse_own_wpa_ie(wpa_s->wpa, ie); 9038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret) { 9048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret == -2) { 9058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Failed to parse WPA IE " 9068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "from association info"); 9078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 9098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Using WPA IE from AssocReq to set " 9128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "cipher suites"); 9138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!(ie->group_cipher & ssid->group_cipher)) { 9148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Driver used disabled group " 9158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "cipher 0x%x (mask 0x%x) - reject", 9168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie->group_cipher, ssid->group_cipher); 9178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 9188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!(ie->pairwise_cipher & ssid->pairwise_cipher)) { 9208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Driver used disabled pairwise " 9218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "cipher 0x%x (mask 0x%x) - reject", 9228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie->pairwise_cipher, ssid->pairwise_cipher); 9238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 9248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!(ie->key_mgmt & ssid->key_mgmt)) { 9268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Driver used disabled key " 9278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "management 0x%x (mask 0x%x) - reject", 9288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie->key_mgmt, ssid->key_mgmt); 9298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 9308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 9338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!(ie->capabilities & WPA_CAPABILITY_MFPC) && 934d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt (ssid->ieee80211w == MGMT_FRAME_PROTECTION_DEFAULT ? 935d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->conf->pmf : ssid->ieee80211w) == 936d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt MGMT_FRAME_PROTECTION_REQUIRED) { 9378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Driver associated with an AP " 9388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "that does not support management frame protection - " 9398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "reject"); 9408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 9418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 9438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 9458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 9468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 9498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_set_suites - Set authentication and encryption parameters 9508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 9518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @bss: Scan results for the selected BSS, or %NULL if not available 9528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid: Configuration data for the selected network 9538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_ie: Buffer for the WPA/RSN IE 9548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_ie_len: Maximum wpa_ie buffer size on input. This is changed to be the 9558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * used buffer length in case the functions returns success. 9568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 on success or -1 on failure 9578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 9588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to configure authentication and encryption parameters 9598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * based on the network configuration and scan result for the selected BSS (if 9608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * available). 9618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 9628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_set_suites(struct wpa_supplicant *wpa_s, 9638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_bss *bss, struct wpa_ssid *ssid, 9648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 *wpa_ie, size_t *wpa_ie_len) 9658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 9668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ie_data ie; 9678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int sel, proto; 968f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt const u8 *bss_wpa, *bss_rsn, *bss_osen; 9698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss) { 9718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_wpa = wpa_bss_get_vendor_ie(bss, WPA_IE_VENDOR_TYPE); 9728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_rsn = wpa_bss_get_ie(bss, WLAN_EID_RSN); 973f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt bss_osen = wpa_bss_get_vendor_ie(bss, OSEN_IE_VENDOR_TYPE); 9748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else 975f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt bss_wpa = bss_rsn = bss_osen = NULL; 9768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss_rsn && (ssid->proto & WPA_PROTO_RSN) && 9788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_parse_wpa_ie(bss_rsn, 2 + bss_rsn[1], &ie) == 0 && 9798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ie.group_cipher & ssid->group_cipher) && 9808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ie.pairwise_cipher & ssid->pairwise_cipher) && 9818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ie.key_mgmt & ssid->key_mgmt)) { 9828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using IEEE 802.11i/D9.0"); 9838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt proto = WPA_PROTO_RSN; 9848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (bss_wpa && (ssid->proto & WPA_PROTO_WPA) && 9858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_parse_wpa_ie(bss_wpa, 2 +bss_wpa[1], &ie) == 0 && 9868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ie.group_cipher & ssid->group_cipher) && 9878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ie.pairwise_cipher & ssid->pairwise_cipher) && 9888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ie.key_mgmt & ssid->key_mgmt)) { 9898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using IEEE 802.11i/D3.0"); 9908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt proto = WPA_PROTO_WPA; 991f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#ifdef CONFIG_HS20 992f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt } else if (bss_osen && (ssid->proto & WPA_PROTO_OSEN)) { 993f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "HS 2.0: using OSEN"); 994f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt /* TODO: parse OSEN element */ 995623d63a3a443027e50efdaaec027befcc3882527Dmitry Shmidt os_memset(&ie, 0, sizeof(ie)); 996f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt ie.group_cipher = WPA_CIPHER_CCMP; 997f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt ie.pairwise_cipher = WPA_CIPHER_CCMP; 998f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt ie.key_mgmt = WPA_KEY_MGMT_OSEN; 999f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt proto = WPA_PROTO_OSEN; 1000f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#endif /* CONFIG_HS20 */ 10018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (bss) { 10028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select WPA/RSN"); 10038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 10048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 1005f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt if (ssid->proto & WPA_PROTO_OSEN) 1006f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt proto = WPA_PROTO_OSEN; 1007f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt else if (ssid->proto & WPA_PROTO_RSN) 10088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt proto = WPA_PROTO_RSN; 10098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 10108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt proto = WPA_PROTO_WPA; 10118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_suites_from_ai(wpa_s, ssid, &ie) < 0) { 10128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memset(&ie, 0, sizeof(ie)); 10138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie.group_cipher = ssid->group_cipher; 10148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie.pairwise_cipher = ssid->pairwise_cipher; 10158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie.key_mgmt = ssid->key_mgmt; 10168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 10178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie.mgmt_group_cipher = 10188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid->ieee80211w != NO_MGMT_FRAME_PROTECTION ? 10198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WPA_CIPHER_AES_128_CMAC : 0; 10208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 10218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Set cipher suites " 10228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "based on configuration"); 10238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else 10248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt proto = ie.proto; 10258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Selected cipher suites: group %d " 10288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "pairwise %d key_mgmt %d proto %d", 10298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie.group_cipher, ie.pairwise_cipher, ie.key_mgmt, proto); 10308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 10318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->ieee80211w) { 10328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Selected mgmt group cipher %d", 10338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie.mgmt_group_cipher); 10348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 10368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10371f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->wpa_proto = proto; 10388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_PROTO, proto); 10398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_RSN_ENABLED, 1040f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt !!(ssid->proto & (WPA_PROTO_RSN | WPA_PROTO_OSEN))); 10418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss || !wpa_s->ap_ies_from_associnfo) { 10438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_sm_set_ap_wpa_ie(wpa_s->wpa, bss_wpa, 10448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_wpa ? 2 + bss_wpa[1] : 0) || 10458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_ap_rsn_ie(wpa_s->wpa, bss_rsn, 10468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_rsn ? 2 + bss_rsn[1] : 0)) 10478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 10488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sel = ie.group_cipher & ssid->group_cipher; 1051a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_s->group_cipher = wpa_pick_group_cipher(sel); 1052a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt if (wpa_s->group_cipher < 0) { 10538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select group " 10548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "cipher"); 10558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 10568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1057a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using GTK %s", 1058a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_cipher_txt(wpa_s->group_cipher)); 10598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sel = ie.pairwise_cipher & ssid->pairwise_cipher; 1061a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_s->pairwise_cipher = wpa_pick_pairwise_cipher(sel, 1); 1062a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt if (wpa_s->pairwise_cipher < 0) { 10638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select pairwise " 10648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "cipher"); 10658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 10668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1067a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using PTK %s", 1068a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_cipher_txt(wpa_s->pairwise_cipher)); 10698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sel = ie.key_mgmt & ssid->key_mgmt; 1071d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt#ifdef CONFIG_SAE 1072d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_SAE)) 1073d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt sel &= ~(WPA_KEY_MGMT_SAE | WPA_KEY_MGMT_FT_SAE); 1074d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt#endif /* CONFIG_SAE */ 10758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (0) { 10768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211R 10778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_FT_IEEE8021X) { 10788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_FT_IEEE8021X; 10798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FT/802.1X"); 10808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_FT_PSK) { 10818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_FT_PSK; 10828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FT/PSK"); 10838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211R */ 1084d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt#ifdef CONFIG_SAE 1085d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt } else if (sel & WPA_KEY_MGMT_SAE) { 1086d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_SAE; 1087d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using KEY_MGMT SAE"); 1088d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt } else if (sel & WPA_KEY_MGMT_FT_SAE) { 1089d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_FT_SAE; 1090d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RSN: using KEY_MGMT FT/SAE"); 1091d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt#endif /* CONFIG_SAE */ 10928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 10938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_IEEE8021X_SHA256) { 10948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X_SHA256; 10958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, 10968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "WPA: using KEY_MGMT 802.1X with SHA256"); 10978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_PSK_SHA256) { 10988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_PSK_SHA256; 10998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, 11008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "WPA: using KEY_MGMT PSK with SHA256"); 11018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 11028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_IEEE8021X) { 11038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X; 11048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT 802.1X"); 11058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_PSK) { 11068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_PSK; 11078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT WPA-PSK"); 11088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_WPA_NONE) { 11098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_WPA_NONE; 11108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT WPA-NONE"); 1111f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#ifdef CONFIG_HS20 1112f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt } else if (sel & WPA_KEY_MGMT_OSEN) { 1113f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt wpa_s->key_mgmt = WPA_KEY_MGMT_OSEN; 1114f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "HS 2.0: using KEY_MGMT OSEN"); 1115f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#endif /* CONFIG_HS20 */ 11168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 11178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to select " 11188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "authenticated key management type"); 11198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 11208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_KEY_MGMT, wpa_s->key_mgmt); 11238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_PAIRWISE, 11248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pairwise_cipher); 11258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_GROUP, wpa_s->group_cipher); 11268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 11288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sel = ie.mgmt_group_cipher; 1129d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if ((ssid->ieee80211w == MGMT_FRAME_PROTECTION_DEFAULT ? 1130d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->conf->pmf : ssid->ieee80211w) == NO_MGMT_FRAME_PROTECTION || 11318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt !(ie.capabilities & WPA_CAPABILITY_MFPC)) 11328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sel = 0; 11338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (sel & WPA_CIPHER_AES_128_CMAC) { 11348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->mgmt_group_cipher = WPA_CIPHER_AES_128_CMAC; 11358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher " 11368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "AES-128-CMAC"); 1137b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt } else if (sel & WPA_CIPHER_BIP_GMAC_128) { 1138b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt wpa_s->mgmt_group_cipher = WPA_CIPHER_BIP_GMAC_128; 1139b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher " 1140b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt "BIP-GMAC-128"); 1141b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt } else if (sel & WPA_CIPHER_BIP_GMAC_256) { 1142b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt wpa_s->mgmt_group_cipher = WPA_CIPHER_BIP_GMAC_256; 1143b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher " 1144b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt "BIP-GMAC-256"); 1145b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt } else if (sel & WPA_CIPHER_BIP_CMAC_256) { 1146b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt wpa_s->mgmt_group_cipher = WPA_CIPHER_BIP_CMAC_256; 1147b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: using MGMT group cipher " 1148b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt "BIP-CMAC-256"); 11498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 11508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->mgmt_group_cipher = 0; 11518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: not using MGMT group cipher"); 11528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_MGMT_GROUP, 11548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->mgmt_group_cipher); 1155d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_MFP, 1156d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt (ssid->ieee80211w == MGMT_FRAME_PROTECTION_DEFAULT ? 1157d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->conf->pmf : ssid->ieee80211w)); 11588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 11598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_sm_set_assoc_wpa_ie_default(wpa_s->wpa, wpa_ie, wpa_ie_len)) { 11618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to generate WPA IE"); 11628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 11638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11651f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpa_key_mgmt_wpa_psk(ssid->key_mgmt)) { 11668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_pmk(wpa_s->wpa, ssid->psk, PMK_LEN); 11671f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#ifndef CONFIG_NO_PBKDF2 11681f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (bss && ssid->bssid_set && ssid->ssid_len == 0 && 11691f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt ssid->passphrase) { 11701f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt u8 psk[PMK_LEN]; 117161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt pbkdf2_sha1(ssid->passphrase, bss->ssid, bss->ssid_len, 117261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 4096, psk, PMK_LEN); 11731f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_hexdump_key(MSG_MSGDUMP, "PSK (from passphrase)", 11741f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt psk, PMK_LEN); 11751f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_sm_set_pmk(wpa_s->wpa, psk, PMK_LEN); 11761f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 11771f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#endif /* CONFIG_NO_PBKDF2 */ 117861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#ifdef CONFIG_EXT_PASSWORD 117961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (ssid->ext_psk) { 118061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt struct wpabuf *pw = ext_password_get(wpa_s->ext_pw, 118161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->ext_psk); 118261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt char pw_str[64 + 1]; 118361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt u8 psk[PMK_LEN]; 118461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 118561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (pw == NULL) { 118661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "EXT PW: No PSK " 118761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "found from external storage"); 118861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 118961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 119061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 119161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wpabuf_len(pw) < 8 || wpabuf_len(pw) > 64) { 119261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "EXT PW: Unexpected " 119361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "PSK length %d in external storage", 119461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt (int) wpabuf_len(pw)); 119561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ext_password_free(pw); 119661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 119761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 119861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 119961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt os_memcpy(pw_str, wpabuf_head(pw), wpabuf_len(pw)); 120061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt pw_str[wpabuf_len(pw)] = '\0'; 120161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 120261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#ifndef CONFIG_NO_PBKDF2 120361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wpabuf_len(pw) >= 8 && wpabuf_len(pw) < 64 && bss) 120461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt { 120561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt pbkdf2_sha1(pw_str, bss->ssid, bss->ssid_len, 120661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 4096, psk, PMK_LEN); 120761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt os_memset(pw_str, 0, sizeof(pw_str)); 120861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_key(MSG_MSGDUMP, "PSK (from " 120961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "external passphrase)", 121061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt psk, PMK_LEN); 121161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_sm_set_pmk(wpa_s->wpa, psk, PMK_LEN); 121261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } else 121361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#endif /* CONFIG_NO_PBKDF2 */ 121461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wpabuf_len(pw) == 2 * PMK_LEN) { 121561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (hexstr2bin(pw_str, psk, PMK_LEN) < 0) { 121661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "EXT PW: " 121761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "Invalid PSK hex string"); 121861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt os_memset(pw_str, 0, sizeof(pw_str)); 121961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ext_password_free(pw); 122061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 122161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 122261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_sm_set_pmk(wpa_s->wpa, psk, PMK_LEN); 122361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } else { 122461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "EXT PW: No suitable " 122561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "PSK available"); 122661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt os_memset(pw_str, 0, sizeof(pw_str)); 122761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ext_password_free(pw); 122861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 122961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 123061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 123161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt os_memset(pw_str, 0, sizeof(pw_str)); 123261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ext_password_free(pw); 123361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 123461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#endif /* CONFIG_EXT_PASSWORD */ 12351f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } else 12368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_pmk_from_pmksa(wpa_s->wpa); 12378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 12398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 12408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1242444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidtstatic void wpas_ext_capab_byte(struct wpa_supplicant *wpa_s, u8 *pos, int idx) 1243a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt{ 1244444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos = 0x00; 1245a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 1246444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt switch (idx) { 1247444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt case 0: /* Bits 0-7 */ 1248444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt break; 1249444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt case 1: /* Bits 8-15 */ 1250444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt break; 1251444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt case 2: /* Bits 16-23 */ 1252444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt#ifdef CONFIG_WNM 1253444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos |= 0x02; /* Bit 17 - WNM-Sleep Mode */ 1254444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos |= 0x08; /* Bit 19 - BSS Transition */ 1255444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt#endif /* CONFIG_WNM */ 1256444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt break; 1257444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt case 3: /* Bits 24-31 */ 1258444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt#ifdef CONFIG_WNM 1259444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos |= 0x02; /* Bit 25 - SSID List */ 1260444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt#endif /* CONFIG_WNM */ 1261a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt#ifdef CONFIG_INTERWORKING 1262444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt if (wpa_s->conf->interworking) 1263444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos |= 0x80; /* Bit 31 - Interworking */ 1264a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt#endif /* CONFIG_INTERWORKING */ 1265444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt break; 1266444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt case 4: /* Bits 32-39 */ 1267051af73b8f8014eff33330aead0f36944b3403e6Dmitry Shmidt#ifdef CONFIG_INTERWORKING 1268fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (wpa_s->drv_flags / WPA_DRIVER_FLAGS_QOS_MAPPING) 1269fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt *pos |= 0x01; /* Bit 32 - QoS Map */ 1270051af73b8f8014eff33330aead0f36944b3403e6Dmitry Shmidt#endif /* CONFIG_INTERWORKING */ 1271444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt break; 1272444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt case 5: /* Bits 40-47 */ 1273f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#ifdef CONFIG_HS20 1274f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt if (wpa_s->conf->hs20) 1275f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt *pos |= 0x40; /* Bit 46 - WNM-Notification */ 1276f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt#endif /* CONFIG_HS20 */ 1277444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt break; 1278444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt case 6: /* Bits 48-55 */ 1279444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt break; 1280444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt } 1281444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt} 1282a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 1283a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 128409f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidtint wpas_build_ext_capab(struct wpa_supplicant *wpa_s, u8 *buf, size_t buflen) 1285444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt{ 1286444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt u8 *pos = buf; 1287f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt u8 len = 6, i; 1288444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt 1289444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt if (len < wpa_s->extended_capa_len) 1290444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt len = wpa_s->extended_capa_len; 129109f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt if (buflen < (size_t) len + 2) { 129209f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt wpa_printf(MSG_INFO, 129309f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt "Not enough room for building extended capabilities element"); 129409f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt return -1; 129509f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt } 1296a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 1297a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt *pos++ = WLAN_EID_EXT_CAPAB; 1298444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos++ = len; 1299444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt for (i = 0; i < len; i++, pos++) { 1300444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt wpas_ext_capab_byte(wpa_s, pos, i); 1301444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt 1302444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt if (i < wpa_s->extended_capa_len) { 1303444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos &= ~wpa_s->extended_capa_mask[i]; 1304444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt *pos |= wpa_s->extended_capa[i]; 1305444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt } 1306444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt } 1307444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt 1308444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt while (len > 0 && buf[1 + len] == 0) { 1309444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt len--; 1310444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt buf[1] = len; 1311444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt } 1312444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt if (len == 0) 1313444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt return 0; 1314a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 1315444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt return 2 + len; 1316a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt} 1317a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 1318a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 1319fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtstatic int wpas_valid_bss(struct wpa_supplicant *wpa_s, 1320fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_bss *test_bss) 1321fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 1322fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_bss *bss; 1323fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1324fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) { 1325fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (bss == test_bss) 1326fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return 1; 1327fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 1328fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1329fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return 0; 1330fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 1331fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1332fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1333fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtstatic int wpas_valid_ssid(struct wpa_supplicant *wpa_s, 1334fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_ssid *test_ssid) 1335fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 1336fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_ssid *ssid; 1337fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1338fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 1339fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (ssid == test_ssid) 1340fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return 1; 1341fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 1342fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1343fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return 0; 1344fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 1345fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1346fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1347fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtint wpas_valid_bss_ssid(struct wpa_supplicant *wpa_s, struct wpa_bss *test_bss, 1348fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_ssid *test_ssid) 1349fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 1350fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (test_bss && !wpas_valid_bss(wpa_s, test_bss)) 1351fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return 0; 1352fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1353fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return test_ssid == NULL || wpas_valid_ssid(wpa_s, test_ssid); 1354fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 1355fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1356fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1357fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtvoid wpas_connect_work_free(struct wpa_connect_work *cwork) 1358fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 1359fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (cwork == NULL) 1360fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 1361fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_free(cwork); 1362fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 1363fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1364fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1365fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtvoid wpas_connect_work_done(struct wpa_supplicant *wpa_s) 1366fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 1367fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_connect_work *cwork; 1368fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_radio_work *work = wpa_s->connect_work; 1369fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1370fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (!work) 1371fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 1372fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1373fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s->connect_work = NULL; 1374fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt cwork = work->ctx; 1375fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->ctx = NULL; 1376fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpas_connect_work_free(cwork); 1377fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt radio_work_done(work); 1378fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 1379fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1380fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1381661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidtint wpas_update_random_addr(struct wpa_supplicant *wpa_s, int style) 1382661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt{ 1383661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt struct os_reltime now; 1384661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt u8 addr[ETH_ALEN]; 1385661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1386661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt os_get_reltime(&now); 1387661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpa_s->last_mac_addr_style == style && 1388661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_s->last_mac_addr_change.sec != 0 && 1389661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt !os_reltime_expired(&now, &wpa_s->last_mac_addr_change, 1390661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_s->conf->rand_addr_lifetime)) { 1391661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, 1392661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt "Previously selected random MAC address has not yet expired"); 1393661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return 0; 1394661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } 1395661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1396661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt switch (style) { 1397661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt case 1: 1398661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (random_mac_addr(addr) < 0) 1399661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return -1; 1400661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt break; 1401661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt case 2: 1402661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt os_memcpy(addr, wpa_s->perm_addr, ETH_ALEN); 1403661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (random_mac_addr_keep_oui(addr) < 0) 1404661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return -1; 1405661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt break; 1406661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt default: 1407661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return -1; 1408661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } 1409661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1410661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpa_drv_set_mac_addr(wpa_s, addr) < 0) { 1411661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, 1412661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt "Failed to set random MAC address"); 1413661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return -1; 1414661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } 1415661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1416661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt os_get_reltime(&wpa_s->last_mac_addr_change); 1417661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_s->mac_addr_changed = 1; 1418661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_s->last_mac_addr_style = style; 1419661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1420661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpa_supplicant_update_mac_addr(wpa_s) < 0) { 1421661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, 1422661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt "Could not update MAC address information"); 1423661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return -1; 1424661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } 1425661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1426661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "Using random MAC address " MACSTR, 1427661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt MAC2STR(addr)); 1428661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1429661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return 0; 1430661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt} 1431661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1432661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1433661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidtint wpas_update_random_addr_disassoc(struct wpa_supplicant *wpa_s) 1434661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt{ 1435661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpa_s->wpa_state >= WPA_AUTHENTICATING || 1436661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt !wpa_s->conf->preassoc_mac_addr) 1437661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return 0; 1438661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1439661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return wpas_update_random_addr(wpa_s, wpa_s->conf->preassoc_mac_addr); 1440661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt} 1441661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1442661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1443fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtstatic void wpas_start_assoc_cb(struct wpa_radio_work *work, int deinit); 1444fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 14458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 14468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_associate - Request association 14478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 14488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @bss: Scan results for the selected BSS, or %NULL if not available 14498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid: Configuration data for the selected network 14508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 14518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to request %wpa_supplicant to associate with a BSS. 14528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 14538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_associate(struct wpa_supplicant *wpa_s, 14548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_bss *bss, struct wpa_ssid *ssid) 14558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1456fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_connect_work *cwork; 1457661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt int rand_style; 1458661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1459661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (ssid->mac_addr == -1) 1460661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt rand_style = wpa_s->conf->mac_addr; 1461661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt else 1462661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt rand_style = ssid->mac_addr; 1463661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 1464661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpa_s->last_ssid == ssid) { 1465661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Re-association to the same ESS"); 1466661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } else if (rand_style > 0) { 1467661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpas_update_random_addr(wpa_s, rand_style) < 0) 1468661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return; 1469661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_sm_pmksa_cache_flush(wpa_s->wpa, ssid); 1470661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } else if (wpa_s->mac_addr_changed) { 1471661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpa_drv_set_mac_addr(wpa_s, NULL) < 0) { 1472661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, 1473661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt "Could not restore permanent MAC address"); 1474661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return; 1475661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } 1476661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_s->mac_addr_changed = 0; 1477661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt if (wpa_supplicant_update_mac_addr(wpa_s) < 0) { 1478661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, 1479661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt "Could not update MAC address information"); 1480661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt return; 1481661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } 1482661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "Using permanent MAC address"); 1483661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt } 1484661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_s->last_ssid = ssid; 14858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 14868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IBSS_RSN 14878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ibss_rsn_deinit(wpa_s->ibss_rsn); 14888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->ibss_rsn = NULL; 14898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IBSS_RSN */ 14908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 14918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->mode == WPAS_MODE_AP || ssid->mode == WPAS_MODE_P2P_GO || 14928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION) { 14938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_AP 14948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_AP)) { 14958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "Driver does not support AP " 14968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "mode"); 14978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 14988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1499aa532510a7b8c4da2d7d6e2c11dda5db840894e4Dmitry Shmidt if (wpa_supplicant_create_ap(wpa_s, ssid) < 0) { 1500aa532510a7b8c4da2d7d6e2c11dda5db840894e4Dmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED); 1501391c59f0632df8db1c325da1d31d479b2eedce45Dmitry Shmidt if (ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION) 1502391c59f0632df8db1c325da1d31d479b2eedce45Dmitry Shmidt wpas_p2p_ap_setup_failed(wpa_s); 1503aa532510a7b8c4da2d7d6e2c11dda5db840894e4Dmitry Shmidt return; 1504aa532510a7b8c4da2d7d6e2c11dda5db840894e4Dmitry Shmidt } 15058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->current_bss = bss; 15068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* CONFIG_AP */ 15078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "AP mode support not included in " 15088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "the build"); 15098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_AP */ 15108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 15118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 15128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 15138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_TDLS 15148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss) 15158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_tdls_ap_ies(wpa_s->wpa, (const u8 *) (bss + 1), 15168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss->ie_len); 15178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_TDLS */ 15188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 15198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_SME) && 15208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid->mode == IEEE80211_MODE_INFRA) { 15218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sme_authenticate(wpa_s, bss, ssid); 15228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 15238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 15248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1525fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (wpa_s->connect_work) { 1526fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Reject wpa_supplicant_associate() call since connect_work exist"); 1527fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 1528fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 1529fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1530f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt if (radio_work_pending(wpa_s, "connect")) { 1531f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Reject wpa_supplicant_associate() call since pending work exist"); 1532f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt return; 1533f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt } 1534f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt 1535fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt cwork = os_zalloc(sizeof(*cwork)); 1536fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (cwork == NULL) 1537fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 1538fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1539fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt cwork->bss = bss; 1540fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt cwork->ssid = ssid; 1541fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1542fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (radio_add_work(wpa_s, bss ? bss->freq : 0, "connect", 1, 1543fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpas_start_assoc_cb, cwork) < 0) { 1544fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_free(cwork); 1545fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 1546fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 1547fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1548fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1549fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtstatic void wpas_start_assoc_cb(struct wpa_radio_work *work, int deinit) 1550fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 1551fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_connect_work *cwork = work->ctx; 1552fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_bss *bss = cwork->bss; 1553fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_ssid *ssid = cwork->ssid; 1554fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_supplicant *wpa_s = work->wpa_s; 1555fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt u8 wpa_ie[200]; 1556fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt size_t wpa_ie_len; 1557fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt int use_crypt, ret, i, bssid_changed; 1558fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt int algs = WPA_AUTH_ALG_OPEN; 1559fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt unsigned int cipher_pairwise, cipher_group; 1560fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_driver_associate_params params; 1561fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt int wep_keys_set = 0; 1562fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt int assoc_failed = 0; 1563fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_ssid *old_ssid; 1564fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt#ifdef CONFIG_HT_OVERRIDES 1565fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct ieee80211_ht_capabilities htcaps; 1566fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct ieee80211_ht_capabilities htcaps_mask; 1567fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt#endif /* CONFIG_HT_OVERRIDES */ 1568b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt#ifdef CONFIG_VHT_OVERRIDES 1569b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt struct ieee80211_vht_capabilities vhtcaps; 1570b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt struct ieee80211_vht_capabilities vhtcaps_mask; 1571b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt#endif /* CONFIG_VHT_OVERRIDES */ 1572fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1573fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (deinit) { 1574bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt if (work->started) { 1575bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt wpa_s->connect_work = NULL; 1576bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt 1577bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt /* cancel possible auth. timeout */ 1578bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, 1579bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt NULL); 1580bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt } 1581fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpas_connect_work_free(cwork); 1582fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 1583fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 1584fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 1585fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s->connect_work = work; 1586fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 15872e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt if (cwork->bss_removed || !wpas_valid_bss_ssid(wpa_s, bss, ssid)) { 1588fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "BSS/SSID entry for association not valid anymore - drop connection attempt"); 1589fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpas_connect_work_done(wpa_s); 1590fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 1591fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 1592fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 15938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memset(¶ms, 0, sizeof(params)); 15948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->reassociate = 0; 1595344abd362cfe2d03ed956666527352826b67bde5Dmitry Shmidt wpa_s->eap_expected_failure = 0; 15961f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (bss && !wpas_driver_bss_selection(wpa_s)) { 15978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211R 15988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *ie, *md = NULL; 15998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211R */ 16008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "Trying to associate with " MACSTR 16018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt " (SSID='%s' freq=%d MHz)", MAC2STR(bss->bssid), 16028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ssid_txt(bss->ssid, bss->ssid_len), bss->freq); 16038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bssid_changed = !is_zero_ether_addr(wpa_s->bssid); 16048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memset(wpa_s->bssid, 0, ETH_ALEN); 16058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(wpa_s->pending_bssid, bss->bssid, ETH_ALEN); 16068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bssid_changed) 16078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_bssid_changed(wpa_s); 16088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211R 16098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie = wpa_bss_get_ie(bss, WLAN_EID_MOBILITY_DOMAIN); 16108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ie && ie[1] >= MOBILITY_DOMAIN_ID_LEN) 16118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt md = ie + 2; 16128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_ft_params(wpa_s->wpa, ie, ie ? 2 + ie[1] : 0); 16138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (md) { 16148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Prepare for the next transition */ 16158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ft_prepare_auth_request(wpa_s->wpa, ie); 16168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 16178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211R */ 16188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_WPS 16198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if ((ssid->ssid == NULL || ssid->ssid_len == 0) && 16208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->ap_scan == 2 && 16218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ssid->key_mgmt & WPA_KEY_MGMT_WPS)) { 16228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Use ap_scan==1 style network selection to find the network 16238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 16242e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt wpas_connect_work_done(wpa_s); 1625d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->scan_req = MANUAL_SCAN_REQ; 16268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->reassociate = 1; 16278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_req_scan(wpa_s, 0, 0); 16288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 16298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_WPS */ 16308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 16318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "Trying to associate with SSID '%s'", 16328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 16338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memset(wpa_s->pending_bssid, 0, ETH_ALEN); 16348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 16351f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_supplicant_cancel_sched_scan(wpa_s); 16368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_cancel_scan(wpa_s); 16378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 16388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Starting new association, so clear the possibly used WPA IE from the 16398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * previous association. */ 16408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_assoc_wpa_ie(wpa_s->wpa, NULL, 0); 16418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 16428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef IEEE8021X_EAPOL 16438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_NO_WPA) { 16448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->leap) { 16458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->non_leap == 0) 16468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt algs = WPA_AUTH_ALG_LEAP; 16478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 16488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt algs |= WPA_AUTH_ALG_LEAP; 16498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 16508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 16518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* IEEE8021X_EAPOL */ 16528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Automatic auth_alg selection: 0x%x", algs); 16538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->auth_alg) { 16548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt algs = ssid->auth_alg; 16558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Overriding auth_alg selection: " 16568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "0x%x", algs); 16578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 16588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 16598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss && (wpa_bss_get_vendor_ie(bss, WPA_IE_VENDOR_TYPE) || 16608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_bss_get_ie(bss, WLAN_EID_RSN)) && 16611f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_key_mgmt_wpa(ssid->key_mgmt)) { 16628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int try_opportunistic; 1663d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt try_opportunistic = (ssid->proactive_key_caching < 0 ? 1664d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->conf->okc : 1665d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt ssid->proactive_key_caching) && 16668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (ssid->proto & WPA_PROTO_RSN); 16678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pmksa_cache_set_current(wpa_s->wpa, NULL, bss->bssid, 1668700a137ab366edc72e371da68ba187b4717ee660Dmitry Shmidt ssid, try_opportunistic) == 0) 16698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_pmkid_attempt(wpa_s->eapol, 1); 16708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie_len = sizeof(wpa_ie); 16718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_set_suites(wpa_s, bss, ssid, 16728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie, &wpa_ie_len)) { 16738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to set WPA " 16748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "key management and encryption suites"); 16752e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt wpas_connect_work_done(wpa_s); 16768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 16778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 167861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } else if ((ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_NO_WPA) && bss && 167961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_key_mgmt_wpa_ieee8021x(ssid->key_mgmt)) { 168061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt /* 168161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Both WPA and non-WPA IEEE 802.1X enabled in configuration - 168261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * use non-WPA since the scan results did not indicate that the 168361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * AP is using WPA or WPA2. 168461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt */ 168561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_supplicant_set_non_wpa_policy(wpa_s, ssid); 168661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_ie_len = 0; 168761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_s->wpa_proto = 0; 16881f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } else if (wpa_key_mgmt_wpa_any(ssid->key_mgmt)) { 16898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie_len = sizeof(wpa_ie); 16908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_set_suites(wpa_s, NULL, ssid, 16918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie, &wpa_ie_len)) { 16928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "WPA: Failed to set WPA " 16938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "key management and encryption suites (no " 16948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "scan results)"); 16952e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt wpas_connect_work_done(wpa_s); 16968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 16978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 16988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_WPS 16998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (ssid->key_mgmt & WPA_KEY_MGMT_WPS) { 17008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpabuf *wps_ie; 17018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wps_ie = wps_build_assoc_req_ie(wpas_wps_get_req_type(ssid)); 17028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wps_ie && wpabuf_len(wps_ie) <= sizeof(wpa_ie)) { 17038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie_len = wpabuf_len(wps_ie); 17048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(wpa_ie, wpabuf_head(wps_ie), wpa_ie_len); 17058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else 17068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie_len = 0; 17078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_free(wps_ie); 17088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_set_non_wpa_policy(wpa_s, ssid); 17098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!bss || (bss->caps & IEEE80211_CAP_PRIVACY)) 17108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.wps = WPS_MODE_PRIVACY; 17118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 17128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.wps = WPS_MODE_OPEN; 17131f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->wpa_proto = 0; 17148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_WPS */ 17158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 17168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_set_non_wpa_policy(wpa_s, ssid); 17178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie_len = 0; 17181f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->wpa_proto = 0; 17198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 17208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 17218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_P2P 17228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->global->p2p) { 17238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 *pos; 17248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t len; 17258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int res; 17268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = wpa_ie + wpa_ie_len; 17278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt len = sizeof(wpa_ie) - wpa_ie_len; 172804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt res = wpas_p2p_assoc_req_ie(wpa_s, bss, pos, len, 172904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt ssid->p2p_group); 17308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (res >= 0) 17318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_ie_len += res; 17328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 17338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 17348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->cross_connect_disallowed = 0; 17358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss) { 17368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpabuf *p2p; 17378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt p2p = wpa_bss_get_vendor_ie_multi(bss, P2P_IE_VENDOR_TYPE); 17388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (p2p) { 17398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->cross_connect_disallowed = 17408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt p2p_get_cross_connect_disallowed(p2p); 17418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_free(p2p); 17428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "P2P: WLAN AP %s cross " 17438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "connection", 17448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->cross_connect_disallowed ? 17458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "disallows" : "allows"); 17468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 17478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1748cf32e60fa7e0d33fe1551a6dba8dcbbec47ea50eDmitry Shmidt 1749cf32e60fa7e0d33fe1551a6dba8dcbbec47ea50eDmitry Shmidt os_memset(wpa_s->p2p_ip_addr_info, 0, sizeof(wpa_s->p2p_ip_addr_info)); 17508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_P2P */ 17518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 175204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#ifdef CONFIG_HS20 175351b6ea882f234c14cd1fe1332a3840cf61fafccaDmitry Shmidt if (is_hs20_network(wpa_s, ssid, bss)) { 175404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt struct wpabuf *hs20; 175504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt hs20 = wpabuf_alloc(20); 175604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (hs20) { 1757f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt int pps_mo_id = hs20_get_pps_mo_id(wpa_s, ssid); 1758c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt size_t len; 1759c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt 1760f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt wpas_hs20_add_indication(hs20, pps_mo_id); 1761c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt len = sizeof(wpa_ie) - wpa_ie_len; 1762c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt if (wpabuf_len(hs20) <= len) { 1763c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt os_memcpy(wpa_ie + wpa_ie_len, 1764c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt wpabuf_head(hs20), wpabuf_len(hs20)); 1765c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt wpa_ie_len += wpabuf_len(hs20); 1766c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt } 176704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpabuf_free(hs20); 176804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 176904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 177004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#endif /* CONFIG_HS20 */ 177104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 17725605286c30e1701491bd3af974ae423727750eddDmitry Shmidt /* 17735605286c30e1701491bd3af974ae423727750eddDmitry Shmidt * Workaround: Add Extended Capabilities element only if the AP 17745605286c30e1701491bd3af974ae423727750eddDmitry Shmidt * included this element in Beacon/Probe Response frames. Some older 17755605286c30e1701491bd3af974ae423727750eddDmitry Shmidt * APs seem to have interoperability issues if this element is 17765605286c30e1701491bd3af974ae423727750eddDmitry Shmidt * included, so while the standard may require us to include the 17775605286c30e1701491bd3af974ae423727750eddDmitry Shmidt * element in all cases, it is justifiable to skip it to avoid 17785605286c30e1701491bd3af974ae423727750eddDmitry Shmidt * interoperability issues. 17795605286c30e1701491bd3af974ae423727750eddDmitry Shmidt */ 17805605286c30e1701491bd3af974ae423727750eddDmitry Shmidt if (!bss || wpa_bss_get_ie(bss, WLAN_EID_EXT_CAPAB)) { 178109f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt u8 ext_capab[18]; 17825605286c30e1701491bd3af974ae423727750eddDmitry Shmidt int ext_capab_len; 178309f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt ext_capab_len = wpas_build_ext_capab(wpa_s, ext_capab, 178409f57babfc1e4473db20ced4f58a4c9f082c8ed8Dmitry Shmidt sizeof(ext_capab)); 17855605286c30e1701491bd3af974ae423727750eddDmitry Shmidt if (ext_capab_len > 0) { 17865605286c30e1701491bd3af974ae423727750eddDmitry Shmidt u8 *pos = wpa_ie; 17875605286c30e1701491bd3af974ae423727750eddDmitry Shmidt if (wpa_ie_len > 0 && pos[0] == WLAN_EID_RSN) 17885605286c30e1701491bd3af974ae423727750eddDmitry Shmidt pos += 2 + pos[1]; 17895605286c30e1701491bd3af974ae423727750eddDmitry Shmidt os_memmove(pos + ext_capab_len, pos, 17905605286c30e1701491bd3af974ae423727750eddDmitry Shmidt wpa_ie_len - (pos - wpa_ie)); 17915605286c30e1701491bd3af974ae423727750eddDmitry Shmidt wpa_ie_len += ext_capab_len; 17925605286c30e1701491bd3af974ae423727750eddDmitry Shmidt os_memcpy(pos, ext_capab, ext_capab_len); 17935605286c30e1701491bd3af974ae423727750eddDmitry Shmidt } 17941f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 17951f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 17968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_clear_keys(wpa_s, bss ? bss->bssid : NULL); 17978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt use_crypt = 1; 1798fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt cipher_pairwise = wpa_s->pairwise_cipher; 1799fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt cipher_group = wpa_s->group_cipher; 18008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE || 18018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) { 18028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE) 18038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt use_crypt = 0; 18048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_set_wep_keys(wpa_s, ssid)) { 18058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt use_crypt = 1; 18068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wep_keys_set = 1; 18078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 18088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 18098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_WPS) 18108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt use_crypt = 0; 18118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 18128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef IEEE8021X_EAPOL 18138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) { 18148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if ((ssid->eapol_flags & 18158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (EAPOL_FLAG_REQUIRE_KEY_UNICAST | 18168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt EAPOL_FLAG_REQUIRE_KEY_BROADCAST)) == 0 && 18178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt !wep_keys_set) { 18188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt use_crypt = 0; 18198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 18208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Assume that dynamic WEP-104 keys will be used and 18218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * set cipher suites in order for drivers to expect 18228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * encryption. */ 1823fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt cipher_pairwise = cipher_group = WPA_CIPHER_WEP104; 18248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 18258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 18268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* IEEE8021X_EAPOL */ 18278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 18288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_WPA_NONE) { 18298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Set the key before (and later after) association */ 18308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_set_wpa_none_key(wpa_s, ssid); 18318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 18328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 18338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_ASSOCIATING); 18348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss) { 18358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.ssid = bss->ssid; 18368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.ssid_len = bss->ssid_len; 183704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (!wpas_driver_bss_selection(wpa_s) || ssid->bssid_set) { 183804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_printf(MSG_DEBUG, "Limit connection to BSSID " 183904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt MACSTR " freq=%u MHz based on scan results " 184004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt "(bssid_set=%d)", 184104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt MAC2STR(bss->bssid), bss->freq, 184204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt ssid->bssid_set); 18431f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt params.bssid = bss->bssid; 18449ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt params.freq.freq = bss->freq; 18451f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 184696be6222df414a7dde5c5b1b72df22e67b1a77fcDmitry Shmidt params.bssid_hint = bss->bssid; 184796be6222df414a7dde5c5b1b72df22e67b1a77fcDmitry Shmidt params.freq_hint = bss->freq; 18488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 18498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.ssid = ssid->ssid; 18508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.ssid_len = ssid->ssid_len; 18518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1852c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 1853c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (ssid->mode == WPAS_MODE_IBSS && ssid->bssid_set && 1854c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_s->conf->ap_scan == 2) { 1855c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt params.bssid = ssid->bssid; 1856c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt params.fixed_bssid = 1; 1857c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 1858c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 18598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->mode == WPAS_MODE_IBSS && ssid->frequency > 0 && 18609ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt params.freq.freq == 0) { 18619ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt enum hostapd_hw_mode hw_mode; 18629ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt u8 channel; 18639ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt 18649ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt params.freq.freq = ssid->frequency; 18659ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt 18669ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt hw_mode = ieee80211_freq_to_chan(ssid->frequency, &channel); 18679ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt for (i = 0; wpa_s->hw.modes && i < wpa_s->hw.num_modes; i++) { 18689ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt if (wpa_s->hw.modes[i].mode == hw_mode) { 18699ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt struct hostapd_hw_modes *mode; 18709ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt 18719ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt mode = &wpa_s->hw.modes[i]; 18729ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt params.freq.ht_enabled = ht_supported(mode); 18739ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt break; 18749ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt } 18759ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt } 18769ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt } 18772ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt 18782ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt if (ssid->mode == WPAS_MODE_IBSS) { 18792ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt if (ssid->beacon_int) 18802ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt params.beacon_int = ssid->beacon_int; 18812ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt else 18822ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt params.beacon_int = wpa_s->conf->beacon_int; 18832ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt } 18842ac5f6049e74103a8fe8e9c78b330020081d7df4Dmitry Shmidt 18858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.wpa_ie = wpa_ie; 18868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.wpa_ie_len = wpa_ie_len; 18878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.pairwise_suite = cipher_pairwise; 18888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.group_suite = cipher_group; 1889fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt params.key_mgmt_suite = wpa_s->key_mgmt; 18901f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt params.wpa_proto = wpa_s->wpa_proto; 18918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.auth_alg = algs; 18928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.mode = ssid->mode; 189304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt params.bg_scan_period = ssid->bg_scan_period; 18948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < NUM_WEP_KEYS; i++) { 18958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->wep_key_len[i]) 18968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.wep_key[i] = ssid->wep_key[i]; 18978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.wep_key_len[i] = ssid->wep_key_len[i]; 18988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 18998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.wep_tx_keyidx = ssid->wep_tx_keyidx; 19008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 19018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE) && 1902fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt (params.key_mgmt_suite == WPA_KEY_MGMT_PSK || 1903fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt params.key_mgmt_suite == WPA_KEY_MGMT_FT_PSK)) { 19048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.passphrase = ssid->passphrase; 19058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid->psk_set) 19068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.psk = ssid->psk; 19078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 19088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 19098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.drop_unencrypted = use_crypt; 19108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 19118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IEEE80211W 1912d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt params.mgmt_frame_protection = 1913d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt ssid->ieee80211w == MGMT_FRAME_PROTECTION_DEFAULT ? 1914d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->conf->pmf : ssid->ieee80211w; 1915d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (params.mgmt_frame_protection != NO_MGMT_FRAME_PROTECTION && bss) { 19168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *rsn = wpa_bss_get_ie(bss, WLAN_EID_RSN); 19178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ie_data ie; 19188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (rsn && wpa_parse_wpa_ie(rsn, 2 + rsn[1], &ie) == 0 && 19198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ie.capabilities & 19208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (WPA_CAPABILITY_MFPC | WPA_CAPABILITY_MFPR)) { 19218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "WPA: Selected AP supports " 19228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "MFP: require MFP"); 19238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.mgmt_frame_protection = 19248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt MGMT_FRAME_PROTECTION_REQUIRED; 19258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 19268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 19278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IEEE80211W */ 19288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 19291f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt params.p2p = ssid->p2p_group; 19308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 19318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->parent->set_sta_uapsd) 19328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.uapsd = wpa_s->parent->sta_uapsd; 19338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 19348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params.uapsd = -1; 19358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1936c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt#ifdef CONFIG_HT_OVERRIDES 1937c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt os_memset(&htcaps, 0, sizeof(htcaps)); 1938c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt os_memset(&htcaps_mask, 0, sizeof(htcaps_mask)); 1939c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt params.htcaps = (u8 *) &htcaps; 1940c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt params.htcaps_mask = (u8 *) &htcaps_mask; 1941c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_supplicant_apply_ht_overrides(wpa_s, ssid, ¶ms); 1942c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt#endif /* CONFIG_HT_OVERRIDES */ 1943b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt#ifdef CONFIG_VHT_OVERRIDES 1944b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt os_memset(&vhtcaps, 0, sizeof(vhtcaps)); 1945b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt os_memset(&vhtcaps_mask, 0, sizeof(vhtcaps_mask)); 1946b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt params.vhtcaps = &vhtcaps; 1947b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt params.vhtcaps_mask = &vhtcaps_mask; 1948b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt wpa_supplicant_apply_vht_overrides(wpa_s, wpa_s->current_ssid, ¶ms); 1949b36ed7cd946148d829f311de8fe53ea3ffaaffe3Dmitry Shmidt#endif /* CONFIG_VHT_OVERRIDES */ 1950c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 195104f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt#ifdef CONFIG_P2P 195204f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt /* 195304f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt * If multi-channel concurrency is not supported, check for any 195404f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt * frequency conflict. In case of any frequency conflict, remove the 195504f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt * least prioritized connection. 195604f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt */ 195704f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt if (wpa_s->num_multichan_concurrent < 2) { 1958f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt int freq, num; 1959f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt num = get_shared_radio_freqs(wpa_s, &freq, 1); 19609ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt if (num > 0 && freq > 0 && freq != params.freq.freq) { 1961f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt wpa_printf(MSG_DEBUG, 1962f9bdef99ce3b2858f2812c745a3d6bb093fb0e5dDmitry Shmidt "Assoc conflicting freq found (%d != %d)", 19639ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt freq, params.freq.freq); 19649ead16e203b81d44a2d84eadc2901ceeb7daf805Dmitry Shmidt if (wpas_p2p_handle_frequency_conflicts( 19652e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt wpa_s, params.freq.freq, ssid) < 0) { 19662e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt wpas_connect_work_done(wpa_s); 196704f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt return; 19682e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt } 196904f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt } 197004f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt } 197104f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt#endif /* CONFIG_P2P */ 197204f534e89ed127da4077485376f24debc50d80d5Dmitry Shmidt 19731f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt ret = wpa_drv_associate(wpa_s, ¶ms); 19748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret < 0) { 19758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "Association request to the driver " 19768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "failed"); 19778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->drv_flags & WPA_DRIVER_FLAGS_SANE_ERROR_CODES) { 19788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 19798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * The driver is known to mean what is saying, so we 19808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * can stop right here; the association will not 19818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * succeed. 19828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 19838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_connection_failed(wpa_s, wpa_s->pending_bssid); 198404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED); 19858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memset(wpa_s->pending_bssid, 0, ETH_ALEN); 19868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 19878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 19888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* try to continue anyway; new association will be tried again 19898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * after timeout */ 19908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt assoc_failed = 1; 19918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 19928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 19938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_WPA_NONE) { 19948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Set the key after the association just in case association 19958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * cleared the previously configured key. */ 19968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_set_wpa_none_key(wpa_s, ssid); 19978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* No need to timeout authentication since there is no key 19988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * management. */ 19998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_cancel_auth_timeout(wpa_s); 20008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_COMPLETED); 20018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IBSS_RSN 20028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (ssid->mode == WPAS_MODE_IBSS && 20038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt != WPA_KEY_MGMT_NONE && 20048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt != WPA_KEY_MGMT_WPA_NONE) { 20058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 20068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * RSN IBSS authentication is per-STA and we can disable the 20078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * per-BSSID authentication. 20088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 20098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_cancel_auth_timeout(wpa_s); 20108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IBSS_RSN */ 20118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 20128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Timeout for IEEE 802.11 authentication and association */ 20138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int timeout = 60; 20148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 20158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (assoc_failed) { 20168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* give IBSS a bit more time */ 20178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt timeout = ssid->mode == WPAS_MODE_IBSS ? 10 : 5; 20188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (wpa_s->conf->ap_scan == 1) { 20198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* give IBSS a bit more time */ 20208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt timeout = ssid->mode == WPAS_MODE_IBSS ? 20 : 10; 20218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 20228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_req_auth_timeout(wpa_s, timeout, 0); 20238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 20248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 202551b6ea882f234c14cd1fe1332a3840cf61fafccaDmitry Shmidt if (wep_keys_set && 202651b6ea882f234c14cd1fe1332a3840cf61fafccaDmitry Shmidt (wpa_s->drv_flags & WPA_DRIVER_FLAGS_SET_KEYS_AFTER_ASSOC)) { 20278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Set static WEP keys again */ 20288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_set_wep_keys(wpa_s, ssid); 20298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 20308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 20318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->current_ssid && wpa_s->current_ssid != ssid) { 20328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 20338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Do not allow EAP session resumption between different 20348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * network configurations. 20358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 20368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_invalidate_cached_session(wpa_s->eapol); 20378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 20388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_ssid = wpa_s->current_ssid; 20398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->current_ssid = ssid; 20408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->current_bss = bss; 20418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_rsn_supp_set_config(wpa_s, wpa_s->current_ssid); 20428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_initiate_eapol(wpa_s); 20438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (old_ssid != wpa_s->current_ssid) 20448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_changed(wpa_s); 20458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 20468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 20478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 20488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_clear_connection(struct wpa_supplicant *wpa_s, 20498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *addr) 20508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 20518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *old_ssid; 20528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 20538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_clear_keys(wpa_s, addr); 20548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_ssid = wpa_s->current_ssid; 205561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_supplicant_mark_disassoc(wpa_s); 20568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_config(wpa_s->wpa, NULL); 20578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_config(wpa_s->eapol, NULL, NULL); 20588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (old_ssid != wpa_s->current_ssid) 20598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_changed(wpa_s); 20608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL); 20618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 20628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 20638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 20648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 20658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_deauthenticate - Deauthenticate the current connection 20668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 20678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @reason_code: IEEE 802.11 reason code for the deauthenticate frame 20688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 20698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to request %wpa_supplicant to deauthenticate from the 20708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * current AP. 20718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 20728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_deauthenticate(struct wpa_supplicant *wpa_s, 20738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int reason_code) 20748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 20758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 *addr = NULL; 207604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt union wpa_event_data event; 2077d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt int zero_addr = 0; 2078d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 2079d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Request to deauthenticate - bssid=" MACSTR 2080d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt " pending_bssid=" MACSTR " reason=%d state=%s", 2081d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt MAC2STR(wpa_s->bssid), MAC2STR(wpa_s->pending_bssid), 2082d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt reason_code, wpa_supplicant_state_txt(wpa_s->wpa_state)); 20838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2084d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (!is_zero_ether_addr(wpa_s->bssid)) 20858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt addr = wpa_s->bssid; 2086d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt else if (!is_zero_ether_addr(wpa_s->pending_bssid) && 2087d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt (wpa_s->wpa_state == WPA_AUTHENTICATING || 2088d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->wpa_state == WPA_ASSOCIATING)) 2089d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt addr = wpa_s->pending_bssid; 2090d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt else if (wpa_s->wpa_state == WPA_ASSOCIATING) { 2091d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt /* 2092d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * When using driver-based BSS selection, we may not know the 2093d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * BSSID with which we are currently trying to associate. We 2094d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * need to notify the driver of this disconnection even in such 2095d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * a case, so use the all zeros address here. 2096d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt */ 2097d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt addr = wpa_s->bssid; 2098d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt zero_addr = 1; 2099d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt } 2100d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 2101f86232838cf712377867cb42417c1613ab5dc425Dmitry Shmidt#ifdef CONFIG_TDLS 2102f86232838cf712377867cb42417c1613ab5dc425Dmitry Shmidt wpa_tdls_teardown_peers(wpa_s->wpa); 2103f86232838cf712377867cb42417c1613ab5dc425Dmitry Shmidt#endif /* CONFIG_TDLS */ 2104f86232838cf712377867cb42417c1613ab5dc425Dmitry Shmidt 2105d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (addr) { 2106d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_drv_deauthenticate(wpa_s, addr, reason_code); 210704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt os_memset(&event, 0, sizeof(event)); 210804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt event.deauth_info.reason_code = (u16) reason_code; 210904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt event.deauth_info.locally_generated = 1; 211004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_event(wpa_s, EVENT_DEAUTH, &event); 2111d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (zero_addr) 2112d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt addr = NULL; 21138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 21148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_clear_connection(wpa_s, addr); 21168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 21178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21182f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidtstatic void wpa_supplicant_enable_one_network(struct wpa_supplicant *wpa_s, 21192f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt struct wpa_ssid *ssid) 21202f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt{ 21212f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (!ssid || !ssid->disabled || ssid->disabled == 2) 21222f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt return; 21232f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 21242f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt ssid->disabled = 0; 21252f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpas_clear_temp_disabled(wpa_s, ssid, 1); 21262f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpas_notify_network_enabled_changed(wpa_s, ssid); 21272f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 21282f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt /* 21292f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt * Try to reassociate since there is no current configuration and a new 21302f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt * network was made available. 21312f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt */ 21324ce9c87407c036fc83eb5a6044ddf976c86f53fcDmitry Shmidt if (!wpa_s->current_ssid && !wpa_s->disconnected) 21332f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_s->reassociate = 1; 21342f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt} 21352f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 21368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 21388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_enable_network - Mark a configured network as enabled 21398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 21408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid: wpa_ssid structure for a configured network or %NULL 21418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 21428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Enables the specified network or all networks if no network specified. 21438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 21448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_enable_network(struct wpa_supplicant *wpa_s, 21458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid) 21468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 21478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid == NULL) { 21482f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) 21492f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_supplicant_enable_one_network(wpa_s, ssid); 21502f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt } else 21512f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_supplicant_enable_one_network(wpa_s, ssid); 21528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21534ce9c87407c036fc83eb5a6044ddf976c86f53fcDmitry Shmidt if (wpa_s->reassociate && !wpa_s->disconnected) { 21542f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (wpa_s->sched_scanning) { 21552f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_printf(MSG_DEBUG, "Stop ongoing sched_scan to add " 21562f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt "new network to scan filters"); 21572f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_supplicant_cancel_sched_scan(wpa_s); 21588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 21598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2160f7e0a9905988e62e4f70fed8b795722abeab719bDmitry Shmidt if (wpa_supplicant_fast_associate(wpa_s) != 1) 2161f7e0a9905988e62e4f70fed8b795722abeab719bDmitry Shmidt wpa_supplicant_req_scan(wpa_s, 0, 0); 21628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 21638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 21648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 21678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_disable_network - Mark a configured network as disabled 21688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 21698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid: wpa_ssid structure for a configured network or %NULL 21708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 21718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Disables the specified network or all networks if no network specified. 21728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 21738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_disable_network(struct wpa_supplicant *wpa_s, 21748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid) 21758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 21768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *other_ssid; 21778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int was_disabled; 21788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid == NULL) { 21802f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (wpa_s->sched_scanning) 21812f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_supplicant_cancel_sched_scan(wpa_s); 21822f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 21838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (other_ssid = wpa_s->conf->ssid; other_ssid; 21848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt other_ssid = other_ssid->next) { 21858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt was_disabled = other_ssid->disabled; 21868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (was_disabled == 2) 21878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; /* do not change persistent P2P group 21888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * data */ 21898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt other_ssid->disabled = 1; 21918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 21928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (was_disabled != other_ssid->disabled) 21938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_enabled_changed( 21948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s, other_ssid); 21958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 21968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->current_ssid) 2197d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_supplicant_deauthenticate( 21988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s, WLAN_REASON_DEAUTH_LEAVING); 21998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (ssid->disabled != 2) { 22008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid == wpa_s->current_ssid) 2201d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_supplicant_deauthenticate( 22028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s, WLAN_REASON_DEAUTH_LEAVING); 22038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt was_disabled = ssid->disabled; 22058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid->disabled = 1; 22078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22082f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (was_disabled != ssid->disabled) { 22098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_enabled_changed(wpa_s, ssid); 22102f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (wpa_s->sched_scanning) { 22112f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_printf(MSG_DEBUG, "Stop ongoing sched_scan " 22122f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt "to remove network from filters"); 22132f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_supplicant_cancel_sched_scan(wpa_s); 22142f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt wpa_supplicant_req_scan(wpa_s, 0, 0); 22152f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt } 22162f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt } 22178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 22188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 22198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 22228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_select_network - Attempt association with a network 22238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 22248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid: wpa_ssid structure for a configured network or %NULL for any network 22258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 22268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_select_network(struct wpa_supplicant *wpa_s, 22278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid) 22288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 22298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *other_ssid; 2231c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt int disconnected = 0; 22328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2233c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (ssid && ssid != wpa_s->current_ssid && wpa_s->current_ssid) { 2234d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_supplicant_deauthenticate( 22358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s, WLAN_REASON_DEAUTH_LEAVING); 2236c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt disconnected = 1; 2237c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 22388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 223961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (ssid) 224061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpas_clear_temp_disabled(wpa_s, ssid, 1); 224161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 22428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 22438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Mark all other networks disabled or mark all networks enabled if no 22448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * network specified. 22458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 22468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (other_ssid = wpa_s->conf->ssid; other_ssid; 22478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt other_ssid = other_ssid->next) { 22488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int was_disabled = other_ssid->disabled; 22498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (was_disabled == 2) 22508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; /* do not change persistent P2P group data */ 22518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt other_ssid->disabled = ssid ? (ssid->id != other_ssid->id) : 0; 225361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (was_disabled && !other_ssid->disabled) 225461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpas_clear_temp_disabled(wpa_s, other_ssid, 0); 22558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (was_disabled != other_ssid->disabled) 22578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_enabled_changed(wpa_s, other_ssid); 22588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 22591f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 22601f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (ssid && ssid == wpa_s->current_ssid && wpa_s->current_ssid) { 22611f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt /* We are already associated with the selected network */ 22621f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_printf(MSG_DEBUG, "Already associated with the " 22631f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt "selected network - do nothing"); 22641f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return; 22651f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 22661f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 2267b7b4d0ec07161a6d76c40ba7ef1306e82fbb7e15Dmitry Shmidt if (ssid) { 2268c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_s->current_ssid = ssid; 2269b7b4d0ec07161a6d76c40ba7ef1306e82fbb7e15Dmitry Shmidt eapol_sm_notify_config(wpa_s->eapol, NULL, NULL); 2270b7b4d0ec07161a6d76c40ba7ef1306e82fbb7e15Dmitry Shmidt } 227175ecf5267604f166b85a7ee2cf0d9cb682966680Jouni Malinen wpa_s->connect_without_scan = NULL; 22728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->disconnected = 0; 22738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->reassociate = 1; 22744b9d52f502481b258fec743c03a5e957e5605afcDmitry Shmidt 22754b9d52f502481b258fec743c03a5e957e5605afcDmitry Shmidt if (wpa_supplicant_fast_associate(wpa_s) != 1) 22764b9d52f502481b258fec743c03a5e957e5605afcDmitry Shmidt wpa_supplicant_req_scan(wpa_s, 0, disconnected ? 100000 : 0); 22778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid) 22798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_selected(wpa_s, ssid); 22808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 22818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 22838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 228401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * wpas_set_pkcs11_engine_and_module_path - Set PKCS #11 engine and module path 228501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 228601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * @pkcs11_engine_path: PKCS #11 engine path or NULL 228701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * @pkcs11_module_path: PKCS #11 module path or NULL 228801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * Returns: 0 on success; -1 on failure 228901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * 229001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * Sets the PKCS #11 engine and module path. Both have to be NULL or a valid 229101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * path. If resetting the EAPOL state machine with the new PKCS #11 engine and 229201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt * module path fails the paths will be reset to the default value (NULL). 229301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt */ 229401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidtint wpas_set_pkcs11_engine_and_module_path(struct wpa_supplicant *wpa_s, 229501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt const char *pkcs11_engine_path, 229601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt const char *pkcs11_module_path) 229701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt{ 229801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt char *pkcs11_engine_path_copy = NULL; 229901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt char *pkcs11_module_path_copy = NULL; 230001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 230101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (pkcs11_engine_path != NULL) { 230201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt pkcs11_engine_path_copy = os_strdup(pkcs11_engine_path); 230301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (pkcs11_engine_path_copy == NULL) 230401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return -1; 230501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 230601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (pkcs11_module_path != NULL) { 230701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt pkcs11_module_path_copy = os_strdup(pkcs11_module_path); 23089767226d8e6a1adaa33beb9f517ef40dddfa460cDmitry Shmidt if (pkcs11_module_path_copy == NULL) { 230901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt os_free(pkcs11_engine_path_copy); 231001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return -1; 231101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 231201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 231301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 231401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt os_free(wpa_s->conf->pkcs11_engine_path); 231501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt os_free(wpa_s->conf->pkcs11_module_path); 231601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->conf->pkcs11_engine_path = pkcs11_engine_path_copy; 231701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->conf->pkcs11_module_path = pkcs11_module_path_copy; 231801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 231901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_sm_set_eapol(wpa_s->wpa, NULL); 232001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt eapol_sm_deinit(wpa_s->eapol); 232101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->eapol = NULL; 232201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (wpa_supplicant_init_eapol(wpa_s)) { 232301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt /* Error -> Reset paths to the default value (NULL) once. */ 232401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (pkcs11_engine_path != NULL && pkcs11_module_path != NULL) 232501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpas_set_pkcs11_engine_and_module_path(wpa_s, NULL, 232601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt NULL); 232701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 232801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return -1; 232901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 233001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_sm_set_eapol(wpa_s->wpa, wpa_s->eapol); 233101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 233201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return 0; 233301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt} 233401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 233501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 233601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt/** 23378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_set_ap_scan - Set AP scan mode for interface 23388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 23398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ap_scan: AP scan mode 23408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 if succeed or -1 if ap_scan has an invalid value 23418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 23428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 23438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_set_ap_scan(struct wpa_supplicant *wpa_s, int ap_scan) 23448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 23458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int old_ap_scan; 23478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ap_scan < 0 || ap_scan > 2) 23498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 23508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2351114c3866dda61e84385bb5327f0acf727f2156daDmitry Shmidt#ifdef ANDROID 23521f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (ap_scan == 2 && ap_scan != wpa_s->conf->ap_scan && 23531f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->wpa_state >= WPA_ASSOCIATING && 23541f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->wpa_state < WPA_COMPLETED) { 23551f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_printf(MSG_ERROR, "ap_scan = %d (%d) rejected while " 23561f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt "associating", wpa_s->conf->ap_scan, ap_scan); 2357114c3866dda61e84385bb5327f0acf727f2156daDmitry Shmidt return 0; 2358114c3866dda61e84385bb5327f0acf727f2156daDmitry Shmidt } 23591f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#endif /* ANDROID */ 2360114c3866dda61e84385bb5327f0acf727f2156daDmitry Shmidt 23618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_ap_scan = wpa_s->conf->ap_scan; 23628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->ap_scan = ap_scan; 23638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (old_ap_scan != wpa_s->conf->ap_scan) 23658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_ap_scan_changed(wpa_s); 23668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 23688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 23698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 23728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_set_bss_expiration_age - Set BSS entry expiration age 23738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 23748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @expire_age: Expiration age in seconds 23758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 if succeed or -1 if expire_age has an invalid value 23768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 23778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 23788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_set_bss_expiration_age(struct wpa_supplicant *wpa_s, 23798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int bss_expire_age) 23808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 23818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss_expire_age < 10) { 23828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Invalid bss expiration age %u", 23838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_expire_age); 23848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 23858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 23868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "Setting bss expiration age: %d sec", 23878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_expire_age); 23888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->bss_expiration_age = bss_expire_age; 23898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 23918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 23928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 23948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 23958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_set_bss_expiration_count - Set BSS entry expiration scan count 23968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 23978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @expire_count: number of scans after which an unseen BSS is reclaimed 23988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 if succeed or -1 if expire_count has an invalid value 23998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 24008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 24018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_set_bss_expiration_count(struct wpa_supplicant *wpa_s, 24028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int bss_expire_count) 24038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 24048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss_expire_count < 1) { 24058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Invalid bss expiration count %u", 24068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_expire_count); 24078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 24088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 24098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "Setting bss expiration scan count: %u", 24108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt bss_expire_count); 24118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->bss_expiration_scan_count = bss_expire_count; 24128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 24148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 24158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 241804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt * wpa_supplicant_set_scan_interval - Set scan interval 241904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt * @wpa_s: wpa_supplicant structure for a network interface 242004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt * @scan_interval: scan interval in seconds 242104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt * Returns: 0 if succeed or -1 if scan_interval has an invalid value 242204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt * 242304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt */ 242404949598a23f501be6eec21697465fd46a28840aDmitry Shmidtint wpa_supplicant_set_scan_interval(struct wpa_supplicant *wpa_s, 242504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt int scan_interval) 242604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 242704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (scan_interval < 0) { 242804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Invalid scan interval %d", 242904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt scan_interval); 243004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return -1; 243104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 243204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "Setting scan interval: %d sec", 243304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt scan_interval); 24344b9d52f502481b258fec743c03a5e957e5605afcDmitry Shmidt wpa_supplicant_update_scan_int(wpa_s, scan_interval); 243504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 243604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 0; 243704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 243804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 243904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 244004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt/** 24418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_set_debug_params - Set global debug params 24428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @global: wpa_global structure 24438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @debug_level: debug level 24448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @debug_timestamp: determines if show timestamp in debug data 24458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @debug_show_keys: determines if show keys in debug data 24468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 if succeed or -1 if debug_level has wrong value 24478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 24488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_set_debug_params(struct wpa_global *global, int debug_level, 24498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int debug_timestamp, int debug_show_keys) 24508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 24518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int old_level, old_timestamp, old_show_keys; 24538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* check for allowed debuglevels */ 24558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (debug_level != MSG_EXCESSIVE && 24568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt debug_level != MSG_MSGDUMP && 24578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt debug_level != MSG_DEBUG && 24588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt debug_level != MSG_INFO && 24598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt debug_level != MSG_WARNING && 24608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt debug_level != MSG_ERROR) 24618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 24628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_level = wpa_debug_level; 24648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_timestamp = wpa_debug_timestamp; 24658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt old_show_keys = wpa_debug_show_keys; 24668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_level = debug_level; 24688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_timestamp = debug_timestamp ? 1 : 0; 24698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_show_keys = debug_show_keys ? 1 : 0; 24708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_debug_level != old_level) 24728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_debug_level_changed(global); 24738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_debug_timestamp != old_timestamp) 24748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_debug_timestamp_changed(global); 24758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_debug_show_keys != old_show_keys) 24768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_debug_show_keys_changed(global); 24778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 24798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 24808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 24838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_get_ssid - Get a pointer to the current network structure 24848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 24858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: A pointer to the current network structure or %NULL on failure 24868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 24878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct wpa_ssid * wpa_supplicant_get_ssid(struct wpa_supplicant *wpa_s) 24888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 24898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *entry; 24908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 ssid[MAX_SSID_LEN]; 24918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int res; 24928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t ssid_len; 24938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 bssid[ETH_ALEN]; 24948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int wired; 24958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 24961f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt res = wpa_drv_get_ssid(wpa_s, ssid); 24971f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (res < 0) { 24981f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "Could not read SSID from " 24991f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt "driver"); 25001f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return NULL; 25018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 25021f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt ssid_len = res; 25038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25041f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpa_drv_get_bssid(wpa_s, bssid) < 0) { 25058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_WARNING, "Could not read BSSID from " 25068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "driver"); 25078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 25088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 25098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wired = wpa_s->conf->ap_scan == 0 && 25118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED); 25128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt entry = wpa_s->conf->ssid; 25148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (entry) { 251504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (!wpas_network_disabled(wpa_s, entry) && 25168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ((ssid_len == entry->ssid_len && 25178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcmp(ssid, entry->ssid, ssid_len) == 0) || wired) && 25188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (!entry->bssid_set || 25198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0)) 25208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return entry; 25218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_WPS 252204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (!wpas_network_disabled(wpa_s, entry) && 25238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (entry->key_mgmt & WPA_KEY_MGMT_WPS) && 25248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (entry->ssid == NULL || entry->ssid_len == 0) && 25258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (!entry->bssid_set || 25268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0)) 25278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return entry; 25288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_WPS */ 25291f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 253004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (!wpas_network_disabled(wpa_s, entry) && entry->bssid_set && 25311f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt entry->ssid_len == 0 && 25321f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0) 25331f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return entry; 25341f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 25358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt entry = entry->next; 25368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 25378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 25398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 25408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25421f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidtstatic int select_driver(struct wpa_supplicant *wpa_s, int i) 25431f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt{ 25441f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt struct wpa_global *global = wpa_s->global; 25451f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 25461f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpa_drivers[i]->global_init && global->drv_priv[i] == NULL) { 25471f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt global->drv_priv[i] = wpa_drivers[i]->global_init(); 25481f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (global->drv_priv[i] == NULL) { 25491f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_printf(MSG_ERROR, "Failed to initialize driver " 25501f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt "'%s'", wpa_drivers[i]->name); 25511f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return -1; 25521f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 25531f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 25541f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 25551f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->driver = wpa_drivers[i]; 25561f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->global_drv_priv = global->drv_priv[i]; 25571f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 25581f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return 0; 25591f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt} 25601f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 25611f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 25628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int wpa_supplicant_set_driver(struct wpa_supplicant *wpa_s, 25638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *name) 25648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 25658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 25668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t len; 25678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *pos, *driver = name; 25688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s == NULL) 25708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 25718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_drivers[0] == NULL) { 25738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "No driver interfaces build into " 25748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "wpa_supplicant"); 25758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 25768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 25778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (name == NULL) { 25798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* default to first driver in the list */ 25801f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return select_driver(wpa_s, 0); 25818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 25828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt do { 25848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strchr(driver, ','); 25858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos) 25868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt len = pos - driver; 25878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 25888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt len = os_strlen(driver); 25898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 25908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; wpa_drivers[i]; i++) { 25918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strlen(wpa_drivers[i]->name) == len && 25928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strncmp(driver, wpa_drivers[i]->name, len) == 2593c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 0) { 2594c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* First driver that succeeds wins */ 2595c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (select_driver(wpa_s, i) == 0) 2596c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 2597c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 25988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 25998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 26008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt driver = pos + 1; 26018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } while (pos); 26028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 26038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Unsupported driver '%s'", name); 26048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 26058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 26068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 26078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 26088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 26098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_rx_eapol - Deliver a received EAPOL frame to wpa_supplicant 26108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ctx: Context pointer (wpa_s); this is the ctx variable registered 26118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * with struct wpa_driver_ops::init() 26128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @src_addr: Source address of the EAPOL frame 26138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @buf: EAPOL data starting from the EAPOL header (i.e., no Ethernet header) 26148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @len: Length of the EAPOL data 26158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 26168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is called for each received EAPOL frame. Most driver 26178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * interfaces rely on more generic OS mechanism for receiving frames through 26188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * l2_packet, but if such a mechanism is not available, the driver wrapper may 26198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * take care of received EAPOL frames and deliver them to the core supplicant 26208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * code by calling this function. 26218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 26228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_rx_eapol(void *ctx, const u8 *src_addr, 26238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *buf, size_t len) 26248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 26258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s = ctx; 26268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 26278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RX EAPOL from " MACSTR, MAC2STR(src_addr)); 26288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_hexdump(MSG_MSGDUMP, "RX EAPOL", buf, len); 26298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2630fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt#ifdef CONFIG_PEERKEY 2631fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (wpa_s->wpa_state > WPA_ASSOCIATED && wpa_s->current_ssid && 2632fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s->current_ssid->peerkey && 2633fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt !(wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE) && 2634fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_sm_rx_eapol_peerkey(wpa_s->wpa, src_addr, buf, len) == 1) { 2635fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RSN: Processed PeerKey EAPOL-Key"); 2636fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 2637fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 2638fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt#endif /* CONFIG_PEERKEY */ 2639fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 2640a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen if (wpa_s->wpa_state < WPA_ASSOCIATED || 2641a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen (wpa_s->last_eapol_matches_bssid && 2642a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen#ifdef CONFIG_AP 2643a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen !wpa_s->ap_iface && 2644a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen#endif /* CONFIG_AP */ 2645a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen os_memcmp(src_addr, wpa_s->bssid, ETH_ALEN) != 0)) { 26468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 26478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * There is possible race condition between receiving the 26488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * association event and the EAPOL frame since they are coming 26498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * through different paths from the driver. In order to avoid 26508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * issues in trying to process the EAPOL frame before receiving 26518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * association information, lets queue it for processing until 2652a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen * the association event is received. This may also be needed in 2653a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen * driver-based roaming case, so also use src_addr != BSSID as a 2654a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen * trigger if we have previously confirmed that the 2655a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen * Authenticator uses BSSID as the src_addr (which is not the 2656a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen * case with wired IEEE 802.1X). 26578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 26588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Not associated - Delay processing " 2659a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen "of received EAPOL frame (state=%s bssid=" MACSTR ")", 2660a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen wpa_supplicant_state_txt(wpa_s->wpa_state), 2661a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen MAC2STR(wpa_s->bssid)); 26628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_free(wpa_s->pending_eapol_rx); 26638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->pending_eapol_rx = wpabuf_alloc_copy(buf, len); 26648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->pending_eapol_rx) { 2665fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_get_reltime(&wpa_s->pending_eapol_rx_time); 26668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(wpa_s->pending_eapol_rx_src, src_addr, 26678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ETH_ALEN); 26688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 26698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 26708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 26718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2672a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen wpa_s->last_eapol_matches_bssid = 2673a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen os_memcmp(src_addr, wpa_s->bssid, ETH_ALEN) == 0; 2674a05074ca1abe62b3fd8a8c30a5558e044b1356d5Jouni Malinen 26758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_AP 26768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->ap_iface) { 26778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_ap_rx_eapol(wpa_s, src_addr, buf, len); 26788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 26798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 26808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_AP */ 26818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 26828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE) { 26838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Ignored received EAPOL frame since " 26848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "no key management is configured"); 26858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 26868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 26878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 26888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->eapol_received == 0 && 26898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE) || 26908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt !wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) || 26918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->wpa_state != WPA_COMPLETED) && 26928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (wpa_s->current_ssid == NULL || 26938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->current_ssid->mode != IEEE80211_MODE_IBSS)) { 26948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Timeout for completing IEEE 802.1X and WPA authentication */ 26958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_req_auth_timeout( 26968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s, 26978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) || 26988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA || 26998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt == WPA_KEY_MGMT_WPS) ? 27008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 70 : 10, 0); 27018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 27028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->eapol_received++; 27038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 27048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->countermeasures) { 27058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, "WPA: Countermeasures - dropped " 27068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "EAPOL packet"); 27078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 27088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 27098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 27108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_IBSS_RSN 27118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->current_ssid && 27128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->current_ssid->mode == WPAS_MODE_IBSS) { 27138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ibss_rsn_rx_eapol(wpa_s->ibss_rsn, src_addr, buf, len); 27148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 27158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 27168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_IBSS_RSN */ 27178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 27188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Source address of the incoming EAPOL frame could be compared to the 27198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * current BSSID. However, it is possible that a centralized 27208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Authenticator could be using another MAC address than the BSSID of 27218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * an AP, so just allow any address to be used for now. The replies are 27228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * still sent to the current BSSID (if available), though. */ 27238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 27248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(wpa_s->last_eapol_src, src_addr, ETH_ALEN); 27258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) && 27268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_rx_eapol(wpa_s->eapol, src_addr, buf, len) > 0) 27278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 27288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_poll(wpa_s); 27298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE)) 27308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_rx_eapol(wpa_s->wpa, src_addr, buf, len); 27318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt)) { 27328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 27338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Set portValid = TRUE here since we are going to skip 4-way 27348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * handshake processing which would normally set portValid. We 27358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * need this to allow the EAPOL state machines to be completed 27368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * without going through EAPOL-Key handshake. 27378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 27388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_portValid(wpa_s->eapol, TRUE); 27398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 27408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 27418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 27428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 27431f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidtint wpa_supplicant_update_mac_addr(struct wpa_supplicant *wpa_s) 27448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 27458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->driver->send_eapol) { 27468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *addr = wpa_drv_get_mac_addr(wpa_s); 27478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (addr) 27488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(wpa_s->own_addr, addr, ETH_ALEN); 274934af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt } else if ((!wpa_s->p2p_mgmt || 275034af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt !(wpa_s->drv_flags & 275134af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt WPA_DRIVER_FLAGS_DEDICATED_P2P_DEVICE)) && 275234af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt !(wpa_s->drv_flags & 27538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WPA_DRIVER_FLAGS_P2P_DEDICATED_INTERFACE)) { 27541f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt l2_packet_deinit(wpa_s->l2); 27558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->l2 = l2_packet_init(wpa_s->ifname, 27568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_get_mac_addr(wpa_s), 27578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ETH_P_EAPOL, 27588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_rx_eapol, wpa_s, 0); 27598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->l2 == NULL) 27608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 27618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 27628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *addr = wpa_drv_get_mac_addr(wpa_s); 27638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (addr) 27648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(wpa_s->own_addr, addr, ETH_ALEN); 27658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 27668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 27678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->l2 && l2_packet_get_own_addr(wpa_s->l2, wpa_s->own_addr)) { 27688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Failed to get own L2 address"); 27698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 27708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 27718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2772661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt wpa_sm_set_own_addr(wpa_s->wpa, wpa_s->own_addr); 2773661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt 27741f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return 0; 27751f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt} 27761f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 27771f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 277804949598a23f501be6eec21697465fd46a28840aDmitry Shmidtstatic void wpa_supplicant_rx_eapol_bridge(void *ctx, const u8 *src_addr, 277904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt const u8 *buf, size_t len) 278004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 278104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt struct wpa_supplicant *wpa_s = ctx; 278204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt const struct l2_ethhdr *eth; 278304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 278404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (len < sizeof(*eth)) 278504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return; 278604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eth = (const struct l2_ethhdr *) buf; 278704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 278804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (os_memcmp(eth->h_dest, wpa_s->own_addr, ETH_ALEN) != 0 && 278904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt !(eth->h_dest[0] & 0x01)) { 279004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RX EAPOL from " MACSTR " to " MACSTR 279104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt " (bridge - not for this interface - ignore)", 279204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt MAC2STR(src_addr), MAC2STR(eth->h_dest)); 279304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return; 279404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 279504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 279604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RX EAPOL from " MACSTR " to " MACSTR 279704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt " (bridge)", MAC2STR(src_addr), MAC2STR(eth->h_dest)); 279804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_rx_eapol(wpa_s, src_addr, buf + sizeof(*eth), 279904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt len - sizeof(*eth)); 280004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 280104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 280204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 28031f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt/** 28041f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt * wpa_supplicant_driver_init - Initialize driver interface parameters 28051f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 28061f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt * Returns: 0 on success, -1 on failure 28071f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt * 28081f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt * This function is called to initialize driver interface parameters. 28091f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt * wpa_drv_init() must have been called before this function to initialize the 28101f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt * driver interface. 28111f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt */ 28121f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidtint wpa_supplicant_driver_init(struct wpa_supplicant *wpa_s) 28131f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt{ 28141f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt static int interface_count = 0; 28151f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 28161f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpa_supplicant_update_mac_addr(wpa_s) < 0) 28171f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return -1; 28188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 281934af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Own MAC address: " MACSTR, 282034af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt MAC2STR(wpa_s->own_addr)); 2821661b4f78e48c697429dc46154a4125892c001718Dmitry Shmidt os_memcpy(wpa_s->perm_addr, wpa_s->own_addr, ETH_ALEN); 282234af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_sm_set_own_addr(wpa_s->wpa, wpa_s->own_addr); 282334af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt 28248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->bridge_ifname[0]) { 28258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Receiving packets from bridge " 28268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "interface '%s'", wpa_s->bridge_ifname); 28278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->l2_br = l2_packet_init(wpa_s->bridge_ifname, 28288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->own_addr, 28298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ETH_P_EAPOL, 283004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_rx_eapol_bridge, 283104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s, 1); 28328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->l2_br == NULL) { 28338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Failed to open l2_packet " 28348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "connection for the bridge interface '%s'", 28358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->bridge_ifname); 28368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 28378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 28388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 28398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_clear_keys(wpa_s, NULL); 28418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Make sure that TKIP countermeasures are not left enabled (could 28438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * happen if wpa_supplicant is killed during countermeasures. */ 28448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_countermeasures(wpa_s, 0); 28458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "RSN: flushing PMKID list in the driver"); 28478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_flush_pmkid(wpa_s); 28488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN; 2850c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_s->prev_scan_wildcard = 0; 2851c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 285204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (wpa_supplicant_enabled_networks(wpa_s)) { 28539e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt if (wpa_s->wpa_state == WPA_INTERFACE_DISABLED) { 28549e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED); 28559e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt interface_count = 0; 28569e3f8ee32a0c11c56b11985805b5492d04886a99Dmitry Shmidt } 2857a38abf9af7bec7e89dbfb39ac7bb77223fe47c72Dmitry Shmidt if (!wpa_s->p2p_mgmt && 28589866086a955d00e237cc8df3722e7dff75c02532Dmitry Shmidt wpa_supplicant_delayed_sched_scan(wpa_s, 28599866086a955d00e237cc8df3722e7dff75c02532Dmitry Shmidt interface_count % 3, 28601f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 100000)) 28619866086a955d00e237cc8df3722e7dff75c02532Dmitry Shmidt wpa_supplicant_req_scan(wpa_s, interface_count % 3, 28621f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 100000); 28638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt interface_count++; 28648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else 28658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_INACTIVE); 28668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 28688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 28698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int wpa_supplicant_daemon(const char *pid_file) 28728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 28738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "Daemonize.."); 28748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return os_daemonize(pid_file); 28758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 28768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic struct wpa_supplicant * wpa_supplicant_alloc(void) 28798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 28808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s; 28818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s = os_zalloc(sizeof(*wpa_s)); 28838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s == NULL) 28848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 2885d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->scan_req = INITIAL_SCAN_REQ; 28868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->scan_interval = 5; 28878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->new_connection = 1; 28888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->parent = wpa_s; 28891f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->sched_scanning = 0; 28908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return wpa_s; 28928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 28938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 28948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2895c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt#ifdef CONFIG_HT_OVERRIDES 2896c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2897c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidtstatic int wpa_set_htcap_mcs(struct wpa_supplicant *wpa_s, 2898c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps, 2899c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask, 2900c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt const char *ht_mcs) 2901c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt{ 2902c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* parse ht_mcs into hex array */ 2903c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt int i; 2904c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt const char *tmp = ht_mcs; 2905c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt char *end = NULL; 2906c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2907c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* If ht_mcs is null, do not set anything */ 2908c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (!ht_mcs) 2909c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 2910c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2911c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* This is what we are setting in the kernel */ 2912c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt os_memset(&htcaps->supported_mcs_set, 0, IEEE80211_HT_MCS_MASK_LEN); 2913c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2914c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "set_htcap, ht_mcs -:%s:-", ht_mcs); 2915c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2916c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt for (i = 0; i < IEEE80211_HT_MCS_MASK_LEN; i++) { 2917c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt errno = 0; 2918c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt long v = strtol(tmp, &end, 16); 2919c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (errno == 0) { 2920c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, 2921c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt "htcap value[%i]: %ld end: %p tmp: %p", 2922c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt i, v, end, tmp); 2923c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (end == tmp) 2924c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt break; 2925c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2926c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->supported_mcs_set[i] = v; 2927c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt tmp = end; 2928c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } else { 2929c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, 2930c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt "Failed to parse ht-mcs: %s, error: %s\n", 2931c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt ht_mcs, strerror(errno)); 2932c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return -1; 2933c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 2934c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 2935c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2936c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* 2937c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt * If we were able to parse any values, then set mask for the MCS set. 2938c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt */ 2939c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (i) { 2940c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt os_memset(&htcaps_mask->supported_mcs_set, 0xff, 2941c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt IEEE80211_HT_MCS_MASK_LEN - 1); 2942c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* skip the 3 reserved bits */ 2943c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps_mask->supported_mcs_set[IEEE80211_HT_MCS_MASK_LEN - 1] = 2944c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 0x1f; 2945c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 2946c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2947c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 2948c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt} 2949c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2950c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2951c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidtstatic int wpa_disable_max_amsdu(struct wpa_supplicant *wpa_s, 2952c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps, 2953c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask, 2954c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt int disabled) 2955c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt{ 2956c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt le16 msk; 2957c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2958c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "set_disable_max_amsdu: %d", disabled); 2959c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2960c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (disabled == -1) 2961c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 2962c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2963c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt msk = host_to_le16(HT_CAP_INFO_MAX_AMSDU_SIZE); 2964c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps_mask->ht_capabilities_info |= msk; 2965c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (disabled) 2966c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->ht_capabilities_info &= msk; 2967c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt else 2968c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->ht_capabilities_info |= msk; 2969c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2970c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 2971c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt} 2972c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2973c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2974c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidtstatic int wpa_set_ampdu_factor(struct wpa_supplicant *wpa_s, 2975c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps, 2976c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask, 2977c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt int factor) 2978c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt{ 2979c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "set_ampdu_factor: %d", factor); 2980c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2981c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (factor == -1) 2982c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 2983c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2984c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (factor < 0 || factor > 3) { 2985c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "ampdu_factor: %d out of range. " 2986c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt "Must be 0-3 or -1", factor); 2987c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return -EINVAL; 2988c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 2989c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2990c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps_mask->a_mpdu_params |= 0x3; /* 2 bits for factor */ 2991c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->a_mpdu_params &= ~0x3; 2992c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->a_mpdu_params |= factor & 0x3; 2993c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2994c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 2995c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt} 2996c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2997c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 2998c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidtstatic int wpa_set_ampdu_density(struct wpa_supplicant *wpa_s, 2999c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps, 3000c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask, 3001c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt int density) 3002c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt{ 3003c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "set_ampdu_density: %d", density); 3004c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3005c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (density == -1) 3006c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 3007c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3008c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (density < 0 || density > 7) { 3009c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, 3010c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt "ampdu_density: %d out of range. Must be 0-7 or -1.", 3011c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt density); 3012c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return -EINVAL; 3013c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt } 3014c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3015c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps_mask->a_mpdu_params |= 0x1C; 3016c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->a_mpdu_params &= ~(0x1C); 3017c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->a_mpdu_params |= (density << 2) & 0x1C; 3018c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3019c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 3020c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt} 3021c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3022c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3023c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidtstatic int wpa_set_disable_ht40(struct wpa_supplicant *wpa_s, 3024c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps, 3025c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask, 3026c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt int disabled) 3027c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt{ 3028c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* Masking these out disables HT40 */ 3029c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt le16 msk = host_to_le16(HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET | 3030c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt HT_CAP_INFO_SHORT_GI40MHZ); 3031c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3032c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "set_disable_ht40: %d", disabled); 3033c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3034c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (disabled) 3035c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->ht_capabilities_info &= ~msk; 3036c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt else 3037c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps->ht_capabilities_info |= msk; 3038c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3039c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps_mask->ht_capabilities_info |= msk; 3040c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3041c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 0; 3042c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt} 3043c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3044c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3045a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidtstatic int wpa_set_disable_sgi(struct wpa_supplicant *wpa_s, 3046a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps, 3047a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask, 3048a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt int disabled) 3049a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt{ 3050a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt /* Masking these out disables SGI */ 3051c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt le16 msk = host_to_le16(HT_CAP_INFO_SHORT_GI20MHZ | 3052c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt HT_CAP_INFO_SHORT_GI40MHZ); 3053a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 3054a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "set_disable_sgi: %d", disabled); 3055a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 3056a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt if (disabled) 3057a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt htcaps->ht_capabilities_info &= ~msk; 3058a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt else 3059a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt htcaps->ht_capabilities_info |= msk; 3060a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 3061a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt htcaps_mask->ht_capabilities_info |= msk; 3062a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 3063a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt return 0; 3064a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt} 3065a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 3066a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt 3067df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidtstatic int wpa_set_disable_ldpc(struct wpa_supplicant *wpa_s, 3068df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps, 3069df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask, 3070df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt int disabled) 3071df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt{ 3072df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt /* Masking these out disables LDPC */ 3073c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt le16 msk = host_to_le16(HT_CAP_INFO_LDPC_CODING_CAP); 3074df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 3075df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt wpa_msg(wpa_s, MSG_DEBUG, "set_disable_ldpc: %d", disabled); 3076df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 3077df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt if (disabled) 3078df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt htcaps->ht_capabilities_info &= ~msk; 3079df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt else 3080df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt htcaps->ht_capabilities_info |= msk; 3081df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 3082df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt htcaps_mask->ht_capabilities_info |= msk; 3083df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 3084df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt return 0; 3085df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt} 3086df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 3087df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 3088c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidtvoid wpa_supplicant_apply_ht_overrides( 3089c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid, 3090c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct wpa_driver_associate_params *params) 3091c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt{ 3092c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps; 3093c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt struct ieee80211_ht_capabilities *htcaps_mask; 3094c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3095c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (!ssid) 3096c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return; 3097c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3098c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt params->disable_ht = ssid->disable_ht; 3099c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt if (!params->htcaps || !params->htcaps_mask) 3100c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return; 3101c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3102c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps = (struct ieee80211_ht_capabilities *) params->htcaps; 3103c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt htcaps_mask = (struct ieee80211_ht_capabilities *) params->htcaps_mask; 3104c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_set_htcap_mcs(wpa_s, htcaps, htcaps_mask, ssid->ht_mcs); 3105c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_disable_max_amsdu(wpa_s, htcaps, htcaps_mask, 3106c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt ssid->disable_max_amsdu); 3107c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_set_ampdu_factor(wpa_s, htcaps, htcaps_mask, ssid->ampdu_factor); 3108c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_set_ampdu_density(wpa_s, htcaps, htcaps_mask, ssid->ampdu_density); 3109c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt wpa_set_disable_ht40(wpa_s, htcaps, htcaps_mask, ssid->disable_ht40); 3110a54fa5fb807eaeff45464139b5a7759f060cec68Dmitry Shmidt wpa_set_disable_sgi(wpa_s, htcaps, htcaps_mask, ssid->disable_sgi); 3111df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt wpa_set_disable_ldpc(wpa_s, htcaps, htcaps_mask, ssid->disable_ldpc); 311261593f02176862f4880ddefcb1f54cb5f5d9f043Dmitry Shmidt 311361593f02176862f4880ddefcb1f54cb5f5d9f043Dmitry Shmidt if (ssid->ht40_intolerant) { 3114c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt le16 bit = host_to_le16(HT_CAP_INFO_40MHZ_INTOLERANT); 311561593f02176862f4880ddefcb1f54cb5f5d9f043Dmitry Shmidt htcaps->ht_capabilities_info |= bit; 311661593f02176862f4880ddefcb1f54cb5f5d9f043Dmitry Shmidt htcaps_mask->ht_capabilities_info |= bit; 311761593f02176862f4880ddefcb1f54cb5f5d9f043Dmitry Shmidt } 3118c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt} 3119c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3120c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt#endif /* CONFIG_HT_OVERRIDES */ 3121c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 3122c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 31232f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt#ifdef CONFIG_VHT_OVERRIDES 31242f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidtvoid wpa_supplicant_apply_vht_overrides( 31252f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid, 31262f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt struct wpa_driver_associate_params *params) 31272f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt{ 31282f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt struct ieee80211_vht_capabilities *vhtcaps; 31292f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt struct ieee80211_vht_capabilities *vhtcaps_mask; 3130df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt#ifdef CONFIG_HT_OVERRIDES 3131df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt int max_ampdu; 3132df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt const u32 max_ampdu_mask = VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MAX; 3133df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt#endif /* CONFIG_HT_OVERRIDES */ 31342f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 31352f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (!ssid) 31362f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt return; 31372f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 31382f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt params->disable_vht = ssid->disable_vht; 31392f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 31402f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps = (void *) params->vhtcaps; 31412f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps_mask = (void *) params->vhtcaps_mask; 31422f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 31432f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (!vhtcaps || !vhtcaps_mask) 31442f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt return; 31452f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 31462f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps->vht_capabilities_info = ssid->vht_capa; 31472f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps_mask->vht_capabilities_info = ssid->vht_capa_mask; 31482f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 3149df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt#ifdef CONFIG_HT_OVERRIDES 3150df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt /* if max ampdu is <= 3, we have to make the HT cap the same */ 3151df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt if (ssid->vht_capa_mask & max_ampdu_mask) { 3152df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt max_ampdu = (ssid->vht_capa & max_ampdu_mask) >> 3153df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt find_first_bit(max_ampdu_mask); 3154df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 3155df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt max_ampdu = max_ampdu < 3 ? max_ampdu : 3; 3156df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt wpa_set_ampdu_factor(wpa_s, 3157df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt (void *) params->htcaps, 3158df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt (void *) params->htcaps_mask, 3159df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt max_ampdu); 3160df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt } 3161df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt#endif /* CONFIG_HT_OVERRIDES */ 3162df5a7e4c5c64890c2425bb47d665bbce4992b676Dmitry Shmidt 31632f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt#define OVERRIDE_MCS(i) \ 31642f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (ssid->vht_tx_mcs_nss_ ##i >= 0) { \ 31652f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps_mask->vht_supported_mcs_set.tx_map |= \ 31662f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 3 << 2 * (i - 1); \ 31672f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps->vht_supported_mcs_set.tx_map |= \ 31682f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt ssid->vht_tx_mcs_nss_ ##i << 2 * (i - 1); \ 31692f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt } \ 31702f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt if (ssid->vht_rx_mcs_nss_ ##i >= 0) { \ 31712f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps_mask->vht_supported_mcs_set.rx_map |= \ 31722f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 3 << 2 * (i - 1); \ 31732f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt vhtcaps->vht_supported_mcs_set.rx_map |= \ 31742f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt ssid->vht_rx_mcs_nss_ ##i << 2 * (i - 1); \ 31752f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt } 31762f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 31772f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(1); 31782f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(2); 31792f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(3); 31802f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(4); 31812f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(5); 31822f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(6); 31832f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(7); 31842f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt OVERRIDE_MCS(8); 31852f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt} 31862f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt#endif /* CONFIG_VHT_OVERRIDES */ 31872f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 31882f023193a0fd630eb82ce6381b80911ad5a3462fDmitry Shmidt 318904949598a23f501be6eec21697465fd46a28840aDmitry Shmidtstatic int pcsc_reader_init(struct wpa_supplicant *wpa_s) 319004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 319104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#ifdef PCSC_FUNCS 319204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt size_t len; 319304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 319404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (!wpa_s->conf->pcsc_reader) 319504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 0; 319604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 3197e0e48dc666fb14a7bb60264ca87463ba7bc1fe0bDmitry Shmidt wpa_s->scard = scard_init(wpa_s->conf->pcsc_reader); 319804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (!wpa_s->scard) 319904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 1; 320004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 320104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (wpa_s->conf->pcsc_pin && 320204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt scard_set_pin(wpa_s->scard, wpa_s->conf->pcsc_pin) < 0) { 320304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt scard_deinit(wpa_s->scard); 320404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->scard = NULL; 320504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "PC/SC PIN validation failed"); 320604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return -1; 320704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 320804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 320904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt len = sizeof(wpa_s->imsi) - 1; 321004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (scard_get_imsi(wpa_s->scard, wpa_s->imsi, &len)) { 321104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt scard_deinit(wpa_s->scard); 321204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->scard = NULL; 321304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Could not read IMSI"); 321404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return -1; 321504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 321604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->imsi[len] = '\0'; 321704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 321804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->mnc_len = scard_get_mnc_len(wpa_s->scard); 321904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 322004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_printf(MSG_DEBUG, "SCARD: IMSI %s (MNC length %d)", 322104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->imsi, wpa_s->mnc_len); 322204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 322304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_sm_set_scard_ctx(wpa_s->wpa, wpa_s->scard); 322404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eapol_sm_register_scard_ctx(wpa_s->eapol, wpa_s->scard); 322504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#endif /* PCSC_FUNCS */ 322604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 322704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 0; 322804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 322904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 323004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 323161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtint wpas_init_ext_pw(struct wpa_supplicant *wpa_s) 323261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 323361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt char *val, *pos; 323461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 323561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ext_password_deinit(wpa_s->ext_pw); 323661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_s->ext_pw = NULL; 323761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt eapol_sm_set_ext_pw_ctx(wpa_s->eapol, NULL); 323861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 323961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (!wpa_s->conf->ext_password_backend) 324061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 0; 324161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 324261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt val = os_strdup(wpa_s->conf->ext_password_backend); 324361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (val == NULL) 324461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 324561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt pos = os_strchr(val, ':'); 324661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (pos) 324761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt *pos++ = '\0'; 324861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 324961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "EXT PW: Initialize backend '%s'", val); 325061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 325161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_s->ext_pw = ext_password_init(val, pos); 325261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt os_free(val); 325361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wpa_s->ext_pw == NULL) { 325461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "EXT PW: Failed to initialize backend"); 325561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 325661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 325761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt eapol_sm_set_ext_pw_ctx(wpa_s->eapol, wpa_s->ext_pw); 325861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 325961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 0; 326061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 326161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 326261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 3263c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidtstatic int wpas_set_wowlan_triggers(struct wpa_supplicant *wpa_s, 3264c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt struct wpa_driver_capa *capa) 3265b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt{ 32660207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt struct wowlan_triggers *triggers; 32670207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt int ret = 0; 3268b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt 3269b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt if (!wpa_s->conf->wowlan_triggers) 3270b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt return 0; 3271b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt 32720207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt triggers = wpa_get_wowlan_triggers(wpa_s->conf->wowlan_triggers, capa); 32730207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt if (triggers) { 32740207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt ret = wpa_drv_wowlan(wpa_s, triggers); 32750207e233ee2e741f7b2c124c1366e905ebb634c8Dmitry Shmidt os_free(triggers); 3276b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt } 3277b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt return ret; 3278b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt} 3279b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt 3280b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt 328101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidtstatic struct wpa_radio * radio_add_interface(struct wpa_supplicant *wpa_s, 328201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt const char *rn) 328301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt{ 328401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt struct wpa_supplicant *iface = wpa_s->global->ifaces; 328501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt struct wpa_radio *radio; 328601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 328701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt while (rn && iface) { 328801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt radio = iface->radio; 328901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (radio && os_strcmp(rn, radio->name) == 0) { 329001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_printf(MSG_DEBUG, "Add interface %s to existing radio %s", 329101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->ifname, rn); 329201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt dl_list_add(&radio->ifaces, &wpa_s->radio_list); 329301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return radio; 329401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 32953cf6f79011d16f23e60cbf2846aab0fd440511daDmitry Shmidt 32963cf6f79011d16f23e60cbf2846aab0fd440511daDmitry Shmidt iface = iface->next; 329701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 329801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 329901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_printf(MSG_DEBUG, "Add interface %s to a new radio %s", 330001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->ifname, rn ? rn : "N/A"); 330101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt radio = os_zalloc(sizeof(*radio)); 330201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (radio == NULL) 330301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return NULL; 330401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 330501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (rn) 330601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt os_strlcpy(radio->name, rn, sizeof(radio->name)); 330701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt dl_list_init(&radio->ifaces); 3308fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt dl_list_init(&radio->work); 330901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt dl_list_add(&radio->ifaces, &wpa_s->radio_list); 331001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 331101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return radio; 331201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt} 331301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 331401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 3315fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtstatic void radio_work_free(struct wpa_radio_work *work) 3316fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 3317fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (work->wpa_s->scan_work == work) { 3318fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt /* This should not really happen. */ 3319fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(work->wpa_s, MSG_INFO, "Freeing radio work '%s'@%p (started=%d) that is marked as scan_work", 3320fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->type, work, work->started); 3321fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->wpa_s->scan_work = NULL; 3322fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 3323fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3324fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt#ifdef CONFIG_P2P 3325fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (work->wpa_s->p2p_scan_work == work) { 3326fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt /* This should not really happen. */ 3327fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(work->wpa_s, MSG_INFO, "Freeing radio work '%s'@%p (started=%d) that is marked as p2p_scan_work", 3328fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->type, work, work->started); 3329fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->wpa_s->p2p_scan_work = NULL; 3330fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 3331fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt#endif /* CONFIG_P2P */ 3332fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3333fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt dl_list_del(&work->list); 3334fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_free(work); 3335fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 3336fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3337fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3338fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtstatic void radio_start_next_work(void *eloop_ctx, void *timeout_ctx) 3339fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 3340fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_radio *radio = eloop_ctx; 3341fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_radio_work *work; 3342fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct os_reltime now, diff; 3343fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_supplicant *wpa_s; 3344fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3345fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work = dl_list_first(&radio->work, struct wpa_radio_work, list); 3346fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (work == NULL) 3347fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 3348fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3349fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (work->started) 3350fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; /* already started and still in progress */ 3351fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3352fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_s = dl_list_first(&radio->ifaces, struct wpa_supplicant, 3353fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt radio_list); 3354fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (wpa_s && wpa_s->external_scan_running) { 3355fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_printf(MSG_DEBUG, "Delay radio work start until externally triggered scan completes"); 3356fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 3357fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 3358fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3359fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_get_reltime(&now); 3360fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_reltime_sub(&now, &work->time, &diff); 3361fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(work->wpa_s, MSG_DEBUG, "Starting radio work '%s'@%p after %ld.%06ld second wait", 3362fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->type, work, diff.sec, diff.usec); 3363fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->started = 1; 3364fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->time = now; 3365fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->cb(work, 0); 3366fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 3367fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3368fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3369bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt/* 3370bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * This function removes both started and pending radio works running on 3371bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * the provided interface's radio. 3372bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * Prior to the removal of the radio work, its callback (cb) is called with 3373bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * deinit set to be 1. Each work's callback is responsible for clearing its 3374bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * internal data and restoring to a correct state. 3375bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * @wpa_s: wpa_supplicant data 3376bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * @type: type of works to be removed 3377bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * @remove_all: 1 to remove all the works on this radio, 0 to remove only 3378bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt * this interface's works. 3379bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt */ 3380bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidtvoid radio_remove_works(struct wpa_supplicant *wpa_s, 3381bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt const char *type, int remove_all) 3382fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 3383fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_radio_work *work, *tmp; 3384fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_radio *radio = wpa_s->radio; 3385fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3386fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt dl_list_for_each_safe(work, tmp, &radio->work, struct wpa_radio_work, 3387fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt list) { 3388bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt if (type && os_strcmp(type, work->type) != 0) 3389fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt continue; 3390bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt 3391bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt /* skip other ifaces' works */ 3392bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt if (!remove_all && work->wpa_s != wpa_s) 3393fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt continue; 3394bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt 3395bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Remove radio work '%s'@%p%s", 3396bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt work->type, work, work->started ? " (started)" : ""); 3397fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->cb(work, 1); 3398fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt radio_work_free(work); 3399fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 3400bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt 3401bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt /* in case we removed the started work */ 3402bd14a57187b024f49f5b9ace55ef457d8d04650aDmitry Shmidt radio_work_check_next(wpa_s); 3403fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 3404fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3405fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 340601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidtstatic void radio_remove_interface(struct wpa_supplicant *wpa_s) 340701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt{ 340801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt struct wpa_radio *radio = wpa_s->radio; 340901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 341001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (!radio) 341101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return; 341201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 341301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_printf(MSG_DEBUG, "Remove interface %s from radio %s", 341401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->ifname, radio->name); 341501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt dl_list_del(&wpa_s->radio_list); 3416d11f019d62a42a8fc4c4d1f2ec17cf35b0763153Dmitry Shmidt radio_remove_works(wpa_s, NULL, 0); 3417d11f019d62a42a8fc4c4d1f2ec17cf35b0763153Dmitry Shmidt wpa_s->radio = NULL; 3418d11f019d62a42a8fc4c4d1f2ec17cf35b0763153Dmitry Shmidt if (!dl_list_empty(&radio->ifaces)) 341901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return; /* Interfaces remain for this radio */ 342001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 342101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_printf(MSG_DEBUG, "Remove radio %s", radio->name); 3422fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt eloop_cancel_timeout(radio_start_next_work, radio, NULL); 342301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt os_free(radio); 342401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt} 342501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 342601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 3427fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtvoid radio_work_check_next(struct wpa_supplicant *wpa_s) 3428fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 3429fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_radio *radio = wpa_s->radio; 3430fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3431fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (dl_list_empty(&radio->work)) 3432fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return; 3433fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt eloop_cancel_timeout(radio_start_next_work, radio, NULL); 3434fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt eloop_register_timeout(0, 0, radio_start_next_work, radio, NULL); 3435fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 3436fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3437fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3438fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt/** 3439fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * radio_add_work - Add a radio work item 3440fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * @wpa_s: Pointer to wpa_supplicant data 3441fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * @freq: Frequency of the offchannel operation in MHz or 0 3442fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * @type: Unique identifier for each type of work 3443fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * @next: Force as the next work to be executed 3444fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * @cb: Callback function for indicating when radio is available 3445fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * @ctx: Context pointer for the work (work->ctx in cb()) 3446fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * Returns: 0 on success, -1 on failure 3447fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * 3448fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * This function is used to request time for an operation that requires 3449fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * exclusive radio control. Once the radio is available, the registered callback 3450fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * function will be called. radio_work_done() must be called once the exclusive 3451fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * radio operation has been completed, so that the radio is freed for other 3452fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * operations. The special case of deinit=1 is used to free the context data 3453fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * during interface removal. That does not allow the callback function to start 3454fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * the radio operation, i.e., it must free any resources allocated for the radio 3455fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * work and return. 3456fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * 3457fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * The @freq parameter can be used to indicate a single channel on which the 3458fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * offchannel operation will occur. This may allow multiple radio work 3459fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * operations to be performed in parallel if they apply for the same channel. 3460fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * Setting this to 0 indicates that the work item may use multiple channels or 3461fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * requires exclusive control of the radio. 3462fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt */ 3463fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtint radio_add_work(struct wpa_supplicant *wpa_s, unsigned int freq, 3464fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt const char *type, int next, 3465fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt void (*cb)(struct wpa_radio_work *work, int deinit), 3466fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt void *ctx) 3467fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 3468fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_radio_work *work; 3469fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt int was_empty; 3470fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3471fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work = os_zalloc(sizeof(*work)); 3472fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (work == NULL) 3473fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return -1; 3474fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Add radio work '%s'@%p", type, work); 3475fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_get_reltime(&work->time); 3476fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->freq = freq; 3477fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->type = type; 3478fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->wpa_s = wpa_s; 3479fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->cb = cb; 3480fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->ctx = ctx; 3481fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3482fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt was_empty = dl_list_empty(&wpa_s->radio->work); 3483fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (next) 3484fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt dl_list_add(&wpa_s->radio->work, &work->list); 3485fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt else 3486fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt dl_list_add_tail(&wpa_s->radio->work, &work->list); 3487fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (was_empty) { 3488fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "First radio work item in the queue - schedule start immediately"); 3489fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt radio_work_check_next(wpa_s); 3490fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt } 3491fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3492fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt return 0; 3493fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 3494fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3495fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3496fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt/** 3497fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * radio_work_done - Indicate that a radio work item has been completed 3498fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * @work: Completed work 3499fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * 3500fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * This function is called once the callback function registered with 3501fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt * radio_add_work() has completed its work. 3502fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt */ 3503fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidtvoid radio_work_done(struct wpa_radio_work *work) 3504fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt{ 3505fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct wpa_supplicant *wpa_s = work->wpa_s; 3506fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct os_reltime now, diff; 3507fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt unsigned int started = work->started; 3508fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3509fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_get_reltime(&now); 3510fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_reltime_sub(&now, &work->time, &diff); 3511fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Radio work '%s'@%p %s in %ld.%06ld seconds", 3512fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt work->type, work, started ? "done" : "canceled", 3513fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt diff.sec, diff.usec); 3514fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt radio_work_free(work); 3515fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt if (started) 3516fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt radio_work_check_next(wpa_s); 3517fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt} 3518fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 3519fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 35202e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidtstruct wpa_radio_work * 35212e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidtradio_work_pending(struct wpa_supplicant *wpa_s, const char *type) 3522f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt{ 3523f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt struct wpa_radio_work *work; 3524f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt struct wpa_radio *radio = wpa_s->radio; 3525f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt 3526f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt dl_list_for_each(work, &radio->work, struct wpa_radio_work, list) { 3527f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt if (work->wpa_s == wpa_s && os_strcmp(work->type, type) == 0) 35282e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt return work; 3529f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt } 3530f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt 35312e425d69801667e42b4874548f2a49dc16e95617Dmitry Shmidt return NULL; 3532f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt} 3533f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt 3534f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt 353501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidtstatic int wpas_init_driver(struct wpa_supplicant *wpa_s, 353601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt struct wpa_interface *iface) 353701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt{ 353801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt const char *ifname, *driver, *rn; 353901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 354001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt driver = iface->driver; 354101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidtnext_driver: 354201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (wpa_supplicant_set_driver(wpa_s, driver) < 0) 354301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return -1; 354401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 354501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->drv_priv = wpa_drv_init(wpa_s, wpa_s->ifname); 354601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (wpa_s->drv_priv == NULL) { 354701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt const char *pos; 354801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt pos = driver ? os_strchr(driver, ',') : NULL; 354901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (pos) { 355001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Failed to initialize " 355101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt "driver interface - try next driver wrapper"); 355201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt driver = pos + 1; 355301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt goto next_driver; 355401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 355501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Failed to initialize driver " 355601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt "interface"); 355701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return -1; 355801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 355901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (wpa_drv_set_param(wpa_s, wpa_s->conf->driver_param) < 0) { 356001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Driver interface rejected " 356101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt "driver_param '%s'", wpa_s->conf->driver_param); 356201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return -1; 356301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 356401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 356501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt ifname = wpa_drv_get_ifname(wpa_s); 356601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (ifname && os_strcmp(ifname, wpa_s->ifname) != 0) { 356701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Driver interface replaced " 356801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt "interface name with '%s'", ifname); 356901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt os_strlcpy(wpa_s->ifname, ifname, sizeof(wpa_s->ifname)); 357001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt } 357101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 3572d11f019d62a42a8fc4c4d1f2ec17cf35b0763153Dmitry Shmidt rn = wpa_driver_get_radio_name(wpa_s); 357301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (rn && rn[0] == '\0') 357401904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt rn = NULL; 357501904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 357601904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt wpa_s->radio = radio_add_interface(wpa_s, rn); 357701904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (wpa_s->radio == NULL) 357801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return -1; 357901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 358001904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt return 0; 358101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt} 358201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 358301904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 35848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int wpa_supplicant_init_iface(struct wpa_supplicant *wpa_s, 35858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_interface *iface) 35868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 35878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_driver_capa capa; 35888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 35898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "Initializing interface '%s' conf '%s' driver " 35908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "'%s' ctrl_interface '%s' bridge '%s'", iface->ifname, 35918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->confname ? iface->confname : "N/A", 35928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->driver ? iface->driver : "default", 35938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->ctrl_interface ? iface->ctrl_interface : "N/A", 35948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->bridge_ifname ? iface->bridge_ifname : "N/A"); 35958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 35968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (iface->confname) { 35978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_BACKEND_FILE 35988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->confname = os_rel2abs_path(iface->confname); 35998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->confname == NULL) { 36008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "Failed to get absolute path " 36018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "for configuration file '%s'.", 36028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->confname); 36038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "Configuration file '%s' -> '%s'", 36068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->confname, wpa_s->confname); 36078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* CONFIG_BACKEND_FILE */ 36088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->confname = os_strdup(iface->confname); 36098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_BACKEND_FILE */ 361064f47c5c24428834677459e048420f86e3514c20Dmitry Shmidt wpa_s->conf = wpa_config_read(wpa_s->confname, NULL); 36118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->conf == NULL) { 36128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "Failed to read or parse " 36138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "configuration '%s'.", wpa_s->confname); 36148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 361664f47c5c24428834677459e048420f86e3514c20Dmitry Shmidt wpa_s->confanother = os_rel2abs_path(iface->confanother); 361764f47c5c24428834677459e048420f86e3514c20Dmitry Shmidt wpa_config_read(wpa_s->confanother, wpa_s->conf); 36188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 36208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Override ctrl_interface and driver_param if set on command 36218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * line. 36228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 36238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (iface->ctrl_interface) { 36248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(wpa_s->conf->ctrl_interface); 36258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->ctrl_interface = 36268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strdup(iface->ctrl_interface); 36278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (iface->driver_param) { 36308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(wpa_s->conf->driver_param); 36318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->driver_param = 36328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strdup(iface->driver_param); 36338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 363434af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt 363534af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt if (iface->p2p_mgmt && !iface->ctrl_interface) { 363634af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt os_free(wpa_s->conf->ctrl_interface); 363734af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_s->conf->ctrl_interface = NULL; 363834af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt } 36398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else 36408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf = wpa_config_alloc_empty(iface->ctrl_interface, 36418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->driver_param); 36428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->conf == NULL) { 36448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "\nNo configuration found."); 36458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (iface->ifname == NULL) { 36498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "\nInterface name is required."); 36508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strlen(iface->ifname) >= sizeof(wpa_s->ifname)) { 36538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "\nToo long interface name '%s'.", 36548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->ifname); 36558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strlcpy(wpa_s->ifname, iface->ifname, sizeof(wpa_s->ifname)); 36588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (iface->bridge_ifname) { 36608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strlen(iface->bridge_ifname) >= 36618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sizeof(wpa_s->bridge_ifname)) { 36628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "\nToo long bridge interface " 36638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "name '%s'.", iface->bridge_ifname); 36648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strlcpy(wpa_s->bridge_ifname, iface->bridge_ifname, 36678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sizeof(wpa_s->bridge_ifname)); 36688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* RSNA Supplicant Key Management - INITIALIZE */ 36718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_portEnabled(wpa_s->eapol, FALSE); 36728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_sm_notify_portValid(wpa_s->eapol, FALSE); 36738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Initialize driver interface and register driver event handler before 36758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * L2 receive handler so that association events are processed before 36768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * EAPOL-Key packets if both become available for the same select() 36778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * call. */ 367801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt if (wpas_init_driver(wpa_s, iface) < 0) 36798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_init_wpa(wpa_s) < 0) 36828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_ifname(wpa_s->wpa, wpa_s->ifname, 36858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->bridge_ifname[0] ? wpa_s->bridge_ifname : 36868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt NULL); 36878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_fast_reauth(wpa_s->wpa, wpa_s->conf->fast_reauth); 36888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->conf->dot11RSNAConfigPMKLifetime && 36908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, RSNA_PMK_LIFETIME, 36918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->dot11RSNAConfigPMKLifetime)) { 36928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Invalid WPA parameter value for " 36938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "dot11RSNAConfigPMKLifetime"); 36948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 36958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 36968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 36978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->conf->dot11RSNAConfigPMKReauthThreshold && 36988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, RSNA_PMK_REAUTH_THRESHOLD, 36998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->dot11RSNAConfigPMKReauthThreshold)) { 37008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Invalid WPA parameter value for " 37018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "dot11RSNAConfigPMKReauthThreshold"); 37028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 37048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->conf->dot11RSNAConfigSATimeout && 37068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_param(wpa_s->wpa, RSNA_SA_TIMEOUT, 37078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->dot11RSNAConfigSATimeout)) { 37088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Invalid WPA parameter value for " 37098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "dot11RSNAConfigSATimeout"); 37108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 37128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37131f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->hw.modes = wpa_drv_get_hw_feature_data(wpa_s, 37141f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt &wpa_s->hw.num_modes, 37151f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt &wpa_s->hw.flags); 37161f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 37178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_drv_get_capa(wpa_s, &capa) == 0) { 37181f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->drv_capa_known = 1; 37198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->drv_flags = capa.flags; 372004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->drv_enc = capa.enc; 37211f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->probe_resp_offloads = capa.probe_resp_offloads; 37228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->max_scan_ssids = capa.max_scan_ssids; 37231f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->max_sched_scan_ssids = capa.max_sched_scan_ssids; 37241f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->sched_scan_supported = capa.sched_scan_supported; 37251f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->max_match_sets = capa.max_match_sets; 37268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->max_remain_on_chan = capa.max_remain_on_chan; 37278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->max_stations = capa.max_stations; 3728444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt wpa_s->extended_capa = capa.extended_capa; 3729444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt wpa_s->extended_capa_mask = capa.extended_capa_mask; 3730444d567b27731d8572ef37697dd12fd1c37c2f24Dmitry Shmidt wpa_s->extended_capa_len = capa.extended_capa_len; 3731c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt wpa_s->num_multichan_concurrent = 3732c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt capa.num_multichan_concurrent; 37338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 37348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->max_remain_on_chan == 0) 37358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->max_remain_on_chan = 1000; 37368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 373734af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt /* 373834af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt * Only take p2p_mgmt parameters when P2P Device is supported. 373934af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt * Doing it here as it determines whether l2_packet_init() will be done 374034af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt * during wpa_supplicant_driver_init(). 374134af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt */ 374234af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt if (wpa_s->drv_flags & WPA_DRIVER_FLAGS_DEDICATED_P2P_DEVICE) 374334af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_s->p2p_mgmt = iface->p2p_mgmt; 374434af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt else 374534af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt iface->p2p_mgmt = 1; 374634af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt 3747c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt if (wpa_s->num_multichan_concurrent == 0) 3748c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt wpa_s->num_multichan_concurrent = 1; 3749c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt 37508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_driver_init(wpa_s) < 0) 37518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_TDLS 375434af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt if ((!iface->p2p_mgmt || 375534af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt !(wpa_s->drv_flags & 375634af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt WPA_DRIVER_FLAGS_DEDICATED_P2P_DEVICE)) && 375734af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_tdls_init(wpa_s->wpa)) 37588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_TDLS */ 37608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->conf->country[0] && wpa_s->conf->country[1] && 37628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_country(wpa_s, wpa_s->conf->country)) { 37638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Failed to set country"); 37648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 37668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpas_wps_init(wpa_s)) 37688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_init_eapol(wpa_s) < 0) 37718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_sm_set_eapol(wpa_s->wpa, wpa_s->eapol); 37738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->ctrl_iface = wpa_supplicant_ctrl_iface_init(wpa_s); 37758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->ctrl_iface == NULL) { 37768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, 37778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "Failed to initialize control interface '%s'.\n" 37788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "You may have another wpa_supplicant process " 37798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "already running or the file was\n" 37808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "left by an unclean termination of wpa_supplicant " 37818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "in which case you will need\n" 37828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "to manually remove this file before starting " 37838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "wpa_supplicant again.\n", 37848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->ctrl_interface); 37858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 37878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37881f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_s->gas = gas_query_init(wpa_s); 37891f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt if (wpa_s->gas == NULL) { 37901f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt wpa_printf(MSG_ERROR, "Failed to initialize GAS query"); 37911f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return -1; 37921f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 37931f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 379434af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt if (iface->p2p_mgmt && wpas_p2p_init(wpa_s->global, wpa_s) < 0) { 37958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg(wpa_s, MSG_ERROR, "Failed to init P2P"); 37968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 37978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 37988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 37998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_bss_init(wpa_s) < 0) 38008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 38018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3802b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt /* 3803b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt * Set Wake-on-WLAN triggers, if configured. 3804b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt * Note: We don't restore/remove the triggers on shutdown (it doesn't 3805b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt * have effect anyway when the interface is down). 3806b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt */ 3807b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt if (wpas_set_wowlan_triggers(wpa_s, &capa) < 0) 3808b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt return -1; 3809b58836ed5520bf4b769f76ef7dcb802af8c900b8Dmitry Shmidt 381034af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt#ifdef CONFIG_EAP_PROXY 381134af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt{ 381234af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt size_t len; 38134ce9c87407c036fc83eb5a6044ddf976c86f53fcDmitry Shmidt wpa_s->mnc_len = eapol_sm_get_eap_proxy_imsi(wpa_s->eapol, wpa_s->imsi, 38144ce9c87407c036fc83eb5a6044ddf976c86f53fcDmitry Shmidt &len); 381534af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt if (wpa_s->mnc_len > 0) { 381634af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_s->imsi[len] = '\0'; 381734af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_printf(MSG_DEBUG, "eap_proxy: IMSI %s (MNC length %d)", 381834af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_s->imsi, wpa_s->mnc_len); 381934af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt } else { 382034af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt wpa_printf(MSG_DEBUG, "eap_proxy: IMSI not available"); 382134af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt } 382234af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt} 382334af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt#endif /* CONFIG_EAP_PROXY */ 382434af306c42b7ccf956508e7cd23f0ba90606e360Dmitry Shmidt 382504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (pcsc_reader_init(wpa_s) < 0) 382604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return -1; 382704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 382861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wpas_init_ext_pw(wpa_s) < 0) 382961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 383061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 38318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 38328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 38338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void wpa_supplicant_deinit_iface(struct wpa_supplicant *wpa_s, 3836e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt int notify, int terminate) 38378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3838ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt wpa_s->disconnected = 1; 38398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->drv_priv) { 38408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_deauthenticate(wpa_s, 38418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WLAN_REASON_DEAUTH_LEAVING); 38428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_set_countermeasures(wpa_s, 0); 38448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_clear_keys(wpa_s, NULL); 38458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 38468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_cleanup(wpa_s); 384843cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt wpas_p2p_deinit_iface(wpa_s); 384904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 3850fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpas_ctrl_radio_work_flush(wpa_s); 385101904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt radio_remove_interface(wpa_s); 385201904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt 38538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->drv_priv) 38548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drv_deinit(wpa_s); 3855622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff 3856e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt if (notify) 3857e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt wpas_notify_iface_removed(wpa_s); 3858e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt 3859e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt if (terminate) 3860e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_TERMINATING); 3861622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff 3862622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff if (wpa_s->ctrl_iface) { 3863622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff wpa_supplicant_ctrl_iface_deinit(wpa_s->ctrl_iface); 3864622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff wpa_s->ctrl_iface = NULL; 3865622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff } 3866622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff 3867622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff if (wpa_s->conf != NULL) { 3868622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff wpa_config_free(wpa_s->conf); 3869622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff wpa_s->conf = NULL; 3870622b66d6efd0cccfeb8623184fadf2f76e7e8206Irfan Sheriff } 38718da800a193fb6f8832218715f82a7b4e2d2ad338Dmitry Shmidt 38728da800a193fb6f8832218715f82a7b4e2d2ad338Dmitry Shmidt os_free(wpa_s); 38738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 38748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 38778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_add_iface - Add a new network interface 38788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @global: Pointer to global data from wpa_supplicant_init() 38798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @iface: Interface configuration options 38808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Pointer to the created interface or %NULL on failure 38818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 38828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to add new network interfaces for %wpa_supplicant. 38838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This can be called before wpa_supplicant_run() to add interfaces before the 38848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * main event loop has been started. In addition, new interfaces can be added 38858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * dynamically while %wpa_supplicant is already running. This could happen, 38868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * e.g., when a hotplug network adapter is inserted. 38878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 38888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct wpa_supplicant * wpa_supplicant_add_iface(struct wpa_global *global, 38898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_interface *iface) 38908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 38918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s; 38928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_interface t_iface; 38938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_ssid *ssid; 38948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global == NULL || iface == NULL) 38968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 38978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 38988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s = wpa_supplicant_alloc(); 38998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s == NULL) 39008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 39018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->global = global; 39038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt t_iface = *iface; 39058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->params.override_driver) { 39068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "Override interface parameter: driver " 39078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "('%s' -> '%s')", 39088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->driver, global->params.override_driver); 39098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt t_iface.driver = global->params.override_driver; 39108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 39118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->params.override_ctrl_interface) { 39128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "Override interface parameter: " 39138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "ctrl_interface ('%s' -> '%s')", 39148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->ctrl_interface, 39158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.override_ctrl_interface); 39168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt t_iface.ctrl_interface = 39178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.override_ctrl_interface; 39188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 39198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_supplicant_init_iface(wpa_s, &t_iface)) { 39208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "Failed to add interface %s", 39218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt iface->ifname); 3922e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt wpa_supplicant_deinit_iface(wpa_s, 0, 0); 39238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 39248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 39258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Notify the control interfaces about new iface */ 39278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpas_notify_iface_added(wpa_s)) { 3928e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt wpa_supplicant_deinit_iface(wpa_s, 1, 0); 39298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 39308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 39318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) 39338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_network_added(wpa_s, ssid); 39348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->next = global->ifaces; 39368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->ifaces = wpa_s; 39378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Added interface %s", wpa_s->ifname); 393904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED); 39408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return wpa_s; 39428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 39438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 39468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_remove_iface - Remove a network interface 39478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @global: Pointer to global data from wpa_supplicant_init() 39488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to the network interface to be removed 39498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 if interface was removed, -1 if interface was not found 39508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 39518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function can be used to dynamically remove network interfaces from 39528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * %wpa_supplicant, e.g., when a hotplug network adapter is ejected. In 39538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * addition, this function is used to remove all remaining interfaces when 39548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * %wpa_supplicant is terminated. 39558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 39568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_remove_iface(struct wpa_global *global, 3957e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt struct wpa_supplicant *wpa_s, 3958e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt int terminate) 39598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 39608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *prev; 39618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Remove interface from the global list of interfaces */ 39638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt prev = global->ifaces; 39648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (prev == wpa_s) { 39658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->ifaces = wpa_s->next; 39668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 39678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (prev && prev->next != wpa_s) 39688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt prev = prev->next; 39698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (prev == NULL) 39708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 39718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt prev->next = wpa_s->next; 39728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 39738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Removing interface %s", wpa_s->ifname); 39758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->p2p_group_formation == wpa_s) 39778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->p2p_group_formation = NULL; 3978700a137ab366edc72e371da68ba187b4717ee660Dmitry Shmidt if (global->p2p_invite_group == wpa_s) 3979700a137ab366edc72e371da68ba187b4717ee660Dmitry Shmidt global->p2p_invite_group = NULL; 3980e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt wpa_supplicant_deinit_iface(wpa_s, 1, terminate); 39818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 39838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 39848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 39878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_get_eap_mode - Get the current EAP mode 39888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @wpa_s: Pointer to the network interface 39898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Pointer to the eap mode or the string "UNKNOWN" if not found 39908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 39918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char * wpa_supplicant_get_eap_mode(struct wpa_supplicant *wpa_s) 39928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 39938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *eapol_method; 39948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 39958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) == 0 && 39968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->key_mgmt != WPA_KEY_MGMT_IEEE8021X_NO_WPA) { 39978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "NO-EAP"; 39988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 39998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eapol_method = eapol_sm_get_method_name(wpa_s->eapol); 40018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (eapol_method == NULL) 40028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return "UNKNOWN-EAP"; 40038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return eapol_method; 40058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 40068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 40098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_get_iface - Get a new network interface 40108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @global: Pointer to global data from wpa_supplicant_init() 40118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ifname: Interface name 40128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Pointer to the interface or %NULL if not found 40138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 40148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct wpa_supplicant * wpa_supplicant_get_iface(struct wpa_global *global, 40158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *ifname) 40168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 40178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s; 40188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next) { 40208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strcmp(wpa_s->ifname, ifname) == 0) 40218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return wpa_s; 40228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 40238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 40248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 40258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifndef CONFIG_NO_WPA_MSG 40288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic const char * wpa_supplicant_msg_ifname_cb(void *ctx) 40298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 40308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s = ctx; 40318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s == NULL) 40328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 40338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return wpa_s->ifname; 40348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 40358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NO_WPA_MSG */ 40368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 40398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_init - Initialize %wpa_supplicant 40408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @params: Parameters for %wpa_supplicant 40418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Pointer to global %wpa_supplicant data, or %NULL on failure 40428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 40438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is used to initialize %wpa_supplicant. After successful 40448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * initialization, the returned data pointer can be used to add and remove 40458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * network interfaces, and eventually, to deinitialize %wpa_supplicant. 40468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 40478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct wpa_global * wpa_supplicant_init(struct wpa_params *params) 40488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 40498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_global *global; 40508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int ret, i; 40518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (params == NULL) 40538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 40548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40551f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#ifdef CONFIG_DRIVER_NDIS 40561f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt { 40571f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt void driver_ndis_init_ops(void); 40581f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt driver_ndis_init_ops(); 40591f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt } 40601f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt#endif /* CONFIG_DRIVER_NDIS */ 40611f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 40628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifndef CONFIG_NO_WPA_MSG 40638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_msg_register_ifname_cb(wpa_supplicant_msg_ifname_cb); 40648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NO_WPA_MSG */ 40658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_open_file(params->wpa_debug_file_path); 40678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (params->wpa_debug_syslog) 40688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_open_syslog(); 406904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (params->wpa_debug_tracing) { 407004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt ret = wpa_debug_open_linux_tracing(); 407104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ret) { 407204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_printf(MSG_ERROR, 407304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt "Failed to enable trace logging"); 407404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return NULL; 407504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 407604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 40778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ret = eap_register_methods(); 40798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret) { 40808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "Failed to register EAP methods"); 40818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret == -2) 40828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "Two or more EAP methods used " 40838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "the same EAP type."); 40848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 40858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 40868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 40878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global = os_zalloc(sizeof(*global)); 40888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global == NULL) 40898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 40908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt dl_list_init(&global->p2p_srv_bonjour); 40918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt dl_list_init(&global->p2p_srv_upnp); 40928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.daemonize = params->daemonize; 40938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.wait_for_monitor = params->wait_for_monitor; 40948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.dbus_ctrl_interface = params->dbus_ctrl_interface; 40958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (params->pid_file) 40968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.pid_file = os_strdup(params->pid_file); 40978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (params->ctrl_interface) 40988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.ctrl_interface = 40998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strdup(params->ctrl_interface); 4100b6e9aaf735990dc64cdb6efccc03d076768eabf3Dmitry Shmidt if (params->ctrl_interface_group) 4101b6e9aaf735990dc64cdb6efccc03d076768eabf3Dmitry Shmidt global->params.ctrl_interface_group = 4102b6e9aaf735990dc64cdb6efccc03d076768eabf3Dmitry Shmidt os_strdup(params->ctrl_interface_group); 41038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (params->override_driver) 41048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.override_driver = 41058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strdup(params->override_driver); 41068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (params->override_ctrl_interface) 41078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->params.override_ctrl_interface = 41088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_strdup(params->override_ctrl_interface); 41098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_level = global->params.wpa_debug_level = 41108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params->wpa_debug_level; 41118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_show_keys = global->params.wpa_debug_show_keys = 41128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params->wpa_debug_show_keys; 41138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_timestamp = global->params.wpa_debug_timestamp = 41148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt params->wpa_debug_timestamp; 41158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "wpa_supplicant v" VERSION_STR); 41178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (eloop_init()) { 41198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "Failed to initialize event loop"); 41208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_deinit(global); 41218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 41228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 41238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 412475ecf5267604f166b85a7ee2cf0d9cb682966680Jouni Malinen random_init(params->entropy_file); 41258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->ctrl_iface = wpa_supplicant_global_ctrl_iface_init(global); 41278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->ctrl_iface == NULL) { 41288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_deinit(global); 41298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 41308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 41318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpas_notify_supplicant_initialized(global)) { 41338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_deinit(global); 41348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 41358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 41368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; wpa_drivers[i]; i++) 41388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->drv_count++; 41398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->drv_count == 0) { 41408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "No drivers enabled"); 41418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_deinit(global); 41428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 41438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 41448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt global->drv_priv = os_zalloc(global->drv_count * sizeof(void *)); 41458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->drv_priv == NULL) { 41468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_deinit(global); 41478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 41488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 41498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 415061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#ifdef CONFIG_WIFI_DISPLAY 415161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wifi_display_init(global) < 0) { 415261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_ERROR, "Failed to initialize Wi-Fi Display"); 415361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_supplicant_deinit(global); 415461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return NULL; 415561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 415661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#endif /* CONFIG_WIFI_DISPLAY */ 415761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 41588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return global; 41598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 41608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 41638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_run - Run the %wpa_supplicant main event loop 41648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @global: Pointer to global data from wpa_supplicant_init() 41658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 after successful event loop run, -1 on failure 41668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 41678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function starts the main event loop and continues running as long as 41688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * there are any remaining events. In most cases, this function is running as 41698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * long as the %wpa_supplicant process in still in use. 41708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 41718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_supplicant_run(struct wpa_global *global) 41728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 41738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_supplicant *wpa_s; 41748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->params.daemonize && 41768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_daemon(global->params.pid_file)) 41778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 41788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->params.wait_for_monitor) { 41808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next) 41818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_s->ctrl_iface) 41828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_ctrl_iface_wait( 41838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->ctrl_iface); 41848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 41858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_register_signal_terminate(wpa_supplicant_terminate, global); 41878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_register_signal_reconfig(wpa_supplicant_reconfig, global); 41888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_run(); 41908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 41928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 41938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 41958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 41968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant_deinit - Deinitialize %wpa_supplicant 41978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @global: Pointer to global data from wpa_supplicant_init() 41988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 41998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function is called to deinitialize %wpa_supplicant and to free all 42008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * allocated resources. Remaining network interfaces will also be removed. 42018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 42028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_deinit(struct wpa_global *global) 42038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 42048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 42058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global == NULL) 42078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 42081f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 420961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#ifdef CONFIG_WIFI_DISPLAY 421061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wifi_display_deinit(global); 421161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#endif /* CONFIG_WIFI_DISPLAY */ 42128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (global->ifaces) 4214e15c7b57cc7a214d5adaa0fc1d7204378eaf62a5Dmitry Shmidt wpa_supplicant_remove_iface(global, global->ifaces, 1); 42158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->ctrl_iface) 42178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_global_ctrl_iface_deinit(global->ctrl_iface); 42188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_notify_supplicant_deinitialized(global); 42208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eap_peer_unregister_methods(); 42228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_AP 42238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eap_server_unregister_methods(); 42248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_AP */ 42258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; wpa_drivers[i] && global->drv_priv; i++) { 42278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (!global->drv_priv[i]) 42288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 42298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_drivers[i]->global_deinit(global->drv_priv[i]); 42308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 42318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(global->drv_priv); 42328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt random_deinit(); 42348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt eloop_destroy(); 42368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (global->params.pid_file) { 42388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_daemonize_terminate(global->params.pid_file); 42398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(global->params.pid_file); 42408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 42418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(global->params.ctrl_interface); 4242b6e9aaf735990dc64cdb6efccc03d076768eabf3Dmitry Shmidt os_free(global->params.ctrl_interface_group); 42438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(global->params.override_driver); 42448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(global->params.override_ctrl_interface); 42458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42464ce9c87407c036fc83eb5a6044ddf976c86f53fcDmitry Shmidt os_free(global->p2p_disallow_freq.range); 4247cf32e60fa7e0d33fe1551a6dba8dcbbec47ea50eDmitry Shmidt os_free(global->p2p_go_avoid_freq.range); 4248391c59f0632df8db1c325da1d31d479b2eedce45Dmitry Shmidt os_free(global->add_psk); 424904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 42508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(global); 42518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_close_syslog(); 42528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_debug_close_file(); 425304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_debug_close_linux_tracing(); 42548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 42558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_supplicant_update_config(struct wpa_supplicant *wpa_s) 42588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 42598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if ((wpa_s->conf->changed_parameters & CFG_CHANGED_COUNTRY) && 42608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->country[0] && wpa_s->conf->country[1]) { 42618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char country[3]; 42628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt country[0] = wpa_s->conf->country[0]; 42638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt country[1] = wpa_s->conf->country[1]; 42648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt country[2] = '\0'; 42658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (wpa_drv_set_country(wpa_s, country) < 0) { 42668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "Failed to set country code " 42678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "'%s'", country); 42688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 42698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 42708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 427161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wpa_s->conf->changed_parameters & CFG_CHANGED_EXT_PW_BACKEND) 427261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpas_init_ext_pw(wpa_s); 427361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 42748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_WPS 42758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_wps_update_config(wpa_s); 42768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_WPS */ 42778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpas_p2p_update_config(wpa_s); 42788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->conf->changed_parameters = 0; 42798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 42808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void add_freq(int *freqs, int *num_freqs, int freq) 42838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 42848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 42858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < *num_freqs; i++) { 42878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (freqs[i] == freq) 42888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return; 42898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 42908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt freqs[*num_freqs] = freq; 42928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (*num_freqs)++; 42938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 42948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 42968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int * get_bss_freqs_in_ess(struct wpa_supplicant *wpa_s) 42978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 42988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpa_bss *bss, *cbss; 42998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const int max_freqs = 10; 43008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int *freqs; 43018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int num_freqs = 0; 43028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 43038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt freqs = os_zalloc(sizeof(int) * (max_freqs + 1)); 43048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (freqs == NULL) 43058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 43068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 43078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt cbss = wpa_s->current_bss; 43088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 43098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) { 43108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss == cbss) 43118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 43128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (bss->ssid_len == cbss->ssid_len && 43138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcmp(bss->ssid, cbss->ssid, bss->ssid_len) == 0 && 43148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_blacklist_get(wpa_s, bss->bssid) == NULL) { 43158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt add_freq(freqs, &num_freqs, bss->freq); 43168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (num_freqs == max_freqs) 43178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 43188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 43198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 43208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 43218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (num_freqs == 0) { 43228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(freqs); 43238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt freqs = NULL; 43248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 43258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 43268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return freqs; 43278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 43288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 43298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 43308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpas_connection_failed(struct wpa_supplicant *wpa_s, const u8 *bssid) 43318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 43328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int timeout; 43338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int count; 43348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int *freqs = NULL; 43358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4336fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt wpas_connect_work_done(wpa_s); 4337fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt 43388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 4339c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt * Remove possible authentication timeout since the connection failed. 4340c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt */ 4341c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt eloop_cancel_timeout(wpa_supplicant_timeout, wpa_s, NULL); 4342c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 4343ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt if (wpa_s->disconnected) { 4344ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt /* 4345ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt * There is no point in blacklisting the AP if this event is 4346ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt * generated based on local request to disconnect. 4347ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt */ 4348ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Ignore connection failure " 4349ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt "indication since interface has been put into " 4350ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt "disconnected state"); 4351ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt return; 4352ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt } 4353ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt 4354c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt /* 43558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Add the failed BSSID into the blacklist and speed up next scan 43568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * attempt if there could be other APs that could accept association. 43578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * The current blacklist count indicates how many times we have tried 43588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * connecting to this AP and multiple attempts mean that other APs are 43598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * either not available or has already been tried, so that we can start 43608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * increasing the delay here to avoid constant scanning. 43618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 43628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt count = wpa_blacklist_add(wpa_s, bssid); 43638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (count == 1 && wpa_s->current_bss) { 43648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 43658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This BSS was not in the blacklist before. If there is 43668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * another BSS available for the same ESS, we should try that 43678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * next. Otherwise, we may as well try this one once more 43688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * before allowing other, likely worse, ESSes to be considered. 43698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 43708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt freqs = get_bss_freqs_in_ess(wpa_s); 43718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (freqs) { 43728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Another BSS in this ESS " 43738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "has been seen; try it next"); 43748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_blacklist_add(wpa_s, bssid); 43758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 43768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * On the next scan, go through only the known channels 43778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * used in this ESS based on previous scans to speed up 43788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * common load balancing use case. 43798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 43808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(wpa_s->next_scan_freqs); 43818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_s->next_scan_freqs = freqs; 43828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 43838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 43848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4385d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt /* 4386d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * Add previous failure count in case the temporary blacklist was 4387d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * cleared due to no other BSSes being available. 4388d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt */ 4389d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt count += wpa_s->extra_blacklist_count; 4390d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 43914b06059785b935dd1f4f09314e4e12c417d2c6a4Dmitry Shmidt if (count > 3 && wpa_s->current_ssid) { 43924b06059785b935dd1f4f09314e4e12c417d2c6a4Dmitry Shmidt wpa_printf(MSG_DEBUG, "Continuous association failures - " 43934b06059785b935dd1f4f09314e4e12c417d2c6a4Dmitry Shmidt "consider temporary network disabling"); 43946dc03bd757d3befd2c03a543a402338db03914d6Dmitry Shmidt wpas_auth_failed(wpa_s, "CONN_FAILED"); 43954b06059785b935dd1f4f09314e4e12c417d2c6a4Dmitry Shmidt } 43964b06059785b935dd1f4f09314e4e12c417d2c6a4Dmitry Shmidt 43978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt switch (count) { 43988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case 1: 43998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt timeout = 100; 44008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 44018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case 2: 44028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt timeout = 500; 44038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 44048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case 3: 44058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt timeout = 1000; 44068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 4407d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt case 4: 44088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt timeout = 5000; 4409d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt break; 4410d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt default: 4411d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt timeout = 10000; 4412d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt break; 44138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 44148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4415d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Blacklist count %d --> request scan in %d " 4416d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt "ms", count, timeout); 4417d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 44188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 44198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * TODO: if more than one possible AP is available in scan results, 44208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * could try the other ones before requesting a new scan. 44218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 44228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_supplicant_req_scan(wpa_s, timeout / 1000, 44238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1000 * (timeout % 1000)); 44248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 44251f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 44261f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt 44271f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidtint wpas_driver_bss_selection(struct wpa_supplicant *wpa_s) 44281f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt{ 44291f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt return wpa_s->conf->ap_scan == 2 || 44301f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt (wpa_s->drv_flags & WPA_DRIVER_FLAGS_BSS_SELECTION); 44311f69aa52ea2e0a73ac502565df8c666ee49cab6aDmitry Shmidt} 4432c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt 443304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 443404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#if defined(CONFIG_CTRL_IFACE) || defined(CONFIG_CTRL_IFACE_DBUS_NEW) 443504949598a23f501be6eec21697465fd46a28840aDmitry Shmidtint wpa_supplicant_ctrl_iface_ctrl_rsp_handle(struct wpa_supplicant *wpa_s, 443604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt struct wpa_ssid *ssid, 443704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt const char *field, 443804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt const char *value) 443904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 444004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#ifdef IEEE8021X_EAPOL 444104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt struct eap_peer_config *eap = &ssid->eap; 444204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 444304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_printf(MSG_DEBUG, "CTRL_IFACE: response handle field=%s", field); 444404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_hexdump_ascii_key(MSG_DEBUG, "CTRL_IFACE: response value", 444504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt (const u8 *) value, os_strlen(value)); 444604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 444704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt switch (wpa_supplicant_ctrl_req_from_string(field)) { 444804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt case WPA_CTRL_REQ_EAP_IDENTITY: 444904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt os_free(eap->identity); 445004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->identity = (u8 *) os_strdup(value); 445104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->identity_len = os_strlen(value); 445204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pending_req_identity = 0; 445304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ssid == wpa_s->current_ssid) 445404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->reassociate = 1; 445504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt break; 445604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt case WPA_CTRL_REQ_EAP_PASSWORD: 4457c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt bin_clear_free(eap->password, eap->password_len); 445804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->password = (u8 *) os_strdup(value); 445904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->password_len = os_strlen(value); 446004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pending_req_password = 0; 446104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ssid == wpa_s->current_ssid) 446204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->reassociate = 1; 446304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt break; 446404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt case WPA_CTRL_REQ_EAP_NEW_PASSWORD: 4465c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt bin_clear_free(eap->new_password, eap->new_password_len); 446604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->new_password = (u8 *) os_strdup(value); 446704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->new_password_len = os_strlen(value); 446804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pending_req_new_password = 0; 446904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ssid == wpa_s->current_ssid) 447004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->reassociate = 1; 447104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt break; 447204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt case WPA_CTRL_REQ_EAP_PIN: 4473c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt str_clear_free(eap->pin); 447404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pin = os_strdup(value); 447504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pending_req_pin = 0; 447604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ssid == wpa_s->current_ssid) 447704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->reassociate = 1; 447804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt break; 447904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt case WPA_CTRL_REQ_EAP_OTP: 4480c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt bin_clear_free(eap->otp, eap->otp_len); 448104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->otp = (u8 *) os_strdup(value); 448204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->otp_len = os_strlen(value); 448304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt os_free(eap->pending_req_otp); 448404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pending_req_otp = NULL; 448504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pending_req_otp_len = 0; 448604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt break; 448704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt case WPA_CTRL_REQ_EAP_PASSPHRASE: 4488c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt str_clear_free(eap->private_key_passwd); 4489c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt eap->private_key_passwd = os_strdup(value); 449004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt eap->pending_req_passphrase = 0; 449104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ssid == wpa_s->current_ssid) 449204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_s->reassociate = 1; 449304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt break; 4494051af73b8f8014eff33330aead0f36944b3403e6Dmitry Shmidt case WPA_CTRL_REQ_SIM: 4495c28170251eb54dbf64a9074a07fee377587425b2Dmitry Shmidt str_clear_free(eap->external_sim_resp); 4496051af73b8f8014eff33330aead0f36944b3403e6Dmitry Shmidt eap->external_sim_resp = os_strdup(value); 4497051af73b8f8014eff33330aead0f36944b3403e6Dmitry Shmidt break; 449804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt default: 449904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_printf(MSG_DEBUG, "CTRL_IFACE: Unknown field '%s'", field); 450004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return -1; 450104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 450204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 450304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 0; 450404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#else /* IEEE8021X_EAPOL */ 450504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt wpa_printf(MSG_DEBUG, "CTRL_IFACE: IEEE 802.1X not included"); 450604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return -1; 450704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#endif /* IEEE8021X_EAPOL */ 450804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 450904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt#endif /* CONFIG_CTRL_IFACE || CONFIG_CTRL_IFACE_DBUS_NEW */ 451004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 451104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 451204949598a23f501be6eec21697465fd46a28840aDmitry Shmidtint wpas_network_disabled(struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid) 451304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt{ 451404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt int i; 451504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt unsigned int drv_enc; 451604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 451704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ssid == NULL) 451804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 1; 451904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 452004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (ssid->disabled) 452104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 1; 452204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 452304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (wpa_s && wpa_s->drv_capa_known) 452404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt drv_enc = wpa_s->drv_enc; 452504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt else 452604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt drv_enc = (unsigned int) -1; 452704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 452804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt for (i = 0; i < NUM_WEP_KEYS; i++) { 452904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt size_t len = ssid->wep_key_len[i]; 453004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (len == 0) 453104949598a23f501be6eec21697465fd46a28840aDmitry Shmidt continue; 453204949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (len == 5 && (drv_enc & WPA_DRIVER_CAPA_ENC_WEP40)) 453304949598a23f501be6eec21697465fd46a28840aDmitry Shmidt continue; 453404949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (len == 13 && (drv_enc & WPA_DRIVER_CAPA_ENC_WEP104)) 453504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt continue; 453604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt if (len == 16 && (drv_enc & WPA_DRIVER_CAPA_ENC_WEP128)) 453704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt continue; 453804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 1; /* invalid WEP key */ 453904949598a23f501be6eec21697465fd46a28840aDmitry Shmidt } 454004949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 454161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (wpa_key_mgmt_wpa_psk(ssid->key_mgmt) && !ssid->psk_set && 45427dba0e5708da7276a43a44cf479aa743564e15b9Dmitry Shmidt (!ssid->passphrase || ssid->ssid_len != 0) && !ssid->ext_psk) 454361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 1; 454461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 454504949598a23f501be6eec21697465fd46a28840aDmitry Shmidt return 0; 454604949598a23f501be6eec21697465fd46a28840aDmitry Shmidt} 454704949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 454804949598a23f501be6eec21697465fd46a28840aDmitry Shmidt 4549687922c7347bdc3b4f8c921efe1d1388cb3baac0Dmitry Shmidtint wpas_is_p2p_prioritized(struct wpa_supplicant *wpa_s) 4550c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt{ 45512fb777c379ad560c309c54b96c2c13291da23f54Dmitry Shmidt if (wpa_s->global->conc_pref == WPA_CONC_PREF_P2P) 4552c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt return 1; 45532fb777c379ad560c309c54b96c2c13291da23f54Dmitry Shmidt if (wpa_s->global->conc_pref == WPA_CONC_PREF_STA) 4554687922c7347bdc3b4f8c921efe1d1388cb3baac0Dmitry Shmidt return 0; 4555687922c7347bdc3b4f8c921efe1d1388cb3baac0Dmitry Shmidt return -1; 4556c5ec7f57ead87efa365800228aa0b09a12d9e6c4Dmitry Shmidt} 455761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 455861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 45596dc03bd757d3befd2c03a543a402338db03914d6Dmitry Shmidtvoid wpas_auth_failed(struct wpa_supplicant *wpa_s, char *reason) 456061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 456161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt struct wpa_ssid *ssid = wpa_s->current_ssid; 456261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt int dur; 4563fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt struct os_reltime now; 456461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 456561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (ssid == NULL) { 456661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "Authentication failure but no known " 456761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "SSID block"); 456861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return; 456961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 457061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 457161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (ssid->key_mgmt == WPA_KEY_MGMT_WPS) 457261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return; 457361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 457461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->auth_failures++; 4575d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt 4576d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt#ifdef CONFIG_P2P 4577d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt if (ssid->p2p_group && 4578d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt (wpa_s->p2p_in_provisioning || wpa_s->show_group_started)) { 4579d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt /* 4580d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt * Skip the wait time since there is a short timeout on the 4581d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt * connection to a P2P group. 4582d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt */ 4583d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt return; 4584d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt } 4585d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt#endif /* CONFIG_P2P */ 4586d5c075b0c218277d0f926daf1f9eff974b9656dcDmitry Shmidt 458761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (ssid->auth_failures > 50) 458861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt dur = 300; 458961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt else if (ssid->auth_failures > 10) 4590f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt dur = 120; 459161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt else if (ssid->auth_failures > 5) 4592f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt dur = 90; 4593f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt else if (ssid->auth_failures > 3) 4594f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt dur = 60; 4595f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt else if (ssid->auth_failures > 2) 459661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt dur = 30; 459761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt else if (ssid->auth_failures > 1) 459861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt dur = 20; 459961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt else 460061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt dur = 10; 460161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 4602f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt if (ssid->auth_failures > 1 && 4603f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt wpa_key_mgmt_wpa_ieee8021x(ssid->key_mgmt)) 4604f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt dur += os_random() % (ssid->auth_failures * 10); 4605f21452aea786ac056eb01f1cbba4f553bd502747Dmitry Shmidt 4606fb79edc9df1f20461e90e478363d207348213d35Dmitry Shmidt os_get_reltime(&now); 460761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (now.sec + dur <= ssid->disabled_until.sec) 460861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return; 460961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 461061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->disabled_until.sec = now.sec + dur; 461161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 461261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_TEMP_DISABLED 46136dc03bd757d3befd2c03a543a402338db03914d6Dmitry Shmidt "id=%d ssid=\"%s\" auth_failures=%u duration=%d reason=%s", 461461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->id, wpa_ssid_txt(ssid->ssid, ssid->ssid_len), 46156dc03bd757d3befd2c03a543a402338db03914d6Dmitry Shmidt ssid->auth_failures, dur, reason); 461661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 461761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 461861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 461961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtvoid wpas_clear_temp_disabled(struct wpa_supplicant *wpa_s, 462061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt struct wpa_ssid *ssid, int clear_failures) 462161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 462261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (ssid == NULL) 462361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return; 462461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 462561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (ssid->disabled_until.sec) { 462661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_REENABLED 462761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "id=%d ssid=\"%s\"", 462861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->id, wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 462961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 463061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->disabled_until.sec = 0; 463161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->disabled_until.usec = 0; 463261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (clear_failures) 463361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ssid->auth_failures = 0; 463461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 4635d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4636d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4637d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidtint disallowed_bssid(struct wpa_supplicant *wpa_s, const u8 *bssid) 4638d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt{ 4639d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt size_t i; 4640d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4641d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (wpa_s->disallow_aps_bssid == NULL) 4642d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt return 0; 4643d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4644d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt for (i = 0; i < wpa_s->disallow_aps_bssid_count; i++) { 4645d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (os_memcmp(wpa_s->disallow_aps_bssid + i * ETH_ALEN, 4646d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt bssid, ETH_ALEN) == 0) 4647d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt return 1; 4648d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt } 4649d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4650d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt return 0; 4651d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt} 4652d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4653d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4654d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidtint disallowed_ssid(struct wpa_supplicant *wpa_s, const u8 *ssid, 4655d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt size_t ssid_len) 4656d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt{ 4657d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt size_t i; 4658d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4659d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (wpa_s->disallow_aps_ssid == NULL || ssid == NULL) 4660d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt return 0; 4661d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4662d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt for (i = 0; i < wpa_s->disallow_aps_ssid_count; i++) { 4663d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt struct wpa_ssid_value *s = &wpa_s->disallow_aps_ssid[i]; 4664d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt if (ssid_len == s->ssid_len && 4665d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt os_memcmp(ssid, s->ssid, ssid_len) == 0) 4666d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt return 1; 4667d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt } 4668d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4669d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt return 0; 4670d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt} 4671d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4672d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt 4673d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt/** 4674d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * wpas_request_connection - Request a new connection 4675d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * @wpa_s: Pointer to the network interface 4676d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * 4677d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * This function is used to request a new connection to be found. It will mark 4678d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * the interface to allow reassociation and request a new scan to find a 4679d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt * suitable network to connect to. 4680d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt */ 4681d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidtvoid wpas_request_connection(struct wpa_supplicant *wpa_s) 4682d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt{ 4683d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->normal_scans = 0; 4684d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_supplicant_reinit_autoscan(wpa_s); 4685d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->extra_blacklist_count = 0; 4686d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->disconnected = 0; 4687d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt wpa_s->reassociate = 1; 46882f3b8dec59373945c5feef8a78ced8967a80cc66Dmitry Shmidt 46892f3b8dec59373945c5feef8a78ced8967a80cc66Dmitry Shmidt if (wpa_supplicant_fast_associate(wpa_s) != 1) 46902f3b8dec59373945c5feef8a78ced8967a80cc66Dmitry Shmidt wpa_supplicant_req_scan(wpa_s, 0, 0); 4691d5e4923d04122f81300fa68fb07d64ede28fd44dDmitry Shmidt} 4692ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt 4693ea69e84a6f4455c59348485895d3d5e3af77a65bDmitry Shmidt 469443cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidtvoid dump_freq_data(struct wpa_supplicant *wpa_s, const char *title, 469543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt struct wpa_used_freq_data *freqs_data, 469643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt unsigned int len) 4697b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt{ 4698b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt unsigned int i; 4699b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt 4700b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "Shared frequencies (len=%u): %s", 4701b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt len, title); 470243cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt for (i = 0; i < len; i++) { 470343cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt struct wpa_used_freq_data *cur = &freqs_data[i]; 470443cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, "freq[%u]: %d, flags=0x%X", 470543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt i, cur->freq, cur->flags); 470643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt } 4707b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt} 4708b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt 4709b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt 4710c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt/* 4711c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt * Find the operating frequencies of any of the virtual interfaces that 471243cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt * are using the same radio as the current interface, and in addition, get 471343cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt * information about the interface types that are using the frequency. 4714c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt */ 471543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidtint get_shared_radio_freqs_data(struct wpa_supplicant *wpa_s, 471643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt struct wpa_used_freq_data *freqs_data, 471743cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt unsigned int len) 4718c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt{ 4719c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt struct wpa_supplicant *ifs; 4720c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt u8 bssid[ETH_ALEN]; 4721c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt int freq; 4722c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt unsigned int idx = 0, i; 4723c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt 4724b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt wpa_dbg(wpa_s, MSG_DEBUG, 4725b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt "Determining shared radio frequencies (max len %u)", len); 472643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt os_memset(freqs_data, 0, sizeof(struct wpa_used_freq_data) * len); 4727c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt 472801904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt dl_list_for_each(ifs, &wpa_s->radio->ifaces, struct wpa_supplicant, 472901904cfafd75a70b9f29c0220b90bdef45595491Dmitry Shmidt radio_list) { 473043cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt if (idx == len) 473143cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt break; 4732c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt 4733c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt if (ifs->current_ssid == NULL || ifs->assoc_freq == 0) 4734c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt continue; 4735c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt 4736c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt if (ifs->current_ssid->mode == WPAS_MODE_AP || 4737c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt ifs->current_ssid->mode == WPAS_MODE_P2P_GO) 4738c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt freq = ifs->current_ssid->frequency; 4739c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt else if (wpa_drv_get_bssid(ifs, bssid) == 0) 4740c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt freq = ifs->assoc_freq; 4741c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt else 4742c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt continue; 4743c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt 4744c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt /* Hold only distinct freqs */ 4745c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt for (i = 0; i < idx; i++) 474643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt if (freqs_data[i].freq == freq) 4747c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt break; 4748c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt 4749c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt if (i == idx) 475043cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt freqs_data[idx++].freq = freq; 475143cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 475243cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt if (ifs->current_ssid->mode == WPAS_MODE_INFRA) { 475343cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt freqs_data[i].flags = ifs->current_ssid->p2p_group ? 475443cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt WPA_FREQ_USED_BY_P2P_CLIENT : 475543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt WPA_FREQ_USED_BY_INFRA_STATION; 475643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt } 4757c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt } 4758b96dad47218788efffa3db0fe7f1b54a7d19e366Dmitry Shmidt 475943cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt dump_freq_data(wpa_s, "completed iteration", freqs_data, idx); 4760c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt return idx; 4761c2ebb4b85d69b65f552fee71ac68f44e8d87b39eDmitry Shmidt} 476243cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 476343cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 476443cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt/* 476543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt * Find the operating frequencies of any of the virtual interfaces that 476643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt * are using the same radio as the current interface. 476743cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt */ 476843cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidtint get_shared_radio_freqs(struct wpa_supplicant *wpa_s, 476943cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt int *freq_array, unsigned int len) 477043cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt{ 477143cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt struct wpa_used_freq_data *freqs_data; 477243cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt int num, i; 477343cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 477443cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt os_memset(freq_array, 0, sizeof(int) * len); 477543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 477643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt freqs_data = os_calloc(len, sizeof(struct wpa_used_freq_data)); 477743cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt if (!freqs_data) 477843cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt return -1; 477943cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 478043cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt num = get_shared_radio_freqs_data(wpa_s, freqs_data, len); 478143cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt for (i = 0; i < num; i++) 478243cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt freq_array[i] = freqs_data[i].freq; 478343cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 478443cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt os_free(freqs_data); 478543cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt 478643cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt return num; 478743cb578dfe2c492257636f6234a24178ed27789eDmitry Shmidt} 4788