]> git.ipfire.org Git - thirdparty/hostap.git/blame - wpa_supplicant/ap.c
P2P: Add support for VHT 80+80 MHz and 160 MHz
[thirdparty/hostap.git] / wpa_supplicant / ap.c
CommitLineData
f1a48710
JM
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 *
0f3d578e
JM
6 * This software may be distributed under the terms of the BSD license.
7 * See README for more details.
f1a48710
JM
8 */
9
6226e38d 10#include "utils/includes.h"
f1a48710 11
6226e38d 12#include "utils/common.h"
70d84f11 13#include "utils/eloop.h"
ab45223b 14#include "utils/uuid.h"
58c26600 15#include "common/ieee802_11_defs.h"
a0dee797 16#include "common/wpa_ctrl.h"
25a8f9e3 17#include "eapol_supp/eapol_supp_sm.h"
db6ae69e 18#include "crypto/dh_group5.h"
1057d78e 19#include "ap/hostapd.h"
6226e38d 20#include "ap/ap_config.h"
fe99fb74 21#include "ap/ap_drv_ops.h"
fe6bdb77 22#ifdef NEED_AP_MLME
1057d78e 23#include "ap/ieee802_11.h"
fe6bdb77 24#endif /* NEED_AP_MLME */
b22128ef 25#include "ap/beacon.h"
a8e0505b 26#include "ap/ieee802_1x.h"
363b9e60 27#include "ap/wps_hostapd.h"
0e2d35c6 28#include "ap/ctrl_iface_ap.h"
bd0f68c4 29#include "ap/dfs.h"
3ec97afe 30#include "wps/wps.h"
e44f8bf2 31#include "common/ieee802_11_defs.h"
1f1b62a0 32#include "config_ssid.h"
094393b1 33#include "config.h"
1f1b62a0 34#include "wpa_supplicant_i.h"
2d5b792d 35#include "driver_i.h"
e44f8bf2 36#include "p2p_supplicant.h"
2d5b792d 37#include "ap.h"
2f9929ff 38#include "ap/sta_info.h"
d8a43924 39#include "notify.h"
f1a48710
JM
40
41
0fe620de 42#ifdef CONFIG_WPS
70d84f11 43static void wpas_wps_ap_pin_timeout(void *eloop_data, void *user_ctx);
0fe620de 44#endif /* CONFIG_WPS */
70d84f11
JM
45
46
c20bc9d4 47#ifdef CONFIG_IEEE80211N
ca9bc5b5
EP
48static void wpas_conf_ap_vht(struct wpa_supplicant *wpa_s,
49 struct hostapd_config *conf,
50 struct hostapd_hw_modes *mode)
51{
f8b10c17 52#ifdef CONFIG_P2P
ca9bc5b5
EP
53 u8 center_chan = 0;
54 u8 channel = conf->channel;
55
56 if (!conf->secondary_channel)
57 goto no_vht;
58
c27f4c90
AK
59 switch (conf->vht_oper_chwidth) {
60 case VHT_CHANWIDTH_80MHZ:
61 case VHT_CHANWIDTH_80P80MHZ:
62 center_chan = wpas_p2p_get_vht80_center(wpa_s, mode, channel);
63 break;
64 case VHT_CHANWIDTH_160MHZ:
65 center_chan = wpas_p2p_get_vht160_center(wpa_s, mode, channel);
66 break;
67 default:
68 /*
69 * conf->vht_oper_chwidth might not be set for non-P2P GO cases,
70 * try oper_cwidth 160 MHz first then VHT 80 MHz, if 160 MHz is
71 * not supported.
72 */
73 conf->vht_oper_chwidth = VHT_CHANWIDTH_160MHZ;
74 center_chan = wpas_p2p_get_vht160_center(wpa_s, mode, channel);
75 if (!center_chan) {
76 conf->vht_oper_chwidth = VHT_CHANWIDTH_80MHZ;
77 center_chan = wpas_p2p_get_vht80_center(wpa_s, mode,
78 channel);
79 }
80 break;
81 }
ca9bc5b5
EP
82 if (!center_chan)
83 goto no_vht;
84
ca9bc5b5
EP
85 conf->vht_oper_centr_freq_seg0_idx = center_chan;
86 return;
87
88no_vht:
89 conf->vht_oper_centr_freq_seg0_idx =
90 channel + conf->secondary_channel * 2;
f8b10c17
JM
91#else /* CONFIG_P2P */
92 conf->vht_oper_centr_freq_seg0_idx =
93 conf->channel + conf->secondary_channel * 2;
94#endif /* CONFIG_P2P */
ca9bc5b5 95}
c20bc9d4 96#endif /* CONFIG_IEEE80211N */
ca9bc5b5
EP
97
98
73afc20d
AO
99int wpa_supplicant_conf_ap_ht(struct wpa_supplicant *wpa_s,
100 struct wpa_ssid *ssid,
101 struct hostapd_config *conf)
07f117ed 102{
73afc20d
AO
103 conf->hw_mode = ieee80211_freq_to_chan(ssid->frequency,
104 &conf->channel);
105
106 if (conf->hw_mode == NUM_HOSTAPD_MODES) {
107 wpa_printf(MSG_ERROR, "Unsupported AP mode frequency: %d MHz",
108 ssid->frequency);
109 return -1;
110 }
111
2db91745 112 /* TODO: enable HT40 if driver supports it;
07f117ed
JM
113 * drop to 11b if driver does not support 11g */
114
2db91745
AC
115#ifdef CONFIG_IEEE80211N
116 /*
79b8c60f
AN
117 * Enable HT20 if the driver supports it, by setting conf->ieee80211n
118 * and a mask of allowed capabilities within conf->ht_capab.
2db91745 119 * Using default config settings for: conf->ht_op_mode_fixed,
79b8c60f 120 * conf->secondary_channel, conf->require_ht
2db91745 121 */
6bf731e8 122 if (wpa_s->hw.modes) {
2db91745 123 struct hostapd_hw_modes *mode = NULL;
5cbf5fd9 124 int i, no_ht = 0;
6bf731e8
CL
125 for (i = 0; i < wpa_s->hw.num_modes; i++) {
126 if (wpa_s->hw.modes[i].mode == conf->hw_mode) {
127 mode = &wpa_s->hw.modes[i];
2db91745
AC
128 break;
129 }
130 }
5cbf5fd9
VT
131
132#ifdef CONFIG_HT_OVERRIDES
133 if (ssid->disable_ht) {
134 conf->ieee80211n = 0;
135 conf->ht_capab = 0;
136 no_ht = 1;
137 }
138#endif /* CONFIG_HT_OVERRIDES */
139
140 if (!no_ht && mode && mode->ht_capab) {
2db91745 141 conf->ieee80211n = 1;
7aeac985
RM
142#ifdef CONFIG_P2P
143 if (conf->hw_mode == HOSTAPD_MODE_IEEE80211A &&
144 (mode->ht_capab &
145 HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET) &&
146 ssid->ht40)
147 conf->secondary_channel =
148 wpas_p2p_get_ht40_mode(wpa_s, mode,
149 conf->channel);
150 if (conf->secondary_channel)
151 conf->ht_capab |=
152 HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET;
153#endif /* CONFIG_P2P */
79b8c60f
AN
154
155 /*
156 * white-list capabilities that won't cause issues
157 * to connecting stations, while leaving the current
158 * capabilities intact (currently disabled SMPS).
159 */
160 conf->ht_capab |= mode->ht_capab &
161 (HT_CAP_INFO_GREEN_FIELD |
162 HT_CAP_INFO_SHORT_GI20MHZ |
163 HT_CAP_INFO_SHORT_GI40MHZ |
164 HT_CAP_INFO_RX_STBC_MASK |
fd83335f 165 HT_CAP_INFO_TX_STBC |
79b8c60f 166 HT_CAP_INFO_MAX_AMSDU_SIZE);
ca9bc5b5
EP
167
168 if (mode->vht_capab && ssid->vht) {
169 conf->ieee80211ac = 1;
170 wpas_conf_ap_vht(wpa_s, conf, mode);
171 }
79b8c60f 172 }
2db91745 173 }
55413ce0
JM
174
175 if (conf->secondary_channel) {
176 struct wpa_supplicant *iface;
177
178 for (iface = wpa_s->global->ifaces; iface; iface = iface->next)
179 {
180 if (iface == wpa_s ||
181 iface->wpa_state < WPA_AUTHENTICATING ||
182 (int) iface->assoc_freq != ssid->frequency)
183 continue;
184
185 /*
186 * Do not allow 40 MHz co-ex PRI/SEC switch to force us
187 * to change our PRI channel since we have an existing,
188 * concurrent connection on that channel and doing
189 * multi-channel concurrency is likely to cause more
190 * harm than using different PRI/SEC selection in
191 * environment with multiple BSSes on these two channels
192 * with mixed 20 MHz or PRI channel selection.
193 */
194 conf->no_pri_sec_switch = 1;
195 }
196 }
2db91745 197#endif /* CONFIG_IEEE80211N */
73afc20d
AO
198
199 return 0;
5cfb672d
JM
200}
201
202
203static int wpa_supplicant_conf_ap(struct wpa_supplicant *wpa_s,
204 struct wpa_ssid *ssid,
205 struct hostapd_config *conf)
206{
207 struct hostapd_bss_config *bss = conf->bss[0];
208
209 conf->driver = wpa_s->driver;
210
211 os_strlcpy(bss->iface, wpa_s->ifname, sizeof(bss->iface));
212
73afc20d 213 if (wpa_supplicant_conf_ap_ht(wpa_s, ssid, conf))
5cfb672d 214 return -1;
2db91745 215
6e9023ea
JM
216 if (ieee80211_is_dfs(ssid->frequency) && wpa_s->conf->country[0]) {
217 conf->ieee80211h = 1;
218 conf->ieee80211d = 1;
219 conf->country[0] = wpa_s->conf->country[0];
220 conf->country[1] = wpa_s->conf->country[1];
221 }
222
4c2c3028 223#ifdef CONFIG_P2P
1e0e943e
AB
224 if (conf->hw_mode == HOSTAPD_MODE_IEEE80211G &&
225 (ssid->mode == WPAS_MODE_P2P_GO ||
226 ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)) {
4c2c3028
JM
227 /* Remove 802.11b rates from supported and basic rate sets */
228 int *list = os_malloc(4 * sizeof(int));
229 if (list) {
230 list[0] = 60;
231 list[1] = 120;
232 list[2] = 240;
233 list[3] = -1;
234 }
235 conf->basic_rates = list;
236
237 list = os_malloc(9 * sizeof(int));
238 if (list) {
239 list[0] = 60;
240 list[1] = 90;
241 list[2] = 120;
242 list[3] = 180;
243 list[4] = 240;
244 list[5] = 360;
245 list[6] = 480;
246 list[7] = 540;
247 list[8] = -1;
248 }
249 conf->supported_rates = list;
250 }
6cd930cb
JB
251
252 bss->isolate = !wpa_s->conf->p2p_intra_bss;
05766ed8 253 bss->force_per_enrollee_psk = wpa_s->global->p2p_per_sta_psk;
25ef8529
JM
254
255 if (ssid->p2p_group) {
256 os_memcpy(bss->ip_addr_go, wpa_s->parent->conf->ip_addr_go, 4);
257 os_memcpy(bss->ip_addr_mask, wpa_s->parent->conf->ip_addr_mask,
258 4);
259 os_memcpy(bss->ip_addr_start,
260 wpa_s->parent->conf->ip_addr_start, 4);
261 os_memcpy(bss->ip_addr_end, wpa_s->parent->conf->ip_addr_end,
262 4);
263 }
4c2c3028
JM
264#endif /* CONFIG_P2P */
265
07f117ed
JM
266 if (ssid->ssid_len == 0) {
267 wpa_printf(MSG_ERROR, "No SSID configured for AP mode");
268 return -1;
269 }
270 os_memcpy(bss->ssid.ssid, ssid->ssid, ssid->ssid_len);
07f117ed
JM
271 bss->ssid.ssid_len = ssid->ssid_len;
272 bss->ssid.ssid_set = 1;
273
e62f4ed0
VN
274 bss->ignore_broadcast_ssid = ssid->ignore_broadcast_ssid;
275
0399f2e4
VT
276 if (ssid->auth_alg)
277 bss->auth_algs = ssid->auth_alg;
278
07f117ed
JM
279 if (wpa_key_mgmt_wpa_psk(ssid->key_mgmt))
280 bss->wpa = ssid->proto;
281 bss->wpa_key_mgmt = ssid->key_mgmt;
282 bss->wpa_pairwise = ssid->pairwise_cipher;
30c371e8 283 if (ssid->psk_set) {
ce52d031 284 bin_clear_free(bss->ssid.wpa_psk, sizeof(*bss->ssid.wpa_psk));
07f117ed
JM
285 bss->ssid.wpa_psk = os_zalloc(sizeof(struct hostapd_wpa_psk));
286 if (bss->ssid.wpa_psk == NULL)
287 return -1;
288 os_memcpy(bss->ssid.wpa_psk->psk, ssid->psk, PMK_LEN);
289 bss->ssid.wpa_psk->group = 1;
30c371e8
MH
290 } else if (ssid->passphrase) {
291 bss->ssid.wpa_passphrase = os_strdup(ssid->passphrase);
6bcb1c2b
JM
292 } else if (ssid->wep_key_len[0] || ssid->wep_key_len[1] ||
293 ssid->wep_key_len[2] || ssid->wep_key_len[3]) {
294 struct hostapd_wep_keys *wep = &bss->ssid.wep;
295 int i;
296 for (i = 0; i < NUM_WEP_KEYS; i++) {
297 if (ssid->wep_key_len[i] == 0)
298 continue;
299 wep->key[i] = os_malloc(ssid->wep_key_len[i]);
300 if (wep->key[i] == NULL)
301 return -1;
302 os_memcpy(wep->key[i], ssid->wep_key[i],
303 ssid->wep_key_len[i]);
304 wep->len[i] = ssid->wep_key_len[i];
305 }
306 wep->idx = ssid->wep_tx_keyidx;
307 wep->keys_set = 1;
07f117ed
JM
308 }
309
07f53b8c
VT
310 if (ssid->ap_max_inactivity)
311 bss->ap_max_inactivity = ssid->ap_max_inactivity;
312
fdfb1c8b
EL
313 if (ssid->dtim_period)
314 bss->dtim_period = ssid->dtim_period;
18206e02
JM
315 else if (wpa_s->conf->dtim_period)
316 bss->dtim_period = wpa_s->conf->dtim_period;
317
318 if (ssid->beacon_int)
319 conf->beacon_int = ssid->beacon_int;
320 else if (wpa_s->conf->beacon_int)
321 conf->beacon_int = wpa_s->conf->beacon_int;
fdfb1c8b 322
0b8bcaa5 323#ifdef CONFIG_P2P
0aed3f5a
AS
324 if (ssid->mode == WPAS_MODE_P2P_GO ||
325 ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION) {
326 if (wpa_s->conf->p2p_go_ctwindow > conf->beacon_int) {
327 wpa_printf(MSG_INFO,
328 "CTWindow (%d) is bigger than beacon interval (%d) - avoid configuring it",
329 wpa_s->conf->p2p_go_ctwindow,
330 conf->beacon_int);
331 conf->p2p_go_ctwindow = 0;
332 } else {
333 conf->p2p_go_ctwindow = wpa_s->conf->p2p_go_ctwindow;
334 }
0b8bcaa5
EP
335 }
336#endif /* CONFIG_P2P */
337
cf830c1c
JM
338 if ((bss->wpa & 2) && bss->rsn_pairwise == 0)
339 bss->rsn_pairwise = bss->wpa_pairwise;
340 bss->wpa_group = wpa_select_ap_group_cipher(bss->wpa, bss->wpa_pairwise,
341 bss->rsn_pairwise);
07d9a552
JM
342
343 if (bss->wpa && bss->ieee802_1x)
344 bss->ssid.security_policy = SECURITY_WPA;
345 else if (bss->wpa)
346 bss->ssid.security_policy = SECURITY_WPA_PSK;
347 else if (bss->ieee802_1x) {
697cd03f 348 int cipher = WPA_CIPHER_NONE;
07d9a552
JM
349 bss->ssid.security_policy = SECURITY_IEEE_802_1X;
350 bss->ssid.wep.default_len = bss->default_wep_key_len;
697cd03f
JM
351 if (bss->default_wep_key_len)
352 cipher = bss->default_wep_key_len >= 13 ?
353 WPA_CIPHER_WEP104 : WPA_CIPHER_WEP40;
354 bss->wpa_group = cipher;
355 bss->wpa_pairwise = cipher;
356 bss->rsn_pairwise = cipher;
357 } else if (bss->ssid.wep.keys_set) {
358 int cipher = WPA_CIPHER_WEP40;
359 if (bss->ssid.wep.len[0] >= 13)
360 cipher = WPA_CIPHER_WEP104;
07d9a552 361 bss->ssid.security_policy = SECURITY_STATIC_WEP;
697cd03f
JM
362 bss->wpa_group = cipher;
363 bss->wpa_pairwise = cipher;
364 bss->rsn_pairwise = cipher;
365 } else {
07d9a552 366 bss->ssid.security_policy = SECURITY_PLAINTEXT;
697cd03f
JM
367 bss->wpa_group = WPA_CIPHER_NONE;
368 bss->wpa_pairwise = WPA_CIPHER_NONE;
369 bss->rsn_pairwise = WPA_CIPHER_NONE;
370 }
07d9a552 371
2a07a276
JM
372 if (bss->wpa_group_rekey < 86400 && (bss->wpa & 2) &&
373 (bss->wpa_group == WPA_CIPHER_CCMP ||
30675c34
JM
374 bss->wpa_group == WPA_CIPHER_GCMP ||
375 bss->wpa_group == WPA_CIPHER_CCMP_256 ||
376 bss->wpa_group == WPA_CIPHER_GCMP_256)) {
2a07a276
JM
377 /*
378 * Strong ciphers do not need frequent rekeying, so increase
379 * the default GTK rekeying period to 24 hours.
380 */
381 bss->wpa_group_rekey = 86400;
382 }
383
9a1a538f
JM
384#ifdef CONFIG_IEEE80211W
385 if (ssid->ieee80211w != MGMT_FRAME_PROTECTION_DEFAULT)
386 bss->ieee80211w = ssid->ieee80211w;
387#endif /* CONFIG_IEEE80211W */
388
3ec97afe
JM
389#ifdef CONFIG_WPS
390 /*
04ed4e98
JM
391 * Enable WPS by default for open and WPA/WPA2-Personal network, but
392 * require user interaction to actually use it. Only the internal
393 * Registrar is supported.
3ec97afe 394 */
04ed4e98
JM
395 if (bss->ssid.security_policy != SECURITY_WPA_PSK &&
396 bss->ssid.security_policy != SECURITY_PLAINTEXT)
397 goto no_wps;
c0f83f31 398 if (bss->ssid.security_policy == SECURITY_WPA_PSK &&
d77419d2
AM
399 (!(bss->rsn_pairwise & (WPA_CIPHER_CCMP | WPA_CIPHER_GCMP)) ||
400 !(bss->wpa & 2)))
c0f83f31
JM
401 goto no_wps; /* WPS2 does not allow WPA/TKIP-only
402 * configuration */
3ec97afe 403 bss->eap_server = 1;
e62f4ed0
VN
404
405 if (!ssid->ignore_broadcast_ssid)
406 bss->wps_state = 2;
407
9dd7d6b0 408 bss->ap_setup_locked = 2;
094393b1
JM
409 if (wpa_s->conf->config_methods)
410 bss->config_methods = os_strdup(wpa_s->conf->config_methods);
2f646b6e
JB
411 os_memcpy(bss->device_type, wpa_s->conf->device_type,
412 WPS_DEV_TYPE_LEN);
e44f8bf2
JM
413 if (wpa_s->conf->device_name) {
414 bss->device_name = os_strdup(wpa_s->conf->device_name);
415 bss->friendly_name = os_strdup(wpa_s->conf->device_name);
416 }
56815b2b
JM
417 if (wpa_s->conf->manufacturer)
418 bss->manufacturer = os_strdup(wpa_s->conf->manufacturer);
419 if (wpa_s->conf->model_name)
420 bss->model_name = os_strdup(wpa_s->conf->model_name);
421 if (wpa_s->conf->model_number)
422 bss->model_number = os_strdup(wpa_s->conf->model_number);
423 if (wpa_s->conf->serial_number)
424 bss->serial_number = os_strdup(wpa_s->conf->serial_number);
ab45223b
JM
425 if (is_nil_uuid(wpa_s->conf->uuid))
426 os_memcpy(bss->uuid, wpa_s->wps->uuid, WPS_UUID_LEN);
427 else
428 os_memcpy(bss->uuid, wpa_s->conf->uuid, WPS_UUID_LEN);
56815b2b 429 os_memcpy(bss->os_version, wpa_s->conf->os_version, 4);
1298c145 430 bss->pbc_in_m1 = wpa_s->conf->pbc_in_m1;
04ed4e98 431no_wps:
56815b2b 432#endif /* CONFIG_WPS */
e44f8bf2 433
de979d8f
JM
434 if (wpa_s->max_stations &&
435 wpa_s->max_stations < wpa_s->conf->max_num_sta)
436 bss->max_num_sta = wpa_s->max_stations;
437 else
438 bss->max_num_sta = wpa_s->conf->max_num_sta;
dae608d5 439
0d7e5a3a
JB
440 bss->disassoc_low_ack = wpa_s->conf->disassoc_low_ack;
441
18a2eaab
JM
442 if (wpa_s->conf->ap_vendor_elements) {
443 bss->vendor_elements =
444 wpabuf_dup(wpa_s->conf->ap_vendor_elements);
445 }
446
07f117ed
JM
447 return 0;
448}
449
450
c706d5aa
JM
451static void ap_public_action_rx(void *ctx, const u8 *buf, size_t len, int freq)
452{
e44f8bf2
JM
453#ifdef CONFIG_P2P
454 struct wpa_supplicant *wpa_s = ctx;
455 const struct ieee80211_mgmt *mgmt;
e44f8bf2
JM
456
457 mgmt = (const struct ieee80211_mgmt *) buf;
35c03184 458 if (len < IEEE80211_HDRLEN + 1)
e44f8bf2 459 return;
5ce00d09
JM
460 if (mgmt->u.action.category != WLAN_ACTION_PUBLIC)
461 return;
e44f8bf2
JM
462 wpas_p2p_rx_action(wpa_s, mgmt->da, mgmt->sa, mgmt->bssid,
463 mgmt->u.action.category,
35c03184
JM
464 buf + IEEE80211_HDRLEN + 1,
465 len - IEEE80211_HDRLEN - 1, freq);
e44f8bf2
JM
466#endif /* CONFIG_P2P */
467}
468
469
a0dee797
AGS
470static void ap_wps_event_cb(void *ctx, enum wps_event event,
471 union wps_event_data *data)
472{
ca806fb5 473#ifdef CONFIG_P2P
a0dee797 474 struct wpa_supplicant *wpa_s = ctx;
8be6450c
JMB
475
476 if (event == WPS_EV_FAIL) {
477 struct wps_event_fail *fail = &data->fail;
478
479 if (wpa_s->parent && wpa_s->parent != wpa_s &&
480 wpa_s == wpa_s->global->p2p_group_formation) {
481 /*
482 * src/ap/wps_hostapd.c has already sent this on the
483 * main interface, so only send on the parent interface
484 * here if needed.
485 */
486 wpa_msg(wpa_s->parent, MSG_INFO, WPS_EVENT_FAIL
487 "msg=%d config_error=%d",
488 fail->msg, fail->config_error);
489 }
490 wpas_p2p_wps_failed(wpa_s, fail);
a0dee797 491 }
ca806fb5 492#endif /* CONFIG_P2P */
a0dee797
AGS
493}
494
495
d8a43924 496static void ap_sta_authorized_cb(void *ctx, const u8 *mac_addr,
fbdcfd57 497 int authorized, const u8 *p2p_dev_addr)
d8a43924 498{
fbdcfd57 499 wpas_notify_sta_authorized(ctx, mac_addr, authorized, p2p_dev_addr);
d8a43924
JB
500}
501
502
01a57fe4
JM
503#ifdef CONFIG_P2P
504static void ap_new_psk_cb(void *ctx, const u8 *mac_addr, const u8 *p2p_dev_addr,
505 const u8 *psk, size_t psk_len)
506{
507
508 struct wpa_supplicant *wpa_s = ctx;
509 if (wpa_s->ap_iface == NULL || wpa_s->current_ssid == NULL)
510 return;
511 wpas_p2p_new_psk_cb(wpa_s, mac_addr, p2p_dev_addr, psk, psk_len);
512}
513#endif /* CONFIG_P2P */
514
515
e44f8bf2
JM
516static int ap_vendor_action_rx(void *ctx, const u8 *buf, size_t len, int freq)
517{
518#ifdef CONFIG_P2P
519 struct wpa_supplicant *wpa_s = ctx;
520 const struct ieee80211_mgmt *mgmt;
e44f8bf2
JM
521
522 mgmt = (const struct ieee80211_mgmt *) buf;
fb5d4171 523 if (len < IEEE80211_HDRLEN + 1)
e44f8bf2
JM
524 return -1;
525 wpas_p2p_rx_action(wpa_s, mgmt->da, mgmt->sa, mgmt->bssid,
526 mgmt->u.action.category,
fb5d4171
JM
527 buf + IEEE80211_HDRLEN + 1,
528 len - IEEE80211_HDRLEN - 1, freq);
e44f8bf2
JM
529#endif /* CONFIG_P2P */
530 return 0;
c706d5aa
JM
531}
532
533
04a85e44 534static int ap_probe_req_rx(void *ctx, const u8 *sa, const u8 *da,
baf513d6
JB
535 const u8 *bssid, const u8 *ie, size_t ie_len,
536 int ssi_signal)
c706d5aa 537{
e44f8bf2 538 struct wpa_supplicant *wpa_s = ctx;
0799b3f8
AO
539 unsigned int freq = 0;
540
541 if (wpa_s->ap_iface)
542 freq = wpa_s->ap_iface->freq;
543
baf513d6 544 return wpas_p2p_probe_req_rx(wpa_s, sa, da, bssid, ie, ie_len,
0799b3f8 545 freq, ssi_signal);
c706d5aa
JM
546}
547
548
549static void ap_wps_reg_success_cb(void *ctx, const u8 *mac_addr,
550 const u8 *uuid_e)
551{
e44f8bf2
JM
552 struct wpa_supplicant *wpa_s = ctx;
553 wpas_p2p_wps_success(wpa_s, mac_addr, 1);
c706d5aa
JM
554}
555
556
c76e5d7f
JB
557static void wpas_ap_configured_cb(void *ctx)
558{
559 struct wpa_supplicant *wpa_s = ctx;
560
561 wpa_supplicant_set_state(wpa_s, WPA_COMPLETED);
562
563 if (wpa_s->ap_configured_cb)
564 wpa_s->ap_configured_cb(wpa_s->ap_configured_cb_ctx,
565 wpa_s->ap_configured_cb_data);
566}
567
568
2d5b792d
JM
569int wpa_supplicant_create_ap(struct wpa_supplicant *wpa_s,
570 struct wpa_ssid *ssid)
571{
572 struct wpa_driver_associate_params params;
573 struct hostapd_iface *hapd_iface;
574 struct hostapd_config *conf;
575 size_t i;
f1a48710 576
2d5b792d
JM
577 if (ssid->ssid == NULL || ssid->ssid_len == 0) {
578 wpa_printf(MSG_ERROR, "No SSID configured for AP mode");
579 return -1;
f1a48710
JM
580 }
581
2d5b792d 582 wpa_supplicant_ap_deinit(wpa_s);
d2440ba0
JM
583
584 wpa_printf(MSG_DEBUG, "Setting up AP (SSID='%s')",
585 wpa_ssid_txt(ssid->ssid, ssid->ssid_len));
586
587 os_memset(&params, 0, sizeof(params));
588 params.ssid = ssid->ssid;
589 params.ssid_len = ssid->ssid_len;
d7dcba70 590 switch (ssid->mode) {
d7dcba70 591 case WPAS_MODE_AP:
2c5d725c
JM
592 case WPAS_MODE_P2P_GO:
593 case WPAS_MODE_P2P_GROUP_FORMATION:
d7dcba70
JM
594 params.mode = IEEE80211_MODE_AP;
595 break;
94ff22ea
JM
596 default:
597 return -1;
d7dcba70 598 }
973622cd
AS
599 if (ssid->frequency == 0)
600 ssid->frequency = 2462; /* default channel 11 */
4ec68377 601 params.freq.freq = ssid->frequency;
d2440ba0 602
64fa840a 603 params.wpa_proto = ssid->proto;
508545f3
JM
604 if (ssid->key_mgmt & WPA_KEY_MGMT_PSK)
605 wpa_s->key_mgmt = WPA_KEY_MGMT_PSK;
606 else
607 wpa_s->key_mgmt = WPA_KEY_MGMT_NONE;
4848a38d 608 params.key_mgmt_suite = wpa_s->key_mgmt;
508545f3 609
edbd2a19
JM
610 wpa_s->pairwise_cipher = wpa_pick_pairwise_cipher(ssid->pairwise_cipher,
611 1);
612 if (wpa_s->pairwise_cipher < 0) {
508545f3
JM
613 wpa_printf(MSG_WARNING, "WPA: Failed to select pairwise "
614 "cipher.");
615 return -1;
616 }
4848a38d 617 params.pairwise_suite = wpa_s->pairwise_cipher;
508545f3
JM
618 params.group_suite = params.pairwise_suite;
619
6e3f4b89
JM
620#ifdef CONFIG_P2P
621 if (ssid->mode == WPAS_MODE_P2P_GO ||
622 ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)
623 params.p2p = 1;
624#endif /* CONFIG_P2P */
625
eea2fd9e
JM
626 if (wpa_s->parent->set_ap_uapsd)
627 params.uapsd = wpa_s->parent->ap_uapsd;
94a3df50
JM
628 else if (params.p2p && (wpa_s->drv_flags & WPA_DRIVER_FLAGS_AP_UAPSD))
629 params.uapsd = 1; /* mandatory for P2P GO */
eea2fd9e
JM
630 else
631 params.uapsd = -1;
632
6e9023ea
JM
633 if (ieee80211_is_dfs(params.freq.freq))
634 params.freq.freq = 0; /* set channel after CAC */
635
d2440ba0
JM
636 if (wpa_drv_associate(wpa_s, &params) < 0) {
637 wpa_msg(wpa_s, MSG_INFO, "Failed to start AP functionality");
638 return -1;
639 }
640
2d5b792d
JM
641 wpa_s->ap_iface = hapd_iface = os_zalloc(sizeof(*wpa_s->ap_iface));
642 if (hapd_iface == NULL)
643 return -1;
0f2b2c19 644 hapd_iface->owner = wpa_s;
a57db49c 645 hapd_iface->drv_flags = wpa_s->drv_flags;
04ee647d 646 hapd_iface->smps_modes = wpa_s->drv_smps_modes;
4f73d88a 647 hapd_iface->probe_resp_offloads = wpa_s->probe_resp_offloads;
8cd6b7bc
JB
648 hapd_iface->extended_capa = wpa_s->extended_capa;
649 hapd_iface->extended_capa_mask = wpa_s->extended_capa_mask;
650 hapd_iface->extended_capa_len = wpa_s->extended_capa_len;
1f1b62a0 651
2d5b792d
JM
652 wpa_s->ap_iface->conf = conf = hostapd_config_defaults();
653 if (conf == NULL) {
654 wpa_supplicant_ap_deinit(wpa_s);
655 return -1;
656 }
1f1b62a0 657
c27f4c90
AK
658 /* Use the maximum oper channel width if it's given. */
659 if (ssid->max_oper_chwidth)
660 conf->vht_oper_chwidth = ssid->max_oper_chwidth;
661
662 ieee80211_freq_to_chan(ssid->vht_center_freq2,
663 &conf->vht_oper_centr_freq_seg1_idx);
664
c26effe1
YD
665 os_memcpy(wpa_s->ap_iface->conf->wmm_ac_params,
666 wpa_s->conf->wmm_ac_params,
667 sizeof(wpa_s->conf->wmm_ac_params));
668
d26e45a4 669 if (params.uapsd > 0) {
ebd79f07
JM
670 conf->bss[0]->wmm_enabled = 1;
671 conf->bss[0]->wmm_uapsd = 1;
d26e45a4
EP
672 }
673
07f117ed
JM
674 if (wpa_supplicant_conf_ap(wpa_s, ssid, conf)) {
675 wpa_printf(MSG_ERROR, "Failed to create AP configuration");
676 wpa_supplicant_ap_deinit(wpa_s);
677 return -1;
678 }
679
e44f8bf2
JM
680#ifdef CONFIG_P2P
681 if (ssid->mode == WPAS_MODE_P2P_GO)
ebd79f07 682 conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER;
e44f8bf2 683 else if (ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)
ebd79f07 684 conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER |
e44f8bf2
JM
685 P2P_GROUP_FORMATION;
686#endif /* CONFIG_P2P */
687
2d5b792d 688 hapd_iface->num_bss = conf->num_bss;
f9884c09 689 hapd_iface->bss = os_calloc(conf->num_bss,
2d5b792d
JM
690 sizeof(struct hostapd_data *));
691 if (hapd_iface->bss == NULL) {
692 wpa_supplicant_ap_deinit(wpa_s);
693 return -1;
694 }
1f1b62a0 695
2d5b792d
JM
696 for (i = 0; i < conf->num_bss; i++) {
697 hapd_iface->bss[i] =
698 hostapd_alloc_bss_data(hapd_iface, conf,
ebd79f07 699 conf->bss[i]);
2d5b792d
JM
700 if (hapd_iface->bss[i] == NULL) {
701 wpa_supplicant_ap_deinit(wpa_s);
702 return -1;
703 }
4f760fcc
JM
704
705 hapd_iface->bss[i]->msg_ctx = wpa_s;
8a5e75f6 706 hapd_iface->bss[i]->msg_ctx_parent = wpa_s->parent;
c706d5aa
JM
707 hapd_iface->bss[i]->public_action_cb = ap_public_action_rx;
708 hapd_iface->bss[i]->public_action_cb_ctx = wpa_s;
e44f8bf2
JM
709 hapd_iface->bss[i]->vendor_action_cb = ap_vendor_action_rx;
710 hapd_iface->bss[i]->vendor_action_cb_ctx = wpa_s;
c706d5aa
JM
711 hostapd_register_probereq_cb(hapd_iface->bss[i],
712 ap_probe_req_rx, wpa_s);
713 hapd_iface->bss[i]->wps_reg_success_cb = ap_wps_reg_success_cb;
714 hapd_iface->bss[i]->wps_reg_success_cb_ctx = wpa_s;
a0dee797
AGS
715 hapd_iface->bss[i]->wps_event_cb = ap_wps_event_cb;
716 hapd_iface->bss[i]->wps_event_cb_ctx = wpa_s;
d8a43924
JB
717 hapd_iface->bss[i]->sta_authorized_cb = ap_sta_authorized_cb;
718 hapd_iface->bss[i]->sta_authorized_cb_ctx = wpa_s;
e44f8bf2 719#ifdef CONFIG_P2P
01a57fe4
JM
720 hapd_iface->bss[i]->new_psk_cb = ap_new_psk_cb;
721 hapd_iface->bss[i]->new_psk_cb_ctx = wpa_s;
e44f8bf2 722 hapd_iface->bss[i]->p2p = wpa_s->global->p2p;
6f251b6b
JM
723 hapd_iface->bss[i]->p2p_group = wpas_p2p_group_init(wpa_s,
724 ssid);
e44f8bf2 725#endif /* CONFIG_P2P */
c76e5d7f
JB
726 hapd_iface->bss[i]->setup_complete_cb = wpas_ap_configured_cb;
727 hapd_iface->bss[i]->setup_complete_cb_ctx = wpa_s;
9d4ff04a
JM
728#ifdef CONFIG_TESTING_OPTIONS
729 hapd_iface->bss[i]->ext_eapol_frame_io =
730 wpa_s->ext_eapol_frame_io;
731#endif /* CONFIG_TESTING_OPTIONS */
2d5b792d
JM
732 }
733
a911a6e6
JM
734 os_memcpy(hapd_iface->bss[0]->own_addr, wpa_s->own_addr, ETH_ALEN);
735 hapd_iface->bss[0]->driver = wpa_s->driver;
736 hapd_iface->bss[0]->drv_priv = wpa_s->drv_priv;
737
e73edcaa 738 wpa_s->current_ssid = ssid;
25a8f9e3 739 eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
e73edcaa
JM
740 os_memcpy(wpa_s->bssid, wpa_s->own_addr, ETH_ALEN);
741 wpa_s->assoc_freq = ssid->frequency;
742
a911a6e6 743 if (hostapd_setup_interface(wpa_s->ap_iface)) {
2d5b792d
JM
744 wpa_printf(MSG_ERROR, "Failed to initialize AP interface");
745 wpa_supplicant_ap_deinit(wpa_s);
746 return -1;
1f1b62a0
JM
747 }
748
2d5b792d
JM
749 return 0;
750}
751
752
753void wpa_supplicant_ap_deinit(struct wpa_supplicant *wpa_s)
754{
0fe620de 755#ifdef CONFIG_WPS
70d84f11 756 eloop_cancel_timeout(wpas_wps_ap_pin_timeout, wpa_s, NULL);
0fe620de 757#endif /* CONFIG_WPS */
70d84f11 758
2d5b792d
JM
759 if (wpa_s->ap_iface == NULL)
760 return;
761
7a649c7d 762 wpa_s->current_ssid = NULL;
25a8f9e3 763 eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
3c85f144 764 wpa_s->assoc_freq = 0;
bd10d938 765 wpas_p2p_ap_deinit(wpa_s);
354c903f
MB
766 wpa_s->ap_iface->driver_ap_teardown =
767 !!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_AP_TEARDOWN_SUPPORT);
768
2d5b792d 769 hostapd_interface_deinit(wpa_s->ap_iface);
f7c47833 770 hostapd_interface_free(wpa_s->ap_iface);
2d5b792d 771 wpa_s->ap_iface = NULL;
7a649c7d 772 wpa_drv_deinit_ap(wpa_s);
f10487e1
JM
773 wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_DISCONNECTED "bssid=" MACSTR
774 " reason=%d locally_generated=1",
775 MAC2STR(wpa_s->own_addr), WLAN_REASON_DEAUTH_LEAVING);
1f1b62a0 776}
0915d02c
JM
777
778
779void ap_tx_status(void *ctx, const u8 *addr,
780 const u8 *buf, size_t len, int ack)
781{
f8b1f695 782#ifdef NEED_AP_MLME
0915d02c
JM
783 struct wpa_supplicant *wpa_s = ctx;
784 hostapd_tx_status(wpa_s->ap_iface->bss[0], addr, buf, len, ack);
f8b1f695 785#endif /* NEED_AP_MLME */
0915d02c
JM
786}
787
788
dd840f79
JB
789void ap_eapol_tx_status(void *ctx, const u8 *dst,
790 const u8 *data, size_t len, int ack)
791{
792#ifdef NEED_AP_MLME
793 struct wpa_supplicant *wpa_s = ctx;
6fc61e18
JM
794 if (!wpa_s->ap_iface)
795 return;
dd840f79
JB
796 hostapd_tx_status(wpa_s->ap_iface->bss[0], dst, data, len, ack);
797#endif /* NEED_AP_MLME */
798}
799
800
bcf24348
JB
801void ap_client_poll_ok(void *ctx, const u8 *addr)
802{
803#ifdef NEED_AP_MLME
804 struct wpa_supplicant *wpa_s = ctx;
805 if (wpa_s->ap_iface)
806 hostapd_client_poll_ok(wpa_s->ap_iface->bss[0], addr);
807#endif /* NEED_AP_MLME */
808}
809
810
9b90955e 811void ap_rx_from_unknown_sta(void *ctx, const u8 *addr, int wds)
0915d02c 812{
f8b1f695 813#ifdef NEED_AP_MLME
0915d02c 814 struct wpa_supplicant *wpa_s = ctx;
9b90955e 815 ieee802_11_rx_from_unknown(wpa_s->ap_iface->bss[0], addr, wds);
f8b1f695 816#endif /* NEED_AP_MLME */
0915d02c
JM
817}
818
819
2a8b7416 820void ap_mgmt_rx(void *ctx, struct rx_mgmt *rx_mgmt)
0915d02c 821{
f8b1f695 822#ifdef NEED_AP_MLME
0915d02c 823 struct wpa_supplicant *wpa_s = ctx;
2a8b7416
JM
824 struct hostapd_frame_info fi;
825 os_memset(&fi, 0, sizeof(fi));
826 fi.datarate = rx_mgmt->datarate;
827 fi.ssi_signal = rx_mgmt->ssi_signal;
828 ieee802_11_mgmt(wpa_s->ap_iface->bss[0], rx_mgmt->frame,
829 rx_mgmt->frame_len, &fi);
f8b1f695 830#endif /* NEED_AP_MLME */
0915d02c
JM
831}
832
833
f8b1f695 834void ap_mgmt_tx_cb(void *ctx, const u8 *buf, size_t len, u16 stype, int ok)
0915d02c 835{
f8b1f695 836#ifdef NEED_AP_MLME
0915d02c
JM
837 struct wpa_supplicant *wpa_s = ctx;
838 ieee802_11_mgmt_cb(wpa_s->ap_iface->bss[0], buf, len, stype, ok);
fe6bdb77 839#endif /* NEED_AP_MLME */
f8b1f695 840}
db149ac9
JM
841
842
843void wpa_supplicant_ap_rx_eapol(struct wpa_supplicant *wpa_s,
844 const u8 *src_addr, const u8 *buf, size_t len)
845{
a8e0505b 846 ieee802_1x_receive(wpa_s->ap_iface->bss[0], src_addr, buf, len);
db149ac9 847}
3ec97afe
JM
848
849
850#ifdef CONFIG_WPS
851
d601247c
JM
852int wpa_supplicant_ap_wps_pbc(struct wpa_supplicant *wpa_s, const u8 *bssid,
853 const u8 *p2p_dev_addr)
3ec97afe 854{
48b357a9
JM
855 if (!wpa_s->ap_iface)
856 return -1;
d601247c
JM
857 return hostapd_wps_button_pushed(wpa_s->ap_iface->bss[0],
858 p2p_dev_addr);
3ec97afe
JM
859}
860
861
2f9929ff
AC
862int wpa_supplicant_ap_wps_cancel(struct wpa_supplicant *wpa_s)
863{
864 struct wps_registrar *reg;
865 int reg_sel = 0, wps_sta = 0;
866
867 if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0]->wps)
868 return -1;
869
870 reg = wpa_s->ap_iface->bss[0]->wps->registrar;
871 reg_sel = wps_registrar_wps_cancel(reg);
872 wps_sta = ap_for_each_sta(wpa_s->ap_iface->bss[0],
4c374cde 873 ap_sta_wps_cancel, NULL);
2f9929ff
AC
874
875 if (!reg_sel && !wps_sta) {
876 wpa_printf(MSG_DEBUG, "No WPS operation in progress at this "
877 "time");
878 return -1;
879 }
880
881 /*
882 * There are 2 cases to return wps cancel as success:
883 * 1. When wps cancel was initiated but no connection has been
884 * established with client yet.
885 * 2. Client is in the middle of exchanging WPS messages.
886 */
887
888 return 0;
889}
890
891
3ec97afe 892int wpa_supplicant_ap_wps_pin(struct wpa_supplicant *wpa_s, const u8 *bssid,
c423708f
JM
893 const char *pin, char *buf, size_t buflen,
894 int timeout)
3ec97afe
JM
895{
896 int ret, ret_len = 0;
897
48b357a9
JM
898 if (!wpa_s->ap_iface)
899 return -1;
900
3ec97afe
JM
901 if (pin == NULL) {
902 unsigned int rpin = wps_generate_pin();
9337e876 903 ret_len = os_snprintf(buf, buflen, "%08d", rpin);
aaadd727
JM
904 if (os_snprintf_error(buflen, ret_len))
905 return -1;
3ec97afe 906 pin = buf;
aaadd727 907 } else if (buf) {
f80a2237 908 ret_len = os_snprintf(buf, buflen, "%s", pin);
aaadd727
JM
909 if (os_snprintf_error(buflen, ret_len))
910 return -1;
911 }
3ec97afe 912
31fcea93 913 ret = hostapd_wps_add_pin(wpa_s->ap_iface->bss[0], bssid, "any", pin,
c423708f 914 timeout);
3ec97afe
JM
915 if (ret)
916 return -1;
917 return ret_len;
918}
919
70d84f11
JM
920
921static void wpas_wps_ap_pin_timeout(void *eloop_data, void *user_ctx)
922{
923 struct wpa_supplicant *wpa_s = eloop_data;
924 wpa_printf(MSG_DEBUG, "WPS: AP PIN timed out");
925 wpas_wps_ap_pin_disable(wpa_s);
926}
927
928
929static void wpas_wps_ap_pin_enable(struct wpa_supplicant *wpa_s, int timeout)
930{
931 struct hostapd_data *hapd;
932
933 if (wpa_s->ap_iface == NULL)
934 return;
935 hapd = wpa_s->ap_iface->bss[0];
936 wpa_printf(MSG_DEBUG, "WPS: Enabling AP PIN (timeout=%d)", timeout);
937 hapd->ap_pin_failures = 0;
938 eloop_cancel_timeout(wpas_wps_ap_pin_timeout, wpa_s, NULL);
939 if (timeout > 0)
940 eloop_register_timeout(timeout, 0,
941 wpas_wps_ap_pin_timeout, wpa_s, NULL);
942}
943
944
945void wpas_wps_ap_pin_disable(struct wpa_supplicant *wpa_s)
946{
947 struct hostapd_data *hapd;
948
949 if (wpa_s->ap_iface == NULL)
950 return;
951 wpa_printf(MSG_DEBUG, "WPS: Disabling AP PIN");
952 hapd = wpa_s->ap_iface->bss[0];
953 os_free(hapd->conf->ap_pin);
954 hapd->conf->ap_pin = NULL;
955 eloop_cancel_timeout(wpas_wps_ap_pin_timeout, wpa_s, NULL);
956}
957
958
959const char * wpas_wps_ap_pin_random(struct wpa_supplicant *wpa_s, int timeout)
960{
961 struct hostapd_data *hapd;
962 unsigned int pin;
963 char pin_txt[9];
964
965 if (wpa_s->ap_iface == NULL)
966 return NULL;
967 hapd = wpa_s->ap_iface->bss[0];
968 pin = wps_generate_pin();
9337e876 969 os_snprintf(pin_txt, sizeof(pin_txt), "%08u", pin);
70d84f11
JM
970 os_free(hapd->conf->ap_pin);
971 hapd->conf->ap_pin = os_strdup(pin_txt);
972 if (hapd->conf->ap_pin == NULL)
973 return NULL;
974 wpas_wps_ap_pin_enable(wpa_s, timeout);
975
976 return hapd->conf->ap_pin;
977}
978
979
980const char * wpas_wps_ap_pin_get(struct wpa_supplicant *wpa_s)
981{
982 struct hostapd_data *hapd;
983 if (wpa_s->ap_iface == NULL)
984 return NULL;
985 hapd = wpa_s->ap_iface->bss[0];
986 return hapd->conf->ap_pin;
987}
988
989
990int wpas_wps_ap_pin_set(struct wpa_supplicant *wpa_s, const char *pin,
991 int timeout)
992{
993 struct hostapd_data *hapd;
994 char pin_txt[9];
995 int ret;
996
997 if (wpa_s->ap_iface == NULL)
998 return -1;
999 hapd = wpa_s->ap_iface->bss[0];
1000 ret = os_snprintf(pin_txt, sizeof(pin_txt), "%s", pin);
d85e1fc8 1001 if (os_snprintf_error(sizeof(pin_txt), ret))
70d84f11
JM
1002 return -1;
1003 os_free(hapd->conf->ap_pin);
1004 hapd->conf->ap_pin = os_strdup(pin_txt);
1005 if (hapd->conf->ap_pin == NULL)
1006 return -1;
1007 wpas_wps_ap_pin_enable(wpa_s, timeout);
1008
1009 return 0;
1010}
1011
1012
1013void wpa_supplicant_ap_pwd_auth_fail(struct wpa_supplicant *wpa_s)
1014{
1015 struct hostapd_data *hapd;
1016
1017 if (wpa_s->ap_iface == NULL)
1018 return;
1019 hapd = wpa_s->ap_iface->bss[0];
1020
1021 /*
1022 * Registrar failed to prove its knowledge of the AP PIN. Disable AP
1023 * PIN if this happens multiple times to slow down brute force attacks.
1024 */
1025 hapd->ap_pin_failures++;
1026 wpa_printf(MSG_DEBUG, "WPS: AP PIN authentication failure number %u",
1027 hapd->ap_pin_failures);
1028 if (hapd->ap_pin_failures < 3)
1029 return;
1030
1031 wpa_printf(MSG_DEBUG, "WPS: Disable AP PIN");
1032 hapd->ap_pin_failures = 0;
1033 os_free(hapd->conf->ap_pin);
1034 hapd->conf->ap_pin = NULL;
1035}
1036
bbf41865 1037
87470ea2
JM
1038#ifdef CONFIG_WPS_NFC
1039
bbf41865
JM
1040struct wpabuf * wpas_ap_wps_nfc_config_token(struct wpa_supplicant *wpa_s,
1041 int ndef)
1042{
1043 struct hostapd_data *hapd;
1044
1045 if (wpa_s->ap_iface == NULL)
1046 return NULL;
1047 hapd = wpa_s->ap_iface->bss[0];
1048 return hostapd_wps_nfc_config_token(hapd, ndef);
1049}
1050
5ab9a6a5
JM
1051
1052struct wpabuf * wpas_ap_wps_nfc_handover_sel(struct wpa_supplicant *wpa_s,
1053 int ndef)
1054{
1055 struct hostapd_data *hapd;
1056
1057 if (wpa_s->ap_iface == NULL)
1058 return NULL;
1059 hapd = wpa_s->ap_iface->bss[0];
1060 return hostapd_wps_nfc_hs_cr(hapd, ndef);
1061}
1062
d9507936
JM
1063
1064int wpas_ap_wps_nfc_report_handover(struct wpa_supplicant *wpa_s,
1065 const struct wpabuf *req,
1066 const struct wpabuf *sel)
1067{
1068 struct hostapd_data *hapd;
1069
1070 if (wpa_s->ap_iface == NULL)
1071 return -1;
1072 hapd = wpa_s->ap_iface->bss[0];
1073 return hostapd_wps_nfc_report_handover(hapd, req, sel);
1074}
1075
87470ea2
JM
1076#endif /* CONFIG_WPS_NFC */
1077
3ec97afe 1078#endif /* CONFIG_WPS */
e653b622
JM
1079
1080
35deb646
JM
1081#ifdef CONFIG_CTRL_IFACE
1082
e653b622
JM
1083int ap_ctrl_iface_sta_first(struct wpa_supplicant *wpa_s,
1084 char *buf, size_t buflen)
1085{
e7700713
JM
1086 struct hostapd_data *hapd;
1087
1088 if (wpa_s->ap_iface)
1089 hapd = wpa_s->ap_iface->bss[0];
1090 else if (wpa_s->ifmsh)
1091 hapd = wpa_s->ifmsh->bss[0];
1092 else
e653b622 1093 return -1;
e7700713 1094 return hostapd_ctrl_iface_sta_first(hapd, buf, buflen);
e653b622
JM
1095}
1096
1097
1098int ap_ctrl_iface_sta(struct wpa_supplicant *wpa_s, const char *txtaddr,
1099 char *buf, size_t buflen)
1100{
e7700713
JM
1101 struct hostapd_data *hapd;
1102
1103 if (wpa_s->ap_iface)
1104 hapd = wpa_s->ap_iface->bss[0];
1105 else if (wpa_s->ifmsh)
1106 hapd = wpa_s->ifmsh->bss[0];
1107 else
e653b622 1108 return -1;
e7700713 1109 return hostapd_ctrl_iface_sta(hapd, txtaddr, buf, buflen);
e653b622
JM
1110}
1111
1112
1113int ap_ctrl_iface_sta_next(struct wpa_supplicant *wpa_s, const char *txtaddr,
1114 char *buf, size_t buflen)
1115{
e7700713
JM
1116 struct hostapd_data *hapd;
1117
1118 if (wpa_s->ap_iface)
1119 hapd = wpa_s->ap_iface->bss[0];
1120 else if (wpa_s->ifmsh)
1121 hapd = wpa_s->ifmsh->bss[0];
1122 else
e653b622 1123 return -1;
e7700713 1124 return hostapd_ctrl_iface_sta_next(hapd, txtaddr, buf, buflen);
e653b622 1125}
35deb646 1126
43fb5297 1127
e60b2951
JJ
1128int ap_ctrl_iface_sta_disassociate(struct wpa_supplicant *wpa_s,
1129 const char *txtaddr)
1130{
1131 if (wpa_s->ap_iface == NULL)
1132 return -1;
1133 return hostapd_ctrl_iface_disassociate(wpa_s->ap_iface->bss[0],
1134 txtaddr);
1135}
1136
1137
1138int ap_ctrl_iface_sta_deauthenticate(struct wpa_supplicant *wpa_s,
1139 const char *txtaddr)
1140{
1141 if (wpa_s->ap_iface == NULL)
1142 return -1;
1143 return hostapd_ctrl_iface_deauthenticate(wpa_s->ap_iface->bss[0],
1144 txtaddr);
1145}
1146
1147
43fb5297
JM
1148int ap_ctrl_iface_wpa_get_status(struct wpa_supplicant *wpa_s, char *buf,
1149 size_t buflen, int verbose)
1150{
1151 char *pos = buf, *end = buf + buflen;
1152 int ret;
1153 struct hostapd_bss_config *conf;
1154
1155 if (wpa_s->ap_iface == NULL)
1156 return -1;
1157
1158 conf = wpa_s->ap_iface->bss[0]->conf;
1159 if (conf->wpa == 0)
1160 return 0;
1161
1162 ret = os_snprintf(pos, end - pos,
1163 "pairwise_cipher=%s\n"
1164 "group_cipher=%s\n"
1165 "key_mgmt=%s\n",
1166 wpa_cipher_txt(conf->rsn_pairwise),
1167 wpa_cipher_txt(conf->wpa_group),
1168 wpa_key_mgmt_txt(conf->wpa_key_mgmt,
1169 conf->wpa));
d85e1fc8 1170 if (os_snprintf_error(end - pos, ret))
43fb5297
JM
1171 return pos - buf;
1172 pos += ret;
1173 return pos - buf;
1174}
1175
35deb646 1176#endif /* CONFIG_CTRL_IFACE */
f90ceeaa
JM
1177
1178
b22128ef
JM
1179int wpa_supplicant_ap_update_beacon(struct wpa_supplicant *wpa_s)
1180{
1181 struct hostapd_iface *iface = wpa_s->ap_iface;
1182 struct wpa_ssid *ssid = wpa_s->current_ssid;
1183 struct hostapd_data *hapd;
1184
72d48a80
JM
1185 if (ssid == NULL || wpa_s->ap_iface == NULL ||
1186 ssid->mode == WPAS_MODE_INFRA ||
1187 ssid->mode == WPAS_MODE_IBSS)
b22128ef
JM
1188 return -1;
1189
e44f8bf2
JM
1190#ifdef CONFIG_P2P
1191 if (ssid->mode == WPAS_MODE_P2P_GO)
ebd79f07 1192 iface->conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER;
e44f8bf2 1193 else if (ssid->mode == WPAS_MODE_P2P_GROUP_FORMATION)
ebd79f07 1194 iface->conf->bss[0]->p2p = P2P_ENABLED | P2P_GROUP_OWNER |
e44f8bf2
JM
1195 P2P_GROUP_FORMATION;
1196#endif /* CONFIG_P2P */
1197
b22128ef 1198 hapd = iface->bss[0];
72d48a80
JM
1199 if (hapd->drv_priv == NULL)
1200 return -1;
1201 ieee802_11_set_beacons(iface);
fe99fb74 1202 hostapd_set_ap_wps_ie(hapd);
b22128ef
JM
1203
1204 return 0;
1205}
1206
1207
bf281c12
AO
1208int ap_switch_channel(struct wpa_supplicant *wpa_s,
1209 struct csa_settings *settings)
1210{
1211#ifdef NEED_AP_MLME
1212 if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0])
1213 return -1;
1214
1215 return hostapd_switch_channel(wpa_s->ap_iface->bss[0], settings);
1216#else /* NEED_AP_MLME */
1217 return -1;
1218#endif /* NEED_AP_MLME */
1219}
1220
1221
b7991185 1222#ifdef CONFIG_CTRL_IFACE
334bf36a
AO
1223int ap_ctrl_iface_chanswitch(struct wpa_supplicant *wpa_s, const char *pos)
1224{
1225 struct csa_settings settings;
1226 int ret = hostapd_parse_csa_settings(pos, &settings);
1227
1228 if (ret)
1229 return ret;
1230
1231 return ap_switch_channel(wpa_s, &settings);
1232}
b7991185 1233#endif /* CONFIG_CTRL_IFACE */
334bf36a
AO
1234
1235
1b487b8b 1236void wpas_ap_ch_switch(struct wpa_supplicant *wpa_s, int freq, int ht,
8d1fdde7 1237 int offset, int width, int cf1, int cf2)
1b487b8b
TP
1238{
1239 if (!wpa_s->ap_iface)
1240 return;
1241
1242 wpa_s->assoc_freq = freq;
d7ded547
AO
1243 if (wpa_s->current_ssid)
1244 wpa_s->current_ssid->frequency = freq;
55b4cc6d
AO
1245 hostapd_event_ch_switch(wpa_s->ap_iface->bss[0], freq, ht,
1246 offset, width, cf1, cf2);
1b487b8b
TP
1247}
1248
1249
f90ceeaa
JM
1250int wpa_supplicant_ap_mac_addr_filter(struct wpa_supplicant *wpa_s,
1251 const u8 *addr)
1252{
1253 struct hostapd_data *hapd;
1254 struct hostapd_bss_config *conf;
1255
1256 if (!wpa_s->ap_iface)
1257 return -1;
1258
1259 if (addr)
1260 wpa_printf(MSG_DEBUG, "AP: Set MAC address filter: " MACSTR,
1261 MAC2STR(addr));
1262 else
1263 wpa_printf(MSG_DEBUG, "AP: Clear MAC address filter");
1264
1265 hapd = wpa_s->ap_iface->bss[0];
1266 conf = hapd->conf;
1267
1268 os_free(conf->accept_mac);
1269 conf->accept_mac = NULL;
1270 conf->num_accept_mac = 0;
1271 os_free(conf->deny_mac);
1272 conf->deny_mac = NULL;
1273 conf->num_deny_mac = 0;
1274
1275 if (addr == NULL) {
1276 conf->macaddr_acl = ACCEPT_UNLESS_DENIED;
1277 return 0;
1278 }
1279
1280 conf->macaddr_acl = DENY_UNLESS_ACCEPTED;
1281 conf->accept_mac = os_zalloc(sizeof(struct mac_acl_entry));
1282 if (conf->accept_mac == NULL)
1283 return -1;
1284 os_memcpy(conf->accept_mac[0].addr, addr, ETH_ALEN);
1285 conf->num_accept_mac = 1;
1286
1287 return 0;
1288}
db6ae69e
JM
1289
1290
1291#ifdef CONFIG_WPS_NFC
1292int wpas_ap_wps_add_nfc_pw(struct wpa_supplicant *wpa_s, u16 pw_id,
1293 const struct wpabuf *pw, const u8 *pubkey_hash)
1294{
1295 struct hostapd_data *hapd;
1296 struct wps_context *wps;
1297
1298 if (!wpa_s->ap_iface)
1299 return -1;
1300 hapd = wpa_s->ap_iface->bss[0];
1301 wps = hapd->wps;
1302
1303 if (wpa_s->parent->conf->wps_nfc_dh_pubkey == NULL ||
1304 wpa_s->parent->conf->wps_nfc_dh_privkey == NULL) {
1305 wpa_printf(MSG_DEBUG, "P2P: No NFC DH key known");
1306 return -1;
1307 }
1308
1309 dh5_free(wps->dh_ctx);
1310 wpabuf_free(wps->dh_pubkey);
1311 wpabuf_free(wps->dh_privkey);
1312 wps->dh_privkey = wpabuf_dup(
1313 wpa_s->parent->conf->wps_nfc_dh_privkey);
1314 wps->dh_pubkey = wpabuf_dup(
1315 wpa_s->parent->conf->wps_nfc_dh_pubkey);
1316 if (wps->dh_privkey == NULL || wps->dh_pubkey == NULL) {
1317 wps->dh_ctx = NULL;
1318 wpabuf_free(wps->dh_pubkey);
1319 wps->dh_pubkey = NULL;
1320 wpabuf_free(wps->dh_privkey);
1321 wps->dh_privkey = NULL;
1322 return -1;
1323 }
1324 wps->dh_ctx = dh5_init_fixed(wps->dh_privkey, wps->dh_pubkey);
1325 if (wps->dh_ctx == NULL)
1326 return -1;
1327
1328 return wps_registrar_add_nfc_pw_token(hapd->wps->registrar, pubkey_hash,
1329 pw_id,
1330 pw ? wpabuf_head(pw) : NULL,
1331 pw ? wpabuf_len(pw) : 0, 1);
1332}
1333#endif /* CONFIG_WPS_NFC */
99650cad
JM
1334
1335
b7991185 1336#ifdef CONFIG_CTRL_IFACE
99650cad
JM
1337int wpas_ap_stop_ap(struct wpa_supplicant *wpa_s)
1338{
1339 struct hostapd_data *hapd;
1340
1341 if (!wpa_s->ap_iface)
1342 return -1;
1343 hapd = wpa_s->ap_iface->bss[0];
1344 return hostapd_ctrl_iface_stop_ap(hapd);
1345}
b7991185 1346#endif /* CONFIG_CTRL_IFACE */
bd0f68c4
AK
1347
1348
1349#ifdef NEED_AP_MLME
1350void wpas_event_dfs_radar_detected(struct wpa_supplicant *wpa_s,
1351 struct dfs_event *radar)
1352{
1353 if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0])
1354 return;
1355 wpa_printf(MSG_DEBUG, "DFS radar detected on %d MHz", radar->freq);
1356 hostapd_dfs_radar_detected(wpa_s->ap_iface, radar->freq,
1357 radar->ht_enabled, radar->chan_offset,
1358 radar->chan_width,
1359 radar->cf1, radar->cf2);
1360}
1361
1362
1363void wpas_event_dfs_cac_started(struct wpa_supplicant *wpa_s,
1364 struct dfs_event *radar)
1365{
1366 if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0])
1367 return;
1368 wpa_printf(MSG_DEBUG, "DFS CAC started on %d MHz", radar->freq);
1369 hostapd_dfs_start_cac(wpa_s->ap_iface, radar->freq,
1370 radar->ht_enabled, radar->chan_offset,
1371 radar->chan_width, radar->cf1, radar->cf2);
1372}
1373
1374
1375void wpas_event_dfs_cac_finished(struct wpa_supplicant *wpa_s,
1376 struct dfs_event *radar)
1377{
1378 if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0])
1379 return;
1380 wpa_printf(MSG_DEBUG, "DFS CAC finished on %d MHz", radar->freq);
1381 hostapd_dfs_complete_cac(wpa_s->ap_iface, 1, radar->freq,
1382 radar->ht_enabled, radar->chan_offset,
1383 radar->chan_width, radar->cf1, radar->cf2);
1384}
1385
1386
1387void wpas_event_dfs_cac_aborted(struct wpa_supplicant *wpa_s,
1388 struct dfs_event *radar)
1389{
1390 if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0])
1391 return;
1392 wpa_printf(MSG_DEBUG, "DFS CAC aborted on %d MHz", radar->freq);
1393 hostapd_dfs_complete_cac(wpa_s->ap_iface, 0, radar->freq,
1394 radar->ht_enabled, radar->chan_offset,
1395 radar->chan_width, radar->cf1, radar->cf2);
1396}
1397
1398
1399void wpas_event_dfs_cac_nop_finished(struct wpa_supplicant *wpa_s,
1400 struct dfs_event *radar)
1401{
1402 if (!wpa_s->ap_iface || !wpa_s->ap_iface->bss[0])
1403 return;
1404 wpa_printf(MSG_DEBUG, "DFS NOP finished on %d MHz", radar->freq);
1405 hostapd_dfs_nop_finished(wpa_s->ap_iface, radar->freq,
1406 radar->ht_enabled, radar->chan_offset,
1407 radar->chan_width, radar->cf1, radar->cf2);
1408}
1409#endif /* NEED_AP_MLME */
3188aaba
JM
1410
1411
1412void ap_periodic(struct wpa_supplicant *wpa_s)
1413{
1414 if (wpa_s->ap_iface)
1415 hostapd_periodic_iface(wpa_s->ap_iface);
1416}