LCOV - code coverage report
Current view: top level - wpa_supplicant - ap.c (source / functions) Hit Total Coverage
Test: wpa_supplicant/hostapd combined for hwsim test run 1422976643 Lines: 519 639 81.2 %
Date: 2015-02-03 Functions: 42 45 93.3 %

          Line data    Source code
       1             : /*
       2             :  * WPA Supplicant - Basic AP mode support routines
       3             :  * Copyright (c) 2003-2009, Jouni Malinen <j@w1.fi>
       4             :  * Copyright (c) 2009, Atheros Communications
       5             :  *
       6             :  * This software may be distributed under the terms of the BSD license.
       7             :  * See README for more details.
       8             :  */
       9             : 
      10             : #include "utils/includes.h"
      11             : 
      12             : #include "utils/common.h"
      13             : #include "utils/eloop.h"
      14             : #include "utils/uuid.h"
      15             : #include "common/ieee802_11_defs.h"
      16             : #include "common/wpa_ctrl.h"
      17             : #include "eapol_supp/eapol_supp_sm.h"
      18             : #include "crypto/dh_group5.h"
      19             : #include "ap/hostapd.h"
      20             : #include "ap/ap_config.h"
      21             : #include "ap/ap_drv_ops.h"
      22             : #ifdef NEED_AP_MLME
      23             : #include "ap/ieee802_11.h"
      24             : #endif /* NEED_AP_MLME */
      25             : #include "ap/beacon.h"
      26             : #include "ap/ieee802_1x.h"
      27             : #include "ap/wps_hostapd.h"
      28             : #include "ap/ctrl_iface_ap.h"
      29             : #include "wps/wps.h"
      30             : #include "common/ieee802_11_defs.h"
      31             : #include "config_ssid.h"
      32             : #include "config.h"
      33             : #include "wpa_supplicant_i.h"
      34             : #include "driver_i.h"
      35             : #include "p2p_supplicant.h"
      36             : #include "ap.h"
      37             : #include "ap/sta_info.h"
      38             : #include "notify.h"
      39             : 
      40             : 
      41             : #ifdef CONFIG_WPS
      42             : static void wpas_wps_ap_pin_timeout(void *eloop_data, void *user_ctx);
      43             : #endif /* CONFIG_WPS */
      44             : 
      45             : 
      46             : #ifdef CONFIG_IEEE80211N
      47           9 : static void wpas_conf_ap_vht(struct wpa_supplicant *wpa_s,
      48             :                              struct hostapd_config *conf,
      49             :                              struct hostapd_hw_modes *mode)
      50             : {
      51             : #ifdef CONFIG_P2P
      52           9 :         u8 center_chan = 0;
      53           9 :         u8 channel = conf->channel;
      54             : 
      55           9 :         if (!conf->secondary_channel)
      56           8 :                 goto no_vht;
      57             : 
      58           1 :         center_chan = wpas_p2p_get_vht80_center(wpa_s, mode, channel);
      59           1 :         if (!center_chan)
      60           0 :                 goto no_vht;
      61             : 
      62             :         /* Use 80 MHz channel */
      63           1 :         conf->vht_oper_chwidth = 1;
      64           1 :         conf->vht_oper_centr_freq_seg0_idx = center_chan;
      65          10 :         return;
      66             : 
      67             : no_vht:
      68           8 :         conf->vht_oper_centr_freq_seg0_idx =
      69           8 :                 channel + conf->secondary_channel * 2;
      70             : #else /* CONFIG_P2P */
      71             :         conf->vht_oper_centr_freq_seg0_idx =
      72             :                 conf->channel + conf->secondary_channel * 2;
      73             : #endif /* CONFIG_P2P */
      74             : }
      75             : #endif /* CONFIG_IEEE80211N */
      76             : 
      77             : 
      78         264 : void wpa_supplicant_conf_ap_ht(struct wpa_supplicant *wpa_s,
      79             :                                struct wpa_ssid *ssid,
      80             :                                struct hostapd_config *conf)
      81             : {
      82             :         /* TODO: enable HT40 if driver supports it;
      83             :          * drop to 11b if driver does not support 11g */
      84             : 
      85             : #ifdef CONFIG_IEEE80211N
      86             :         /*
      87             :          * Enable HT20 if the driver supports it, by setting conf->ieee80211n
      88             :          * and a mask of allowed capabilities within conf->ht_capab.
      89             :          * Using default config settings for: conf->ht_op_mode_fixed,
      90             :          * conf->secondary_channel, conf->require_ht
      91             :          */
      92         264 :         if (wpa_s->hw.modes) {
      93         264 :                 struct hostapd_hw_modes *mode = NULL;
      94         264 :                 int i, no_ht = 0;
      95         274 :                 for (i = 0; i < wpa_s->hw.num_modes; i++) {
      96         274 :                         if (wpa_s->hw.modes[i].mode == conf->hw_mode) {
      97         264 :                                 mode = &wpa_s->hw.modes[i];
      98         264 :                                 break;
      99             :                         }
     100             :                 }
     101             : 
     102             : #ifdef CONFIG_HT_OVERRIDES
     103         264 :                 if (ssid->disable_ht) {
     104           0 :                         conf->ieee80211n = 0;
     105           0 :                         conf->ht_capab = 0;
     106           0 :                         no_ht = 1;
     107             :                 }
     108             : #endif /* CONFIG_HT_OVERRIDES */
     109             : 
     110         264 :                 if (!no_ht && mode && mode->ht_capab) {
     111         264 :                         conf->ieee80211n = 1;
     112             : #ifdef CONFIG_P2P
     113         274 :                         if (conf->hw_mode == HOSTAPD_MODE_IEEE80211A &&
     114          10 :                             (mode->ht_capab &
     115          10 :                              HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET) &&
     116          10 :                             ssid->ht40)
     117           1 :                                 conf->secondary_channel =
     118           1 :                                         wpas_p2p_get_ht40_mode(wpa_s, mode,
     119           1 :                                                                conf->channel);
     120         264 :                         if (conf->secondary_channel)
     121           1 :                                 conf->ht_capab |=
     122             :                                         HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET;
     123             : #endif /* CONFIG_P2P */
     124             : 
     125             :                         /*
     126             :                          * white-list capabilities that won't cause issues
     127             :                          * to connecting stations, while leaving the current
     128             :                          * capabilities intact (currently disabled SMPS).
     129             :                          */
     130         264 :                         conf->ht_capab |= mode->ht_capab &
     131             :                                 (HT_CAP_INFO_GREEN_FIELD |
     132             :                                  HT_CAP_INFO_SHORT_GI20MHZ |
     133             :                                  HT_CAP_INFO_SHORT_GI40MHZ |
     134             :                                  HT_CAP_INFO_RX_STBC_MASK |
     135             :                                  HT_CAP_INFO_TX_STBC |
     136             :                                  HT_CAP_INFO_MAX_AMSDU_SIZE);
     137             : 
     138         264 :                         if (mode->vht_capab && ssid->vht) {
     139           9 :                                 conf->ieee80211ac = 1;
     140           9 :                                 wpas_conf_ap_vht(wpa_s, conf, mode);
     141             :                         }
     142             :                 }
     143             :         }
     144             : #endif /* CONFIG_IEEE80211N */
     145         264 : }
     146             : 
     147             : 
     148         236 : static int wpa_supplicant_conf_ap(struct wpa_supplicant *wpa_s,
     149             :                                   struct wpa_ssid *ssid,
     150             :                                   struct hostapd_config *conf)
     151             : {
     152         236 :         struct hostapd_bss_config *bss = conf->bss[0];
     153             : 
     154         236 :         conf->driver = wpa_s->driver;
     155             : 
     156         236 :         os_strlcpy(bss->iface, wpa_s->ifname, sizeof(bss->iface));
     157             : 
     158         236 :         conf->hw_mode = ieee80211_freq_to_chan(ssid->frequency,
     159             :                                                &conf->channel);
     160         236 :         if (conf->hw_mode == NUM_HOSTAPD_MODES) {
     161           0 :                 wpa_printf(MSG_ERROR, "Unsupported AP mode frequency: %d MHz",
     162             :                            ssid->frequency);
     163           0 :                 return -1;
     164             :         }
     165             : 
     166         236 :         wpa_supplicant_conf_ap_ht(wpa_s, ssid, conf);
     167             : 
     168             : #ifdef CONFIG_P2P
     169         464 :         if (conf->hw_mode == HOSTAPD_MODE_IEEE80211G &&
     170         334 :             (ssid->mode == WPAS_MODE_P2P_GO ||
     171         106 :              ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)) {
     172             :                 /* Remove 802.11b rates from supported and basic rate sets */
     173         218 :                 int *list = os_malloc(4 * sizeof(int));
     174         218 :                 if (list) {
     175         218 :                         list[0] = 60;
     176         218 :                         list[1] = 120;
     177         218 :                         list[2] = 240;
     178         218 :                         list[3] = -1;
     179             :                 }
     180         218 :                 conf->basic_rates = list;
     181             : 
     182         218 :                 list = os_malloc(9 * sizeof(int));
     183         218 :                 if (list) {
     184         218 :                         list[0] = 60;
     185         218 :                         list[1] = 90;
     186         218 :                         list[2] = 120;
     187         218 :                         list[3] = 180;
     188         218 :                         list[4] = 240;
     189         218 :                         list[5] = 360;
     190         218 :                         list[6] = 480;
     191         218 :                         list[7] = 540;
     192         218 :                         list[8] = -1;
     193             :                 }
     194         218 :                 conf->supported_rates = list;
     195             :         }
     196             : 
     197         236 :         bss->isolate = !wpa_s->conf->p2p_intra_bss;
     198         236 :         bss->force_per_enrollee_psk = wpa_s->global->p2p_per_sta_psk;
     199             : 
     200         236 :         if (ssid->p2p_group) {
     201         225 :                 os_memcpy(bss->ip_addr_go, wpa_s->parent->conf->ip_addr_go, 4);
     202         225 :                 os_memcpy(bss->ip_addr_mask, wpa_s->parent->conf->ip_addr_mask,
     203             :                           4);
     204         225 :                 os_memcpy(bss->ip_addr_start,
     205             :                           wpa_s->parent->conf->ip_addr_start, 4);
     206         225 :                 os_memcpy(bss->ip_addr_end, wpa_s->parent->conf->ip_addr_end,
     207             :                           4);
     208             :         }
     209             : #endif /* CONFIG_P2P */
     210             : 
     211         236 :         if (ssid->ssid_len == 0) {
     212           0 :                 wpa_printf(MSG_ERROR, "No SSID configured for AP mode");
     213           0 :                 return -1;
     214             :         }
     215         236 :         os_memcpy(bss->ssid.ssid, ssid->ssid, ssid->ssid_len);
     216         236 :         bss->ssid.ssid_len = ssid->ssid_len;
     217         236 :         bss->ssid.ssid_set = 1;
     218             : 
     219         236 :         bss->ignore_broadcast_ssid = ssid->ignore_broadcast_ssid;
     220             : 
     221         236 :         if (ssid->auth_alg)
     222         225 :                 bss->auth_algs = ssid->auth_alg;
     223             : 
     224         236 :         if (wpa_key_mgmt_wpa_psk(ssid->key_mgmt))
     225         231 :                 bss->wpa = ssid->proto;
     226         236 :         bss->wpa_key_mgmt = ssid->key_mgmt;
     227         236 :         bss->wpa_pairwise = ssid->pairwise_cipher;
     228         236 :         if (ssid->psk_set) {
     229         231 :                 bin_clear_free(bss->ssid.wpa_psk, sizeof(*bss->ssid.wpa_psk));
     230         231 :                 bss->ssid.wpa_psk = os_zalloc(sizeof(struct hostapd_wpa_psk));
     231         231 :                 if (bss->ssid.wpa_psk == NULL)
     232           0 :                         return -1;
     233         231 :                 os_memcpy(bss->ssid.wpa_psk->psk, ssid->psk, PMK_LEN);
     234         231 :                 bss->ssid.wpa_psk->group = 1;
     235           5 :         } else if (ssid->passphrase) {
     236           0 :                 bss->ssid.wpa_passphrase = os_strdup(ssid->passphrase);
     237           9 :         } else if (ssid->wep_key_len[0] || ssid->wep_key_len[1] ||
     238           8 :                    ssid->wep_key_len[2] || ssid->wep_key_len[3]) {
     239           1 :                 struct hostapd_wep_keys *wep = &bss->ssid.wep;
     240             :                 int i;
     241           5 :                 for (i = 0; i < NUM_WEP_KEYS; i++) {
     242           4 :                         if (ssid->wep_key_len[i] == 0)
     243           3 :                                 continue;
     244           1 :                         wep->key[i] = os_malloc(ssid->wep_key_len[i]);
     245           1 :                         if (wep->key[i] == NULL)
     246           0 :                                 return -1;
     247           1 :                         os_memcpy(wep->key[i], ssid->wep_key[i],
     248             :                                   ssid->wep_key_len[i]);
     249           1 :                         wep->len[i] = ssid->wep_key_len[i];
     250             :                 }
     251           1 :                 wep->idx = ssid->wep_tx_keyidx;
     252           1 :                 wep->keys_set = 1;
     253             :         }
     254             : 
     255         236 :         if (ssid->ap_max_inactivity)
     256         225 :                 bss->ap_max_inactivity = ssid->ap_max_inactivity;
     257             : 
     258         236 :         if (ssid->dtim_period)
     259           0 :                 bss->dtim_period = ssid->dtim_period;
     260         236 :         else if (wpa_s->conf->dtim_period)
     261           0 :                 bss->dtim_period = wpa_s->conf->dtim_period;
     262             : 
     263         236 :         if (ssid->beacon_int)
     264           0 :                 conf->beacon_int = ssid->beacon_int;
     265         236 :         else if (wpa_s->conf->beacon_int)
     266           0 :                 conf->beacon_int = wpa_s->conf->beacon_int;
     267             : 
     268         236 :         if ((bss->wpa & 2) && bss->rsn_pairwise == 0)
     269         231 :                 bss->rsn_pairwise = bss->wpa_pairwise;
     270         236 :         bss->wpa_group = wpa_select_ap_group_cipher(bss->wpa, bss->wpa_pairwise,
     271             :                                                     bss->rsn_pairwise);
     272             : 
     273         236 :         if (bss->wpa && bss->ieee802_1x)
     274           0 :                 bss->ssid.security_policy = SECURITY_WPA;
     275         236 :         else if (bss->wpa)
     276         231 :                 bss->ssid.security_policy = SECURITY_WPA_PSK;
     277           5 :         else if (bss->ieee802_1x) {
     278           0 :                 int cipher = WPA_CIPHER_NONE;
     279           0 :                 bss->ssid.security_policy = SECURITY_IEEE_802_1X;
     280           0 :                 bss->ssid.wep.default_len = bss->default_wep_key_len;
     281           0 :                 if (bss->default_wep_key_len)
     282           0 :                         cipher = bss->default_wep_key_len >= 13 ?
     283           0 :                                 WPA_CIPHER_WEP104 : WPA_CIPHER_WEP40;
     284           0 :                 bss->wpa_group = cipher;
     285           0 :                 bss->wpa_pairwise = cipher;
     286           0 :                 bss->rsn_pairwise = cipher;
     287           5 :         } else if (bss->ssid.wep.keys_set) {
     288           1 :                 int cipher = WPA_CIPHER_WEP40;
     289           1 :                 if (bss->ssid.wep.len[0] >= 13)
     290           0 :                         cipher = WPA_CIPHER_WEP104;
     291           1 :                 bss->ssid.security_policy = SECURITY_STATIC_WEP;
     292           1 :                 bss->wpa_group = cipher;
     293           1 :                 bss->wpa_pairwise = cipher;
     294           1 :                 bss->rsn_pairwise = cipher;
     295             :         } else {
     296           4 :                 bss->ssid.security_policy = SECURITY_PLAINTEXT;
     297           4 :                 bss->wpa_group = WPA_CIPHER_NONE;
     298           4 :                 bss->wpa_pairwise = WPA_CIPHER_NONE;
     299           4 :                 bss->rsn_pairwise = WPA_CIPHER_NONE;
     300             :         }
     301             : 
     302         467 :         if (bss->wpa_group_rekey < 86400 && (bss->wpa & 2) &&
     303         233 :             (bss->wpa_group == WPA_CIPHER_CCMP ||
     304           4 :              bss->wpa_group == WPA_CIPHER_GCMP ||
     305           4 :              bss->wpa_group == WPA_CIPHER_CCMP_256 ||
     306           2 :              bss->wpa_group == WPA_CIPHER_GCMP_256)) {
     307             :                 /*
     308             :                  * Strong ciphers do not need frequent rekeying, so increase
     309             :                  * the default GTK rekeying period to 24 hours.
     310             :                  */
     311         229 :                 bss->wpa_group_rekey = 86400;
     312             :         }
     313             : 
     314             : #ifdef CONFIG_IEEE80211W
     315         236 :         if (ssid->ieee80211w != MGMT_FRAME_PROTECTION_DEFAULT)
     316           3 :                 bss->ieee80211w = ssid->ieee80211w;
     317             : #endif /* CONFIG_IEEE80211W */
     318             : 
     319             : #ifdef CONFIG_WPS
     320             :         /*
     321             :          * Enable WPS by default for open and WPA/WPA2-Personal network, but
     322             :          * require user interaction to actually use it. Only the internal
     323             :          * Registrar is supported.
     324             :          */
     325         241 :         if (bss->ssid.security_policy != SECURITY_WPA_PSK &&
     326           5 :             bss->ssid.security_policy != SECURITY_PLAINTEXT)
     327           1 :                 goto no_wps;
     328         466 :         if (bss->ssid.security_policy == SECURITY_WPA_PSK &&
     329         462 :             (!(bss->rsn_pairwise & (WPA_CIPHER_CCMP | WPA_CIPHER_GCMP)) ||
     330         231 :              !(bss->wpa & 2)))
     331             :                 goto no_wps; /* WPS2 does not allow WPA/TKIP-only
     332             :                               * configuration */
     333         235 :         bss->eap_server = 1;
     334             : 
     335         235 :         if (!ssid->ignore_broadcast_ssid)
     336         235 :                 bss->wps_state = 2;
     337             : 
     338         235 :         bss->ap_setup_locked = 2;
     339         235 :         if (wpa_s->conf->config_methods)
     340           7 :                 bss->config_methods = os_strdup(wpa_s->conf->config_methods);
     341         235 :         os_memcpy(bss->device_type, wpa_s->conf->device_type,
     342             :                   WPS_DEV_TYPE_LEN);
     343         235 :         if (wpa_s->conf->device_name) {
     344         219 :                 bss->device_name = os_strdup(wpa_s->conf->device_name);
     345         219 :                 bss->friendly_name = os_strdup(wpa_s->conf->device_name);
     346             :         }
     347         235 :         if (wpa_s->conf->manufacturer)
     348           0 :                 bss->manufacturer = os_strdup(wpa_s->conf->manufacturer);
     349         235 :         if (wpa_s->conf->model_name)
     350           0 :                 bss->model_name = os_strdup(wpa_s->conf->model_name);
     351         235 :         if (wpa_s->conf->model_number)
     352           0 :                 bss->model_number = os_strdup(wpa_s->conf->model_number);
     353         235 :         if (wpa_s->conf->serial_number)
     354           0 :                 bss->serial_number = os_strdup(wpa_s->conf->serial_number);
     355         235 :         if (is_nil_uuid(wpa_s->conf->uuid))
     356         235 :                 os_memcpy(bss->uuid, wpa_s->wps->uuid, WPS_UUID_LEN);
     357             :         else
     358           0 :                 os_memcpy(bss->uuid, wpa_s->conf->uuid, WPS_UUID_LEN);
     359         235 :         os_memcpy(bss->os_version, wpa_s->conf->os_version, 4);
     360         235 :         bss->pbc_in_m1 = wpa_s->conf->pbc_in_m1;
     361             : no_wps:
     362             : #endif /* CONFIG_WPS */
     363             : 
     364         236 :         if (wpa_s->max_stations &&
     365           0 :             wpa_s->max_stations < wpa_s->conf->max_num_sta)
     366           0 :                 bss->max_num_sta = wpa_s->max_stations;
     367             :         else
     368         236 :                 bss->max_num_sta = wpa_s->conf->max_num_sta;
     369             : 
     370         236 :         bss->disassoc_low_ack = wpa_s->conf->disassoc_low_ack;
     371             : 
     372         236 :         if (wpa_s->conf->ap_vendor_elements) {
     373           0 :                 bss->vendor_elements =
     374           0 :                         wpabuf_dup(wpa_s->conf->ap_vendor_elements);
     375             :         }
     376             : 
     377         236 :         return 0;
     378             : }
     379             : 
     380             : 
     381          70 : static void ap_public_action_rx(void *ctx, const u8 *buf, size_t len, int freq)
     382             : {
     383             : #ifdef CONFIG_P2P
     384          70 :         struct wpa_supplicant *wpa_s = ctx;
     385             :         const struct ieee80211_mgmt *mgmt;
     386             : 
     387          70 :         mgmt = (const struct ieee80211_mgmt *) buf;
     388          70 :         if (len < IEEE80211_HDRLEN + 1)
     389           0 :                 return;
     390          70 :         if (mgmt->u.action.category != WLAN_ACTION_PUBLIC)
     391           0 :                 return;
     392         140 :         wpas_p2p_rx_action(wpa_s, mgmt->da, mgmt->sa, mgmt->bssid,
     393          70 :                            mgmt->u.action.category,
     394             :                            buf + IEEE80211_HDRLEN + 1,
     395             :                            len - IEEE80211_HDRLEN - 1, freq);
     396             : #endif /* CONFIG_P2P */
     397             : }
     398             : 
     399             : 
     400         231 : static void ap_wps_event_cb(void *ctx, enum wps_event event,
     401             :                             union wps_event_data *data)
     402             : {
     403             : #ifdef CONFIG_P2P
     404         231 :         struct wpa_supplicant *wpa_s = ctx;
     405             : 
     406         231 :         if (event == WPS_EV_FAIL) {
     407          10 :                 struct wps_event_fail *fail = &data->fail;
     408             : 
     409          10 :                 if (wpa_s->parent && wpa_s->parent != wpa_s &&
     410           0 :                     wpa_s == wpa_s->global->p2p_group_formation) {
     411             :                         /*
     412             :                          * src/ap/wps_hostapd.c has already sent this on the
     413             :                          * main interface, so only send on the parent interface
     414             :                          * here if needed.
     415             :                          */
     416           0 :                         wpa_msg(wpa_s->parent, MSG_INFO, WPS_EVENT_FAIL
     417             :                                 "msg=%d config_error=%d",
     418           0 :                                 fail->msg, fail->config_error);
     419             :                 }
     420          10 :                 wpas_p2p_wps_failed(wpa_s, fail);
     421             :         }
     422             : #endif /* CONFIG_P2P */
     423         231 : }
     424             : 
     425             : 
     426         412 : static void ap_sta_authorized_cb(void *ctx, const u8 *mac_addr,
     427             :                                  int authorized, const u8 *p2p_dev_addr)
     428             : {
     429         412 :         wpas_notify_sta_authorized(ctx, mac_addr, authorized, p2p_dev_addr);
     430         412 : }
     431             : 
     432             : 
     433             : #ifdef CONFIG_P2P
     434           8 : static void ap_new_psk_cb(void *ctx, const u8 *mac_addr, const u8 *p2p_dev_addr,
     435             :                           const u8 *psk, size_t psk_len)
     436             : {
     437             : 
     438           8 :         struct wpa_supplicant *wpa_s = ctx;
     439           8 :         if (wpa_s->ap_iface == NULL || wpa_s->current_ssid == NULL)
     440           8 :                 return;
     441           8 :         wpas_p2p_new_psk_cb(wpa_s, mac_addr, p2p_dev_addr, psk, psk_len);
     442             : }
     443             : #endif /* CONFIG_P2P */
     444             : 
     445             : 
     446           5 : static int ap_vendor_action_rx(void *ctx, const u8 *buf, size_t len, int freq)
     447             : {
     448             : #ifdef CONFIG_P2P
     449           5 :         struct wpa_supplicant *wpa_s = ctx;
     450             :         const struct ieee80211_mgmt *mgmt;
     451             : 
     452           5 :         mgmt = (const struct ieee80211_mgmt *) buf;
     453           5 :         if (len < IEEE80211_HDRLEN + 1)
     454           0 :                 return -1;
     455          10 :         wpas_p2p_rx_action(wpa_s, mgmt->da, mgmt->sa, mgmt->bssid,
     456           5 :                            mgmt->u.action.category,
     457             :                            buf + IEEE80211_HDRLEN + 1,
     458             :                            len - IEEE80211_HDRLEN - 1, freq);
     459             : #endif /* CONFIG_P2P */
     460           5 :         return 0;
     461             : }
     462             : 
     463             : 
     464         378 : static int ap_probe_req_rx(void *ctx, const u8 *sa, const u8 *da,
     465             :                            const u8 *bssid, const u8 *ie, size_t ie_len,
     466             :                            int ssi_signal)
     467             : {
     468         378 :         struct wpa_supplicant *wpa_s = ctx;
     469         378 :         return wpas_p2p_probe_req_rx(wpa_s, sa, da, bssid, ie, ie_len,
     470             :                                      ssi_signal);
     471             : }
     472             : 
     473             : 
     474         160 : static void ap_wps_reg_success_cb(void *ctx, const u8 *mac_addr,
     475             :                                   const u8 *uuid_e)
     476             : {
     477         160 :         struct wpa_supplicant *wpa_s = ctx;
     478         160 :         wpas_p2p_wps_success(wpa_s, mac_addr, 1);
     479         160 : }
     480             : 
     481             : 
     482         236 : static void wpas_ap_configured_cb(void *ctx)
     483             : {
     484         236 :         struct wpa_supplicant *wpa_s = ctx;
     485             : 
     486         236 :         wpa_supplicant_set_state(wpa_s, WPA_COMPLETED);
     487             : 
     488         236 :         if (wpa_s->ap_configured_cb)
     489         225 :                 wpa_s->ap_configured_cb(wpa_s->ap_configured_cb_ctx,
     490             :                                         wpa_s->ap_configured_cb_data);
     491         236 : }
     492             : 
     493             : 
     494         238 : int wpa_supplicant_create_ap(struct wpa_supplicant *wpa_s,
     495             :                              struct wpa_ssid *ssid)
     496             : {
     497             :         struct wpa_driver_associate_params params;
     498             :         struct hostapd_iface *hapd_iface;
     499             :         struct hostapd_config *conf;
     500             :         size_t i;
     501             : 
     502         238 :         if (ssid->ssid == NULL || ssid->ssid_len == 0) {
     503           1 :                 wpa_printf(MSG_ERROR, "No SSID configured for AP mode");
     504           1 :                 return -1;
     505             :         }
     506             : 
     507         237 :         wpa_supplicant_ap_deinit(wpa_s);
     508             : 
     509         474 :         wpa_printf(MSG_DEBUG, "Setting up AP (SSID='%s')",
     510         237 :                    wpa_ssid_txt(ssid->ssid, ssid->ssid_len));
     511             : 
     512         237 :         os_memset(&params, 0, sizeof(params));
     513         237 :         params.ssid = ssid->ssid;
     514         237 :         params.ssid_len = ssid->ssid_len;
     515         237 :         switch (ssid->mode) {
     516             :         case WPAS_MODE_AP:
     517             :         case WPAS_MODE_P2P_GO:
     518             :         case WPAS_MODE_P2P_GROUP_FORMATION:
     519         237 :                 params.mode = IEEE80211_MODE_AP;
     520         237 :                 break;
     521             :         default:
     522           0 :                 return -1;
     523             :         }
     524         237 :         if (ssid->frequency == 0)
     525           1 :                 ssid->frequency = 2462; /* default channel 11 */
     526         237 :         params.freq.freq = ssid->frequency;
     527             : 
     528         237 :         params.wpa_proto = ssid->proto;
     529         237 :         if (ssid->key_mgmt & WPA_KEY_MGMT_PSK)
     530         228 :                 wpa_s->key_mgmt = WPA_KEY_MGMT_PSK;
     531             :         else
     532           9 :                 wpa_s->key_mgmt = WPA_KEY_MGMT_NONE;
     533         237 :         params.key_mgmt_suite = wpa_s->key_mgmt;
     534             : 
     535         237 :         wpa_s->pairwise_cipher = wpa_pick_pairwise_cipher(ssid->pairwise_cipher,
     536             :                                                           1);
     537         237 :         if (wpa_s->pairwise_cipher < 0) {
     538           0 :                 wpa_printf(MSG_WARNING, "WPA: Failed to select pairwise "
     539             :                            "cipher.");
     540           0 :                 return -1;
     541             :         }
     542         237 :         params.pairwise_suite = wpa_s->pairwise_cipher;
     543         237 :         params.group_suite = params.pairwise_suite;
     544             : 
     545             : #ifdef CONFIG_P2P
     546         349 :         if (ssid->mode == WPAS_MODE_P2P_GO ||
     547         112 :             ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)
     548         225 :                 params.p2p = 1;
     549             : #endif /* CONFIG_P2P */
     550             : 
     551         237 :         if (wpa_s->parent->set_ap_uapsd)
     552           0 :                 params.uapsd = wpa_s->parent->ap_uapsd;
     553         237 :         else if (params.p2p && (wpa_s->drv_flags & WPA_DRIVER_FLAGS_AP_UAPSD))
     554         225 :                 params.uapsd = 1; /* mandatory for P2P GO */
     555             :         else
     556          12 :                 params.uapsd = -1;
     557             : 
     558         237 :         if (wpa_drv_associate(wpa_s, &params) < 0) {
     559           1 :                 wpa_msg(wpa_s, MSG_INFO, "Failed to start AP functionality");
     560           1 :                 return -1;
     561             :         }
     562             : 
     563         236 :         wpa_s->ap_iface = hapd_iface = os_zalloc(sizeof(*wpa_s->ap_iface));
     564         236 :         if (hapd_iface == NULL)
     565           0 :                 return -1;
     566         236 :         hapd_iface->owner = wpa_s;
     567         236 :         hapd_iface->drv_flags = wpa_s->drv_flags;
     568         236 :         hapd_iface->smps_modes = wpa_s->drv_smps_modes;
     569         236 :         hapd_iface->probe_resp_offloads = wpa_s->probe_resp_offloads;
     570         236 :         hapd_iface->extended_capa = wpa_s->extended_capa;
     571         236 :         hapd_iface->extended_capa_mask = wpa_s->extended_capa_mask;
     572         236 :         hapd_iface->extended_capa_len = wpa_s->extended_capa_len;
     573             : 
     574         236 :         wpa_s->ap_iface->conf = conf = hostapd_config_defaults();
     575         236 :         if (conf == NULL) {
     576           0 :                 wpa_supplicant_ap_deinit(wpa_s);
     577           0 :                 return -1;
     578             :         }
     579             : 
     580         236 :         os_memcpy(wpa_s->ap_iface->conf->wmm_ac_params,
     581             :                   wpa_s->conf->wmm_ac_params,
     582             :                   sizeof(wpa_s->conf->wmm_ac_params));
     583             : 
     584         236 :         if (params.uapsd > 0) {
     585         225 :                 conf->bss[0]->wmm_enabled = 1;
     586         225 :                 conf->bss[0]->wmm_uapsd = 1;
     587             :         }
     588             : 
     589         236 :         if (wpa_supplicant_conf_ap(wpa_s, ssid, conf)) {
     590           0 :                 wpa_printf(MSG_ERROR, "Failed to create AP configuration");
     591           0 :                 wpa_supplicant_ap_deinit(wpa_s);
     592           0 :                 return -1;
     593             :         }
     594             : 
     595             : #ifdef CONFIG_P2P
     596         236 :         if (ssid->mode == WPAS_MODE_P2P_GO)
     597         125 :                 conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER;
     598         111 :         else if (ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)
     599         100 :                 conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER |
     600             :                         P2P_GROUP_FORMATION;
     601             : #endif /* CONFIG_P2P */
     602             : 
     603         236 :         hapd_iface->num_bss = conf->num_bss;
     604         236 :         hapd_iface->bss = os_calloc(conf->num_bss,
     605             :                                     sizeof(struct hostapd_data *));
     606         236 :         if (hapd_iface->bss == NULL) {
     607           0 :                 wpa_supplicant_ap_deinit(wpa_s);
     608           0 :                 return -1;
     609             :         }
     610             : 
     611         472 :         for (i = 0; i < conf->num_bss; i++) {
     612         472 :                 hapd_iface->bss[i] =
     613         236 :                         hostapd_alloc_bss_data(hapd_iface, conf,
     614         236 :                                                conf->bss[i]);
     615         236 :                 if (hapd_iface->bss[i] == NULL) {
     616           0 :                         wpa_supplicant_ap_deinit(wpa_s);
     617           0 :                         return -1;
     618             :                 }
     619             : 
     620         236 :                 hapd_iface->bss[i]->msg_ctx = wpa_s;
     621         236 :                 hapd_iface->bss[i]->msg_ctx_parent = wpa_s->parent;
     622         236 :                 hapd_iface->bss[i]->public_action_cb = ap_public_action_rx;
     623         236 :                 hapd_iface->bss[i]->public_action_cb_ctx = wpa_s;
     624         236 :                 hapd_iface->bss[i]->vendor_action_cb = ap_vendor_action_rx;
     625         236 :                 hapd_iface->bss[i]->vendor_action_cb_ctx = wpa_s;
     626         236 :                 hostapd_register_probereq_cb(hapd_iface->bss[i],
     627             :                                              ap_probe_req_rx, wpa_s);
     628         236 :                 hapd_iface->bss[i]->wps_reg_success_cb = ap_wps_reg_success_cb;
     629         236 :                 hapd_iface->bss[i]->wps_reg_success_cb_ctx = wpa_s;
     630         236 :                 hapd_iface->bss[i]->wps_event_cb = ap_wps_event_cb;
     631         236 :                 hapd_iface->bss[i]->wps_event_cb_ctx = wpa_s;
     632         236 :                 hapd_iface->bss[i]->sta_authorized_cb = ap_sta_authorized_cb;
     633         236 :                 hapd_iface->bss[i]->sta_authorized_cb_ctx = wpa_s;
     634             : #ifdef CONFIG_P2P
     635         236 :                 hapd_iface->bss[i]->new_psk_cb = ap_new_psk_cb;
     636         236 :                 hapd_iface->bss[i]->new_psk_cb_ctx = wpa_s;
     637         236 :                 hapd_iface->bss[i]->p2p = wpa_s->global->p2p;
     638         236 :                 hapd_iface->bss[i]->p2p_group = wpas_p2p_group_init(wpa_s,
     639             :                                                                     ssid);
     640             : #endif /* CONFIG_P2P */
     641         236 :                 hapd_iface->bss[i]->setup_complete_cb = wpas_ap_configured_cb;
     642         236 :                 hapd_iface->bss[i]->setup_complete_cb_ctx = wpa_s;
     643             : #ifdef CONFIG_TESTING_OPTIONS
     644         472 :                 hapd_iface->bss[i]->ext_eapol_frame_io =
     645         236 :                         wpa_s->ext_eapol_frame_io;
     646             : #endif /* CONFIG_TESTING_OPTIONS */
     647             :         }
     648             : 
     649         236 :         os_memcpy(hapd_iface->bss[0]->own_addr, wpa_s->own_addr, ETH_ALEN);
     650         236 :         hapd_iface->bss[0]->driver = wpa_s->driver;
     651         236 :         hapd_iface->bss[0]->drv_priv = wpa_s->drv_priv;
     652             : 
     653         236 :         wpa_s->current_ssid = ssid;
     654         236 :         eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
     655         236 :         os_memcpy(wpa_s->bssid, wpa_s->own_addr, ETH_ALEN);
     656         236 :         wpa_s->assoc_freq = ssid->frequency;
     657             : 
     658         236 :         if (hostapd_setup_interface(wpa_s->ap_iface)) {
     659           0 :                 wpa_printf(MSG_ERROR, "Failed to initialize AP interface");
     660           0 :                 wpa_supplicant_ap_deinit(wpa_s);
     661           0 :                 return -1;
     662             :         }
     663             : 
     664         236 :         return 0;
     665             : }
     666             : 
     667             : 
     668        5564 : void wpa_supplicant_ap_deinit(struct wpa_supplicant *wpa_s)
     669             : {
     670             : #ifdef CONFIG_WPS
     671        5564 :         eloop_cancel_timeout(wpas_wps_ap_pin_timeout, wpa_s, NULL);
     672             : #endif /* CONFIG_WPS */
     673             : 
     674        5564 :         if (wpa_s->ap_iface == NULL)
     675       10892 :                 return;
     676             : 
     677         236 :         wpa_s->current_ssid = NULL;
     678         236 :         eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
     679         236 :         wpa_s->assoc_freq = 0;
     680         236 :         wpas_p2p_ap_deinit(wpa_s);
     681         472 :         wpa_s->ap_iface->driver_ap_teardown =
     682         236 :                 !!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_AP_TEARDOWN_SUPPORT);
     683             : 
     684         236 :         hostapd_interface_deinit(wpa_s->ap_iface);
     685         236 :         hostapd_interface_free(wpa_s->ap_iface);
     686         236 :         wpa_s->ap_iface = NULL;
     687         236 :         wpa_drv_deinit_ap(wpa_s);
     688             : }
     689             : 
     690             : 
     691          10 : void ap_tx_status(void *ctx, const u8 *addr,
     692             :                   const u8 *buf, size_t len, int ack)
     693             : {
     694             : #ifdef NEED_AP_MLME
     695          10 :         struct wpa_supplicant *wpa_s = ctx;
     696          10 :         hostapd_tx_status(wpa_s->ap_iface->bss[0], addr, buf, len, ack);
     697             : #endif /* NEED_AP_MLME */
     698          10 : }
     699             : 
     700             : 
     701        1579 : void ap_eapol_tx_status(void *ctx, const u8 *dst,
     702             :                         const u8 *data, size_t len, int ack)
     703             : {
     704             : #ifdef NEED_AP_MLME
     705        1579 :         struct wpa_supplicant *wpa_s = ctx;
     706        1579 :         if (!wpa_s->ap_iface)
     707        1580 :                 return;
     708        1578 :         hostapd_tx_status(wpa_s->ap_iface->bss[0], dst, data, len, ack);
     709             : #endif /* NEED_AP_MLME */
     710             : }
     711             : 
     712             : 
     713           0 : void ap_client_poll_ok(void *ctx, const u8 *addr)
     714             : {
     715             : #ifdef NEED_AP_MLME
     716           0 :         struct wpa_supplicant *wpa_s = ctx;
     717           0 :         if (wpa_s->ap_iface)
     718           0 :                 hostapd_client_poll_ok(wpa_s->ap_iface->bss[0], addr);
     719             : #endif /* NEED_AP_MLME */
     720           0 : }
     721             : 
     722             : 
     723           0 : void ap_rx_from_unknown_sta(void *ctx, const u8 *addr, int wds)
     724             : {
     725             : #ifdef NEED_AP_MLME
     726           0 :         struct wpa_supplicant *wpa_s = ctx;
     727           0 :         ieee802_11_rx_from_unknown(wpa_s->ap_iface->bss[0], addr, wds);
     728             : #endif /* NEED_AP_MLME */
     729           0 : }
     730             : 
     731             : 
     732        1812 : void ap_mgmt_rx(void *ctx, struct rx_mgmt *rx_mgmt)
     733             : {
     734             : #ifdef NEED_AP_MLME
     735        1812 :         struct wpa_supplicant *wpa_s = ctx;
     736             :         struct hostapd_frame_info fi;
     737        1812 :         os_memset(&fi, 0, sizeof(fi));
     738        1812 :         fi.datarate = rx_mgmt->datarate;
     739        1812 :         fi.ssi_signal = rx_mgmt->ssi_signal;
     740        1812 :         ieee802_11_mgmt(wpa_s->ap_iface->bss[0], rx_mgmt->frame,
     741             :                         rx_mgmt->frame_len, &fi);
     742             : #endif /* NEED_AP_MLME */
     743        1812 : }
     744             : 
     745             : 
     746        1223 : void ap_mgmt_tx_cb(void *ctx, const u8 *buf, size_t len, u16 stype, int ok)
     747             : {
     748             : #ifdef NEED_AP_MLME
     749        1223 :         struct wpa_supplicant *wpa_s = ctx;
     750        1223 :         ieee802_11_mgmt_cb(wpa_s->ap_iface->bss[0], buf, len, stype, ok);
     751             : #endif /* NEED_AP_MLME */
     752        1223 : }
     753             : 
     754             : 
     755        1423 : void wpa_supplicant_ap_rx_eapol(struct wpa_supplicant *wpa_s,
     756             :                                 const u8 *src_addr, const u8 *buf, size_t len)
     757             : {
     758        1423 :         ieee802_1x_receive(wpa_s->ap_iface->bss[0], src_addr, buf, len);
     759        1423 : }
     760             : 
     761             : 
     762             : #ifdef CONFIG_WPS
     763             : 
     764          28 : int wpa_supplicant_ap_wps_pbc(struct wpa_supplicant *wpa_s, const u8 *bssid,
     765             :                               const u8 *p2p_dev_addr)
     766             : {
     767          28 :         if (!wpa_s->ap_iface)
     768           0 :                 return -1;
     769          28 :         return hostapd_wps_button_pushed(wpa_s->ap_iface->bss[0],
     770             :                                          p2p_dev_addr);
     771             : }
     772             : 
     773             : 
     774           8 : int wpa_supplicant_ap_wps_cancel(struct wpa_supplicant *wpa_s)
     775             : {
     776             :         struct wps_registrar *reg;
     777           8 :         int reg_sel = 0, wps_sta = 0;
     778             : 
     779           8 :         if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0]->wps)
     780           1 :                 return -1;
     781             : 
     782           7 :         reg = wpa_s->ap_iface->bss[0]->wps->registrar;
     783           7 :         reg_sel = wps_registrar_wps_cancel(reg);
     784           7 :         wps_sta = ap_for_each_sta(wpa_s->ap_iface->bss[0],
     785             :                                   ap_sta_wps_cancel, NULL);
     786             : 
     787           7 :         if (!reg_sel && !wps_sta) {
     788           5 :                 wpa_printf(MSG_DEBUG, "No WPS operation in progress at this "
     789             :                            "time");
     790           5 :                 return -1;
     791             :         }
     792             : 
     793             :         /*
     794             :          * There are 2 cases to return wps cancel as success:
     795             :          * 1. When wps cancel was initiated but no connection has been
     796             :          *    established with client yet.
     797             :          * 2. Client is in the middle of exchanging WPS messages.
     798             :          */
     799             : 
     800           2 :         return 0;
     801             : }
     802             : 
     803             : 
     804         129 : int wpa_supplicant_ap_wps_pin(struct wpa_supplicant *wpa_s, const u8 *bssid,
     805             :                               const char *pin, char *buf, size_t buflen,
     806             :                               int timeout)
     807             : {
     808         129 :         int ret, ret_len = 0;
     809             : 
     810         129 :         if (!wpa_s->ap_iface)
     811           0 :                 return -1;
     812             : 
     813         129 :         if (pin == NULL) {
     814           0 :                 unsigned int rpin = wps_generate_pin();
     815           0 :                 ret_len = os_snprintf(buf, buflen, "%08d", rpin);
     816           0 :                 if (os_snprintf_error(buflen, ret_len))
     817           0 :                         return -1;
     818           0 :                 pin = buf;
     819         129 :         } else if (buf) {
     820          51 :                 ret_len = os_snprintf(buf, buflen, "%s", pin);
     821          51 :                 if (os_snprintf_error(buflen, ret_len))
     822           0 :                         return -1;
     823             :         }
     824             : 
     825         129 :         ret = hostapd_wps_add_pin(wpa_s->ap_iface->bss[0], bssid, "any", pin,
     826             :                                   timeout);
     827         129 :         if (ret)
     828           0 :                 return -1;
     829         129 :         return ret_len;
     830             : }
     831             : 
     832             : 
     833           2 : static void wpas_wps_ap_pin_timeout(void *eloop_data, void *user_ctx)
     834             : {
     835           2 :         struct wpa_supplicant *wpa_s = eloop_data;
     836           2 :         wpa_printf(MSG_DEBUG, "WPS: AP PIN timed out");
     837           2 :         wpas_wps_ap_pin_disable(wpa_s);
     838           2 : }
     839             : 
     840             : 
     841           4 : static void wpas_wps_ap_pin_enable(struct wpa_supplicant *wpa_s, int timeout)
     842             : {
     843             :         struct hostapd_data *hapd;
     844             : 
     845           4 :         if (wpa_s->ap_iface == NULL)
     846           4 :                 return;
     847           4 :         hapd = wpa_s->ap_iface->bss[0];
     848           4 :         wpa_printf(MSG_DEBUG, "WPS: Enabling AP PIN (timeout=%d)", timeout);
     849           4 :         hapd->ap_pin_failures = 0;
     850           4 :         eloop_cancel_timeout(wpas_wps_ap_pin_timeout, wpa_s, NULL);
     851           4 :         if (timeout > 0)
     852           4 :                 eloop_register_timeout(timeout, 0,
     853             :                                        wpas_wps_ap_pin_timeout, wpa_s, NULL);
     854             : }
     855             : 
     856             : 
     857           3 : void wpas_wps_ap_pin_disable(struct wpa_supplicant *wpa_s)
     858             : {
     859             :         struct hostapd_data *hapd;
     860             : 
     861           3 :         if (wpa_s->ap_iface == NULL)
     862           3 :                 return;
     863           3 :         wpa_printf(MSG_DEBUG, "WPS: Disabling AP PIN");
     864           3 :         hapd = wpa_s->ap_iface->bss[0];
     865           3 :         os_free(hapd->conf->ap_pin);
     866           3 :         hapd->conf->ap_pin = NULL;
     867           3 :         eloop_cancel_timeout(wpas_wps_ap_pin_timeout, wpa_s, NULL);
     868             : }
     869             : 
     870             : 
     871           2 : const char * wpas_wps_ap_pin_random(struct wpa_supplicant *wpa_s, int timeout)
     872             : {
     873             :         struct hostapd_data *hapd;
     874             :         unsigned int pin;
     875             :         char pin_txt[9];
     876             : 
     877           2 :         if (wpa_s->ap_iface == NULL)
     878           0 :                 return NULL;
     879           2 :         hapd = wpa_s->ap_iface->bss[0];
     880           2 :         pin = wps_generate_pin();
     881           2 :         os_snprintf(pin_txt, sizeof(pin_txt), "%08u", pin);
     882           2 :         os_free(hapd->conf->ap_pin);
     883           2 :         hapd->conf->ap_pin = os_strdup(pin_txt);
     884           2 :         if (hapd->conf->ap_pin == NULL)
     885           0 :                 return NULL;
     886           2 :         wpas_wps_ap_pin_enable(wpa_s, timeout);
     887             : 
     888           2 :         return hapd->conf->ap_pin;
     889             : }
     890             : 
     891             : 
     892           8 : const char * wpas_wps_ap_pin_get(struct wpa_supplicant *wpa_s)
     893             : {
     894             :         struct hostapd_data *hapd;
     895           8 :         if (wpa_s->ap_iface == NULL)
     896           0 :                 return NULL;
     897           8 :         hapd = wpa_s->ap_iface->bss[0];
     898           8 :         return hapd->conf->ap_pin;
     899             : }
     900             : 
     901             : 
     902           2 : int wpas_wps_ap_pin_set(struct wpa_supplicant *wpa_s, const char *pin,
     903             :                         int timeout)
     904             : {
     905             :         struct hostapd_data *hapd;
     906             :         char pin_txt[9];
     907             :         int ret;
     908             : 
     909           2 :         if (wpa_s->ap_iface == NULL)
     910           0 :                 return -1;
     911           2 :         hapd = wpa_s->ap_iface->bss[0];
     912           2 :         ret = os_snprintf(pin_txt, sizeof(pin_txt), "%s", pin);
     913           2 :         if (os_snprintf_error(sizeof(pin_txt), ret))
     914           0 :                 return -1;
     915           2 :         os_free(hapd->conf->ap_pin);
     916           2 :         hapd->conf->ap_pin = os_strdup(pin_txt);
     917           2 :         if (hapd->conf->ap_pin == NULL)
     918           0 :                 return -1;
     919           2 :         wpas_wps_ap_pin_enable(wpa_s, timeout);
     920             : 
     921           2 :         return 0;
     922             : }
     923             : 
     924             : 
     925           0 : void wpa_supplicant_ap_pwd_auth_fail(struct wpa_supplicant *wpa_s)
     926             : {
     927             :         struct hostapd_data *hapd;
     928             : 
     929           0 :         if (wpa_s->ap_iface == NULL)
     930           0 :                 return;
     931           0 :         hapd = wpa_s->ap_iface->bss[0];
     932             : 
     933             :         /*
     934             :          * Registrar failed to prove its knowledge of the AP PIN. Disable AP
     935             :          * PIN if this happens multiple times to slow down brute force attacks.
     936             :          */
     937           0 :         hapd->ap_pin_failures++;
     938           0 :         wpa_printf(MSG_DEBUG, "WPS: AP PIN authentication failure number %u",
     939             :                    hapd->ap_pin_failures);
     940           0 :         if (hapd->ap_pin_failures < 3)
     941           0 :                 return;
     942             : 
     943           0 :         wpa_printf(MSG_DEBUG, "WPS: Disable AP PIN");
     944           0 :         hapd->ap_pin_failures = 0;
     945           0 :         os_free(hapd->conf->ap_pin);
     946           0 :         hapd->conf->ap_pin = NULL;
     947             : }
     948             : 
     949             : 
     950             : #ifdef CONFIG_WPS_NFC
     951             : 
     952           1 : struct wpabuf * wpas_ap_wps_nfc_config_token(struct wpa_supplicant *wpa_s,
     953             :                                              int ndef)
     954             : {
     955             :         struct hostapd_data *hapd;
     956             : 
     957           1 :         if (wpa_s->ap_iface == NULL)
     958           0 :                 return NULL;
     959           1 :         hapd = wpa_s->ap_iface->bss[0];
     960           1 :         return hostapd_wps_nfc_config_token(hapd, ndef);
     961             : }
     962             : 
     963             : 
     964           4 : struct wpabuf * wpas_ap_wps_nfc_handover_sel(struct wpa_supplicant *wpa_s,
     965             :                                              int ndef)
     966             : {
     967             :         struct hostapd_data *hapd;
     968             : 
     969           4 :         if (wpa_s->ap_iface == NULL)
     970           3 :                 return NULL;
     971           1 :         hapd = wpa_s->ap_iface->bss[0];
     972           1 :         return hostapd_wps_nfc_hs_cr(hapd, ndef);
     973             : }
     974             : 
     975             : 
     976           4 : int wpas_ap_wps_nfc_report_handover(struct wpa_supplicant *wpa_s,
     977             :                                     const struct wpabuf *req,
     978             :                                     const struct wpabuf *sel)
     979             : {
     980             :         struct hostapd_data *hapd;
     981             : 
     982           4 :         if (wpa_s->ap_iface == NULL)
     983           3 :                 return -1;
     984           1 :         hapd = wpa_s->ap_iface->bss[0];
     985           1 :         return hostapd_wps_nfc_report_handover(hapd, req, sel);
     986             : }
     987             : 
     988             : #endif /* CONFIG_WPS_NFC */
     989             : 
     990             : #endif /* CONFIG_WPS */
     991             : 
     992             : 
     993             : #ifdef CONFIG_CTRL_IFACE
     994             : 
     995           1 : int ap_ctrl_iface_sta_first(struct wpa_supplicant *wpa_s,
     996             :                             char *buf, size_t buflen)
     997             : {
     998             :         struct hostapd_data *hapd;
     999             : 
    1000           1 :         if (wpa_s->ap_iface)
    1001           1 :                 hapd = wpa_s->ap_iface->bss[0];
    1002           0 :         else if (wpa_s->ifmsh)
    1003           0 :                 hapd = wpa_s->ifmsh->bss[0];
    1004             :         else
    1005           0 :                 return -1;
    1006           1 :         return hostapd_ctrl_iface_sta_first(hapd, buf, buflen);
    1007             : }
    1008             : 
    1009             : 
    1010           1 : int ap_ctrl_iface_sta(struct wpa_supplicant *wpa_s, const char *txtaddr,
    1011             :                       char *buf, size_t buflen)
    1012             : {
    1013             :         struct hostapd_data *hapd;
    1014             : 
    1015           1 :         if (wpa_s->ap_iface)
    1016           1 :                 hapd = wpa_s->ap_iface->bss[0];
    1017           0 :         else if (wpa_s->ifmsh)
    1018           0 :                 hapd = wpa_s->ifmsh->bss[0];
    1019             :         else
    1020           0 :                 return -1;
    1021           1 :         return hostapd_ctrl_iface_sta(hapd, txtaddr, buf, buflen);
    1022             : }
    1023             : 
    1024             : 
    1025           2 : int ap_ctrl_iface_sta_next(struct wpa_supplicant *wpa_s, const char *txtaddr,
    1026             :                            char *buf, size_t buflen)
    1027             : {
    1028             :         struct hostapd_data *hapd;
    1029             : 
    1030           2 :         if (wpa_s->ap_iface)
    1031           2 :                 hapd = wpa_s->ap_iface->bss[0];
    1032           0 :         else if (wpa_s->ifmsh)
    1033           0 :                 hapd = wpa_s->ifmsh->bss[0];
    1034             :         else
    1035           0 :                 return -1;
    1036           2 :         return hostapd_ctrl_iface_sta_next(hapd, txtaddr, buf, buflen);
    1037             : }
    1038             : 
    1039             : 
    1040          22 : int ap_ctrl_iface_sta_disassociate(struct wpa_supplicant *wpa_s,
    1041             :                                    const char *txtaddr)
    1042             : {
    1043          22 :         if (wpa_s->ap_iface == NULL)
    1044           1 :                 return -1;
    1045          21 :         return hostapd_ctrl_iface_disassociate(wpa_s->ap_iface->bss[0],
    1046             :                                                txtaddr);
    1047             : }
    1048             : 
    1049             : 
    1050          22 : int ap_ctrl_iface_sta_deauthenticate(struct wpa_supplicant *wpa_s,
    1051             :                                      const char *txtaddr)
    1052             : {
    1053          22 :         if (wpa_s->ap_iface == NULL)
    1054           1 :                 return -1;
    1055          21 :         return hostapd_ctrl_iface_deauthenticate(wpa_s->ap_iface->bss[0],
    1056             :                                                  txtaddr);
    1057             : }
    1058             : 
    1059             : 
    1060         181 : int ap_ctrl_iface_wpa_get_status(struct wpa_supplicant *wpa_s, char *buf,
    1061             :                                  size_t buflen, int verbose)
    1062             : {
    1063         181 :         char *pos = buf, *end = buf + buflen;
    1064             :         int ret;
    1065             :         struct hostapd_bss_config *conf;
    1066             : 
    1067         181 :         if (wpa_s->ap_iface == NULL)
    1068           0 :                 return -1;
    1069             : 
    1070         181 :         conf = wpa_s->ap_iface->bss[0]->conf;
    1071         181 :         if (conf->wpa == 0)
    1072           3 :                 return 0;
    1073             : 
    1074         178 :         ret = os_snprintf(pos, end - pos,
    1075             :                           "pairwise_cipher=%s\n"
    1076             :                           "group_cipher=%s\n"
    1077             :                           "key_mgmt=%s\n",
    1078             :                           wpa_cipher_txt(conf->rsn_pairwise),
    1079             :                           wpa_cipher_txt(conf->wpa_group),
    1080             :                           wpa_key_mgmt_txt(conf->wpa_key_mgmt,
    1081             :                                            conf->wpa));
    1082         178 :         if (os_snprintf_error(end - pos, ret))
    1083           0 :                 return pos - buf;
    1084         178 :         pos += ret;
    1085         178 :         return pos - buf;
    1086             : }
    1087             : 
    1088             : #endif /* CONFIG_CTRL_IFACE */
    1089             : 
    1090             : 
    1091        1039 : int wpa_supplicant_ap_update_beacon(struct wpa_supplicant *wpa_s)
    1092             : {
    1093        1039 :         struct hostapd_iface *iface = wpa_s->ap_iface;
    1094        1039 :         struct wpa_ssid *ssid = wpa_s->current_ssid;
    1095             :         struct hostapd_data *hapd;
    1096             : 
    1097        1728 :         if (ssid == NULL || wpa_s->ap_iface == NULL ||
    1098        1378 :             ssid->mode == WPAS_MODE_INFRA ||
    1099         689 :             ssid->mode == WPAS_MODE_IBSS)
    1100         350 :                 return -1;
    1101             : 
    1102             : #ifdef CONFIG_P2P
    1103         689 :         if (ssid->mode == WPAS_MODE_P2P_GO)
    1104         585 :                 iface->conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER;
    1105         104 :         else if (ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)
    1106         104 :                 iface->conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER |
    1107             :                         P2P_GROUP_FORMATION;
    1108             : #endif /* CONFIG_P2P */
    1109             : 
    1110         689 :         hapd = iface->bss[0];
    1111         689 :         if (hapd->drv_priv == NULL)
    1112           0 :                 return -1;
    1113         689 :         ieee802_11_set_beacons(iface);
    1114         689 :         hostapd_set_ap_wps_ie(hapd);
    1115             : 
    1116         689 :         return 0;
    1117             : }
    1118             : 
    1119             : 
    1120           2 : int ap_switch_channel(struct wpa_supplicant *wpa_s,
    1121             :                       struct csa_settings *settings)
    1122             : {
    1123             : #ifdef NEED_AP_MLME
    1124           2 :         if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0])
    1125           1 :                 return -1;
    1126             : 
    1127           1 :         return hostapd_switch_channel(wpa_s->ap_iface->bss[0], settings);
    1128             : #else /* NEED_AP_MLME */
    1129             :         return -1;
    1130             : #endif /* NEED_AP_MLME */
    1131             : }
    1132             : 
    1133             : 
    1134           2 : int ap_ctrl_iface_chanswitch(struct wpa_supplicant *wpa_s, const char *pos)
    1135             : {
    1136             :         struct csa_settings settings;
    1137           2 :         int ret = hostapd_parse_csa_settings(pos, &settings);
    1138             : 
    1139           2 :         if (ret)
    1140           0 :                 return ret;
    1141             : 
    1142           2 :         return ap_switch_channel(wpa_s, &settings);
    1143             : }
    1144             : 
    1145             : 
    1146           1 : void wpas_ap_ch_switch(struct wpa_supplicant *wpa_s, int freq, int ht,
    1147             :                        int offset, int width, int cf1, int cf2)
    1148             : {
    1149           1 :         if (!wpa_s->ap_iface)
    1150           1 :                 return;
    1151             : 
    1152           1 :         wpa_s->assoc_freq = freq;
    1153           1 :         hostapd_event_ch_switch(wpa_s->ap_iface->bss[0], freq, ht, offset, width, cf1, cf1);
    1154             : }
    1155             : 
    1156             : 
    1157         196 : int wpa_supplicant_ap_mac_addr_filter(struct wpa_supplicant *wpa_s,
    1158             :                                       const u8 *addr)
    1159             : {
    1160             :         struct hostapd_data *hapd;
    1161             :         struct hostapd_bss_config *conf;
    1162             : 
    1163         196 :         if (!wpa_s->ap_iface)
    1164           0 :                 return -1;
    1165             : 
    1166         196 :         if (addr)
    1167         600 :                 wpa_printf(MSG_DEBUG, "AP: Set MAC address filter: " MACSTR,
    1168         600 :                            MAC2STR(addr));
    1169             :         else
    1170          96 :                 wpa_printf(MSG_DEBUG, "AP: Clear MAC address filter");
    1171             : 
    1172         196 :         hapd = wpa_s->ap_iface->bss[0];
    1173         196 :         conf = hapd->conf;
    1174             : 
    1175         196 :         os_free(conf->accept_mac);
    1176         196 :         conf->accept_mac = NULL;
    1177         196 :         conf->num_accept_mac = 0;
    1178         196 :         os_free(conf->deny_mac);
    1179         196 :         conf->deny_mac = NULL;
    1180         196 :         conf->num_deny_mac = 0;
    1181             : 
    1182         196 :         if (addr == NULL) {
    1183          96 :                 conf->macaddr_acl = ACCEPT_UNLESS_DENIED;
    1184          96 :                 return 0;
    1185             :         }
    1186             : 
    1187         100 :         conf->macaddr_acl = DENY_UNLESS_ACCEPTED;
    1188         100 :         conf->accept_mac = os_zalloc(sizeof(struct mac_acl_entry));
    1189         100 :         if (conf->accept_mac == NULL)
    1190           0 :                 return -1;
    1191         100 :         os_memcpy(conf->accept_mac[0].addr, addr, ETH_ALEN);
    1192         100 :         conf->num_accept_mac = 1;
    1193             : 
    1194         100 :         return 0;
    1195             : }
    1196             : 
    1197             : 
    1198             : #ifdef CONFIG_WPS_NFC
    1199          13 : int wpas_ap_wps_add_nfc_pw(struct wpa_supplicant *wpa_s, u16 pw_id,
    1200             :                            const struct wpabuf *pw, const u8 *pubkey_hash)
    1201             : {
    1202             :         struct hostapd_data *hapd;
    1203             :         struct wps_context *wps;
    1204             : 
    1205          13 :         if (!wpa_s->ap_iface)
    1206           0 :                 return -1;
    1207          13 :         hapd = wpa_s->ap_iface->bss[0];
    1208          13 :         wps = hapd->wps;
    1209             : 
    1210          26 :         if (wpa_s->parent->conf->wps_nfc_dh_pubkey == NULL ||
    1211          13 :             wpa_s->parent->conf->wps_nfc_dh_privkey == NULL) {
    1212           0 :                 wpa_printf(MSG_DEBUG, "P2P: No NFC DH key known");
    1213           0 :                 return -1;
    1214             :         }
    1215             : 
    1216          13 :         dh5_free(wps->dh_ctx);
    1217          13 :         wpabuf_free(wps->dh_pubkey);
    1218          13 :         wpabuf_free(wps->dh_privkey);
    1219          13 :         wps->dh_privkey = wpabuf_dup(
    1220          13 :                 wpa_s->parent->conf->wps_nfc_dh_privkey);
    1221          13 :         wps->dh_pubkey = wpabuf_dup(
    1222          13 :                 wpa_s->parent->conf->wps_nfc_dh_pubkey);
    1223          13 :         if (wps->dh_privkey == NULL || wps->dh_pubkey == NULL) {
    1224           0 :                 wps->dh_ctx = NULL;
    1225           0 :                 wpabuf_free(wps->dh_pubkey);
    1226           0 :                 wps->dh_pubkey = NULL;
    1227           0 :                 wpabuf_free(wps->dh_privkey);
    1228           0 :                 wps->dh_privkey = NULL;
    1229           0 :                 return -1;
    1230             :         }
    1231          13 :         wps->dh_ctx = dh5_init_fixed(wps->dh_privkey, wps->dh_pubkey);
    1232          13 :         if (wps->dh_ctx == NULL)
    1233           0 :                 return -1;
    1234             : 
    1235          13 :         return wps_registrar_add_nfc_pw_token(hapd->wps->registrar, pubkey_hash,
    1236             :                                               pw_id,
    1237             :                                               pw ? wpabuf_head(pw) : NULL,
    1238             :                                               pw ? wpabuf_len(pw) : 0, 1);
    1239             : }
    1240             : #endif /* CONFIG_WPS_NFC */

Generated by: LCOV version 1.10