]> git.ipfire.org Git - thirdparty/hostap.git/blob - src/common/ieee802_11_common.c
Recognize OWE Transition Mode element in IE parser
[thirdparty/hostap.git] / src / common / ieee802_11_common.c
1 /*
2 * IEEE 802.11 Common routines
3 * Copyright (c) 2002-2019, Jouni Malinen <j@w1.fi>
4 *
5 * This software may be distributed under the terms of the BSD license.
6 * See README for more details.
7 */
8
9 #include "includes.h"
10
11 #include "common.h"
12 #include "defs.h"
13 #include "wpa_common.h"
14 #include "drivers/driver.h"
15 #include "qca-vendor.h"
16 #include "ieee802_11_defs.h"
17 #include "ieee802_11_common.h"
18
19
20 static int ieee802_11_parse_vendor_specific(const u8 *pos, size_t elen,
21 struct ieee802_11_elems *elems,
22 int show_errors)
23 {
24 unsigned int oui;
25
26 /* first 3 bytes in vendor specific information element are the IEEE
27 * OUI of the vendor. The following byte is used a vendor specific
28 * sub-type. */
29 if (elen < 4) {
30 if (show_errors) {
31 wpa_printf(MSG_MSGDUMP, "short vendor specific "
32 "information element ignored (len=%lu)",
33 (unsigned long) elen);
34 }
35 return -1;
36 }
37
38 oui = WPA_GET_BE24(pos);
39 switch (oui) {
40 case OUI_MICROSOFT:
41 /* Microsoft/Wi-Fi information elements are further typed and
42 * subtyped */
43 switch (pos[3]) {
44 case 1:
45 /* Microsoft OUI (00:50:F2) with OUI Type 1:
46 * real WPA information element */
47 elems->wpa_ie = pos;
48 elems->wpa_ie_len = elen;
49 break;
50 case WMM_OUI_TYPE:
51 /* WMM information element */
52 if (elen < 5) {
53 wpa_printf(MSG_MSGDUMP, "short WMM "
54 "information element ignored "
55 "(len=%lu)",
56 (unsigned long) elen);
57 return -1;
58 }
59 switch (pos[4]) {
60 case WMM_OUI_SUBTYPE_INFORMATION_ELEMENT:
61 case WMM_OUI_SUBTYPE_PARAMETER_ELEMENT:
62 /*
63 * Share same pointer since only one of these
64 * is used and they start with same data.
65 * Length field can be used to distinguish the
66 * IEs.
67 */
68 elems->wmm = pos;
69 elems->wmm_len = elen;
70 break;
71 case WMM_OUI_SUBTYPE_TSPEC_ELEMENT:
72 elems->wmm_tspec = pos;
73 elems->wmm_tspec_len = elen;
74 break;
75 default:
76 wpa_printf(MSG_EXCESSIVE, "unknown WMM "
77 "information element ignored "
78 "(subtype=%d len=%lu)",
79 pos[4], (unsigned long) elen);
80 return -1;
81 }
82 break;
83 case 4:
84 /* Wi-Fi Protected Setup (WPS) IE */
85 elems->wps_ie = pos;
86 elems->wps_ie_len = elen;
87 break;
88 default:
89 wpa_printf(MSG_EXCESSIVE, "Unknown Microsoft "
90 "information element ignored "
91 "(type=%d len=%lu)",
92 pos[3], (unsigned long) elen);
93 return -1;
94 }
95 break;
96
97 case OUI_WFA:
98 switch (pos[3]) {
99 case P2P_OUI_TYPE:
100 /* Wi-Fi Alliance - P2P IE */
101 elems->p2p = pos;
102 elems->p2p_len = elen;
103 break;
104 case WFD_OUI_TYPE:
105 /* Wi-Fi Alliance - WFD IE */
106 elems->wfd = pos;
107 elems->wfd_len = elen;
108 break;
109 case HS20_INDICATION_OUI_TYPE:
110 /* Hotspot 2.0 */
111 elems->hs20 = pos;
112 elems->hs20_len = elen;
113 break;
114 case HS20_OSEN_OUI_TYPE:
115 /* Hotspot 2.0 OSEN */
116 elems->osen = pos;
117 elems->osen_len = elen;
118 break;
119 case MBO_OUI_TYPE:
120 /* MBO-OCE */
121 elems->mbo = pos;
122 elems->mbo_len = elen;
123 break;
124 case HS20_ROAMING_CONS_SEL_OUI_TYPE:
125 /* Hotspot 2.0 Roaming Consortium Selection */
126 elems->roaming_cons_sel = pos;
127 elems->roaming_cons_sel_len = elen;
128 break;
129 case MULTI_AP_OUI_TYPE:
130 elems->multi_ap = pos;
131 elems->multi_ap_len = elen;
132 break;
133 case OWE_OUI_TYPE:
134 /* OWE Transition Mode element */
135 break;
136 default:
137 wpa_printf(MSG_MSGDUMP, "Unknown WFA "
138 "information element ignored "
139 "(type=%d len=%lu)",
140 pos[3], (unsigned long) elen);
141 return -1;
142 }
143 break;
144
145 case OUI_BROADCOM:
146 switch (pos[3]) {
147 case VENDOR_HT_CAPAB_OUI_TYPE:
148 elems->vendor_ht_cap = pos;
149 elems->vendor_ht_cap_len = elen;
150 break;
151 case VENDOR_VHT_TYPE:
152 if (elen > 4 &&
153 (pos[4] == VENDOR_VHT_SUBTYPE ||
154 pos[4] == VENDOR_VHT_SUBTYPE2)) {
155 elems->vendor_vht = pos;
156 elems->vendor_vht_len = elen;
157 } else
158 return -1;
159 break;
160 default:
161 wpa_printf(MSG_EXCESSIVE, "Unknown Broadcom "
162 "information element ignored "
163 "(type=%d len=%lu)",
164 pos[3], (unsigned long) elen);
165 return -1;
166 }
167 break;
168
169 case OUI_QCA:
170 switch (pos[3]) {
171 case QCA_VENDOR_ELEM_P2P_PREF_CHAN_LIST:
172 elems->pref_freq_list = pos;
173 elems->pref_freq_list_len = elen;
174 break;
175 default:
176 wpa_printf(MSG_EXCESSIVE,
177 "Unknown QCA information element ignored (type=%d len=%lu)",
178 pos[3], (unsigned long) elen);
179 return -1;
180 }
181 break;
182
183 default:
184 wpa_printf(MSG_EXCESSIVE, "unknown vendor specific "
185 "information element ignored (vendor OUI "
186 "%02x:%02x:%02x len=%lu)",
187 pos[0], pos[1], pos[2], (unsigned long) elen);
188 return -1;
189 }
190
191 return 0;
192 }
193
194
195 static int ieee802_11_parse_extension(const u8 *pos, size_t elen,
196 struct ieee802_11_elems *elems,
197 int show_errors)
198 {
199 u8 ext_id;
200
201 if (elen < 1) {
202 if (show_errors) {
203 wpa_printf(MSG_MSGDUMP,
204 "short information element (Ext)");
205 }
206 return -1;
207 }
208
209 ext_id = *pos++;
210 elen--;
211
212 elems->frag_ies.last_eid_ext = 0;
213
214 switch (ext_id) {
215 case WLAN_EID_EXT_ASSOC_DELAY_INFO:
216 if (elen != 1)
217 break;
218 elems->assoc_delay_info = pos;
219 break;
220 case WLAN_EID_EXT_FILS_REQ_PARAMS:
221 if (elen < 3)
222 break;
223 elems->fils_req_params = pos;
224 elems->fils_req_params_len = elen;
225 break;
226 case WLAN_EID_EXT_FILS_KEY_CONFIRM:
227 elems->fils_key_confirm = pos;
228 elems->fils_key_confirm_len = elen;
229 break;
230 case WLAN_EID_EXT_FILS_SESSION:
231 if (elen != FILS_SESSION_LEN)
232 break;
233 elems->fils_session = pos;
234 break;
235 case WLAN_EID_EXT_FILS_HLP_CONTAINER:
236 if (elen < 2 * ETH_ALEN)
237 break;
238 elems->fils_hlp = pos;
239 elems->fils_hlp_len = elen;
240 break;
241 case WLAN_EID_EXT_FILS_IP_ADDR_ASSIGN:
242 if (elen < 1)
243 break;
244 elems->fils_ip_addr_assign = pos;
245 elems->fils_ip_addr_assign_len = elen;
246 break;
247 case WLAN_EID_EXT_KEY_DELIVERY:
248 if (elen < WPA_KEY_RSC_LEN)
249 break;
250 elems->key_delivery = pos;
251 elems->key_delivery_len = elen;
252 break;
253 case WLAN_EID_EXT_WRAPPED_DATA:
254 elems->wrapped_data = pos;
255 elems->wrapped_data_len = elen;
256 break;
257 case WLAN_EID_EXT_FILS_PUBLIC_KEY:
258 if (elen < 1)
259 break;
260 elems->fils_pk = pos;
261 elems->fils_pk_len = elen;
262 break;
263 case WLAN_EID_EXT_FILS_NONCE:
264 if (elen != FILS_NONCE_LEN)
265 break;
266 elems->fils_nonce = pos;
267 break;
268 case WLAN_EID_EXT_OWE_DH_PARAM:
269 if (elen < 2)
270 break;
271 elems->owe_dh = pos;
272 elems->owe_dh_len = elen;
273 break;
274 case WLAN_EID_EXT_PASSWORD_IDENTIFIER:
275 elems->password_id = pos;
276 elems->password_id_len = elen;
277 break;
278 case WLAN_EID_EXT_HE_CAPABILITIES:
279 elems->he_capabilities = pos;
280 elems->he_capabilities_len = elen;
281 break;
282 case WLAN_EID_EXT_HE_OPERATION:
283 elems->he_operation = pos;
284 elems->he_operation_len = elen;
285 break;
286 case WLAN_EID_EXT_OCV_OCI:
287 elems->oci = pos;
288 elems->oci_len = elen;
289 break;
290 case WLAN_EID_EXT_SHORT_SSID_LIST:
291 elems->short_ssid_list = pos;
292 elems->short_ssid_list_len = elen;
293 break;
294 default:
295 if (show_errors) {
296 wpa_printf(MSG_MSGDUMP,
297 "IEEE 802.11 element parsing ignored unknown element extension (ext_id=%u elen=%u)",
298 ext_id, (unsigned int) elen);
299 }
300 return -1;
301 }
302
303 if (elen == 254)
304 elems->frag_ies.last_eid_ext = ext_id;
305
306 return 0;
307 }
308
309
310 static void ieee802_11_parse_fragment(struct frag_ies_info *frag_ies,
311 const u8 *pos, u8 elen)
312 {
313 if (frag_ies->n_frags >= MAX_NUM_FRAG_IES_SUPPORTED) {
314 wpa_printf(MSG_MSGDUMP, "Too many element fragments - skip");
315 return;
316 }
317
318 /*
319 * Note: while EID == 0 is a valid ID (SSID IE), it should not be
320 * fragmented.
321 */
322 if (!frag_ies->last_eid) {
323 wpa_printf(MSG_MSGDUMP,
324 "Fragment without a valid last element - skip");
325 return;
326 }
327
328 frag_ies->frags[frag_ies->n_frags].ie = pos;
329 frag_ies->frags[frag_ies->n_frags].ie_len = elen;
330 frag_ies->frags[frag_ies->n_frags].eid = frag_ies->last_eid;
331 frag_ies->frags[frag_ies->n_frags].eid_ext = frag_ies->last_eid_ext;
332 frag_ies->n_frags++;
333 }
334
335
336 /**
337 * ieee802_11_parse_elems - Parse information elements in management frames
338 * @start: Pointer to the start of IEs
339 * @len: Length of IE buffer in octets
340 * @elems: Data structure for parsed elements
341 * @show_errors: Whether to show parsing errors in debug log
342 * Returns: Parsing result
343 */
344 ParseRes ieee802_11_parse_elems(const u8 *start, size_t len,
345 struct ieee802_11_elems *elems,
346 int show_errors)
347 {
348 const struct element *elem;
349 int unknown = 0;
350
351 os_memset(elems, 0, sizeof(*elems));
352
353 if (!start)
354 return ParseOK;
355
356 for_each_element(elem, start, len) {
357 u8 id = elem->id, elen = elem->datalen;
358 const u8 *pos = elem->data;
359
360 switch (id) {
361 case WLAN_EID_SSID:
362 if (elen > SSID_MAX_LEN) {
363 wpa_printf(MSG_DEBUG,
364 "Ignored too long SSID element (elen=%u)",
365 elen);
366 break;
367 }
368 elems->ssid = pos;
369 elems->ssid_len = elen;
370 break;
371 case WLAN_EID_SUPP_RATES:
372 elems->supp_rates = pos;
373 elems->supp_rates_len = elen;
374 break;
375 case WLAN_EID_DS_PARAMS:
376 if (elen < 1)
377 break;
378 elems->ds_params = pos;
379 break;
380 case WLAN_EID_CF_PARAMS:
381 case WLAN_EID_TIM:
382 break;
383 case WLAN_EID_CHALLENGE:
384 elems->challenge = pos;
385 elems->challenge_len = elen;
386 break;
387 case WLAN_EID_ERP_INFO:
388 if (elen < 1)
389 break;
390 elems->erp_info = pos;
391 break;
392 case WLAN_EID_EXT_SUPP_RATES:
393 elems->ext_supp_rates = pos;
394 elems->ext_supp_rates_len = elen;
395 break;
396 case WLAN_EID_VENDOR_SPECIFIC:
397 if (ieee802_11_parse_vendor_specific(pos, elen,
398 elems,
399 show_errors))
400 unknown++;
401 break;
402 case WLAN_EID_RSN:
403 elems->rsn_ie = pos;
404 elems->rsn_ie_len = elen;
405 break;
406 case WLAN_EID_RSNX:
407 elems->rsnxe = pos;
408 elems->rsnxe_len = elen;
409 break;
410 case WLAN_EID_PWR_CAPABILITY:
411 if (elen < 2)
412 break;
413 elems->power_capab = pos;
414 elems->power_capab_len = elen;
415 break;
416 case WLAN_EID_SUPPORTED_CHANNELS:
417 elems->supp_channels = pos;
418 elems->supp_channels_len = elen;
419 break;
420 case WLAN_EID_MOBILITY_DOMAIN:
421 if (elen < sizeof(struct rsn_mdie))
422 break;
423 elems->mdie = pos;
424 elems->mdie_len = elen;
425 break;
426 case WLAN_EID_FAST_BSS_TRANSITION:
427 if (elen < sizeof(struct rsn_ftie))
428 break;
429 elems->ftie = pos;
430 elems->ftie_len = elen;
431 break;
432 case WLAN_EID_TIMEOUT_INTERVAL:
433 if (elen != 5)
434 break;
435 elems->timeout_int = pos;
436 break;
437 case WLAN_EID_HT_CAP:
438 if (elen < sizeof(struct ieee80211_ht_capabilities))
439 break;
440 elems->ht_capabilities = pos;
441 break;
442 case WLAN_EID_HT_OPERATION:
443 if (elen < sizeof(struct ieee80211_ht_operation))
444 break;
445 elems->ht_operation = pos;
446 break;
447 case WLAN_EID_MESH_CONFIG:
448 elems->mesh_config = pos;
449 elems->mesh_config_len = elen;
450 break;
451 case WLAN_EID_MESH_ID:
452 elems->mesh_id = pos;
453 elems->mesh_id_len = elen;
454 break;
455 case WLAN_EID_PEER_MGMT:
456 elems->peer_mgmt = pos;
457 elems->peer_mgmt_len = elen;
458 break;
459 case WLAN_EID_VHT_CAP:
460 if (elen < sizeof(struct ieee80211_vht_capabilities))
461 break;
462 elems->vht_capabilities = pos;
463 break;
464 case WLAN_EID_VHT_OPERATION:
465 if (elen < sizeof(struct ieee80211_vht_operation))
466 break;
467 elems->vht_operation = pos;
468 break;
469 case WLAN_EID_VHT_OPERATING_MODE_NOTIFICATION:
470 if (elen != 1)
471 break;
472 elems->vht_opmode_notif = pos;
473 break;
474 case WLAN_EID_LINK_ID:
475 if (elen < 18)
476 break;
477 elems->link_id = pos;
478 break;
479 case WLAN_EID_INTERWORKING:
480 elems->interworking = pos;
481 elems->interworking_len = elen;
482 break;
483 case WLAN_EID_QOS_MAP_SET:
484 if (elen < 16)
485 break;
486 elems->qos_map_set = pos;
487 elems->qos_map_set_len = elen;
488 break;
489 case WLAN_EID_EXT_CAPAB:
490 elems->ext_capab = pos;
491 elems->ext_capab_len = elen;
492 break;
493 case WLAN_EID_BSS_MAX_IDLE_PERIOD:
494 if (elen < 3)
495 break;
496 elems->bss_max_idle_period = pos;
497 break;
498 case WLAN_EID_SSID_LIST:
499 elems->ssid_list = pos;
500 elems->ssid_list_len = elen;
501 break;
502 case WLAN_EID_AMPE:
503 elems->ampe = pos;
504 elems->ampe_len = elen;
505 break;
506 case WLAN_EID_MIC:
507 elems->mic = pos;
508 elems->mic_len = elen;
509 /* after mic everything is encrypted, so stop. */
510 goto done;
511 case WLAN_EID_MULTI_BAND:
512 if (elems->mb_ies.nof_ies >= MAX_NOF_MB_IES_SUPPORTED) {
513 wpa_printf(MSG_MSGDUMP,
514 "IEEE 802.11 element parse ignored MB IE (id=%d elen=%d)",
515 id, elen);
516 break;
517 }
518
519 elems->mb_ies.ies[elems->mb_ies.nof_ies].ie = pos;
520 elems->mb_ies.ies[elems->mb_ies.nof_ies].ie_len = elen;
521 elems->mb_ies.nof_ies++;
522 break;
523 case WLAN_EID_SUPPORTED_OPERATING_CLASSES:
524 elems->supp_op_classes = pos;
525 elems->supp_op_classes_len = elen;
526 break;
527 case WLAN_EID_RRM_ENABLED_CAPABILITIES:
528 elems->rrm_enabled = pos;
529 elems->rrm_enabled_len = elen;
530 break;
531 case WLAN_EID_CAG_NUMBER:
532 elems->cag_number = pos;
533 elems->cag_number_len = elen;
534 break;
535 case WLAN_EID_AP_CSN:
536 if (elen < 1)
537 break;
538 elems->ap_csn = pos;
539 break;
540 case WLAN_EID_FILS_INDICATION:
541 if (elen < 2)
542 break;
543 elems->fils_indic = pos;
544 elems->fils_indic_len = elen;
545 break;
546 case WLAN_EID_DILS:
547 if (elen < 2)
548 break;
549 elems->dils = pos;
550 elems->dils_len = elen;
551 break;
552 case WLAN_EID_FRAGMENT:
553 ieee802_11_parse_fragment(&elems->frag_ies, pos, elen);
554 break;
555 case WLAN_EID_EXTENSION:
556 if (ieee802_11_parse_extension(pos, elen, elems,
557 show_errors))
558 unknown++;
559 break;
560 default:
561 unknown++;
562 if (!show_errors)
563 break;
564 wpa_printf(MSG_MSGDUMP, "IEEE 802.11 element parse "
565 "ignored unknown element (id=%d elen=%d)",
566 id, elen);
567 break;
568 }
569
570 if (id != WLAN_EID_FRAGMENT && elen == 255)
571 elems->frag_ies.last_eid = id;
572
573 if (id == WLAN_EID_EXTENSION && !elems->frag_ies.last_eid_ext)
574 elems->frag_ies.last_eid = 0;
575 }
576
577 if (!for_each_element_completed(elem, start, len)) {
578 if (show_errors) {
579 wpa_printf(MSG_DEBUG,
580 "IEEE 802.11 element parse failed @%d",
581 (int) (start + len - (const u8 *) elem));
582 wpa_hexdump(MSG_MSGDUMP, "IEs", start, len);
583 }
584 return ParseFailed;
585 }
586
587 done:
588 return unknown ? ParseUnknown : ParseOK;
589 }
590
591
592 int ieee802_11_ie_count(const u8 *ies, size_t ies_len)
593 {
594 const struct element *elem;
595 int count = 0;
596
597 if (ies == NULL)
598 return 0;
599
600 for_each_element(elem, ies, ies_len)
601 count++;
602
603 return count;
604 }
605
606
607 struct wpabuf * ieee802_11_vendor_ie_concat(const u8 *ies, size_t ies_len,
608 u32 oui_type)
609 {
610 struct wpabuf *buf;
611 const struct element *elem, *found = NULL;
612
613 for_each_element_id(elem, WLAN_EID_VENDOR_SPECIFIC, ies, ies_len) {
614 if (elem->datalen >= 4 &&
615 WPA_GET_BE32(elem->data) == oui_type) {
616 found = elem;
617 break;
618 }
619 }
620
621 if (!found)
622 return NULL; /* No specified vendor IE found */
623
624 buf = wpabuf_alloc(ies_len);
625 if (buf == NULL)
626 return NULL;
627
628 /*
629 * There may be multiple vendor IEs in the message, so need to
630 * concatenate their data fields.
631 */
632 for_each_element_id(elem, WLAN_EID_VENDOR_SPECIFIC, ies, ies_len) {
633 if (elem->datalen >= 4 && WPA_GET_BE32(elem->data) == oui_type)
634 wpabuf_put_data(buf, elem->data + 4, elem->datalen - 4);
635 }
636
637 return buf;
638 }
639
640
641 const u8 * get_hdr_bssid(const struct ieee80211_hdr *hdr, size_t len)
642 {
643 u16 fc, type, stype;
644
645 /*
646 * PS-Poll frames are 16 bytes. All other frames are
647 * 24 bytes or longer.
648 */
649 if (len < 16)
650 return NULL;
651
652 fc = le_to_host16(hdr->frame_control);
653 type = WLAN_FC_GET_TYPE(fc);
654 stype = WLAN_FC_GET_STYPE(fc);
655
656 switch (type) {
657 case WLAN_FC_TYPE_DATA:
658 if (len < 24)
659 return NULL;
660 switch (fc & (WLAN_FC_FROMDS | WLAN_FC_TODS)) {
661 case WLAN_FC_FROMDS | WLAN_FC_TODS:
662 case WLAN_FC_TODS:
663 return hdr->addr1;
664 case WLAN_FC_FROMDS:
665 return hdr->addr2;
666 default:
667 return NULL;
668 }
669 case WLAN_FC_TYPE_CTRL:
670 if (stype != WLAN_FC_STYPE_PSPOLL)
671 return NULL;
672 return hdr->addr1;
673 case WLAN_FC_TYPE_MGMT:
674 return hdr->addr3;
675 default:
676 return NULL;
677 }
678 }
679
680
681 int hostapd_config_wmm_ac(struct hostapd_wmm_ac_params wmm_ac_params[],
682 const char *name, const char *val)
683 {
684 int num, v;
685 const char *pos;
686 struct hostapd_wmm_ac_params *ac;
687
688 /* skip 'wme_ac_' or 'wmm_ac_' prefix */
689 pos = name + 7;
690 if (os_strncmp(pos, "be_", 3) == 0) {
691 num = 0;
692 pos += 3;
693 } else if (os_strncmp(pos, "bk_", 3) == 0) {
694 num = 1;
695 pos += 3;
696 } else if (os_strncmp(pos, "vi_", 3) == 0) {
697 num = 2;
698 pos += 3;
699 } else if (os_strncmp(pos, "vo_", 3) == 0) {
700 num = 3;
701 pos += 3;
702 } else {
703 wpa_printf(MSG_ERROR, "Unknown WMM name '%s'", pos);
704 return -1;
705 }
706
707 ac = &wmm_ac_params[num];
708
709 if (os_strcmp(pos, "aifs") == 0) {
710 v = atoi(val);
711 if (v < 1 || v > 255) {
712 wpa_printf(MSG_ERROR, "Invalid AIFS value %d", v);
713 return -1;
714 }
715 ac->aifs = v;
716 } else if (os_strcmp(pos, "cwmin") == 0) {
717 v = atoi(val);
718 if (v < 0 || v > 15) {
719 wpa_printf(MSG_ERROR, "Invalid cwMin value %d", v);
720 return -1;
721 }
722 ac->cwmin = v;
723 } else if (os_strcmp(pos, "cwmax") == 0) {
724 v = atoi(val);
725 if (v < 0 || v > 15) {
726 wpa_printf(MSG_ERROR, "Invalid cwMax value %d", v);
727 return -1;
728 }
729 ac->cwmax = v;
730 } else if (os_strcmp(pos, "txop_limit") == 0) {
731 v = atoi(val);
732 if (v < 0 || v > 0xffff) {
733 wpa_printf(MSG_ERROR, "Invalid txop value %d", v);
734 return -1;
735 }
736 ac->txop_limit = v;
737 } else if (os_strcmp(pos, "acm") == 0) {
738 v = atoi(val);
739 if (v < 0 || v > 1) {
740 wpa_printf(MSG_ERROR, "Invalid acm value %d", v);
741 return -1;
742 }
743 ac->admission_control_mandatory = v;
744 } else {
745 wpa_printf(MSG_ERROR, "Unknown wmm_ac_ field '%s'", pos);
746 return -1;
747 }
748
749 return 0;
750 }
751
752
753 enum hostapd_hw_mode ieee80211_freq_to_chan(int freq, u8 *channel)
754 {
755 u8 op_class;
756
757 return ieee80211_freq_to_channel_ext(freq, 0, CHANWIDTH_USE_HT,
758 &op_class, channel);
759 }
760
761
762 /**
763 * ieee80211_freq_to_channel_ext - Convert frequency into channel info
764 * for HT40 and VHT. DFS channels are not covered.
765 * @freq: Frequency (MHz) to convert
766 * @sec_channel: 0 = non-HT40, 1 = sec. channel above, -1 = sec. channel below
767 * @chanwidth: VHT/EDMG channel width (CHANWIDTH_*)
768 * @op_class: Buffer for returning operating class
769 * @channel: Buffer for returning channel number
770 * Returns: hw_mode on success, NUM_HOSTAPD_MODES on failure
771 */
772 enum hostapd_hw_mode ieee80211_freq_to_channel_ext(unsigned int freq,
773 int sec_channel,
774 int chanwidth,
775 u8 *op_class, u8 *channel)
776 {
777 u8 vht_opclass;
778
779 /* TODO: more operating classes */
780
781 if (sec_channel > 1 || sec_channel < -1)
782 return NUM_HOSTAPD_MODES;
783
784 if (freq >= 2412 && freq <= 2472) {
785 if ((freq - 2407) % 5)
786 return NUM_HOSTAPD_MODES;
787
788 if (chanwidth)
789 return NUM_HOSTAPD_MODES;
790
791 /* 2.407 GHz, channels 1..13 */
792 if (sec_channel == 1)
793 *op_class = 83;
794 else if (sec_channel == -1)
795 *op_class = 84;
796 else
797 *op_class = 81;
798
799 *channel = (freq - 2407) / 5;
800
801 return HOSTAPD_MODE_IEEE80211G;
802 }
803
804 if (freq == 2484) {
805 if (sec_channel || chanwidth)
806 return NUM_HOSTAPD_MODES;
807
808 *op_class = 82; /* channel 14 */
809 *channel = 14;
810
811 return HOSTAPD_MODE_IEEE80211B;
812 }
813
814 if (freq >= 4900 && freq < 5000) {
815 if ((freq - 4000) % 5)
816 return NUM_HOSTAPD_MODES;
817 *channel = (freq - 4000) / 5;
818 *op_class = 0; /* TODO */
819 return HOSTAPD_MODE_IEEE80211A;
820 }
821
822 switch (chanwidth) {
823 case CHANWIDTH_80MHZ:
824 vht_opclass = 128;
825 break;
826 case CHANWIDTH_160MHZ:
827 vht_opclass = 129;
828 break;
829 case CHANWIDTH_80P80MHZ:
830 vht_opclass = 130;
831 break;
832 default:
833 vht_opclass = 0;
834 break;
835 }
836
837 /* 5 GHz, channels 36..48 */
838 if (freq >= 5180 && freq <= 5240) {
839 if ((freq - 5000) % 5)
840 return NUM_HOSTAPD_MODES;
841
842 if (vht_opclass)
843 *op_class = vht_opclass;
844 else if (sec_channel == 1)
845 *op_class = 116;
846 else if (sec_channel == -1)
847 *op_class = 117;
848 else
849 *op_class = 115;
850
851 *channel = (freq - 5000) / 5;
852
853 return HOSTAPD_MODE_IEEE80211A;
854 }
855
856 /* 5 GHz, channels 52..64 */
857 if (freq >= 5260 && freq <= 5320) {
858 if ((freq - 5000) % 5)
859 return NUM_HOSTAPD_MODES;
860
861 if (vht_opclass)
862 *op_class = vht_opclass;
863 else if (sec_channel == 1)
864 *op_class = 119;
865 else if (sec_channel == -1)
866 *op_class = 120;
867 else
868 *op_class = 118;
869
870 *channel = (freq - 5000) / 5;
871
872 return HOSTAPD_MODE_IEEE80211A;
873 }
874
875 /* 5 GHz, channels 149..169 */
876 if (freq >= 5745 && freq <= 5845) {
877 if ((freq - 5000) % 5)
878 return NUM_HOSTAPD_MODES;
879
880 if (vht_opclass)
881 *op_class = vht_opclass;
882 else if (sec_channel == 1)
883 *op_class = 126;
884 else if (sec_channel == -1)
885 *op_class = 127;
886 else if (freq <= 5805)
887 *op_class = 124;
888 else
889 *op_class = 125;
890
891 *channel = (freq - 5000) / 5;
892
893 return HOSTAPD_MODE_IEEE80211A;
894 }
895
896 /* 5 GHz, channels 100..140 */
897 if (freq >= 5000 && freq <= 5700) {
898 if ((freq - 5000) % 5)
899 return NUM_HOSTAPD_MODES;
900
901 if (vht_opclass)
902 *op_class = vht_opclass;
903 else if (sec_channel == 1)
904 *op_class = 122;
905 else if (sec_channel == -1)
906 *op_class = 123;
907 else
908 *op_class = 121;
909
910 *channel = (freq - 5000) / 5;
911
912 return HOSTAPD_MODE_IEEE80211A;
913 }
914
915 if (freq >= 5000 && freq < 5900) {
916 if ((freq - 5000) % 5)
917 return NUM_HOSTAPD_MODES;
918 *channel = (freq - 5000) / 5;
919 *op_class = 0; /* TODO */
920 return HOSTAPD_MODE_IEEE80211A;
921 }
922
923 if (freq > 5940 && freq <= 7105) {
924 int bw;
925 u8 idx = (freq - 5940) / 5;
926
927 bw = center_idx_to_bw_6ghz(idx);
928 if (bw < 0)
929 return NUM_HOSTAPD_MODES;
930
931 *channel = idx;
932 *op_class = 131 + bw;
933 return HOSTAPD_MODE_IEEE80211A;
934 }
935
936 /* 56.16 GHz, channel 1..6 */
937 if (freq >= 56160 + 2160 * 1 && freq <= 56160 + 2160 * 6) {
938 if (sec_channel)
939 return NUM_HOSTAPD_MODES;
940
941 switch (chanwidth) {
942 case CHANWIDTH_USE_HT:
943 case CHANWIDTH_2160MHZ:
944 *channel = (freq - 56160) / 2160;
945 *op_class = 180;
946 break;
947 case CHANWIDTH_4320MHZ:
948 /* EDMG channels 9 - 13 */
949 if (freq > 56160 + 2160 * 5)
950 return NUM_HOSTAPD_MODES;
951
952 *channel = (freq - 56160) / 2160 + 8;
953 *op_class = 181;
954 break;
955 case CHANWIDTH_6480MHZ:
956 /* EDMG channels 17 - 20 */
957 if (freq > 56160 + 2160 * 4)
958 return NUM_HOSTAPD_MODES;
959
960 *channel = (freq - 56160) / 2160 + 16;
961 *op_class = 182;
962 break;
963 case CHANWIDTH_8640MHZ:
964 /* EDMG channels 25 - 27 */
965 if (freq > 56160 + 2160 * 3)
966 return NUM_HOSTAPD_MODES;
967
968 *channel = (freq - 56160) / 2160 + 24;
969 *op_class = 183;
970 break;
971 default:
972 return NUM_HOSTAPD_MODES;
973 }
974
975 return HOSTAPD_MODE_IEEE80211AD;
976 }
977
978 return NUM_HOSTAPD_MODES;
979 }
980
981
982 int ieee80211_chaninfo_to_channel(unsigned int freq, enum chan_width chanwidth,
983 int sec_channel, u8 *op_class, u8 *channel)
984 {
985 int cw = CHAN_WIDTH_UNKNOWN;
986
987 switch (chanwidth) {
988 case CHAN_WIDTH_UNKNOWN:
989 case CHAN_WIDTH_20_NOHT:
990 case CHAN_WIDTH_20:
991 case CHAN_WIDTH_40:
992 cw = CHANWIDTH_USE_HT;
993 break;
994 case CHAN_WIDTH_80:
995 cw = CHANWIDTH_80MHZ;
996 break;
997 case CHAN_WIDTH_80P80:
998 cw = CHANWIDTH_80P80MHZ;
999 break;
1000 case CHAN_WIDTH_160:
1001 cw = CHANWIDTH_160MHZ;
1002 break;
1003 case CHAN_WIDTH_2160:
1004 cw = CHANWIDTH_2160MHZ;
1005 break;
1006 case CHAN_WIDTH_4320:
1007 cw = CHANWIDTH_4320MHZ;
1008 break;
1009 case CHAN_WIDTH_6480:
1010 cw = CHANWIDTH_6480MHZ;
1011 break;
1012 case CHAN_WIDTH_8640:
1013 cw = CHANWIDTH_8640MHZ;
1014 break;
1015 }
1016
1017 if (ieee80211_freq_to_channel_ext(freq, sec_channel, cw, op_class,
1018 channel) == NUM_HOSTAPD_MODES) {
1019 wpa_printf(MSG_WARNING,
1020 "Cannot determine operating class and channel (freq=%u chanwidth=%d sec_channel=%d)",
1021 freq, chanwidth, sec_channel);
1022 return -1;
1023 }
1024
1025 return 0;
1026 }
1027
1028
1029 static const char *const us_op_class_cc[] = {
1030 "US", "CA", NULL
1031 };
1032
1033 static const char *const eu_op_class_cc[] = {
1034 "AL", "AM", "AT", "AZ", "BA", "BE", "BG", "BY", "CH", "CY", "CZ", "DE",
1035 "DK", "EE", "EL", "ES", "FI", "FR", "GE", "HR", "HU", "IE", "IS", "IT",
1036 "LI", "LT", "LU", "LV", "MD", "ME", "MK", "MT", "NL", "NO", "PL", "PT",
1037 "RO", "RS", "RU", "SE", "SI", "SK", "TR", "UA", "UK", NULL
1038 };
1039
1040 static const char *const jp_op_class_cc[] = {
1041 "JP", NULL
1042 };
1043
1044 static const char *const cn_op_class_cc[] = {
1045 "CN", NULL
1046 };
1047
1048
1049 static int country_match(const char *const cc[], const char *const country)
1050 {
1051 int i;
1052
1053 if (country == NULL)
1054 return 0;
1055 for (i = 0; cc[i]; i++) {
1056 if (cc[i][0] == country[0] && cc[i][1] == country[1])
1057 return 1;
1058 }
1059
1060 return 0;
1061 }
1062
1063
1064 static int ieee80211_chan_to_freq_us(u8 op_class, u8 chan)
1065 {
1066 switch (op_class) {
1067 case 12: /* channels 1..11 */
1068 case 32: /* channels 1..7; 40 MHz */
1069 case 33: /* channels 5..11; 40 MHz */
1070 if (chan < 1 || chan > 11)
1071 return -1;
1072 return 2407 + 5 * chan;
1073 case 1: /* channels 36,40,44,48 */
1074 case 2: /* channels 52,56,60,64; dfs */
1075 case 22: /* channels 36,44; 40 MHz */
1076 case 23: /* channels 52,60; 40 MHz */
1077 case 27: /* channels 40,48; 40 MHz */
1078 case 28: /* channels 56,64; 40 MHz */
1079 if (chan < 36 || chan > 64)
1080 return -1;
1081 return 5000 + 5 * chan;
1082 case 4: /* channels 100-144 */
1083 case 24: /* channels 100-140; 40 MHz */
1084 if (chan < 100 || chan > 144)
1085 return -1;
1086 return 5000 + 5 * chan;
1087 case 3: /* channels 149,153,157,161 */
1088 case 25: /* channels 149,157; 40 MHz */
1089 case 26: /* channels 149,157; 40 MHz */
1090 case 30: /* channels 153,161; 40 MHz */
1091 case 31: /* channels 153,161; 40 MHz */
1092 if (chan < 149 || chan > 161)
1093 return -1;
1094 return 5000 + 5 * chan;
1095 case 5: /* channels 149,153,157,161,165 */
1096 if (chan < 149 || chan > 165)
1097 return -1;
1098 return 5000 + 5 * chan;
1099 case 34: /* 60 GHz band, channels 1..8 */
1100 if (chan < 1 || chan > 8)
1101 return -1;
1102 return 56160 + 2160 * chan;
1103 case 37: /* 60 GHz band, EDMG CB2, channels 9..15 */
1104 if (chan < 9 || chan > 15)
1105 return -1;
1106 return 56160 + 2160 * (chan - 8);
1107 case 38: /* 60 GHz band, EDMG CB3, channels 17..22 */
1108 if (chan < 17 || chan > 22)
1109 return -1;
1110 return 56160 + 2160 * (chan - 16);
1111 case 39: /* 60 GHz band, EDMG CB4, channels 25..29 */
1112 if (chan < 25 || chan > 29)
1113 return -1;
1114 return 56160 + 2160 * (chan - 24);
1115 }
1116 return -1;
1117 }
1118
1119
1120 static int ieee80211_chan_to_freq_eu(u8 op_class, u8 chan)
1121 {
1122 switch (op_class) {
1123 case 4: /* channels 1..13 */
1124 case 11: /* channels 1..9; 40 MHz */
1125 case 12: /* channels 5..13; 40 MHz */
1126 if (chan < 1 || chan > 13)
1127 return -1;
1128 return 2407 + 5 * chan;
1129 case 1: /* channels 36,40,44,48 */
1130 case 2: /* channels 52,56,60,64; dfs */
1131 case 5: /* channels 36,44; 40 MHz */
1132 case 6: /* channels 52,60; 40 MHz */
1133 case 8: /* channels 40,48; 40 MHz */
1134 case 9: /* channels 56,64; 40 MHz */
1135 if (chan < 36 || chan > 64)
1136 return -1;
1137 return 5000 + 5 * chan;
1138 case 3: /* channels 100-140 */
1139 case 7: /* channels 100-132; 40 MHz */
1140 case 10: /* channels 104-136; 40 MHz */
1141 case 16: /* channels 100-140 */
1142 if (chan < 100 || chan > 140)
1143 return -1;
1144 return 5000 + 5 * chan;
1145 case 17: /* channels 149,153,157,161,165,169 */
1146 if (chan < 149 || chan > 169)
1147 return -1;
1148 return 5000 + 5 * chan;
1149 case 18: /* 60 GHz band, channels 1..6 */
1150 if (chan < 1 || chan > 6)
1151 return -1;
1152 return 56160 + 2160 * chan;
1153 case 21: /* 60 GHz band, EDMG CB2, channels 9..11 */
1154 if (chan < 9 || chan > 11)
1155 return -1;
1156 return 56160 + 2160 * (chan - 8);
1157 case 22: /* 60 GHz band, EDMG CB3, channels 17..18 */
1158 if (chan < 17 || chan > 18)
1159 return -1;
1160 return 56160 + 2160 * (chan - 16);
1161 case 23: /* 60 GHz band, EDMG CB4, channels 25 */
1162 if (chan != 25)
1163 return -1;
1164 return 56160 + 2160 * (chan - 24);
1165 }
1166 return -1;
1167 }
1168
1169
1170 static int ieee80211_chan_to_freq_jp(u8 op_class, u8 chan)
1171 {
1172 switch (op_class) {
1173 case 30: /* channels 1..13 */
1174 case 56: /* channels 1..9; 40 MHz */
1175 case 57: /* channels 5..13; 40 MHz */
1176 if (chan < 1 || chan > 13)
1177 return -1;
1178 return 2407 + 5 * chan;
1179 case 31: /* channel 14 */
1180 if (chan != 14)
1181 return -1;
1182 return 2414 + 5 * chan;
1183 case 1: /* channels 34,38,42,46(old) or 36,40,44,48 */
1184 case 32: /* channels 52,56,60,64 */
1185 case 33: /* channels 52,56,60,64 */
1186 case 36: /* channels 36,44; 40 MHz */
1187 case 37: /* channels 52,60; 40 MHz */
1188 case 38: /* channels 52,60; 40 MHz */
1189 case 41: /* channels 40,48; 40 MHz */
1190 case 42: /* channels 56,64; 40 MHz */
1191 case 43: /* channels 56,64; 40 MHz */
1192 if (chan < 34 || chan > 64)
1193 return -1;
1194 return 5000 + 5 * chan;
1195 case 34: /* channels 100-140 */
1196 case 35: /* channels 100-140 */
1197 case 39: /* channels 100-132; 40 MHz */
1198 case 40: /* channels 100-132; 40 MHz */
1199 case 44: /* channels 104-136; 40 MHz */
1200 case 45: /* channels 104-136; 40 MHz */
1201 case 58: /* channels 100-140 */
1202 if (chan < 100 || chan > 140)
1203 return -1;
1204 return 5000 + 5 * chan;
1205 case 59: /* 60 GHz band, channels 1..6 */
1206 if (chan < 1 || chan > 6)
1207 return -1;
1208 return 56160 + 2160 * chan;
1209 case 62: /* 60 GHz band, EDMG CB2, channels 9..11 */
1210 if (chan < 9 || chan > 11)
1211 return -1;
1212 return 56160 + 2160 * (chan - 8);
1213 case 63: /* 60 GHz band, EDMG CB3, channels 17..18 */
1214 if (chan < 17 || chan > 18)
1215 return -1;
1216 return 56160 + 2160 * (chan - 16);
1217 case 64: /* 60 GHz band, EDMG CB4, channel 25 */
1218 if (chan != 25)
1219 return -1;
1220 return 56160 + 2160 * (chan - 24);
1221 }
1222 return -1;
1223 }
1224
1225
1226 static int ieee80211_chan_to_freq_cn(u8 op_class, u8 chan)
1227 {
1228 switch (op_class) {
1229 case 7: /* channels 1..13 */
1230 case 8: /* channels 1..9; 40 MHz */
1231 case 9: /* channels 5..13; 40 MHz */
1232 if (chan < 1 || chan > 13)
1233 return -1;
1234 return 2407 + 5 * chan;
1235 case 1: /* channels 36,40,44,48 */
1236 case 2: /* channels 52,56,60,64; dfs */
1237 case 4: /* channels 36,44; 40 MHz */
1238 case 5: /* channels 52,60; 40 MHz */
1239 if (chan < 36 || chan > 64)
1240 return -1;
1241 return 5000 + 5 * chan;
1242 case 3: /* channels 149,153,157,161,165 */
1243 case 6: /* channels 149,157; 40 MHz */
1244 if (chan < 149 || chan > 165)
1245 return -1;
1246 return 5000 + 5 * chan;
1247 }
1248 return -1;
1249 }
1250
1251
1252 static int ieee80211_chan_to_freq_global(u8 op_class, u8 chan)
1253 {
1254 /* Table E-4 in IEEE Std 802.11-2012 - Global operating classes */
1255 switch (op_class) {
1256 case 81:
1257 /* channels 1..13 */
1258 if (chan < 1 || chan > 13)
1259 return -1;
1260 return 2407 + 5 * chan;
1261 case 82:
1262 /* channel 14 */
1263 if (chan != 14)
1264 return -1;
1265 return 2414 + 5 * chan;
1266 case 83: /* channels 1..9; 40 MHz */
1267 case 84: /* channels 5..13; 40 MHz */
1268 if (chan < 1 || chan > 13)
1269 return -1;
1270 return 2407 + 5 * chan;
1271 case 115: /* channels 36,40,44,48; indoor only */
1272 case 116: /* channels 36,44; 40 MHz; indoor only */
1273 case 117: /* channels 40,48; 40 MHz; indoor only */
1274 case 118: /* channels 52,56,60,64; dfs */
1275 case 119: /* channels 52,60; 40 MHz; dfs */
1276 case 120: /* channels 56,64; 40 MHz; dfs */
1277 if (chan < 36 || chan > 64)
1278 return -1;
1279 return 5000 + 5 * chan;
1280 case 121: /* channels 100-140 */
1281 case 122: /* channels 100-142; 40 MHz */
1282 case 123: /* channels 104-136; 40 MHz */
1283 if (chan < 100 || chan > 140)
1284 return -1;
1285 return 5000 + 5 * chan;
1286 case 124: /* channels 149,153,157,161 */
1287 case 126: /* channels 149,157; 40 MHz */
1288 case 127: /* channels 153,161; 40 MHz */
1289 if (chan < 149 || chan > 161)
1290 return -1;
1291 return 5000 + 5 * chan;
1292 case 125: /* channels 149,153,157,161,165,169 */
1293 if (chan < 149 || chan > 169)
1294 return -1;
1295 return 5000 + 5 * chan;
1296 case 128: /* center freqs 42, 58, 106, 122, 138, 155; 80 MHz */
1297 case 130: /* center freqs 42, 58, 106, 122, 138, 155; 80 MHz */
1298 if (chan < 36 || chan > 161)
1299 return -1;
1300 return 5000 + 5 * chan;
1301 case 129: /* center freqs 50, 114; 160 MHz */
1302 if (chan < 36 || chan > 128)
1303 return -1;
1304 return 5000 + 5 * chan;
1305 case 131: /* UHB channels, 20 MHz: 1, 5, 9.. */
1306 case 132: /* UHB channels, 40 MHz: 3, 11, 19.. */
1307 case 133: /* UHB channels, 80 MHz: 7, 23, 39.. */
1308 case 134: /* UHB channels, 160 MHz: 15, 47, 79.. */
1309 case 135: /* UHB channels, 80+80 MHz: 7, 23, 39.. */
1310 if (chan < 1 || chan > 233)
1311 return -1;
1312 return 5940 + chan * 5;
1313 case 180: /* 60 GHz band, channels 1..8 */
1314 if (chan < 1 || chan > 8)
1315 return -1;
1316 return 56160 + 2160 * chan;
1317 case 181: /* 60 GHz band, EDMG CB2, channels 9..15 */
1318 if (chan < 9 || chan > 15)
1319 return -1;
1320 return 56160 + 2160 * (chan - 8);
1321 case 182: /* 60 GHz band, EDMG CB3, channels 17..22 */
1322 if (chan < 17 || chan > 22)
1323 return -1;
1324 return 56160 + 2160 * (chan - 16);
1325 case 183: /* 60 GHz band, EDMG CB4, channel 25..29 */
1326 if (chan < 25 || chan > 29)
1327 return -1;
1328 return 56160 + 2160 * (chan - 24);
1329 }
1330 return -1;
1331 }
1332
1333 /**
1334 * ieee80211_chan_to_freq - Convert channel info to frequency
1335 * @country: Country code, if known; otherwise, global operating class is used
1336 * @op_class: Operating class
1337 * @chan: Channel number
1338 * Returns: Frequency in MHz or -1 if the specified channel is unknown
1339 */
1340 int ieee80211_chan_to_freq(const char *country, u8 op_class, u8 chan)
1341 {
1342 int freq;
1343
1344 if (country_match(us_op_class_cc, country)) {
1345 freq = ieee80211_chan_to_freq_us(op_class, chan);
1346 if (freq > 0)
1347 return freq;
1348 }
1349
1350 if (country_match(eu_op_class_cc, country)) {
1351 freq = ieee80211_chan_to_freq_eu(op_class, chan);
1352 if (freq > 0)
1353 return freq;
1354 }
1355
1356 if (country_match(jp_op_class_cc, country)) {
1357 freq = ieee80211_chan_to_freq_jp(op_class, chan);
1358 if (freq > 0)
1359 return freq;
1360 }
1361
1362 if (country_match(cn_op_class_cc, country)) {
1363 freq = ieee80211_chan_to_freq_cn(op_class, chan);
1364 if (freq > 0)
1365 return freq;
1366 }
1367
1368 return ieee80211_chan_to_freq_global(op_class, chan);
1369 }
1370
1371
1372 int ieee80211_is_dfs(int freq, const struct hostapd_hw_modes *modes,
1373 u16 num_modes)
1374 {
1375 int i, j;
1376
1377 if (!modes || !num_modes)
1378 return (freq >= 5260 && freq <= 5320) ||
1379 (freq >= 5500 && freq <= 5700);
1380
1381 for (i = 0; i < num_modes; i++) {
1382 for (j = 0; j < modes[i].num_channels; j++) {
1383 if (modes[i].channels[j].freq == freq &&
1384 (modes[i].channels[j].flag & HOSTAPD_CHAN_RADAR))
1385 return 1;
1386 }
1387 }
1388
1389 return 0;
1390 }
1391
1392
1393 static int is_11b(u8 rate)
1394 {
1395 return rate == 0x02 || rate == 0x04 || rate == 0x0b || rate == 0x16;
1396 }
1397
1398
1399 int supp_rates_11b_only(struct ieee802_11_elems *elems)
1400 {
1401 int num_11b = 0, num_others = 0;
1402 int i;
1403
1404 if (elems->supp_rates == NULL && elems->ext_supp_rates == NULL)
1405 return 0;
1406
1407 for (i = 0; elems->supp_rates && i < elems->supp_rates_len; i++) {
1408 if (is_11b(elems->supp_rates[i]))
1409 num_11b++;
1410 else
1411 num_others++;
1412 }
1413
1414 for (i = 0; elems->ext_supp_rates && i < elems->ext_supp_rates_len;
1415 i++) {
1416 if (is_11b(elems->ext_supp_rates[i]))
1417 num_11b++;
1418 else
1419 num_others++;
1420 }
1421
1422 return num_11b > 0 && num_others == 0;
1423 }
1424
1425
1426 const char * fc2str(u16 fc)
1427 {
1428 u16 stype = WLAN_FC_GET_STYPE(fc);
1429 #define C2S(x) case x: return #x;
1430
1431 switch (WLAN_FC_GET_TYPE(fc)) {
1432 case WLAN_FC_TYPE_MGMT:
1433 switch (stype) {
1434 C2S(WLAN_FC_STYPE_ASSOC_REQ)
1435 C2S(WLAN_FC_STYPE_ASSOC_RESP)
1436 C2S(WLAN_FC_STYPE_REASSOC_REQ)
1437 C2S(WLAN_FC_STYPE_REASSOC_RESP)
1438 C2S(WLAN_FC_STYPE_PROBE_REQ)
1439 C2S(WLAN_FC_STYPE_PROBE_RESP)
1440 C2S(WLAN_FC_STYPE_BEACON)
1441 C2S(WLAN_FC_STYPE_ATIM)
1442 C2S(WLAN_FC_STYPE_DISASSOC)
1443 C2S(WLAN_FC_STYPE_AUTH)
1444 C2S(WLAN_FC_STYPE_DEAUTH)
1445 C2S(WLAN_FC_STYPE_ACTION)
1446 }
1447 break;
1448 case WLAN_FC_TYPE_CTRL:
1449 switch (stype) {
1450 C2S(WLAN_FC_STYPE_PSPOLL)
1451 C2S(WLAN_FC_STYPE_RTS)
1452 C2S(WLAN_FC_STYPE_CTS)
1453 C2S(WLAN_FC_STYPE_ACK)
1454 C2S(WLAN_FC_STYPE_CFEND)
1455 C2S(WLAN_FC_STYPE_CFENDACK)
1456 }
1457 break;
1458 case WLAN_FC_TYPE_DATA:
1459 switch (stype) {
1460 C2S(WLAN_FC_STYPE_DATA)
1461 C2S(WLAN_FC_STYPE_DATA_CFACK)
1462 C2S(WLAN_FC_STYPE_DATA_CFPOLL)
1463 C2S(WLAN_FC_STYPE_DATA_CFACKPOLL)
1464 C2S(WLAN_FC_STYPE_NULLFUNC)
1465 C2S(WLAN_FC_STYPE_CFACK)
1466 C2S(WLAN_FC_STYPE_CFPOLL)
1467 C2S(WLAN_FC_STYPE_CFACKPOLL)
1468 C2S(WLAN_FC_STYPE_QOS_DATA)
1469 C2S(WLAN_FC_STYPE_QOS_DATA_CFACK)
1470 C2S(WLAN_FC_STYPE_QOS_DATA_CFPOLL)
1471 C2S(WLAN_FC_STYPE_QOS_DATA_CFACKPOLL)
1472 C2S(WLAN_FC_STYPE_QOS_NULL)
1473 C2S(WLAN_FC_STYPE_QOS_CFPOLL)
1474 C2S(WLAN_FC_STYPE_QOS_CFACKPOLL)
1475 }
1476 break;
1477 }
1478 return "WLAN_FC_TYPE_UNKNOWN";
1479 #undef C2S
1480 }
1481
1482
1483 const char * reason2str(u16 reason)
1484 {
1485 #define R2S(r) case WLAN_REASON_ ## r: return #r;
1486 switch (reason) {
1487 R2S(UNSPECIFIED)
1488 R2S(PREV_AUTH_NOT_VALID)
1489 R2S(DEAUTH_LEAVING)
1490 R2S(DISASSOC_DUE_TO_INACTIVITY)
1491 R2S(DISASSOC_AP_BUSY)
1492 R2S(CLASS2_FRAME_FROM_NONAUTH_STA)
1493 R2S(CLASS3_FRAME_FROM_NONASSOC_STA)
1494 R2S(DISASSOC_STA_HAS_LEFT)
1495 R2S(STA_REQ_ASSOC_WITHOUT_AUTH)
1496 R2S(PWR_CAPABILITY_NOT_VALID)
1497 R2S(SUPPORTED_CHANNEL_NOT_VALID)
1498 R2S(BSS_TRANSITION_DISASSOC)
1499 R2S(INVALID_IE)
1500 R2S(MICHAEL_MIC_FAILURE)
1501 R2S(4WAY_HANDSHAKE_TIMEOUT)
1502 R2S(GROUP_KEY_UPDATE_TIMEOUT)
1503 R2S(IE_IN_4WAY_DIFFERS)
1504 R2S(GROUP_CIPHER_NOT_VALID)
1505 R2S(PAIRWISE_CIPHER_NOT_VALID)
1506 R2S(AKMP_NOT_VALID)
1507 R2S(UNSUPPORTED_RSN_IE_VERSION)
1508 R2S(INVALID_RSN_IE_CAPAB)
1509 R2S(IEEE_802_1X_AUTH_FAILED)
1510 R2S(CIPHER_SUITE_REJECTED)
1511 R2S(TDLS_TEARDOWN_UNREACHABLE)
1512 R2S(TDLS_TEARDOWN_UNSPECIFIED)
1513 R2S(SSP_REQUESTED_DISASSOC)
1514 R2S(NO_SSP_ROAMING_AGREEMENT)
1515 R2S(BAD_CIPHER_OR_AKM)
1516 R2S(NOT_AUTHORIZED_THIS_LOCATION)
1517 R2S(SERVICE_CHANGE_PRECLUDES_TS)
1518 R2S(UNSPECIFIED_QOS_REASON)
1519 R2S(NOT_ENOUGH_BANDWIDTH)
1520 R2S(DISASSOC_LOW_ACK)
1521 R2S(EXCEEDED_TXOP)
1522 R2S(STA_LEAVING)
1523 R2S(END_TS_BA_DLS)
1524 R2S(UNKNOWN_TS_BA)
1525 R2S(TIMEOUT)
1526 R2S(PEERKEY_MISMATCH)
1527 R2S(AUTHORIZED_ACCESS_LIMIT_REACHED)
1528 R2S(EXTERNAL_SERVICE_REQUIREMENTS)
1529 R2S(INVALID_FT_ACTION_FRAME_COUNT)
1530 R2S(INVALID_PMKID)
1531 R2S(INVALID_MDE)
1532 R2S(INVALID_FTE)
1533 R2S(MESH_PEERING_CANCELLED)
1534 R2S(MESH_MAX_PEERS)
1535 R2S(MESH_CONFIG_POLICY_VIOLATION)
1536 R2S(MESH_CLOSE_RCVD)
1537 R2S(MESH_MAX_RETRIES)
1538 R2S(MESH_CONFIRM_TIMEOUT)
1539 R2S(MESH_INVALID_GTK)
1540 R2S(MESH_INCONSISTENT_PARAMS)
1541 R2S(MESH_INVALID_SECURITY_CAP)
1542 R2S(MESH_PATH_ERROR_NO_PROXY_INFO)
1543 R2S(MESH_PATH_ERROR_NO_FORWARDING_INFO)
1544 R2S(MESH_PATH_ERROR_DEST_UNREACHABLE)
1545 R2S(MAC_ADDRESS_ALREADY_EXISTS_IN_MBSS)
1546 R2S(MESH_CHANNEL_SWITCH_REGULATORY_REQ)
1547 R2S(MESH_CHANNEL_SWITCH_UNSPECIFIED)
1548 }
1549 return "UNKNOWN";
1550 #undef R2S
1551 }
1552
1553
1554 const char * status2str(u16 status)
1555 {
1556 #define S2S(s) case WLAN_STATUS_ ## s: return #s;
1557 switch (status) {
1558 S2S(SUCCESS)
1559 S2S(UNSPECIFIED_FAILURE)
1560 S2S(TDLS_WAKEUP_ALTERNATE)
1561 S2S(TDLS_WAKEUP_REJECT)
1562 S2S(SECURITY_DISABLED)
1563 S2S(UNACCEPTABLE_LIFETIME)
1564 S2S(NOT_IN_SAME_BSS)
1565 S2S(CAPS_UNSUPPORTED)
1566 S2S(REASSOC_NO_ASSOC)
1567 S2S(ASSOC_DENIED_UNSPEC)
1568 S2S(NOT_SUPPORTED_AUTH_ALG)
1569 S2S(UNKNOWN_AUTH_TRANSACTION)
1570 S2S(CHALLENGE_FAIL)
1571 S2S(AUTH_TIMEOUT)
1572 S2S(AP_UNABLE_TO_HANDLE_NEW_STA)
1573 S2S(ASSOC_DENIED_RATES)
1574 S2S(ASSOC_DENIED_NOSHORT)
1575 S2S(SPEC_MGMT_REQUIRED)
1576 S2S(PWR_CAPABILITY_NOT_VALID)
1577 S2S(SUPPORTED_CHANNEL_NOT_VALID)
1578 S2S(ASSOC_DENIED_NO_SHORT_SLOT_TIME)
1579 S2S(ASSOC_DENIED_NO_HT)
1580 S2S(R0KH_UNREACHABLE)
1581 S2S(ASSOC_DENIED_NO_PCO)
1582 S2S(ASSOC_REJECTED_TEMPORARILY)
1583 S2S(ROBUST_MGMT_FRAME_POLICY_VIOLATION)
1584 S2S(UNSPECIFIED_QOS_FAILURE)
1585 S2S(DENIED_INSUFFICIENT_BANDWIDTH)
1586 S2S(DENIED_POOR_CHANNEL_CONDITIONS)
1587 S2S(DENIED_QOS_NOT_SUPPORTED)
1588 S2S(REQUEST_DECLINED)
1589 S2S(INVALID_PARAMETERS)
1590 S2S(REJECTED_WITH_SUGGESTED_CHANGES)
1591 S2S(INVALID_IE)
1592 S2S(GROUP_CIPHER_NOT_VALID)
1593 S2S(PAIRWISE_CIPHER_NOT_VALID)
1594 S2S(AKMP_NOT_VALID)
1595 S2S(UNSUPPORTED_RSN_IE_VERSION)
1596 S2S(INVALID_RSN_IE_CAPAB)
1597 S2S(CIPHER_REJECTED_PER_POLICY)
1598 S2S(TS_NOT_CREATED)
1599 S2S(DIRECT_LINK_NOT_ALLOWED)
1600 S2S(DEST_STA_NOT_PRESENT)
1601 S2S(DEST_STA_NOT_QOS_STA)
1602 S2S(ASSOC_DENIED_LISTEN_INT_TOO_LARGE)
1603 S2S(INVALID_FT_ACTION_FRAME_COUNT)
1604 S2S(INVALID_PMKID)
1605 S2S(INVALID_MDIE)
1606 S2S(INVALID_FTIE)
1607 S2S(REQUESTED_TCLAS_NOT_SUPPORTED)
1608 S2S(INSUFFICIENT_TCLAS_PROCESSING_RESOURCES)
1609 S2S(TRY_ANOTHER_BSS)
1610 S2S(GAS_ADV_PROTO_NOT_SUPPORTED)
1611 S2S(NO_OUTSTANDING_GAS_REQ)
1612 S2S(GAS_RESP_NOT_RECEIVED)
1613 S2S(STA_TIMED_OUT_WAITING_FOR_GAS_RESP)
1614 S2S(GAS_RESP_LARGER_THAN_LIMIT)
1615 S2S(REQ_REFUSED_HOME)
1616 S2S(ADV_SRV_UNREACHABLE)
1617 S2S(REQ_REFUSED_SSPN)
1618 S2S(REQ_REFUSED_UNAUTH_ACCESS)
1619 S2S(INVALID_RSNIE)
1620 S2S(U_APSD_COEX_NOT_SUPPORTED)
1621 S2S(U_APSD_COEX_MODE_NOT_SUPPORTED)
1622 S2S(BAD_INTERVAL_WITH_U_APSD_COEX)
1623 S2S(ANTI_CLOGGING_TOKEN_REQ)
1624 S2S(FINITE_CYCLIC_GROUP_NOT_SUPPORTED)
1625 S2S(CANNOT_FIND_ALT_TBTT)
1626 S2S(TRANSMISSION_FAILURE)
1627 S2S(REQ_TCLAS_NOT_SUPPORTED)
1628 S2S(TCLAS_RESOURCES_EXCHAUSTED)
1629 S2S(REJECTED_WITH_SUGGESTED_BSS_TRANSITION)
1630 S2S(REJECT_WITH_SCHEDULE)
1631 S2S(REJECT_NO_WAKEUP_SPECIFIED)
1632 S2S(SUCCESS_POWER_SAVE_MODE)
1633 S2S(PENDING_ADMITTING_FST_SESSION)
1634 S2S(PERFORMING_FST_NOW)
1635 S2S(PENDING_GAP_IN_BA_WINDOW)
1636 S2S(REJECT_U_PID_SETTING)
1637 S2S(REFUSED_EXTERNAL_REASON)
1638 S2S(REFUSED_AP_OUT_OF_MEMORY)
1639 S2S(REJECTED_EMERGENCY_SERVICE_NOT_SUPPORTED)
1640 S2S(QUERY_RESP_OUTSTANDING)
1641 S2S(REJECT_DSE_BAND)
1642 S2S(TCLAS_PROCESSING_TERMINATED)
1643 S2S(TS_SCHEDULE_CONFLICT)
1644 S2S(DENIED_WITH_SUGGESTED_BAND_AND_CHANNEL)
1645 S2S(MCCAOP_RESERVATION_CONFLICT)
1646 S2S(MAF_LIMIT_EXCEEDED)
1647 S2S(MCCA_TRACK_LIMIT_EXCEEDED)
1648 S2S(DENIED_DUE_TO_SPECTRUM_MANAGEMENT)
1649 S2S(ASSOC_DENIED_NO_VHT)
1650 S2S(ENABLEMENT_DENIED)
1651 S2S(RESTRICTION_FROM_AUTHORIZED_GDB)
1652 S2S(AUTHORIZATION_DEENABLED)
1653 S2S(FILS_AUTHENTICATION_FAILURE)
1654 S2S(UNKNOWN_AUTHENTICATION_SERVER)
1655 S2S(UNKNOWN_PASSWORD_IDENTIFIER)
1656 S2S(SAE_HASH_TO_ELEMENT)
1657 }
1658 return "UNKNOWN";
1659 #undef S2S
1660 }
1661
1662
1663 int mb_ies_info_by_ies(struct mb_ies_info *info, const u8 *ies_buf,
1664 size_t ies_len)
1665 {
1666 const struct element *elem;
1667
1668 os_memset(info, 0, sizeof(*info));
1669
1670 if (!ies_buf)
1671 return 0;
1672
1673 for_each_element_id(elem, WLAN_EID_MULTI_BAND, ies_buf, ies_len) {
1674 if (info->nof_ies >= MAX_NOF_MB_IES_SUPPORTED)
1675 return 0;
1676
1677 wpa_printf(MSG_DEBUG, "MB IE of %u bytes found",
1678 elem->datalen + 2);
1679 info->ies[info->nof_ies].ie = elem->data;
1680 info->ies[info->nof_ies].ie_len = elem->datalen;
1681 info->nof_ies++;
1682 }
1683
1684 if (!for_each_element_completed(elem, ies_buf, ies_len)) {
1685 wpa_hexdump(MSG_DEBUG, "Truncated IEs", ies_buf, ies_len);
1686 return -1;
1687 }
1688
1689 return 0;
1690 }
1691
1692
1693 struct wpabuf * mb_ies_by_info(struct mb_ies_info *info)
1694 {
1695 struct wpabuf *mb_ies = NULL;
1696
1697 WPA_ASSERT(info != NULL);
1698
1699 if (info->nof_ies) {
1700 u8 i;
1701 size_t mb_ies_size = 0;
1702
1703 for (i = 0; i < info->nof_ies; i++)
1704 mb_ies_size += 2 + info->ies[i].ie_len;
1705
1706 mb_ies = wpabuf_alloc(mb_ies_size);
1707 if (mb_ies) {
1708 for (i = 0; i < info->nof_ies; i++) {
1709 wpabuf_put_u8(mb_ies, WLAN_EID_MULTI_BAND);
1710 wpabuf_put_u8(mb_ies, info->ies[i].ie_len);
1711 wpabuf_put_data(mb_ies,
1712 info->ies[i].ie,
1713 info->ies[i].ie_len);
1714 }
1715 }
1716 }
1717
1718 return mb_ies;
1719 }
1720
1721
1722 const struct oper_class_map global_op_class[] = {
1723 { HOSTAPD_MODE_IEEE80211G, 81, 1, 13, 1, BW20, P2P_SUPP },
1724 { HOSTAPD_MODE_IEEE80211G, 82, 14, 14, 1, BW20, NO_P2P_SUPP },
1725
1726 /* Do not enable HT40 on 2.4 GHz for P2P use for now */
1727 { HOSTAPD_MODE_IEEE80211G, 83, 1, 9, 1, BW40PLUS, NO_P2P_SUPP },
1728 { HOSTAPD_MODE_IEEE80211G, 84, 5, 13, 1, BW40MINUS, NO_P2P_SUPP },
1729
1730 { HOSTAPD_MODE_IEEE80211A, 115, 36, 48, 4, BW20, P2P_SUPP },
1731 { HOSTAPD_MODE_IEEE80211A, 116, 36, 44, 8, BW40PLUS, P2P_SUPP },
1732 { HOSTAPD_MODE_IEEE80211A, 117, 40, 48, 8, BW40MINUS, P2P_SUPP },
1733 { HOSTAPD_MODE_IEEE80211A, 118, 52, 64, 4, BW20, NO_P2P_SUPP },
1734 { HOSTAPD_MODE_IEEE80211A, 119, 52, 60, 8, BW40PLUS, NO_P2P_SUPP },
1735 { HOSTAPD_MODE_IEEE80211A, 120, 56, 64, 8, BW40MINUS, NO_P2P_SUPP },
1736 { HOSTAPD_MODE_IEEE80211A, 121, 100, 140, 4, BW20, NO_P2P_SUPP },
1737 { HOSTAPD_MODE_IEEE80211A, 122, 100, 132, 8, BW40PLUS, NO_P2P_SUPP },
1738 { HOSTAPD_MODE_IEEE80211A, 123, 104, 136, 8, BW40MINUS, NO_P2P_SUPP },
1739 { HOSTAPD_MODE_IEEE80211A, 124, 149, 161, 4, BW20, P2P_SUPP },
1740 { HOSTAPD_MODE_IEEE80211A, 125, 149, 169, 4, BW20, P2P_SUPP },
1741 { HOSTAPD_MODE_IEEE80211A, 126, 149, 157, 8, BW40PLUS, P2P_SUPP },
1742 { HOSTAPD_MODE_IEEE80211A, 127, 153, 161, 8, BW40MINUS, P2P_SUPP },
1743
1744 /*
1745 * IEEE P802.11ac/D7.0 Table E-4 actually talks about channel center
1746 * frequency index 42, 58, 106, 122, 138, 155 with channel spacing of
1747 * 80 MHz, but currently use the following definition for simplicity
1748 * (these center frequencies are not actual channels, which makes
1749 * wpas_p2p_allow_channel() fail). wpas_p2p_verify_80mhz() should take
1750 * care of removing invalid channels.
1751 */
1752 { HOSTAPD_MODE_IEEE80211A, 128, 36, 161, 4, BW80, P2P_SUPP },
1753 { HOSTAPD_MODE_IEEE80211A, 129, 50, 114, 16, BW160, P2P_SUPP },
1754 { HOSTAPD_MODE_IEEE80211A, 130, 36, 161, 4, BW80P80, P2P_SUPP },
1755 { HOSTAPD_MODE_IEEE80211A, 131, 1, 233, 4, BW20, P2P_SUPP },
1756
1757 /*
1758 * IEEE Std 802.11ad-2012 and P802.ay/D5.0 60 GHz operating classes.
1759 * Class 180 has the legacy channels 1-6. Classes 181-183 include
1760 * channels which implement channel bonding features.
1761 */
1762 { HOSTAPD_MODE_IEEE80211AD, 180, 1, 6, 1, BW2160, P2P_SUPP },
1763 { HOSTAPD_MODE_IEEE80211AD, 181, 9, 13, 1, BW4320, P2P_SUPP },
1764 { HOSTAPD_MODE_IEEE80211AD, 182, 17, 20, 1, BW6480, P2P_SUPP },
1765 { HOSTAPD_MODE_IEEE80211AD, 183, 25, 27, 1, BW8640, P2P_SUPP },
1766 { -1, 0, 0, 0, 0, BW20, NO_P2P_SUPP }
1767 };
1768
1769
1770 static enum phy_type ieee80211_phy_type_by_freq(int freq)
1771 {
1772 enum hostapd_hw_mode hw_mode;
1773 u8 channel;
1774
1775 hw_mode = ieee80211_freq_to_chan(freq, &channel);
1776
1777 switch (hw_mode) {
1778 case HOSTAPD_MODE_IEEE80211A:
1779 return PHY_TYPE_OFDM;
1780 case HOSTAPD_MODE_IEEE80211B:
1781 return PHY_TYPE_HRDSSS;
1782 case HOSTAPD_MODE_IEEE80211G:
1783 return PHY_TYPE_ERP;
1784 case HOSTAPD_MODE_IEEE80211AD:
1785 return PHY_TYPE_DMG;
1786 default:
1787 return PHY_TYPE_UNSPECIFIED;
1788 };
1789 }
1790
1791
1792 /* ieee80211_get_phy_type - Derive the phy type by freq and bandwidth */
1793 enum phy_type ieee80211_get_phy_type(int freq, int ht, int vht)
1794 {
1795 if (vht)
1796 return PHY_TYPE_VHT;
1797 if (ht)
1798 return PHY_TYPE_HT;
1799
1800 return ieee80211_phy_type_by_freq(freq);
1801 }
1802
1803
1804 size_t global_op_class_size = ARRAY_SIZE(global_op_class);
1805
1806
1807 /**
1808 * get_ie - Fetch a specified information element from IEs buffer
1809 * @ies: Information elements buffer
1810 * @len: Information elements buffer length
1811 * @eid: Information element identifier (WLAN_EID_*)
1812 * Returns: Pointer to the information element (id field) or %NULL if not found
1813 *
1814 * This function returns the first matching information element in the IEs
1815 * buffer or %NULL in case the element is not found.
1816 */
1817 const u8 * get_ie(const u8 *ies, size_t len, u8 eid)
1818 {
1819 const struct element *elem;
1820
1821 if (!ies)
1822 return NULL;
1823
1824 for_each_element_id(elem, eid, ies, len)
1825 return &elem->id;
1826
1827 return NULL;
1828 }
1829
1830
1831 /**
1832 * get_ie_ext - Fetch a specified extended information element from IEs buffer
1833 * @ies: Information elements buffer
1834 * @len: Information elements buffer length
1835 * @ext: Information element extension identifier (WLAN_EID_EXT_*)
1836 * Returns: Pointer to the information element (id field) or %NULL if not found
1837 *
1838 * This function returns the first matching information element in the IEs
1839 * buffer or %NULL in case the element is not found.
1840 */
1841 const u8 * get_ie_ext(const u8 *ies, size_t len, u8 ext)
1842 {
1843 const struct element *elem;
1844
1845 if (!ies)
1846 return NULL;
1847
1848 for_each_element_extid(elem, ext, ies, len)
1849 return &elem->id;
1850
1851 return NULL;
1852 }
1853
1854
1855 const u8 * get_vendor_ie(const u8 *ies, size_t len, u32 vendor_type)
1856 {
1857 const struct element *elem;
1858
1859 for_each_element_id(elem, WLAN_EID_VENDOR_SPECIFIC, ies, len) {
1860 if (elem->datalen >= 4 &&
1861 vendor_type == WPA_GET_BE32(elem->data))
1862 return &elem->id;
1863 }
1864
1865 return NULL;
1866 }
1867
1868
1869 size_t mbo_add_ie(u8 *buf, size_t len, const u8 *attr, size_t attr_len)
1870 {
1871 /*
1872 * MBO IE requires 6 bytes without the attributes: EID (1), length (1),
1873 * OUI (3), OUI type (1).
1874 */
1875 if (len < 6 + attr_len) {
1876 wpa_printf(MSG_DEBUG,
1877 "MBO: Not enough room in buffer for MBO IE: buf len = %zu, attr_len = %zu",
1878 len, attr_len);
1879 return 0;
1880 }
1881
1882 *buf++ = WLAN_EID_VENDOR_SPECIFIC;
1883 *buf++ = attr_len + 4;
1884 WPA_PUT_BE24(buf, OUI_WFA);
1885 buf += 3;
1886 *buf++ = MBO_OUI_TYPE;
1887 os_memcpy(buf, attr, attr_len);
1888
1889 return 6 + attr_len;
1890 }
1891
1892
1893 size_t add_multi_ap_ie(u8 *buf, size_t len, u8 value)
1894 {
1895 u8 *pos = buf;
1896
1897 if (len < 9)
1898 return 0;
1899
1900 *pos++ = WLAN_EID_VENDOR_SPECIFIC;
1901 *pos++ = 7; /* len */
1902 WPA_PUT_BE24(pos, OUI_WFA);
1903 pos += 3;
1904 *pos++ = MULTI_AP_OUI_TYPE;
1905 *pos++ = MULTI_AP_SUB_ELEM_TYPE;
1906 *pos++ = 1; /* len */
1907 *pos++ = value;
1908
1909 return pos - buf;
1910 }
1911
1912
1913 static const struct country_op_class us_op_class[] = {
1914 { 1, 115 },
1915 { 2, 118 },
1916 { 3, 124 },
1917 { 4, 121 },
1918 { 5, 125 },
1919 { 12, 81 },
1920 { 22, 116 },
1921 { 23, 119 },
1922 { 24, 122 },
1923 { 25, 126 },
1924 { 26, 126 },
1925 { 27, 117 },
1926 { 28, 120 },
1927 { 29, 123 },
1928 { 30, 127 },
1929 { 31, 127 },
1930 { 32, 83 },
1931 { 33, 84 },
1932 { 34, 180 },
1933 };
1934
1935 static const struct country_op_class eu_op_class[] = {
1936 { 1, 115 },
1937 { 2, 118 },
1938 { 3, 121 },
1939 { 4, 81 },
1940 { 5, 116 },
1941 { 6, 119 },
1942 { 7, 122 },
1943 { 8, 117 },
1944 { 9, 120 },
1945 { 10, 123 },
1946 { 11, 83 },
1947 { 12, 84 },
1948 { 17, 125 },
1949 { 18, 180 },
1950 };
1951
1952 static const struct country_op_class jp_op_class[] = {
1953 { 1, 115 },
1954 { 30, 81 },
1955 { 31, 82 },
1956 { 32, 118 },
1957 { 33, 118 },
1958 { 34, 121 },
1959 { 35, 121 },
1960 { 36, 116 },
1961 { 37, 119 },
1962 { 38, 119 },
1963 { 39, 122 },
1964 { 40, 122 },
1965 { 41, 117 },
1966 { 42, 120 },
1967 { 43, 120 },
1968 { 44, 123 },
1969 { 45, 123 },
1970 { 56, 83 },
1971 { 57, 84 },
1972 { 58, 121 },
1973 { 59, 180 },
1974 };
1975
1976 static const struct country_op_class cn_op_class[] = {
1977 { 1, 115 },
1978 { 2, 118 },
1979 { 3, 125 },
1980 { 4, 116 },
1981 { 5, 119 },
1982 { 6, 126 },
1983 { 7, 81 },
1984 { 8, 83 },
1985 { 9, 84 },
1986 };
1987
1988 static u8
1989 global_op_class_from_country_array(u8 op_class, size_t array_size,
1990 const struct country_op_class *country_array)
1991 {
1992 size_t i;
1993
1994 for (i = 0; i < array_size; i++) {
1995 if (country_array[i].country_op_class == op_class)
1996 return country_array[i].global_op_class;
1997 }
1998
1999 return 0;
2000 }
2001
2002
2003 u8 country_to_global_op_class(const char *country, u8 op_class)
2004 {
2005 const struct country_op_class *country_array;
2006 size_t size;
2007 u8 g_op_class;
2008
2009 if (country_match(us_op_class_cc, country)) {
2010 country_array = us_op_class;
2011 size = ARRAY_SIZE(us_op_class);
2012 } else if (country_match(eu_op_class_cc, country)) {
2013 country_array = eu_op_class;
2014 size = ARRAY_SIZE(eu_op_class);
2015 } else if (country_match(jp_op_class_cc, country)) {
2016 country_array = jp_op_class;
2017 size = ARRAY_SIZE(jp_op_class);
2018 } else if (country_match(cn_op_class_cc, country)) {
2019 country_array = cn_op_class;
2020 size = ARRAY_SIZE(cn_op_class);
2021 } else {
2022 /*
2023 * Countries that do not match any of the above countries use
2024 * global operating classes
2025 */
2026 return op_class;
2027 }
2028
2029 g_op_class = global_op_class_from_country_array(op_class, size,
2030 country_array);
2031
2032 /*
2033 * If the given operating class did not match any of the country's
2034 * operating classes, assume that global operating class is used.
2035 */
2036 return g_op_class ? g_op_class : op_class;
2037 }
2038
2039
2040 const struct oper_class_map * get_oper_class(const char *country, u8 op_class)
2041 {
2042 const struct oper_class_map *op;
2043
2044 if (country)
2045 op_class = country_to_global_op_class(country, op_class);
2046
2047 op = &global_op_class[0];
2048 while (op->op_class && op->op_class != op_class)
2049 op++;
2050
2051 if (!op->op_class)
2052 return NULL;
2053
2054 return op;
2055 }
2056
2057
2058 int oper_class_bw_to_int(const struct oper_class_map *map)
2059 {
2060 switch (map->bw) {
2061 case BW20:
2062 return 20;
2063 case BW40PLUS:
2064 case BW40MINUS:
2065 return 40;
2066 case BW80:
2067 return 80;
2068 case BW80P80:
2069 case BW160:
2070 return 160;
2071 case BW2160:
2072 return 2160;
2073 default:
2074 return 0;
2075 }
2076 }
2077
2078
2079 int center_idx_to_bw_6ghz(u8 idx)
2080 {
2081 /* channels: 1, 5, 9, 13... */
2082 if ((idx & 0x3) == 0x1)
2083 return 0; /* 20 MHz */
2084 /* channels 3, 11, 19... */
2085 if ((idx & 0x7) == 0x3)
2086 return 1; /* 40 MHz */
2087 /* channels 7, 23, 39.. */
2088 if ((idx & 0xf) == 0x7)
2089 return 2; /* 80 MHz */
2090 /* channels 15, 47, 79...*/
2091 if ((idx & 0x1f) == 0xf)
2092 return 3; /* 160 MHz */
2093
2094 return -1;
2095 }
2096
2097
2098 int is_6ghz_freq(int freq)
2099 {
2100 if (freq < 5940 || freq > 7105)
2101 return 0;
2102
2103 if (center_idx_to_bw_6ghz((freq - 5940) / 5) < 0)
2104 return 0;
2105
2106 return 1;
2107 }
2108
2109
2110 int is_6ghz_op_class(u8 op_class)
2111 {
2112 return op_class >= 131 && op_class <= 135;
2113 }
2114
2115
2116 int is_6ghz_psc_frequency(int freq)
2117 {
2118 int i;
2119
2120 if (!is_6ghz_freq(freq))
2121 return 0;
2122 if ((((freq - 5940) / 5) & 0x3) != 0x1)
2123 return 0;
2124
2125 i = (freq - 5940 + 55) % 80;
2126 if (i == 0)
2127 i = (freq - 5940 + 55) / 80;
2128
2129 if (i >= 1 && i <= 15)
2130 return 1;
2131
2132 return 0;
2133 }
2134
2135
2136 int ieee802_11_parse_candidate_list(const char *pos, u8 *nei_rep,
2137 size_t nei_rep_len)
2138 {
2139 u8 *nei_pos = nei_rep;
2140 const char *end;
2141
2142 /*
2143 * BSS Transition Candidate List Entries - Neighbor Report elements
2144 * neighbor=<BSSID>,<BSSID Information>,<Operating Class>,
2145 * <Channel Number>,<PHY Type>[,<hexdump of Optional Subelements>]
2146 */
2147 while (pos) {
2148 u8 *nei_start;
2149 long int val;
2150 char *endptr, *tmp;
2151
2152 pos = os_strstr(pos, " neighbor=");
2153 if (!pos)
2154 break;
2155 if (nei_pos + 15 > nei_rep + nei_rep_len) {
2156 wpa_printf(MSG_DEBUG,
2157 "Not enough room for additional neighbor");
2158 return -1;
2159 }
2160 pos += 10;
2161
2162 nei_start = nei_pos;
2163 *nei_pos++ = WLAN_EID_NEIGHBOR_REPORT;
2164 nei_pos++; /* length to be filled in */
2165
2166 if (hwaddr_aton(pos, nei_pos)) {
2167 wpa_printf(MSG_DEBUG, "Invalid BSSID");
2168 return -1;
2169 }
2170 nei_pos += ETH_ALEN;
2171 pos += 17;
2172 if (*pos != ',') {
2173 wpa_printf(MSG_DEBUG, "Missing BSSID Information");
2174 return -1;
2175 }
2176 pos++;
2177
2178 val = strtol(pos, &endptr, 0);
2179 WPA_PUT_LE32(nei_pos, val);
2180 nei_pos += 4;
2181 if (*endptr != ',') {
2182 wpa_printf(MSG_DEBUG, "Missing Operating Class");
2183 return -1;
2184 }
2185 pos = endptr + 1;
2186
2187 *nei_pos++ = atoi(pos); /* Operating Class */
2188 pos = os_strchr(pos, ',');
2189 if (pos == NULL) {
2190 wpa_printf(MSG_DEBUG, "Missing Channel Number");
2191 return -1;
2192 }
2193 pos++;
2194
2195 *nei_pos++ = atoi(pos); /* Channel Number */
2196 pos = os_strchr(pos, ',');
2197 if (pos == NULL) {
2198 wpa_printf(MSG_DEBUG, "Missing PHY Type");
2199 return -1;
2200 }
2201 pos++;
2202
2203 *nei_pos++ = atoi(pos); /* PHY Type */
2204 end = os_strchr(pos, ' ');
2205 tmp = os_strchr(pos, ',');
2206 if (tmp && (!end || tmp < end)) {
2207 /* Optional Subelements (hexdump) */
2208 size_t len;
2209
2210 pos = tmp + 1;
2211 end = os_strchr(pos, ' ');
2212 if (end)
2213 len = end - pos;
2214 else
2215 len = os_strlen(pos);
2216 if (nei_pos + len / 2 > nei_rep + nei_rep_len) {
2217 wpa_printf(MSG_DEBUG,
2218 "Not enough room for neighbor subelements");
2219 return -1;
2220 }
2221 if (len & 0x01 ||
2222 hexstr2bin(pos, nei_pos, len / 2) < 0) {
2223 wpa_printf(MSG_DEBUG,
2224 "Invalid neighbor subelement info");
2225 return -1;
2226 }
2227 nei_pos += len / 2;
2228 pos = end;
2229 }
2230
2231 nei_start[1] = nei_pos - nei_start - 2;
2232 }
2233
2234 return nei_pos - nei_rep;
2235 }
2236
2237
2238 int ieee802_11_ext_capab(const u8 *ie, unsigned int capab)
2239 {
2240 if (!ie || ie[1] <= capab / 8)
2241 return 0;
2242 return !!(ie[2 + capab / 8] & BIT(capab % 8));
2243 }
2244
2245
2246 void hostapd_encode_edmg_chan(int edmg_enable, u8 edmg_channel,
2247 int primary_channel,
2248 struct ieee80211_edmg_config *edmg)
2249 {
2250 if (!edmg_enable) {
2251 edmg->channels = 0;
2252 edmg->bw_config = 0;
2253 return;
2254 }
2255
2256 /* Only EDMG CB1 and EDMG CB2 contiguous channels supported for now */
2257 switch (edmg_channel) {
2258 case EDMG_CHANNEL_9:
2259 edmg->channels = EDMG_CHANNEL_9_SUBCHANNELS;
2260 edmg->bw_config = EDMG_BW_CONFIG_5;
2261 return;
2262 case EDMG_CHANNEL_10:
2263 edmg->channels = EDMG_CHANNEL_10_SUBCHANNELS;
2264 edmg->bw_config = EDMG_BW_CONFIG_5;
2265 return;
2266 case EDMG_CHANNEL_11:
2267 edmg->channels = EDMG_CHANNEL_11_SUBCHANNELS;
2268 edmg->bw_config = EDMG_BW_CONFIG_5;
2269 return;
2270 case EDMG_CHANNEL_12:
2271 edmg->channels = EDMG_CHANNEL_12_SUBCHANNELS;
2272 edmg->bw_config = EDMG_BW_CONFIG_5;
2273 return;
2274 case EDMG_CHANNEL_13:
2275 edmg->channels = EDMG_CHANNEL_13_SUBCHANNELS;
2276 edmg->bw_config = EDMG_BW_CONFIG_5;
2277 return;
2278 default:
2279 if (primary_channel > 0 && primary_channel < 7) {
2280 edmg->channels = BIT(primary_channel - 1);
2281 edmg->bw_config = EDMG_BW_CONFIG_4;
2282 } else {
2283 edmg->channels = 0;
2284 edmg->bw_config = 0;
2285 }
2286 break;
2287 }
2288 }
2289
2290
2291 /* Check if the requested EDMG configuration is a subset of the allowed
2292 * EDMG configuration. */
2293 int ieee802_edmg_is_allowed(struct ieee80211_edmg_config allowed,
2294 struct ieee80211_edmg_config requested)
2295 {
2296 /*
2297 * The validation check if the requested EDMG configuration
2298 * is a subset of the allowed EDMG configuration:
2299 * 1. Check that the requested channels are part (set) of the allowed
2300 * channels.
2301 * 2. P802.11ay defines the values of bw_config between 4 and 15.
2302 * (bw config % 4) will give us 4 groups inside bw_config definition,
2303 * inside each group we can check the subset just by comparing the
2304 * bw_config value.
2305 * Between this 4 groups, there is no subset relation - as a result of
2306 * the P802.11ay definition.
2307 * bw_config defined by IEEE P802.11ay/D4.0, 9.4.2.251, Table 13.
2308 */
2309 if (((requested.channels & allowed.channels) != requested.channels) ||
2310 ((requested.bw_config % 4) > (allowed.bw_config % 4)) ||
2311 requested.bw_config > allowed.bw_config)
2312 return 0;
2313
2314 return 1;
2315 }
2316
2317
2318 int op_class_to_bandwidth(u8 op_class)
2319 {
2320 switch (op_class) {
2321 case 81:
2322 case 82:
2323 return 20;
2324 case 83: /* channels 1..9; 40 MHz */
2325 case 84: /* channels 5..13; 40 MHz */
2326 return 40;
2327 case 115: /* channels 36,40,44,48; indoor only */
2328 return 20;
2329 case 116: /* channels 36,44; 40 MHz; indoor only */
2330 case 117: /* channels 40,48; 40 MHz; indoor only */
2331 return 40;
2332 case 118: /* channels 52,56,60,64; dfs */
2333 return 20;
2334 case 119: /* channels 52,60; 40 MHz; dfs */
2335 case 120: /* channels 56,64; 40 MHz; dfs */
2336 return 40;
2337 case 121: /* channels 100-140 */
2338 return 20;
2339 case 122: /* channels 100-142; 40 MHz */
2340 case 123: /* channels 104-136; 40 MHz */
2341 return 40;
2342 case 124: /* channels 149,153,157,161 */
2343 case 125: /* channels 149,153,157,161,165,169 */
2344 return 20;
2345 case 126: /* channels 149,157; 40 MHz */
2346 case 127: /* channels 153,161; 40 MHz */
2347 return 40;
2348 case 128: /* center freqs 42, 58, 106, 122, 138, 155; 80 MHz */
2349 return 80;
2350 case 129: /* center freqs 50, 114; 160 MHz */
2351 return 160;
2352 case 130: /* center freqs 42, 58, 106, 122, 138, 155; 80+80 MHz */
2353 return 80;
2354 case 131: /* UHB channels, 20 MHz: 1, 5, 9.. */
2355 return 20;
2356 case 132: /* UHB channels, 40 MHz: 3, 11, 19.. */
2357 return 40;
2358 case 133: /* UHB channels, 80 MHz: 7, 23, 39.. */
2359 return 80;
2360 case 134: /* UHB channels, 160 MHz: 15, 47, 79.. */
2361 case 135: /* UHB channels, 80+80 MHz: 7, 23, 39.. */
2362 return 160;
2363 case 180: /* 60 GHz band, channels 1..8 */
2364 return 2160;
2365 case 181: /* 60 GHz band, EDMG CB2, channels 9..15 */
2366 return 4320;
2367 case 182: /* 60 GHz band, EDMG CB3, channels 17..22 */
2368 return 6480;
2369 case 183: /* 60 GHz band, EDMG CB4, channel 25..29 */
2370 return 8640;
2371 }
2372
2373 return 20;
2374 }
2375
2376
2377 int op_class_to_ch_width(u8 op_class)
2378 {
2379 switch (op_class) {
2380 case 81:
2381 case 82:
2382 return CHANWIDTH_USE_HT;
2383 case 83: /* channels 1..9; 40 MHz */
2384 case 84: /* channels 5..13; 40 MHz */
2385 return CHANWIDTH_USE_HT;
2386 case 115: /* channels 36,40,44,48; indoor only */
2387 return CHANWIDTH_USE_HT;
2388 case 116: /* channels 36,44; 40 MHz; indoor only */
2389 case 117: /* channels 40,48; 40 MHz; indoor only */
2390 return CHANWIDTH_USE_HT;
2391 case 118: /* channels 52,56,60,64; dfs */
2392 return CHANWIDTH_USE_HT;
2393 case 119: /* channels 52,60; 40 MHz; dfs */
2394 case 120: /* channels 56,64; 40 MHz; dfs */
2395 return CHANWIDTH_USE_HT;
2396 case 121: /* channels 100-140 */
2397 return CHANWIDTH_USE_HT;
2398 case 122: /* channels 100-142; 40 MHz */
2399 case 123: /* channels 104-136; 40 MHz */
2400 return CHANWIDTH_USE_HT;
2401 case 124: /* channels 149,153,157,161 */
2402 case 125: /* channels 149,153,157,161,165,169 */
2403 return CHANWIDTH_USE_HT;
2404 case 126: /* channels 149,157; 40 MHz */
2405 case 127: /* channels 153,161; 40 MHz */
2406 return CHANWIDTH_USE_HT;
2407 case 128: /* center freqs 42, 58, 106, 122, 138, 155; 80 MHz */
2408 return CHANWIDTH_80MHZ;
2409 case 129: /* center freqs 50, 114; 160 MHz */
2410 return CHANWIDTH_160MHZ;
2411 case 130: /* center freqs 42, 58, 106, 122, 138, 155; 80+80 MHz */
2412 return CHANWIDTH_80P80MHZ;
2413 case 131: /* UHB channels, 20 MHz: 1, 5, 9.. */
2414 return CHANWIDTH_USE_HT;
2415 case 132: /* UHB channels, 40 MHz: 3, 11, 19.. */
2416 return CHANWIDTH_USE_HT;
2417 case 133: /* UHB channels, 80 MHz: 7, 23, 39.. */
2418 return CHANWIDTH_80MHZ;
2419 case 134: /* UHB channels, 160 MHz: 15, 47, 79.. */
2420 return CHANWIDTH_160MHZ;
2421 case 135: /* UHB channels, 80+80 MHz: 7, 23, 39.. */
2422 return CHANWIDTH_80P80MHZ;
2423 case 180: /* 60 GHz band, channels 1..8 */
2424 return CHANWIDTH_2160MHZ;
2425 case 181: /* 60 GHz band, EDMG CB2, channels 9..15 */
2426 return CHANWIDTH_4320MHZ;
2427 case 182: /* 60 GHz band, EDMG CB3, channels 17..22 */
2428 return CHANWIDTH_6480MHZ;
2429 case 183: /* 60 GHz band, EDMG CB4, channel 25..29 */
2430 return CHANWIDTH_8640MHZ;
2431 }
2432 return CHANWIDTH_USE_HT;
2433 }
2434
2435
2436 struct wpabuf * ieee802_11_defrag_data(struct ieee802_11_elems *elems,
2437 u8 eid, u8 eid_ext,
2438 const u8 *data, u8 len)
2439 {
2440 struct frag_ies_info *frag_ies = &elems->frag_ies;
2441 struct wpabuf *buf;
2442 unsigned int i;
2443
2444 if (!elems || !data || !len)
2445 return NULL;
2446
2447 buf = wpabuf_alloc_copy(data, len);
2448 if (!buf)
2449 return NULL;
2450
2451 for (i = 0; i < frag_ies->n_frags; i++) {
2452 int ret;
2453
2454 if (frag_ies->frags[i].eid != eid ||
2455 frag_ies->frags[i].eid_ext != eid_ext)
2456 continue;
2457
2458 ret = wpabuf_resize(&buf, frag_ies->frags[i].ie_len);
2459 if (ret < 0) {
2460 wpabuf_free(buf);
2461 return NULL;
2462 }
2463
2464 /* Copy only the fragment data (without the EID and length) */
2465 wpabuf_put_data(buf, frag_ies->frags[i].ie,
2466 frag_ies->frags[i].ie_len);
2467 }
2468
2469 return buf;
2470 }
2471
2472
2473 struct wpabuf * ieee802_11_defrag(struct ieee802_11_elems *elems,
2474 u8 eid, u8 eid_ext)
2475 {
2476 const u8 *data;
2477 u8 len;
2478
2479 /*
2480 * TODO: Defragmentation mechanism can be supported for all IEs. For now
2481 * handle only those that are used (or use ieee802_11_defrag_data()).
2482 */
2483 switch (eid) {
2484 case WLAN_EID_EXTENSION:
2485 switch (eid_ext) {
2486 case WLAN_EID_EXT_FILS_HLP_CONTAINER:
2487 data = elems->fils_hlp;
2488 len = elems->fils_hlp_len;
2489 break;
2490 case WLAN_EID_EXT_WRAPPED_DATA:
2491 data = elems->wrapped_data;
2492 len = elems->wrapped_data_len;
2493 break;
2494 default:
2495 wpa_printf(MSG_DEBUG,
2496 "Defragmentation not supported. eid_ext=%u",
2497 eid_ext);
2498 return NULL;
2499 }
2500 break;
2501 default:
2502 wpa_printf(MSG_DEBUG,
2503 "Defragmentation not supported. eid=%u", eid);
2504 return NULL;
2505 }
2506
2507 return ieee802_11_defrag_data(elems, eid, eid_ext, data, len);
2508 }