1 /*
2  * BSS table
3  * Copyright (c) 2009-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 "utils/includes.h"
10 
11 #include "utils/common.h"
12 #include "utils/eloop.h"
13 #include "common/ieee802_11_defs.h"
14 #include "drivers/driver.h"
15 #include "eap_peer/eap.h"
16 #include "rsn_supp/wpa.h"
17 #include "wpa_supplicant_i.h"
18 #include "config.h"
19 #include "notify.h"
20 #include "scan.h"
21 #include "bssid_ignore.h"
22 #include "bss.h"
23 
wpa_bss_set_hessid(struct wpa_bss * bss)24 static void wpa_bss_set_hessid(struct wpa_bss *bss)
25 {
26 #ifdef CONFIG_INTERWORKING
27 	const u8 *ie = wpa_bss_get_ie(bss, WLAN_EID_INTERWORKING);
28 	if (ie == NULL || (ie[1] != 7 && ie[1] != 9)) {
29 		os_memset(bss->hessid, 0, ETH_ALEN);
30 		return;
31 	}
32 	if (ie[1] == 7)
33 		os_memcpy(bss->hessid, ie + 3, ETH_ALEN);
34 	else
35 		os_memcpy(bss->hessid, ie + 5, ETH_ALEN);
36 #endif /* CONFIG_INTERWORKING */
37 }
38 
39 
40 /**
41  * wpa_bss_anqp_alloc - Allocate ANQP data structure for a BSS entry
42  * Returns: Allocated ANQP data structure or %NULL on failure
43  *
44  * The allocated ANQP data structure has its users count set to 1. It may be
45  * shared by multiple BSS entries and each shared entry is freed with
46  * wpa_bss_anqp_free().
47  */
wpa_bss_anqp_alloc(void)48 struct wpa_bss_anqp * wpa_bss_anqp_alloc(void)
49 {
50 	struct wpa_bss_anqp *anqp;
51 	anqp = os_zalloc(sizeof(*anqp));
52 	if (anqp == NULL)
53 		return NULL;
54 #ifdef CONFIG_INTERWORKING
55 	dl_list_init(&anqp->anqp_elems);
56 #endif /* CONFIG_INTERWORKING */
57 	anqp->users = 1;
58 	return anqp;
59 }
60 
61 
62 /**
63  * wpa_bss_anqp_clone - Clone an ANQP data structure
64  * @anqp: ANQP data structure from wpa_bss_anqp_alloc()
65  * Returns: Cloned ANQP data structure or %NULL on failure
66  */
wpa_bss_anqp_clone(struct wpa_bss_anqp * anqp)67 static struct wpa_bss_anqp * wpa_bss_anqp_clone(struct wpa_bss_anqp *anqp)
68 {
69 	struct wpa_bss_anqp *n;
70 
71 	n = os_zalloc(sizeof(*n));
72 	if (n == NULL)
73 		return NULL;
74 
75 #define ANQP_DUP(f) if (anqp->f) n->f = wpabuf_dup(anqp->f)
76 #ifdef CONFIG_INTERWORKING
77 	dl_list_init(&n->anqp_elems);
78 	ANQP_DUP(capability_list);
79 	ANQP_DUP(venue_name);
80 	ANQP_DUP(network_auth_type);
81 	ANQP_DUP(roaming_consortium);
82 	ANQP_DUP(ip_addr_type_availability);
83 	ANQP_DUP(nai_realm);
84 	ANQP_DUP(anqp_3gpp);
85 	ANQP_DUP(domain_name);
86 	ANQP_DUP(fils_realm_info);
87 #endif /* CONFIG_INTERWORKING */
88 #ifdef CONFIG_HS20
89 	ANQP_DUP(hs20_capability_list);
90 	ANQP_DUP(hs20_operator_friendly_name);
91 	ANQP_DUP(hs20_wan_metrics);
92 	ANQP_DUP(hs20_connection_capability);
93 	ANQP_DUP(hs20_operating_class);
94 #endif /* CONFIG_HS20 */
95 #undef ANQP_DUP
96 
97 	return n;
98 }
99 
100 
101 /**
102  * wpa_bss_anqp_unshare_alloc - Unshare ANQP data (if shared) in a BSS entry
103  * @bss: BSS entry
104  * Returns: 0 on success, -1 on failure
105  *
106  * This function ensures the specific BSS entry has an ANQP data structure that
107  * is not shared with any other BSS entry.
108  */
wpa_bss_anqp_unshare_alloc(struct wpa_bss * bss)109 int wpa_bss_anqp_unshare_alloc(struct wpa_bss *bss)
110 {
111 	struct wpa_bss_anqp *anqp;
112 
113 	if (bss->anqp && bss->anqp->users > 1) {
114 		/* allocated, but shared - clone an unshared copy */
115 		anqp = wpa_bss_anqp_clone(bss->anqp);
116 		if (anqp == NULL)
117 			return -1;
118 		anqp->users = 1;
119 		bss->anqp->users--;
120 		bss->anqp = anqp;
121 		return 0;
122 	}
123 
124 	if (bss->anqp)
125 		return 0; /* already allocated and not shared */
126 
127 	/* not allocated - allocate a new storage area */
128 	bss->anqp = wpa_bss_anqp_alloc();
129 	return bss->anqp ? 0 : -1;
130 }
131 
132 
133 /**
134  * wpa_bss_anqp_free - Free an ANQP data structure
135  * @anqp: ANQP data structure from wpa_bss_anqp_alloc() or wpa_bss_anqp_clone()
136  */
wpa_bss_anqp_free(struct wpa_bss_anqp * anqp)137 static void wpa_bss_anqp_free(struct wpa_bss_anqp *anqp)
138 {
139 #ifdef CONFIG_INTERWORKING
140 	struct wpa_bss_anqp_elem *elem;
141 #endif /* CONFIG_INTERWORKING */
142 
143 	if (anqp == NULL)
144 		return;
145 
146 	anqp->users--;
147 	if (anqp->users > 0) {
148 		/* Another BSS entry holds a pointer to this ANQP info */
149 		return;
150 	}
151 
152 #ifdef CONFIG_INTERWORKING
153 	wpabuf_free(anqp->capability_list);
154 	wpabuf_free(anqp->venue_name);
155 	wpabuf_free(anqp->network_auth_type);
156 	wpabuf_free(anqp->roaming_consortium);
157 	wpabuf_free(anqp->ip_addr_type_availability);
158 	wpabuf_free(anqp->nai_realm);
159 	wpabuf_free(anqp->anqp_3gpp);
160 	wpabuf_free(anqp->domain_name);
161 	wpabuf_free(anqp->fils_realm_info);
162 
163 	while ((elem = dl_list_first(&anqp->anqp_elems,
164 				     struct wpa_bss_anqp_elem, list))) {
165 		dl_list_del(&elem->list);
166 		wpabuf_free(elem->payload);
167 		os_free(elem);
168 	}
169 #endif /* CONFIG_INTERWORKING */
170 #ifdef CONFIG_HS20
171 	wpabuf_free(anqp->hs20_capability_list);
172 	wpabuf_free(anqp->hs20_operator_friendly_name);
173 	wpabuf_free(anqp->hs20_wan_metrics);
174 	wpabuf_free(anqp->hs20_connection_capability);
175 	wpabuf_free(anqp->hs20_operating_class);
176 #endif /* CONFIG_HS20 */
177 
178 	os_free(anqp);
179 }
180 
181 
182 static struct wpa_connect_work *
wpa_bss_check_pending_connect(struct wpa_supplicant * wpa_s,struct wpa_bss * bss)183 wpa_bss_check_pending_connect(struct wpa_supplicant *wpa_s, struct wpa_bss *bss)
184 {
185 	struct wpa_radio_work *work;
186 	struct wpa_connect_work *cwork;
187 
188 	work = radio_work_pending(wpa_s, "sme-connect");
189 	if (!work)
190 		work = radio_work_pending(wpa_s, "connect");
191 	if (!work)
192 		return NULL;
193 
194 	cwork = work->ctx;
195 	if (cwork->bss != bss)
196 		return NULL;
197 
198 	return cwork;
199 }
200 
201 
wpa_bss_update_pending_connect(struct wpa_connect_work * cwork,struct wpa_bss * new_bss)202 static void wpa_bss_update_pending_connect(struct wpa_connect_work *cwork,
203 					   struct wpa_bss *new_bss)
204 {
205 	wpa_printf(MSG_DEBUG,
206 		   "Update BSS pointer for the pending connect radio work");
207 	cwork->bss = new_bss;
208 	if (!new_bss)
209 		cwork->bss_removed = 1;
210 }
211 
212 
wpa_bss_remove(struct wpa_supplicant * wpa_s,struct wpa_bss * bss,const char * reason)213 void wpa_bss_remove(struct wpa_supplicant *wpa_s, struct wpa_bss *bss,
214 		    const char *reason)
215 {
216 	struct wpa_connect_work *cwork;
217 	unsigned int j;
218 
219 	if (wpa_s->last_scan_res) {
220 		unsigned int i;
221 		for (i = 0; i < wpa_s->last_scan_res_used; i++) {
222 			if (wpa_s->last_scan_res[i] == bss) {
223 				os_memmove(&wpa_s->last_scan_res[i],
224 					   &wpa_s->last_scan_res[i + 1],
225 					   (wpa_s->last_scan_res_used - i - 1)
226 					   * sizeof(struct wpa_bss *));
227 				wpa_s->last_scan_res_used--;
228 				break;
229 			}
230 		}
231 	}
232 	cwork = wpa_bss_check_pending_connect(wpa_s, bss);
233 	if (cwork)
234 		wpa_bss_update_pending_connect(cwork, NULL);
235 	dl_list_del(&bss->list);
236 	dl_list_del(&bss->list_id);
237 	wpa_s->num_bss--;
238 	wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Remove id %u BSSID " MACSTR
239 		" SSID '%s' due to %s", bss->id, MAC2STR(bss->bssid),
240 		wpa_ssid_txt(bss->ssid, bss->ssid_len), reason);
241 	wpas_notify_bss_removed(wpa_s, bss->bssid, bss->id);
242 	wpa_bss_anqp_free(bss->anqp);
243 
244 	if (wpa_s->current_bss == bss) {
245 		wpa_printf(MSG_DEBUG,
246 			   "BSS: Clear current_bss due to bss removal");
247 		wpa_s->current_bss = NULL;
248 	}
249 
250 #ifdef CONFIG_INTERWORKING
251 	if (wpa_s->interworking_gas_bss == bss) {
252 		wpa_printf(MSG_DEBUG,
253 			   "BSS: Clear interworking_gas_bss due to bss removal");
254 		wpa_s->interworking_gas_bss = NULL;
255 	}
256 #endif /* CONFIG_INTERWORKING */
257 
258 #ifdef CONFIG_WNM
259 	if (wpa_s->wnm_target_bss == bss) {
260 		wpa_printf(MSG_DEBUG,
261 			   "BSS: Clear wnm_target_bss due to bss removal");
262 		wpa_s->wnm_target_bss = NULL;
263 	}
264 #endif /* CONFIG_WNM */
265 
266 	if (wpa_s->ml_connect_probe_bss == bss) {
267 		wpa_printf(MSG_DEBUG,
268 			   "BSS: Clear ml_connect_probe_bss due to bss removal");
269 		wpa_s->ml_connect_probe_bss = NULL;
270 	}
271 
272 	for (j = 0; j < MAX_NUM_MLD_LINKS; j++) {
273 		if (wpa_s->links[j].bss == bss) {
274 			wpa_printf(MSG_DEBUG,
275 				   "BSS: Clear links[%d].bss due to bss removal",
276 				   j);
277 			wpa_s->valid_links &= ~BIT(j);
278 			wpa_s->links[j].bss = NULL;
279 		}
280 	}
281 
282 	os_free(bss);
283 }
284 
285 
286 /**
287  * wpa_bss_get - Fetch a BSS table entry based on BSSID and SSID
288  * @wpa_s: Pointer to wpa_supplicant data
289  * @bssid: BSSID, or %NULL to match any BSSID
290  * @ssid: SSID
291  * @ssid_len: Length of @ssid
292  * Returns: Pointer to the BSS entry or %NULL if not found
293  */
wpa_bss_get(struct wpa_supplicant * wpa_s,const u8 * bssid,const u8 * ssid,size_t ssid_len)294 struct wpa_bss * wpa_bss_get(struct wpa_supplicant *wpa_s, const u8 *bssid,
295 			     const u8 *ssid, size_t ssid_len)
296 {
297 	struct wpa_bss *bss;
298 
299 	if (bssid && !wpa_supplicant_filter_bssid_match(wpa_s, bssid))
300 		return NULL;
301 	dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
302 		if ((!bssid || ether_addr_equal(bss->bssid, bssid)) &&
303 		    bss->ssid_len == ssid_len &&
304 		    os_memcmp(bss->ssid, ssid, ssid_len) == 0)
305 			return bss;
306 	}
307 	return NULL;
308 }
309 
310 /**
311  * wpa_bss_get_connection - Fetch a BSS table entry based on BSSID and SSID.
312  * @wpa_s: Pointer to wpa_supplicant data
313  * @bssid: BSSID, or %NULL to match any BSSID
314  * @ssid: SSID
315  * @ssid_len: Length of @ssid
316  * Returns: Pointer to the BSS entry or %NULL if not found
317  *
318  * This function is similar to wpa_bss_get() but it will also return OWE
319  * transition mode encrypted networks for which transition-element matches
320  * @ssid.
321  */
wpa_bss_get_connection(struct wpa_supplicant * wpa_s,const u8 * bssid,const u8 * ssid,size_t ssid_len)322 struct wpa_bss * wpa_bss_get_connection(struct wpa_supplicant *wpa_s,
323 					const u8 *bssid,
324 					const u8 *ssid, size_t ssid_len)
325 {
326 	struct wpa_bss *bss;
327 #ifdef CONFIG_OWE
328 	const u8 *owe, *owe_bssid, *owe_ssid;
329 	size_t owe_ssid_len;
330 #endif /* CONFIG_OWE */
331 
332 	if (bssid && !wpa_supplicant_filter_bssid_match(wpa_s, bssid))
333 		return NULL;
334 	dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
335 		if (bssid && !ether_addr_equal(bss->bssid, bssid))
336 			continue;
337 
338 		if (bss->ssid_len == ssid_len &&
339 		    os_memcmp(bss->ssid, ssid, ssid_len) == 0)
340 			return bss;
341 
342 #ifdef CONFIG_OWE
343 		/* Check if OWE transition mode element is present and matches
344 		 * the SSID */
345 		owe = wpa_bss_get_vendor_ie(bss, OWE_IE_VENDOR_TYPE);
346 		if (!owe)
347 			continue;
348 
349 		if (wpas_get_owe_trans_network(owe, &owe_bssid, &owe_ssid,
350 					       &owe_ssid_len))
351 			continue;
352 
353 		if (bss->ssid_len &&
354 		    owe_ssid_len == ssid_len &&
355 		    os_memcmp(owe_ssid, ssid, ssid_len) == 0)
356 			return bss;
357 #endif /* CONFIG_OWE */
358 	}
359 	return NULL;
360 }
361 
362 
calculate_update_time(const struct os_reltime * fetch_time,unsigned int age_ms,struct os_reltime * update_time)363 void calculate_update_time(const struct os_reltime *fetch_time,
364 			   unsigned int age_ms,
365 			   struct os_reltime *update_time)
366 {
367 	os_time_t usec;
368 
369 	update_time->sec = fetch_time->sec;
370 	update_time->usec = fetch_time->usec;
371 	update_time->sec -= age_ms / 1000;
372 	usec = (age_ms % 1000) * 1000;
373 	if (update_time->usec < usec) {
374 		update_time->sec--;
375 		update_time->usec += 1000000;
376 	}
377 	update_time->usec -= usec;
378 }
379 
380 
wpa_bss_copy_res(struct wpa_bss * dst,struct wpa_scan_res * src,struct os_reltime * fetch_time)381 static void wpa_bss_copy_res(struct wpa_bss *dst, struct wpa_scan_res *src,
382 			     struct os_reltime *fetch_time)
383 {
384 	dst->flags = src->flags;
385 	os_memcpy(dst->bssid, src->bssid, ETH_ALEN);
386 	dst->freq = src->freq;
387 	dst->max_cw = src->max_cw;
388 	dst->beacon_int = src->beacon_int;
389 	dst->caps = src->caps;
390 	dst->qual = src->qual;
391 	dst->noise = src->noise;
392 	dst->level = src->level;
393 	dst->tsf = src->tsf;
394 	dst->beacon_newer = src->beacon_newer;
395 	dst->est_throughput = src->est_throughput;
396 	dst->snr = src->snr;
397 
398 	calculate_update_time(fetch_time, src->age, &dst->last_update);
399 }
400 
401 
wpa_bss_is_wps_candidate(struct wpa_supplicant * wpa_s,struct wpa_bss * bss)402 static int wpa_bss_is_wps_candidate(struct wpa_supplicant *wpa_s,
403 				    struct wpa_bss *bss)
404 {
405 #ifdef CONFIG_WPS
406 	struct wpa_ssid *ssid;
407 	struct wpabuf *wps_ie;
408 	int pbc = 0, ret;
409 
410 	wps_ie = wpa_bss_get_vendor_ie_multi(bss, WPS_IE_VENDOR_TYPE);
411 	if (!wps_ie)
412 		return 0;
413 
414 	if (wps_is_selected_pbc_registrar(wps_ie)) {
415 		pbc = 1;
416 	} else if (!wps_is_addr_authorized(wps_ie, wpa_s->own_addr, 1)) {
417 		wpabuf_free(wps_ie);
418 		return 0;
419 	}
420 
421 	for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) {
422 		if (!(ssid->key_mgmt & WPA_KEY_MGMT_WPS))
423 			continue;
424 		if (ssid->ssid_len &&
425 		    (ssid->ssid_len != bss->ssid_len ||
426 		     os_memcmp(ssid->ssid, bss->ssid, ssid->ssid_len) != 0))
427 			continue;
428 
429 		if (pbc)
430 			ret = eap_is_wps_pbc_enrollee(&ssid->eap);
431 		else
432 			ret = eap_is_wps_pin_enrollee(&ssid->eap);
433 		wpabuf_free(wps_ie);
434 		return ret;
435 	}
436 	wpabuf_free(wps_ie);
437 #endif /* CONFIG_WPS */
438 
439 	return 0;
440 }
441 
442 
is_p2p_pending_bss(struct wpa_supplicant * wpa_s,struct wpa_bss * bss)443 static bool is_p2p_pending_bss(struct wpa_supplicant *wpa_s,
444 			       struct wpa_bss *bss)
445 {
446 #ifdef CONFIG_P2P
447 	u8 addr[ETH_ALEN];
448 
449 	if (ether_addr_equal(bss->bssid, wpa_s->pending_join_iface_addr))
450 		return true;
451 	if (!is_zero_ether_addr(wpa_s->pending_join_dev_addr) &&
452 	    p2p_parse_dev_addr(wpa_bss_ie_ptr(bss), bss->ie_len, addr) == 0 &&
453 	    ether_addr_equal(addr, wpa_s->pending_join_dev_addr))
454 		return true;
455 #endif /* CONFIG_P2P */
456 	return false;
457 }
458 
459 
460 #ifdef CONFIG_OWE
wpa_bss_owe_trans_known(struct wpa_supplicant * wpa_s,struct wpa_bss * bss,const u8 * entry_ssid,size_t entry_ssid_len)461 static int wpa_bss_owe_trans_known(struct wpa_supplicant *wpa_s,
462 				   struct wpa_bss *bss,
463 				   const u8 *entry_ssid, size_t entry_ssid_len)
464 {
465 	const u8 *owe, *owe_bssid, *owe_ssid;
466 	size_t owe_ssid_len;
467 
468 	owe = wpa_bss_get_vendor_ie(bss, OWE_IE_VENDOR_TYPE);
469 	if (!owe)
470 		return 0;
471 
472 	if (wpas_get_owe_trans_network(owe, &owe_bssid, &owe_ssid,
473 				       &owe_ssid_len))
474 		return 0;
475 
476 	return entry_ssid_len == owe_ssid_len &&
477 		os_memcmp(owe_ssid, entry_ssid, owe_ssid_len) == 0;
478 }
479 #endif /* CONFIG_OWE */
480 
481 
wpa_bss_known(struct wpa_supplicant * wpa_s,struct wpa_bss * bss)482 static int wpa_bss_known(struct wpa_supplicant *wpa_s, struct wpa_bss *bss)
483 {
484 	struct wpa_ssid *ssid;
485 
486 	if (is_p2p_pending_bss(wpa_s, bss))
487 		return 1;
488 
489 	for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) {
490 		if (ssid->ssid == NULL || ssid->ssid_len == 0)
491 			continue;
492 		if (ssid->ssid_len == bss->ssid_len &&
493 		    os_memcmp(ssid->ssid, bss->ssid, ssid->ssid_len) == 0)
494 			return 1;
495 #ifdef CONFIG_OWE
496 		if (wpa_bss_owe_trans_known(wpa_s, bss, ssid->ssid,
497 					    ssid->ssid_len))
498 			return 1;
499 #endif /* CONFIG_OWE */
500 	}
501 
502 	return 0;
503 }
504 
505 
wpa_bss_in_use(struct wpa_supplicant * wpa_s,struct wpa_bss * bss)506 static int wpa_bss_in_use(struct wpa_supplicant *wpa_s, struct wpa_bss *bss)
507 {
508 	int i;
509 
510 	if (bss == wpa_s->current_bss)
511 		return 1;
512 
513 	if (bss == wpa_s->ml_connect_probe_bss)
514 		return 1;
515 
516 #ifdef CONFIG_WNM
517 	if (bss == wpa_s->wnm_target_bss)
518 		return 1;
519 #endif /* CONFIG_WNM */
520 
521 	if (wpa_s->current_bss &&
522 	    (bss->ssid_len != wpa_s->current_bss->ssid_len ||
523 	     os_memcmp(bss->ssid, wpa_s->current_bss->ssid,
524 		       bss->ssid_len) != 0))
525 		return 0; /* SSID has changed */
526 
527 	if (!is_zero_ether_addr(bss->bssid) &&
528 	    (ether_addr_equal(bss->bssid, wpa_s->bssid) ||
529 	     ether_addr_equal(bss->bssid, wpa_s->pending_bssid)))
530 		return 1;
531 
532 	if (!wpa_s->valid_links)
533 		return 0;
534 
535 	for_each_link(wpa_s->valid_links, i) {
536 		if (ether_addr_equal(bss->bssid, wpa_s->links[i].bssid))
537 			return 1;
538 	}
539 
540 	return 0;
541 }
542 
543 
wpa_bss_remove_oldest_unknown(struct wpa_supplicant * wpa_s)544 static int wpa_bss_remove_oldest_unknown(struct wpa_supplicant *wpa_s)
545 {
546 	struct wpa_bss *bss;
547 
548 	dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
549 		if (!wpa_bss_known(wpa_s, bss) &&
550 		    !wpa_bss_in_use(wpa_s, bss) &&
551 		    !wpa_bss_is_wps_candidate(wpa_s, bss)) {
552 			wpa_bss_remove(wpa_s, bss, __func__);
553 			return 0;
554 		}
555 	}
556 
557 	return -1;
558 }
559 
560 
wpa_bss_remove_oldest(struct wpa_supplicant * wpa_s)561 static int wpa_bss_remove_oldest(struct wpa_supplicant *wpa_s)
562 {
563 	struct wpa_bss *bss;
564 
565 	/*
566 	 * Remove the oldest entry that does not match with any configured
567 	 * network.
568 	 */
569 	if (wpa_bss_remove_oldest_unknown(wpa_s) == 0)
570 		return 0;
571 
572 	/*
573 	 * Remove the oldest entry that isn't currently in use.
574 	 */
575 	dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
576 		if (!wpa_bss_in_use(wpa_s, bss)) {
577 			wpa_bss_remove(wpa_s, bss, __func__);
578 			return 0;
579 		}
580 	}
581 
582 	return -1;
583 }
584 
585 
wpa_bss_add(struct wpa_supplicant * wpa_s,const u8 * ssid,size_t ssid_len,struct wpa_scan_res * res,struct os_reltime * fetch_time)586 static struct wpa_bss * wpa_bss_add(struct wpa_supplicant *wpa_s,
587 				    const u8 *ssid, size_t ssid_len,
588 				    struct wpa_scan_res *res,
589 				    struct os_reltime *fetch_time)
590 {
591 	struct wpa_bss *bss;
592 	char extra[100];
593 	const u8 *ml_ie;
594 	char *pos, *end;
595 	int ret = 0;
596 	const u8 *mld_addr;
597 
598 	bss = os_zalloc(sizeof(*bss) + res->ie_len + res->beacon_ie_len);
599 	if (bss == NULL)
600 		return NULL;
601 	bss->id = wpa_s->bss_next_id++;
602 	bss->last_update_idx = wpa_s->bss_update_idx;
603 	wpa_bss_copy_res(bss, res, fetch_time);
604 	os_memcpy(bss->ssid, ssid, ssid_len);
605 	bss->ssid_len = ssid_len;
606 	bss->ie_len = res->ie_len;
607 	bss->beacon_ie_len = res->beacon_ie_len;
608 	os_memcpy(bss->ies, res + 1, res->ie_len + res->beacon_ie_len);
609 	wpa_bss_set_hessid(bss);
610 
611 	os_memset(bss->mld_addr, 0, ETH_ALEN);
612 	ml_ie = wpa_scan_get_ml_ie(res, MULTI_LINK_CONTROL_TYPE_BASIC);
613 	if (ml_ie) {
614 		mld_addr = get_basic_mle_mld_addr(&ml_ie[3], ml_ie[1] - 1);
615 		if (mld_addr)
616 			os_memcpy(bss->mld_addr, mld_addr, ETH_ALEN);
617 	}
618 
619 	if (wpa_s->num_bss + 1 > wpa_s->conf->bss_max_count &&
620 	    wpa_bss_remove_oldest(wpa_s) != 0) {
621 		wpa_printf(MSG_ERROR, "Increasing the MAX BSS count to %d "
622 			   "because all BSSes are in use. We should normally "
623 			   "not get here!", (int) wpa_s->num_bss + 1);
624 		wpa_s->conf->bss_max_count = wpa_s->num_bss + 1;
625 	}
626 
627 	dl_list_add_tail(&wpa_s->bss, &bss->list);
628 	dl_list_add_tail(&wpa_s->bss_id, &bss->list_id);
629 	wpa_s->num_bss++;
630 
631 	extra[0] = '\0';
632 	pos = extra;
633 	end = pos + sizeof(extra);
634 	if (!is_zero_ether_addr(bss->hessid))
635 		ret = os_snprintf(pos, end - pos, " HESSID " MACSTR,
636 				  MAC2STR(bss->hessid));
637 
638 	if (!is_zero_ether_addr(bss->mld_addr) &&
639 	    !os_snprintf_error(end - pos, ret)) {
640 		pos += ret;
641 		ret = os_snprintf(pos, end - pos, " MLD ADDR " MACSTR,
642 				  MAC2STR(bss->mld_addr));
643 	}
644 
645 	wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Add new id %u BSSID " MACSTR
646 		" SSID '%s' freq %d%s",
647 		bss->id, MAC2STR(bss->bssid), wpa_ssid_txt(ssid, ssid_len),
648 		bss->freq, extra);
649 	wpas_notify_bss_added(wpa_s, bss->bssid, bss->id);
650 	return bss;
651 }
652 
653 
are_ies_equal(const struct wpa_bss * old,const struct wpa_scan_res * new_res,u32 ie)654 static int are_ies_equal(const struct wpa_bss *old,
655 			 const struct wpa_scan_res *new_res, u32 ie)
656 {
657 	const u8 *old_ie, *new_ie;
658 	struct wpabuf *old_ie_buff = NULL;
659 	struct wpabuf *new_ie_buff = NULL;
660 	int new_ie_len, old_ie_len, ret, is_multi;
661 
662 	switch (ie) {
663 	case WPA_IE_VENDOR_TYPE:
664 		old_ie = wpa_bss_get_vendor_ie(old, ie);
665 		new_ie = wpa_scan_get_vendor_ie(new_res, ie);
666 		is_multi = 0;
667 		break;
668 	case WPS_IE_VENDOR_TYPE:
669 		old_ie_buff = wpa_bss_get_vendor_ie_multi(old, ie);
670 		new_ie_buff = wpa_scan_get_vendor_ie_multi(new_res, ie);
671 		is_multi = 1;
672 		break;
673 	case WLAN_EID_RSN:
674 	case WLAN_EID_SUPP_RATES:
675 	case WLAN_EID_EXT_SUPP_RATES:
676 		old_ie = wpa_bss_get_ie(old, ie);
677 		new_ie = wpa_scan_get_ie(new_res, ie);
678 		is_multi = 0;
679 		break;
680 	default:
681 		wpa_printf(MSG_DEBUG, "bss: %s: cannot compare IEs", __func__);
682 		return 0;
683 	}
684 
685 	if (is_multi) {
686 		/* in case of multiple IEs stored in buffer */
687 		old_ie = old_ie_buff ? wpabuf_head_u8(old_ie_buff) : NULL;
688 		new_ie = new_ie_buff ? wpabuf_head_u8(new_ie_buff) : NULL;
689 		old_ie_len = old_ie_buff ? wpabuf_len(old_ie_buff) : 0;
690 		new_ie_len = new_ie_buff ? wpabuf_len(new_ie_buff) : 0;
691 	} else {
692 		/* in case of single IE */
693 		old_ie_len = old_ie ? old_ie[1] + 2 : 0;
694 		new_ie_len = new_ie ? new_ie[1] + 2 : 0;
695 	}
696 
697 	if (!old_ie || !new_ie)
698 		ret = !old_ie && !new_ie;
699 	else
700 		ret = (old_ie_len == new_ie_len &&
701 		       os_memcmp(old_ie, new_ie, old_ie_len) == 0);
702 
703 	wpabuf_free(old_ie_buff);
704 	wpabuf_free(new_ie_buff);
705 
706 	return ret;
707 }
708 
709 
wpa_bss_compare_res(const struct wpa_bss * old,const struct wpa_scan_res * new_res)710 static u32 wpa_bss_compare_res(const struct wpa_bss *old,
711 			       const struct wpa_scan_res *new_res)
712 {
713 	u32 changes = 0;
714 	int caps_diff = old->caps ^ new_res->caps;
715 
716 	if (old->freq != new_res->freq)
717 		changes |= WPA_BSS_FREQ_CHANGED_FLAG;
718 
719 	if (old->level != new_res->level)
720 		changes |= WPA_BSS_SIGNAL_CHANGED_FLAG;
721 
722 	if (caps_diff & IEEE80211_CAP_PRIVACY)
723 		changes |= WPA_BSS_PRIVACY_CHANGED_FLAG;
724 
725 	if (caps_diff & IEEE80211_CAP_IBSS)
726 		changes |= WPA_BSS_MODE_CHANGED_FLAG;
727 
728 	if (old->ie_len == new_res->ie_len &&
729 	    os_memcmp(wpa_bss_ie_ptr(old), new_res + 1, old->ie_len) == 0)
730 		return changes;
731 	changes |= WPA_BSS_IES_CHANGED_FLAG;
732 
733 	if (!are_ies_equal(old, new_res, WPA_IE_VENDOR_TYPE))
734 		changes |= WPA_BSS_WPAIE_CHANGED_FLAG;
735 
736 	if (!are_ies_equal(old, new_res, WLAN_EID_RSN))
737 		changes |= WPA_BSS_RSNIE_CHANGED_FLAG;
738 
739 	if (!are_ies_equal(old, new_res, WPS_IE_VENDOR_TYPE))
740 		changes |= WPA_BSS_WPS_CHANGED_FLAG;
741 
742 	if (!are_ies_equal(old, new_res, WLAN_EID_SUPP_RATES) ||
743 	    !are_ies_equal(old, new_res, WLAN_EID_EXT_SUPP_RATES))
744 		changes |= WPA_BSS_RATES_CHANGED_FLAG;
745 
746 	return changes;
747 }
748 
749 
notify_bss_changes(struct wpa_supplicant * wpa_s,u32 changes,const struct wpa_bss * bss)750 void notify_bss_changes(struct wpa_supplicant *wpa_s, u32 changes,
751 			const struct wpa_bss *bss)
752 {
753 	if (changes & WPA_BSS_FREQ_CHANGED_FLAG)
754 		wpas_notify_bss_freq_changed(wpa_s, bss->id);
755 
756 	if (changes & WPA_BSS_SIGNAL_CHANGED_FLAG)
757 		wpas_notify_bss_signal_changed(wpa_s, bss->id);
758 
759 	if (changes & WPA_BSS_PRIVACY_CHANGED_FLAG)
760 		wpas_notify_bss_privacy_changed(wpa_s, bss->id);
761 
762 	if (changes & WPA_BSS_MODE_CHANGED_FLAG)
763 		wpas_notify_bss_mode_changed(wpa_s, bss->id);
764 
765 	if (changes & WPA_BSS_WPAIE_CHANGED_FLAG)
766 		wpas_notify_bss_wpaie_changed(wpa_s, bss->id);
767 
768 	if (changes & WPA_BSS_RSNIE_CHANGED_FLAG)
769 		wpas_notify_bss_rsnie_changed(wpa_s, bss->id);
770 
771 	if (changes & WPA_BSS_WPS_CHANGED_FLAG)
772 		wpas_notify_bss_wps_changed(wpa_s, bss->id);
773 
774 	if (changes & WPA_BSS_IES_CHANGED_FLAG)
775 		wpas_notify_bss_ies_changed(wpa_s, bss->id);
776 
777 	if (changes & WPA_BSS_RATES_CHANGED_FLAG)
778 		wpas_notify_bss_rates_changed(wpa_s, bss->id);
779 
780 	wpas_notify_bss_seen(wpa_s, bss->id);
781 }
782 
783 
784 static struct wpa_bss *
wpa_bss_update(struct wpa_supplicant * wpa_s,struct wpa_bss * bss,struct wpa_scan_res * res,struct os_reltime * fetch_time)785 wpa_bss_update(struct wpa_supplicant *wpa_s, struct wpa_bss *bss,
786 	       struct wpa_scan_res *res, struct os_reltime *fetch_time)
787 {
788 	u32 changes;
789 
790 	if (bss->last_update_idx == wpa_s->bss_update_idx) {
791 		struct os_reltime update_time;
792 
793 		/*
794 		 * Some drivers (e.g., cfg80211) include multiple BSS entries
795 		 * for the same BSS if that BSS's channel changes. The BSS list
796 		 * implementation in wpa_supplicant does not do that and we need
797 		 * to filter out the obsolete results here to make sure only the
798 		 * most current BSS information remains in the table.
799 		 */
800 		wpa_printf(MSG_DEBUG, "BSS: " MACSTR
801 			   " has multiple entries in the scan results - select the most current one",
802 			   MAC2STR(bss->bssid));
803 		calculate_update_time(fetch_time, res->age, &update_time);
804 		wpa_printf(MSG_DEBUG,
805 			   "Previous last_update: %u.%06u (freq %d%s)",
806 			   (unsigned int) bss->last_update.sec,
807 			   (unsigned int) bss->last_update.usec,
808 			   bss->freq,
809 			   (bss->flags & WPA_BSS_ASSOCIATED) ? " assoc" : "");
810 		wpa_printf(MSG_DEBUG, "New last_update: %u.%06u (freq %d%s)",
811 			   (unsigned int) update_time.sec,
812 			   (unsigned int) update_time.usec,
813 			   res->freq,
814 			   (res->flags & WPA_SCAN_ASSOCIATED) ? " assoc" : "");
815 		if ((bss->flags & WPA_BSS_ASSOCIATED) ||
816 		    (!(res->flags & WPA_SCAN_ASSOCIATED) &&
817 		     !os_reltime_before(&bss->last_update, &update_time))) {
818 			wpa_printf(MSG_DEBUG,
819 				   "Ignore this BSS entry since the previous update looks more current");
820 			return bss;
821 		}
822 		wpa_printf(MSG_DEBUG,
823 			   "Accept this BSS entry since it looks more current than the previous update");
824 	}
825 
826 	changes = wpa_bss_compare_res(bss, res);
827 	if (changes & WPA_BSS_FREQ_CHANGED_FLAG)
828 		wpa_printf(MSG_DEBUG, "BSS: " MACSTR " changed freq %d --> %d",
829 			   MAC2STR(bss->bssid), bss->freq, res->freq);
830 	bss->scan_miss_count = 0;
831 	bss->last_update_idx = wpa_s->bss_update_idx;
832 	wpa_bss_copy_res(bss, res, fetch_time);
833 	/* Move the entry to the end of the list */
834 	dl_list_del(&bss->list);
835 #ifdef CONFIG_P2P
836 	if (wpa_bss_get_vendor_ie(bss, P2P_IE_VENDOR_TYPE) &&
837 	    !wpa_scan_get_vendor_ie(res, P2P_IE_VENDOR_TYPE) &&
838 	    !(changes & WPA_BSS_FREQ_CHANGED_FLAG)) {
839 		/*
840 		 * This can happen when non-P2P station interface runs a scan
841 		 * without P2P IE in the Probe Request frame. P2P GO would reply
842 		 * to that with a Probe Response that does not include P2P IE.
843 		 * Do not update the IEs in this BSS entry to avoid such loss of
844 		 * information that may be needed for P2P operations to
845 		 * determine group information.
846 		 */
847 		wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Do not update scan IEs for "
848 			MACSTR " since that would remove P2P IE information",
849 			MAC2STR(bss->bssid));
850 	} else
851 #endif /* CONFIG_P2P */
852 	if (bss->ie_len + bss->beacon_ie_len >=
853 	    res->ie_len + res->beacon_ie_len) {
854 		os_memcpy(bss->ies, res + 1, res->ie_len + res->beacon_ie_len);
855 		bss->ie_len = res->ie_len;
856 		bss->beacon_ie_len = res->beacon_ie_len;
857 	} else {
858 		struct wpa_bss *nbss;
859 		struct dl_list *prev = bss->list_id.prev;
860 		struct wpa_connect_work *cwork;
861 		unsigned int i, j;
862 		bool update_current_bss = wpa_s->current_bss == bss;
863 		bool update_ml_probe_bss = wpa_s->ml_connect_probe_bss == bss;
864 		int update_link_bss = -1;
865 
866 		for (j = 0; j < MAX_NUM_MLD_LINKS; j++) {
867 			if (wpa_s->links[j].bss == bss) {
868 				update_link_bss = j;
869 				break;
870 			}
871 		}
872 
873 		cwork = wpa_bss_check_pending_connect(wpa_s, bss);
874 
875 		for (i = 0; i < wpa_s->last_scan_res_used; i++) {
876 			if (wpa_s->last_scan_res[i] == bss)
877 				break;
878 		}
879 
880 		dl_list_del(&bss->list_id);
881 		nbss = os_realloc(bss, sizeof(*bss) + res->ie_len +
882 				  res->beacon_ie_len);
883 		if (nbss) {
884 			if (i != wpa_s->last_scan_res_used)
885 				wpa_s->last_scan_res[i] = nbss;
886 
887 			if (update_current_bss)
888 				wpa_s->current_bss = nbss;
889 
890 			if (update_ml_probe_bss)
891 				wpa_s->ml_connect_probe_bss = nbss;
892 
893 			if (update_link_bss >= 0)
894 				wpa_s->links[update_link_bss].bss = nbss;
895 
896 			if (cwork)
897 				wpa_bss_update_pending_connect(cwork, nbss);
898 
899 			bss = nbss;
900 			os_memcpy(bss->ies, res + 1,
901 				  res->ie_len + res->beacon_ie_len);
902 			bss->ie_len = res->ie_len;
903 			bss->beacon_ie_len = res->beacon_ie_len;
904 		}
905 		dl_list_add(prev, &bss->list_id);
906 	}
907 	if (changes & WPA_BSS_IES_CHANGED_FLAG) {
908 		const u8 *ml_ie, *mld_addr;
909 
910 		wpa_bss_set_hessid(bss);
911 		os_memset(bss->mld_addr, 0, ETH_ALEN);
912 		ml_ie = wpa_scan_get_ml_ie(res, MULTI_LINK_CONTROL_TYPE_BASIC);
913 		if (ml_ie) {
914 			mld_addr = get_basic_mle_mld_addr(&ml_ie[3],
915 							  ml_ie[1] - 1);
916 			if (mld_addr)
917 				os_memcpy(bss->mld_addr, mld_addr, ETH_ALEN);
918 		}
919 	}
920 	dl_list_add_tail(&wpa_s->bss, &bss->list);
921 
922 	notify_bss_changes(wpa_s, changes, bss);
923 
924 	return bss;
925 }
926 
927 
928 /**
929  * wpa_bss_update_start - Start a BSS table update from scan results
930  * @wpa_s: Pointer to wpa_supplicant data
931  *
932  * This function is called at the start of each BSS table update round for new
933  * scan results. The actual scan result entries are indicated with calls to
934  * wpa_bss_update_scan_res() and the update round is finished with a call to
935  * wpa_bss_update_end().
936  */
wpa_bss_update_start(struct wpa_supplicant * wpa_s)937 void wpa_bss_update_start(struct wpa_supplicant *wpa_s)
938 {
939 	wpa_s->bss_update_idx++;
940 	wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Start scan result update %u",
941 		wpa_s->bss_update_idx);
942 	wpa_s->last_scan_res_used = 0;
943 }
944 
945 
946 /**
947  * wpa_bss_update_scan_res - Update a BSS table entry based on a scan result
948  * @wpa_s: Pointer to wpa_supplicant data
949  * @res: Scan result
950  * @fetch_time: Time when the result was fetched from the driver
951  *
952  * This function updates a BSS table entry (or adds one) based on a scan result.
953  * This is called separately for each scan result between the calls to
954  * wpa_bss_update_start() and wpa_bss_update_end().
955  */
wpa_bss_update_scan_res(struct wpa_supplicant * wpa_s,struct wpa_scan_res * res,struct os_reltime * fetch_time)956 void wpa_bss_update_scan_res(struct wpa_supplicant *wpa_s,
957 			     struct wpa_scan_res *res,
958 			     struct os_reltime *fetch_time)
959 {
960 	const u8 *ssid, *p2p, *mesh;
961 	struct wpa_bss *bss;
962 
963 	if (wpa_s->conf->ignore_old_scan_res) {
964 		struct os_reltime update;
965 		calculate_update_time(fetch_time, res->age, &update);
966 		if (os_reltime_before(&update, &wpa_s->scan_trigger_time)) {
967 			struct os_reltime age;
968 			os_reltime_sub(&wpa_s->scan_trigger_time, &update,
969 				       &age);
970 			wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Ignore driver BSS "
971 				"table entry that is %u.%06u seconds older "
972 				"than our scan trigger",
973 				(unsigned int) age.sec,
974 				(unsigned int) age.usec);
975 			return;
976 		}
977 	}
978 
979 	ssid = wpa_scan_get_ie(res, WLAN_EID_SSID);
980 	if (ssid == NULL) {
981 		wpa_dbg(wpa_s, MSG_DEBUG, "BSS: No SSID IE included for "
982 			MACSTR, MAC2STR(res->bssid));
983 		return;
984 	}
985 	if (ssid[1] > SSID_MAX_LEN) {
986 		wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Too long SSID IE included for "
987 			MACSTR, MAC2STR(res->bssid));
988 		return;
989 	}
990 
991 	p2p = wpa_scan_get_vendor_ie(res, P2P_IE_VENDOR_TYPE);
992 #ifdef CONFIG_P2P
993 	if (p2p == NULL &&
994 	    wpa_s->p2p_group_interface != NOT_P2P_GROUP_INTERFACE) {
995 		/*
996 		 * If it's a P2P specific interface, then don't update
997 		 * the scan result without a P2P IE.
998 		 */
999 		wpa_printf(MSG_DEBUG, "BSS: No P2P IE - skipping BSS " MACSTR
1000 			   " update for P2P interface", MAC2STR(res->bssid));
1001 		return;
1002 	}
1003 #endif /* CONFIG_P2P */
1004 	if (p2p && ssid[1] == P2P_WILDCARD_SSID_LEN &&
1005 	    os_memcmp(ssid + 2, P2P_WILDCARD_SSID, P2P_WILDCARD_SSID_LEN) == 0)
1006 		return; /* Skip P2P listen discovery results here */
1007 
1008 	/* TODO: add option for ignoring BSSes we are not interested in
1009 	 * (to save memory) */
1010 
1011 	mesh = wpa_scan_get_ie(res, WLAN_EID_MESH_ID);
1012 	if (mesh && mesh[1] <= SSID_MAX_LEN)
1013 		ssid = mesh;
1014 
1015 	bss = wpa_bss_get(wpa_s, res->bssid, ssid + 2, ssid[1]);
1016 	if (bss == NULL)
1017 		bss = wpa_bss_add(wpa_s, ssid + 2, ssid[1], res, fetch_time);
1018 	else {
1019 		bss = wpa_bss_update(wpa_s, bss, res, fetch_time);
1020 		if (wpa_s->last_scan_res) {
1021 			unsigned int i;
1022 			for (i = 0; i < wpa_s->last_scan_res_used; i++) {
1023 				if (bss == wpa_s->last_scan_res[i]) {
1024 					/* Already in the list */
1025 					return;
1026 				}
1027 			}
1028 		}
1029 	}
1030 
1031 	if (bss == NULL)
1032 		return;
1033 	if (wpa_s->last_scan_res_used >= wpa_s->last_scan_res_size) {
1034 		struct wpa_bss **n;
1035 		unsigned int siz;
1036 		if (wpa_s->last_scan_res_size == 0)
1037 			siz = 32;
1038 		else
1039 			siz = wpa_s->last_scan_res_size * 2;
1040 		n = os_realloc_array(wpa_s->last_scan_res, siz,
1041 				     sizeof(struct wpa_bss *));
1042 		if (n == NULL)
1043 			return;
1044 		wpa_s->last_scan_res = n;
1045 		wpa_s->last_scan_res_size = siz;
1046 	}
1047 
1048 	if (wpa_s->last_scan_res)
1049 		wpa_s->last_scan_res[wpa_s->last_scan_res_used++] = bss;
1050 }
1051 
1052 
wpa_bss_included_in_scan(const struct wpa_bss * bss,const struct scan_info * info)1053 static int wpa_bss_included_in_scan(const struct wpa_bss *bss,
1054 				    const struct scan_info *info)
1055 {
1056 	int found;
1057 	size_t i;
1058 
1059 	if (info == NULL)
1060 		return 1;
1061 
1062 	if (info->num_freqs) {
1063 		found = 0;
1064 		for (i = 0; i < info->num_freqs; i++) {
1065 			if (bss->freq == info->freqs[i]) {
1066 				found = 1;
1067 				break;
1068 			}
1069 		}
1070 		if (!found)
1071 			return 0;
1072 	}
1073 
1074 	if (info->num_ssids) {
1075 		found = 0;
1076 		for (i = 0; i < info->num_ssids; i++) {
1077 			const struct wpa_driver_scan_ssid *s = &info->ssids[i];
1078 			if ((s->ssid == NULL || s->ssid_len == 0) ||
1079 			    (s->ssid_len == bss->ssid_len &&
1080 			     os_memcmp(s->ssid, bss->ssid, bss->ssid_len) ==
1081 			     0)) {
1082 				found = 1;
1083 				break;
1084 			}
1085 		}
1086 		if (!found)
1087 			return 0;
1088 	}
1089 
1090 	return 1;
1091 }
1092 
1093 
1094 /**
1095  * wpa_bss_update_end - End a BSS table update from scan results
1096  * @wpa_s: Pointer to wpa_supplicant data
1097  * @info: Information about scan parameters
1098  * @new_scan: Whether this update round was based on a new scan
1099  *
1100  * This function is called at the end of each BSS table update round for new
1101  * scan results. The start of the update was indicated with a call to
1102  * wpa_bss_update_start().
1103  */
wpa_bss_update_end(struct wpa_supplicant * wpa_s,struct scan_info * info,int new_scan)1104 void wpa_bss_update_end(struct wpa_supplicant *wpa_s, struct scan_info *info,
1105 			int new_scan)
1106 {
1107 	struct wpa_bss *bss, *n;
1108 
1109 	os_get_reltime(&wpa_s->last_scan);
1110 	if ((info && info->aborted) || !new_scan)
1111 		return; /* do not expire entries without new scan */
1112 
1113 	dl_list_for_each_safe(bss, n, &wpa_s->bss, struct wpa_bss, list) {
1114 		if (wpa_bss_in_use(wpa_s, bss))
1115 			continue;
1116 		if (!wpa_bss_included_in_scan(bss, info))
1117 			continue; /* expire only BSSes that were scanned */
1118 		if (bss->last_update_idx < wpa_s->bss_update_idx)
1119 			bss->scan_miss_count++;
1120 		if (bss->scan_miss_count >=
1121 		    wpa_s->conf->bss_expiration_scan_count) {
1122 			wpa_bss_remove(wpa_s, bss, "no match in scan");
1123 		}
1124 	}
1125 
1126 	wpa_printf(MSG_DEBUG, "BSS: last_scan_res_used=%zu/%zu",
1127 		   wpa_s->last_scan_res_used, wpa_s->last_scan_res_size);
1128 }
1129 
1130 
1131 /**
1132  * wpa_bss_flush_by_age - Flush old BSS entries
1133  * @wpa_s: Pointer to wpa_supplicant data
1134  * @age: Maximum entry age in seconds
1135  *
1136  * Remove BSS entries that have not been updated during the last @age seconds.
1137  */
wpa_bss_flush_by_age(struct wpa_supplicant * wpa_s,int age)1138 void wpa_bss_flush_by_age(struct wpa_supplicant *wpa_s, int age)
1139 {
1140 	struct wpa_bss *bss, *n;
1141 	struct os_reltime t;
1142 
1143 	if (dl_list_empty(&wpa_s->bss))
1144 		return;
1145 
1146 	os_get_reltime(&t);
1147 
1148 	if (t.sec < age)
1149 		return; /* avoid underflow; there can be no older entries */
1150 
1151 	t.sec -= age;
1152 
1153 	dl_list_for_each_safe(bss, n, &wpa_s->bss, struct wpa_bss, list) {
1154 		if (wpa_bss_in_use(wpa_s, bss))
1155 			continue;
1156 
1157 		if (wpa_s->reassoc_same_ess &&
1158 		    wpa_s->wpa_state != WPA_COMPLETED &&
1159 		    wpa_s->last_ssid &&
1160 		    wpa_s->last_ssid->ssid &&
1161 		    bss->ssid_len == wpa_s->last_ssid->ssid_len &&
1162 		    os_memcmp(bss->ssid, wpa_s->last_ssid->ssid,
1163 			      bss->ssid_len) == 0)
1164 			continue;
1165 
1166 		if (os_reltime_before(&bss->last_update, &t)) {
1167 			wpa_bss_remove(wpa_s, bss, __func__);
1168 		} else
1169 			break;
1170 	}
1171 }
1172 
1173 
1174 /**
1175  * wpa_bss_init - Initialize BSS table
1176  * @wpa_s: Pointer to wpa_supplicant data
1177  * Returns: 0 on success, -1 on failure
1178  *
1179  * This prepares BSS table lists and timer for periodic updates. The BSS table
1180  * is deinitialized with wpa_bss_deinit() once not needed anymore.
1181  */
wpa_bss_init(struct wpa_supplicant * wpa_s)1182 int wpa_bss_init(struct wpa_supplicant *wpa_s)
1183 {
1184 	dl_list_init(&wpa_s->bss);
1185 	dl_list_init(&wpa_s->bss_id);
1186 	return 0;
1187 }
1188 
1189 
1190 /**
1191  * wpa_bss_flush - Flush all unused BSS entries
1192  * @wpa_s: Pointer to wpa_supplicant data
1193  */
wpa_bss_flush(struct wpa_supplicant * wpa_s)1194 void wpa_bss_flush(struct wpa_supplicant *wpa_s)
1195 {
1196 	struct wpa_bss *bss, *n;
1197 
1198 	wpa_s->clear_driver_scan_cache = 1;
1199 
1200 	if (wpa_s->bss.next == NULL)
1201 		return; /* BSS table not yet initialized */
1202 
1203 	dl_list_for_each_safe(bss, n, &wpa_s->bss, struct wpa_bss, list) {
1204 		if (wpa_bss_in_use(wpa_s, bss))
1205 			continue;
1206 		wpa_bss_remove(wpa_s, bss, __func__);
1207 	}
1208 }
1209 
1210 
1211 /**
1212  * wpa_bss_deinit - Deinitialize BSS table
1213  * @wpa_s: Pointer to wpa_supplicant data
1214  */
wpa_bss_deinit(struct wpa_supplicant * wpa_s)1215 void wpa_bss_deinit(struct wpa_supplicant *wpa_s)
1216 {
1217 	wpa_bss_flush(wpa_s);
1218 }
1219 
1220 
1221 /**
1222  * wpa_bss_get_bssid - Fetch a BSS table entry based on BSSID
1223  * @wpa_s: Pointer to wpa_supplicant data
1224  * @bssid: BSSID
1225  * Returns: Pointer to the BSS entry or %NULL if not found
1226  */
wpa_bss_get_bssid(struct wpa_supplicant * wpa_s,const u8 * bssid)1227 struct wpa_bss * wpa_bss_get_bssid(struct wpa_supplicant *wpa_s,
1228 				   const u8 *bssid)
1229 {
1230 	struct wpa_bss *bss;
1231 	if (!wpa_supplicant_filter_bssid_match(wpa_s, bssid))
1232 		return NULL;
1233 	dl_list_for_each_reverse(bss, &wpa_s->bss, struct wpa_bss, list) {
1234 		if (ether_addr_equal(bss->bssid, bssid))
1235 			return bss;
1236 	}
1237 	return NULL;
1238 }
1239 
1240 
1241 /**
1242  * wpa_bss_get_bssid_latest - Fetch the latest BSS table entry based on BSSID
1243  * @wpa_s: Pointer to wpa_supplicant data
1244  * @bssid: BSSID
1245  * Returns: Pointer to the BSS entry or %NULL if not found
1246  *
1247  * This function is like wpa_bss_get_bssid(), but full BSS table is iterated to
1248  * find the entry that has the most recent update. This can help in finding the
1249  * correct entry in cases where the SSID of the AP may have changed recently
1250  * (e.g., in WPS reconfiguration cases).
1251  */
wpa_bss_get_bssid_latest(struct wpa_supplicant * wpa_s,const u8 * bssid)1252 struct wpa_bss * wpa_bss_get_bssid_latest(struct wpa_supplicant *wpa_s,
1253 					  const u8 *bssid)
1254 {
1255 	struct wpa_bss *bss, *found = NULL;
1256 	if (!wpa_supplicant_filter_bssid_match(wpa_s, bssid))
1257 		return NULL;
1258 	dl_list_for_each_reverse(bss, &wpa_s->bss, struct wpa_bss, list) {
1259 		if (!ether_addr_equal(bss->bssid, bssid))
1260 			continue;
1261 		if (found == NULL ||
1262 		    os_reltime_before(&found->last_update, &bss->last_update))
1263 			found = bss;
1264 	}
1265 	return found;
1266 }
1267 
1268 
1269 #ifdef CONFIG_P2P
1270 /**
1271  * wpa_bss_get_p2p_dev_addr - Fetch the latest BSS table entry based on P2P Device Addr
1272  * @wpa_s: Pointer to wpa_supplicant data
1273  * @dev_addr: P2P Device Address of the GO
1274  * Returns: Pointer to the BSS entry or %NULL if not found
1275  *
1276  * This function tries to find the entry that has the most recent update. This
1277  * can help in finding the correct entry in cases where the SSID of the P2P
1278  * Device may have changed recently.
1279  */
wpa_bss_get_p2p_dev_addr(struct wpa_supplicant * wpa_s,const u8 * dev_addr)1280 struct wpa_bss * wpa_bss_get_p2p_dev_addr(struct wpa_supplicant *wpa_s,
1281 					  const u8 *dev_addr)
1282 {
1283 	struct wpa_bss *bss, *found = NULL;
1284 	dl_list_for_each_reverse(bss, &wpa_s->bss, struct wpa_bss, list) {
1285 		u8 addr[ETH_ALEN];
1286 		if (p2p_parse_dev_addr(wpa_bss_ie_ptr(bss), bss->ie_len,
1287 				       addr) != 0 ||
1288 		    !ether_addr_equal(addr, dev_addr))
1289 			continue;
1290 		if (!found ||
1291 		    os_reltime_before(&found->last_update, &bss->last_update))
1292 			found = bss;
1293 	}
1294 	return found;
1295 }
1296 #endif /* CONFIG_P2P */
1297 
1298 
1299 /**
1300  * wpa_bss_get_id - Fetch a BSS table entry based on identifier
1301  * @wpa_s: Pointer to wpa_supplicant data
1302  * @id: Unique identifier (struct wpa_bss::id) assigned for the entry
1303  * Returns: Pointer to the BSS entry or %NULL if not found
1304  */
wpa_bss_get_id(struct wpa_supplicant * wpa_s,unsigned int id)1305 struct wpa_bss * wpa_bss_get_id(struct wpa_supplicant *wpa_s, unsigned int id)
1306 {
1307 	struct wpa_bss *bss;
1308 	dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
1309 		if (bss->id == id)
1310 			return bss;
1311 	}
1312 	return NULL;
1313 }
1314 
1315 
1316 /**
1317  * wpa_bss_get_id_range - Fetch a BSS table entry based on identifier range
1318  * @wpa_s: Pointer to wpa_supplicant data
1319  * @idf: Smallest allowed identifier assigned for the entry
1320  * @idf: Largest allowed identifier assigned for the entry
1321  * Returns: Pointer to the BSS entry or %NULL if not found
1322  *
1323  * This function is similar to wpa_bss_get_id() but allows a BSS entry with the
1324  * smallest id value to be fetched within the specified range without the
1325  * caller having to know the exact id.
1326  */
wpa_bss_get_id_range(struct wpa_supplicant * wpa_s,unsigned int idf,unsigned int idl)1327 struct wpa_bss * wpa_bss_get_id_range(struct wpa_supplicant *wpa_s,
1328 				      unsigned int idf, unsigned int idl)
1329 {
1330 	struct wpa_bss *bss;
1331 	dl_list_for_each(bss, &wpa_s->bss_id, struct wpa_bss, list_id) {
1332 		if (bss->id >= idf && bss->id <= idl)
1333 			return bss;
1334 	}
1335 	return NULL;
1336 }
1337 
1338 
1339 /**
1340  * wpa_bss_get_ie - Fetch a specified information element from a BSS entry
1341  * @bss: BSS table entry
1342  * @ie: Information element identitifier (WLAN_EID_*)
1343  * Returns: Pointer to the information element (id field) or %NULL if not found
1344  *
1345  * This function returns the first matching information element in the BSS
1346  * entry.
1347  */
wpa_bss_get_ie(const struct wpa_bss * bss,u8 ie)1348 const u8 * wpa_bss_get_ie(const struct wpa_bss *bss, u8 ie)
1349 {
1350 	return get_ie(wpa_bss_ie_ptr(bss), bss->ie_len, ie);
1351 }
1352 
1353 
1354 /**
1355  * wpa_bss_get_ie_beacon - Fetch a specified information element from a BSS entry
1356  * @bss: BSS table entry
1357  * @ie: Information element identitifier (WLAN_EID_*)
1358  * Returns: Pointer to the information element (id field) or %NULL if not found
1359  *
1360  * This function returns the first matching information element in the BSS
1361  * entry.
1362  *
1363  * This function is like wpa_bss_get_ie(), but uses IE buffer only from Beacon
1364  * frames instead of either Beacon or Probe Response frames.
1365  */
wpa_bss_get_ie_beacon(const struct wpa_bss * bss,u8 ie)1366 const u8 * wpa_bss_get_ie_beacon(const struct wpa_bss *bss, u8 ie)
1367 {
1368 	const u8 *ies;
1369 
1370 	if (bss->beacon_ie_len == 0)
1371 		return NULL;
1372 
1373 	ies = wpa_bss_ie_ptr(bss);
1374 	ies += bss->ie_len;
1375 	return get_ie(ies, bss->beacon_ie_len, ie);
1376 }
1377 
1378 
1379 /**
1380  * wpa_bss_get_ie_ext - Fetch a specified extended IE from a BSS entry
1381  * @bss: BSS table entry
1382  * @ext: Information element extension identifier (WLAN_EID_EXT_*)
1383  * Returns: Pointer to the information element (id field) or %NULL if not found
1384  *
1385  * This function returns the first matching information element in the BSS
1386  * entry.
1387  */
wpa_bss_get_ie_ext(const struct wpa_bss * bss,u8 ext)1388 const u8 * wpa_bss_get_ie_ext(const struct wpa_bss *bss, u8 ext)
1389 {
1390 	return get_ie_ext(wpa_bss_ie_ptr(bss), bss->ie_len, ext);
1391 }
1392 
1393 
1394 /**
1395  * wpa_bss_get_vendor_ie - Fetch a vendor information element from a BSS entry
1396  * @bss: BSS table entry
1397  * @vendor_type: Vendor type (four octets starting the IE payload)
1398  * Returns: Pointer to the information element (id field) or %NULL if not found
1399  *
1400  * This function returns the first matching information element in the BSS
1401  * entry.
1402  */
wpa_bss_get_vendor_ie(const struct wpa_bss * bss,u32 vendor_type)1403 const u8 * wpa_bss_get_vendor_ie(const struct wpa_bss *bss, u32 vendor_type)
1404 {
1405 	const u8 *ies;
1406 	const struct element *elem;
1407 
1408 	ies = wpa_bss_ie_ptr(bss);
1409 
1410 	for_each_element_id(elem, WLAN_EID_VENDOR_SPECIFIC, ies, bss->ie_len) {
1411 		if (elem->datalen >= 4 &&
1412 		    vendor_type == WPA_GET_BE32(elem->data))
1413 			return &elem->id;
1414 	}
1415 
1416 	return NULL;
1417 }
1418 
1419 
1420 /**
1421  * wpa_bss_get_vendor_ie_beacon - Fetch a vendor information from a BSS entry
1422  * @bss: BSS table entry
1423  * @vendor_type: Vendor type (four octets starting the IE payload)
1424  * Returns: Pointer to the information element (id field) or %NULL if not found
1425  *
1426  * This function returns the first matching information element in the BSS
1427  * entry.
1428  *
1429  * This function is like wpa_bss_get_vendor_ie(), but uses IE buffer only
1430  * from Beacon frames instead of either Beacon or Probe Response frames.
1431  */
wpa_bss_get_vendor_ie_beacon(const struct wpa_bss * bss,u32 vendor_type)1432 const u8 * wpa_bss_get_vendor_ie_beacon(const struct wpa_bss *bss,
1433 					u32 vendor_type)
1434 {
1435 	const u8 *ies;
1436 	const struct element *elem;
1437 
1438 	if (bss->beacon_ie_len == 0)
1439 		return NULL;
1440 
1441 	ies = wpa_bss_ie_ptr(bss);
1442 	ies += bss->ie_len;
1443 
1444 	for_each_element_id(elem, WLAN_EID_VENDOR_SPECIFIC, ies,
1445 			    bss->beacon_ie_len) {
1446 		if (elem->datalen >= 4 &&
1447 		    vendor_type == WPA_GET_BE32(elem->data))
1448 			return &elem->id;
1449 	}
1450 
1451 	return NULL;
1452 }
1453 
1454 
1455 /**
1456  * wpa_bss_get_vendor_ie_multi - Fetch vendor IE data from a BSS entry
1457  * @bss: BSS table entry
1458  * @vendor_type: Vendor type (four octets starting the IE payload)
1459  * Returns: Pointer to the information element payload or %NULL if not found
1460  *
1461  * This function returns concatenated payload of possibly fragmented vendor
1462  * specific information elements in the BSS entry. The caller is responsible for
1463  * freeing the returned buffer.
1464  */
wpa_bss_get_vendor_ie_multi(const struct wpa_bss * bss,u32 vendor_type)1465 struct wpabuf * wpa_bss_get_vendor_ie_multi(const struct wpa_bss *bss,
1466 					    u32 vendor_type)
1467 {
1468 	struct wpabuf *buf;
1469 	const u8 *end, *pos;
1470 
1471 	buf = wpabuf_alloc(bss->ie_len);
1472 	if (buf == NULL)
1473 		return NULL;
1474 
1475 	pos = wpa_bss_ie_ptr(bss);
1476 	end = pos + bss->ie_len;
1477 
1478 	while (end - pos > 1) {
1479 		u8 ie, len;
1480 
1481 		ie = pos[0];
1482 		len = pos[1];
1483 		if (len > end - pos - 2)
1484 			break;
1485 		pos += 2;
1486 		if (ie == WLAN_EID_VENDOR_SPECIFIC && len >= 4 &&
1487 		    vendor_type == WPA_GET_BE32(pos))
1488 			wpabuf_put_data(buf, pos + 4, len - 4);
1489 		pos += len;
1490 	}
1491 
1492 	if (wpabuf_len(buf) == 0) {
1493 		wpabuf_free(buf);
1494 		buf = NULL;
1495 	}
1496 
1497 	return buf;
1498 }
1499 
1500 
1501 /**
1502  * wpa_bss_get_vendor_ie_multi_beacon - Fetch vendor IE data from a BSS entry
1503  * @bss: BSS table entry
1504  * @vendor_type: Vendor type (four octets starting the IE payload)
1505  * Returns: Pointer to the information element payload or %NULL if not found
1506  *
1507  * This function returns concatenated payload of possibly fragmented vendor
1508  * specific information elements in the BSS entry. The caller is responsible for
1509  * freeing the returned buffer.
1510  *
1511  * This function is like wpa_bss_get_vendor_ie_multi(), but uses IE buffer only
1512  * from Beacon frames instead of either Beacon or Probe Response frames.
1513  */
wpa_bss_get_vendor_ie_multi_beacon(const struct wpa_bss * bss,u32 vendor_type)1514 struct wpabuf * wpa_bss_get_vendor_ie_multi_beacon(const struct wpa_bss *bss,
1515 						   u32 vendor_type)
1516 {
1517 	struct wpabuf *buf;
1518 	const u8 *end, *pos;
1519 
1520 	buf = wpabuf_alloc(bss->beacon_ie_len);
1521 	if (buf == NULL)
1522 		return NULL;
1523 
1524 	pos = wpa_bss_ie_ptr(bss);
1525 	pos += bss->ie_len;
1526 	end = pos + bss->beacon_ie_len;
1527 
1528 	while (end - pos > 1) {
1529 		u8 id, len;
1530 
1531 		id = *pos++;
1532 		len = *pos++;
1533 		if (len > end - pos)
1534 			break;
1535 		if (id == WLAN_EID_VENDOR_SPECIFIC && len >= 4 &&
1536 		    vendor_type == WPA_GET_BE32(pos))
1537 			wpabuf_put_data(buf, pos + 4, len - 4);
1538 		pos += len;
1539 	}
1540 
1541 	if (wpabuf_len(buf) == 0) {
1542 		wpabuf_free(buf);
1543 		buf = NULL;
1544 	}
1545 
1546 	return buf;
1547 }
1548 
1549 
1550 /**
1551  * wpa_bss_get_max_rate - Get maximum legacy TX rate supported in a BSS
1552  * @bss: BSS table entry
1553  * Returns: Maximum legacy rate in units of 500 kbps
1554  */
wpa_bss_get_max_rate(const struct wpa_bss * bss)1555 int wpa_bss_get_max_rate(const struct wpa_bss *bss)
1556 {
1557 	int rate = 0;
1558 	const u8 *ie;
1559 	int i;
1560 
1561 	ie = wpa_bss_get_ie(bss, WLAN_EID_SUPP_RATES);
1562 	for (i = 0; ie && i < ie[1]; i++) {
1563 		if ((ie[i + 2] & 0x7f) > rate)
1564 			rate = ie[i + 2] & 0x7f;
1565 	}
1566 
1567 	ie = wpa_bss_get_ie(bss, WLAN_EID_EXT_SUPP_RATES);
1568 	for (i = 0; ie && i < ie[1]; i++) {
1569 		if ((ie[i + 2] & 0x7f) > rate)
1570 			rate = ie[i + 2] & 0x7f;
1571 	}
1572 
1573 	return rate;
1574 }
1575 
1576 
1577 /**
1578  * wpa_bss_get_bit_rates - Get legacy TX rates supported in a BSS
1579  * @bss: BSS table entry
1580  * @rates: Buffer for returning a pointer to the rates list (units of 500 kbps)
1581  * Returns: number of legacy TX rates or -1 on failure
1582  *
1583  * The caller is responsible for freeing the returned buffer with os_free() in
1584  * case of success.
1585  */
wpa_bss_get_bit_rates(const struct wpa_bss * bss,u8 ** rates)1586 int wpa_bss_get_bit_rates(const struct wpa_bss *bss, u8 **rates)
1587 {
1588 	const u8 *ie, *ie2;
1589 	int i, j;
1590 	unsigned int len;
1591 	u8 *r;
1592 
1593 	ie = wpa_bss_get_ie(bss, WLAN_EID_SUPP_RATES);
1594 	ie2 = wpa_bss_get_ie(bss, WLAN_EID_EXT_SUPP_RATES);
1595 
1596 	len = (ie ? ie[1] : 0) + (ie2 ? ie2[1] : 0);
1597 
1598 	r = os_malloc(len);
1599 	if (!r)
1600 		return -1;
1601 
1602 	for (i = 0; ie && i < ie[1]; i++)
1603 		r[i] = ie[i + 2] & 0x7f;
1604 
1605 	for (j = 0; ie2 && j < ie2[1]; j++)
1606 		r[i + j] = ie2[j + 2] & 0x7f;
1607 
1608 	*rates = r;
1609 	return len;
1610 }
1611 
1612 
1613 #ifdef CONFIG_FILS
wpa_bss_get_fils_cache_id(const struct wpa_bss * bss)1614 const u8 * wpa_bss_get_fils_cache_id(const struct wpa_bss *bss)
1615 {
1616 	const u8 *ie;
1617 
1618 	if (bss) {
1619 		ie = wpa_bss_get_ie(bss, WLAN_EID_FILS_INDICATION);
1620 		if (ie && ie[1] >= 4 && WPA_GET_LE16(ie + 2) & BIT(7))
1621 			return ie + 4;
1622 	}
1623 
1624 	return NULL;
1625 }
1626 #endif /* CONFIG_FILS */
1627 
1628 
wpa_bss_ext_capab(const struct wpa_bss * bss,unsigned int capab)1629 int wpa_bss_ext_capab(const struct wpa_bss *bss, unsigned int capab)
1630 {
1631 	if (!bss)
1632 		return 0;
1633 	return ieee802_11_ext_capab(wpa_bss_get_ie(bss, WLAN_EID_EXT_CAPAB),
1634 				    capab);
1635 }
1636 
1637 
1638 static void
wpa_bss_parse_ml_rnr_ap_info(struct wpa_supplicant * wpa_s,struct wpa_bss * bss,u8 mbssid_idx,const struct ieee80211_neighbor_ap_info * ap_info,size_t len,u16 * seen,u16 * missing,struct wpa_ssid * ssid)1639 wpa_bss_parse_ml_rnr_ap_info(struct wpa_supplicant *wpa_s,
1640 			     struct wpa_bss *bss, u8 mbssid_idx,
1641 			     const struct ieee80211_neighbor_ap_info *ap_info,
1642 			     size_t len, u16 *seen, u16 *missing,
1643 			     struct wpa_ssid *ssid)
1644 {
1645 	const u8 *pos, *end;
1646 	const u8 *mld_params;
1647 	u8 count, mld_params_offset;
1648 	u8 i, type, link_id;
1649 
1650 	count = RNR_TBTT_INFO_COUNT_VAL(ap_info->tbtt_info_hdr) + 1;
1651 	type = ap_info->tbtt_info_hdr & RNR_TBTT_INFO_HDR_TYPE_MSK;
1652 
1653 	/* MLD information is at offset 13 or at start */
1654 	if (type == 0 && ap_info->tbtt_info_len >= RNR_TBTT_INFO_MLD_LEN) {
1655 		/* MLD info is appended */
1656 		mld_params_offset = RNR_TBTT_INFO_LEN;
1657 	} else {
1658 		/* TODO: Support NSTR AP */
1659 		return;
1660 	}
1661 
1662 	pos = (const u8 *) ap_info;
1663 	end = pos + len;
1664 	pos += sizeof(*ap_info);
1665 
1666 	for (i = 0; i < count; i++, pos += ap_info->tbtt_info_len) {
1667 		if (end - pos < ap_info->tbtt_info_len)
1668 			break;
1669 
1670 		mld_params = pos + mld_params_offset;
1671 
1672 		link_id = *(mld_params + 1) & EHT_ML_LINK_ID_MSK;
1673 		if (link_id >= MAX_NUM_MLD_LINKS)
1674 			continue;
1675 
1676 		if (*mld_params != mbssid_idx) {
1677 			wpa_printf(MSG_DEBUG,
1678 				   "MLD: Reported link not part of MLD");
1679 		} else if (!(BIT(link_id) & *seen)) {
1680 			struct wpa_bss *neigh_bss;
1681 
1682 			if (ssid && ssid->ssid_len)
1683 				neigh_bss = wpa_bss_get(wpa_s, pos + 1,
1684 							ssid->ssid,
1685 							ssid->ssid_len);
1686 			else
1687 				neigh_bss = wpa_bss_get_bssid(wpa_s, pos + 1);
1688 
1689 			*seen |= BIT(link_id);
1690 			wpa_printf(MSG_DEBUG, "MLD: mld ID=%u, link ID=%u",
1691 				   *mld_params, link_id);
1692 
1693 			if (!neigh_bss) {
1694 				*missing |= BIT(link_id);
1695 			} else if ((!ssid ||
1696 				    wpa_scan_res_match(wpa_s, 0, neigh_bss,
1697 						       ssid, 1, 0, true)) &&
1698 				   !wpa_bssid_ignore_is_listed(
1699 					   wpa_s, neigh_bss->bssid)) {
1700 				struct mld_link *l;
1701 
1702 				bss->valid_links |= BIT(link_id);
1703 				l = &bss->mld_links[link_id];
1704 				os_memcpy(l->bssid, pos + 1, ETH_ALEN);
1705 				l->freq = neigh_bss->freq;
1706 				l->disabled = mld_params[2] &
1707 					RNR_TBTT_INFO_MLD_PARAM2_LINK_DISABLED;
1708 			}
1709 		}
1710 	}
1711 }
1712 
1713 
1714 /**
1715  * wpa_bss_parse_basic_ml_element - Parse the Basic Multi-Link element
1716  * @wpa_s: Pointer to wpa_supplicant data
1717  * @bss: BSS table entry
1718  * @mld_addr: AP MLD address (or %NULL)
1719  * @link_info: Array to store link information (or %NULL),
1720  *   should be initialized and #MAX_NUM_MLD_LINKS elements long
1721  * @missing_links: Result bitmask of links that were not discovered (or %NULL)
1722  * @ssid: Target SSID (or %NULL)
1723  * @ap_mld_id: On return would hold the corresponding AP MLD ID (or %NULL)
1724  * Returns: 0 on success or -1 for non-MLD or parsing failures
1725  *
1726  * Parses the Basic Multi-Link element of the BSS into @link_info using the scan
1727  * information stored in the wpa_supplicant data to fill in information for
1728  * links where possible. The @missing_links out parameter will contain any links
1729  * for which no corresponding BSS was found.
1730  */
wpa_bss_parse_basic_ml_element(struct wpa_supplicant * wpa_s,struct wpa_bss * bss,u8 * ap_mld_addr,u16 * missing_links,struct wpa_ssid * ssid,u8 * ap_mld_id)1731 int wpa_bss_parse_basic_ml_element(struct wpa_supplicant *wpa_s,
1732 				   struct wpa_bss *bss,
1733 				   u8 *ap_mld_addr,
1734 				   u16 *missing_links,
1735 				   struct wpa_ssid *ssid,
1736 				   u8 *ap_mld_id)
1737 {
1738 	struct ieee802_11_elems elems;
1739 	struct wpabuf *mlbuf;
1740 	const struct element *elem;
1741 	u8 mbssid_idx = 0;
1742 	size_t ml_ie_len;
1743 	const struct ieee80211_eht_ml *eht_ml;
1744 	const struct eht_ml_basic_common_info *ml_basic_common_info;
1745 	u8 i, link_id;
1746 	const u16 control_mask =
1747 		MULTI_LINK_CONTROL_TYPE_MASK |
1748 		BASIC_MULTI_LINK_CTRL_PRES_LINK_ID |
1749 		BASIC_MULTI_LINK_CTRL_PRES_BSS_PARAM_CH_COUNT |
1750 		BASIC_MULTI_LINK_CTRL_PRES_MLD_CAPA;
1751 	const u16 control =
1752 		MULTI_LINK_CONTROL_TYPE_BASIC |
1753 		BASIC_MULTI_LINK_CTRL_PRES_LINK_ID |
1754 		BASIC_MULTI_LINK_CTRL_PRES_BSS_PARAM_CH_COUNT |
1755 		BASIC_MULTI_LINK_CTRL_PRES_MLD_CAPA;
1756 	u16 missing = 0;
1757 	u16 seen;
1758 	const u8 *ies_pos = wpa_bss_ie_ptr(bss);
1759 	size_t ies_len = bss->ie_len ? bss->ie_len : bss->beacon_ie_len;
1760 	int ret = -1;
1761 	struct mld_link *l;
1762 
1763 	if (ieee802_11_parse_elems(ies_pos, ies_len, &elems, 1) ==
1764 	    ParseFailed) {
1765 		wpa_dbg(wpa_s, MSG_DEBUG, "MLD: Failed to parse elements");
1766 		return ret;
1767 	}
1768 
1769 	mlbuf = ieee802_11_defrag(elems.basic_mle, elems.basic_mle_len, true);
1770 	if (!mlbuf) {
1771 		wpa_dbg(wpa_s, MSG_DEBUG, "MLD: No Multi-Link element");
1772 		return ret;
1773 	}
1774 
1775 	ml_ie_len = wpabuf_len(mlbuf);
1776 
1777 	if (ssid) {
1778 		struct wpa_ie_data ie;
1779 		const u8 *rsne;
1780 		size_t rsne_len;
1781 
1782 		if (elems.rsne_override_2 && wpas_rsn_overriding(wpa_s, ssid)) {
1783 			rsne = elems.rsne_override_2;
1784 			rsne_len = elems.rsne_override_2_len;
1785 		} else if (elems.rsne_override &&
1786 			   wpas_rsn_overriding(wpa_s, ssid)) {
1787 			rsne = elems.rsne_override;
1788 			rsne_len = elems.rsne_override_len;
1789 		} else {
1790 			rsne = elems.rsn_ie;
1791 			rsne_len = elems.rsn_ie_len;
1792 		}
1793 		if (!rsne ||
1794 		    wpa_parse_wpa_ie(rsne - 2, 2 + rsne_len, &ie)) {
1795 			wpa_dbg(wpa_s, MSG_DEBUG, "MLD: No RSN element");
1796 			goto out;
1797 		}
1798 
1799 		if (!(ie.capabilities & WPA_CAPABILITY_MFPC) ||
1800 		    wpas_get_ssid_pmf(wpa_s, ssid) == NO_MGMT_FRAME_PROTECTION) {
1801 			wpa_dbg(wpa_s, MSG_DEBUG,
1802 				"MLD: No management frame protection");
1803 			goto out;
1804 		}
1805 
1806 		ie.key_mgmt &= ~(WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_FT_PSK |
1807 				 WPA_KEY_MGMT_PSK_SHA256);
1808 		if (!(ie.key_mgmt & ssid->key_mgmt)) {
1809 			wpa_dbg(wpa_s, MSG_DEBUG,
1810 				"MLD: No valid key management");
1811 			goto out;
1812 		}
1813 	}
1814 
1815 	/*
1816 	 * for ext ID + 2 control + common info len + MLD address +
1817 	 * link info
1818 	 */
1819 	if (ml_ie_len < 2UL + 1UL + ETH_ALEN + 1UL)
1820 		goto out;
1821 
1822 	eht_ml = (const struct ieee80211_eht_ml *) wpabuf_head(mlbuf);
1823 	if ((le_to_host16(eht_ml->ml_control) & control_mask) != control) {
1824 		wpa_printf(MSG_DEBUG,
1825 			   "MLD: Unexpected Multi-Link element control=0x%x (mask 0x%x expected 0x%x)",
1826 			   le_to_host16(eht_ml->ml_control), control_mask,
1827 			   control);
1828 		goto out;
1829 	}
1830 
1831 	ml_basic_common_info =
1832 		(const struct eht_ml_basic_common_info *) eht_ml->variable;
1833 
1834 	/* Common info length should be valid */
1835 	if (ml_basic_common_info->len < ETH_ALEN + 1UL)
1836 		goto out;
1837 
1838 	/* Get the MLD address and MLD link ID */
1839 	if (ap_mld_addr)
1840 		os_memcpy(ap_mld_addr, ml_basic_common_info->mld_addr,
1841 			  ETH_ALEN);
1842 
1843 	link_id = ml_basic_common_info->variable[0] & EHT_ML_LINK_ID_MSK;
1844 
1845 	bss->mld_link_id = link_id;
1846 	seen = bss->valid_links = BIT(link_id);
1847 
1848 	l = &bss->mld_links[link_id];
1849 	os_memcpy(l->bssid, bss->bssid, ETH_ALEN);
1850 	l->freq = bss->freq;
1851 
1852 
1853 	/*
1854 	 * The AP MLD ID in the RNR corresponds to the MBSSID index, see
1855 	 * IEEE P802.11be/D4.0, 9.4.2.169.2 (Neighbor AP Information field).
1856 	 *
1857 	 * For the transmitting BSSID it is clear that both the MBSSID index
1858 	 * and the AP MLD ID in the RNR are zero.
1859 	 *
1860 	 * For nontransmitted BSSIDs we will have a BSS generated from the
1861 	 * MBSSID element(s) using inheritance rules. Included in the elements
1862 	 * is the MBSSID Index Element. The RNR is copied from the Beacon/Probe
1863 	 * Response frame that was send by the transmitting BSSID. As such, the
1864 	 * reported AP MLD ID in the RNR will match the value in the MBSSID
1865 	 * Index Element.
1866 	 */
1867 	elem = (const struct element *)
1868 		wpa_bss_get_ie(bss, WLAN_EID_MULTIPLE_BSSID_INDEX);
1869 	if (elem && elem->datalen >= 1)
1870 		mbssid_idx = elem->data[0];
1871 
1872 	for_each_element_id(elem, WLAN_EID_REDUCED_NEIGHBOR_REPORT,
1873 			    wpa_bss_ie_ptr(bss),
1874 			    bss->ie_len ? bss->ie_len : bss->beacon_ie_len) {
1875 		const struct ieee80211_neighbor_ap_info *ap_info;
1876 		const u8 *pos = elem->data;
1877 		size_t len = elem->datalen;
1878 
1879 		/* RNR IE may contain more than one Neighbor AP Info */
1880 		while (sizeof(*ap_info) <= len) {
1881 			size_t ap_info_len = sizeof(*ap_info);
1882 			u8 count;
1883 
1884 			ap_info = (const struct ieee80211_neighbor_ap_info *)
1885 				pos;
1886 			count = RNR_TBTT_INFO_COUNT_VAL(ap_info->tbtt_info_hdr) + 1;
1887 			ap_info_len += count * ap_info->tbtt_info_len;
1888 
1889 			if (ap_info_len > len)
1890 				goto out;
1891 
1892 			wpa_bss_parse_ml_rnr_ap_info(wpa_s, bss, mbssid_idx,
1893 						     ap_info, ap_info_len,
1894 						     &seen, &missing, ssid);
1895 
1896 			pos += ap_info_len;
1897 			len -= ap_info_len;
1898 		}
1899 	}
1900 
1901 	wpa_printf(MSG_DEBUG, "MLD: valid_links=%04hx (unresolved: 0x%04hx)",
1902 		   bss->valid_links, missing);
1903 
1904 	for_each_link(bss->valid_links, i) {
1905 		wpa_printf(MSG_DEBUG, "MLD: link=%u, bssid=" MACSTR,
1906 			   i, MAC2STR(bss->mld_links[i].bssid));
1907 	}
1908 
1909 	if (missing_links)
1910 		*missing_links = missing;
1911 
1912 	if (ap_mld_id)
1913 		*ap_mld_id = mbssid_idx;
1914 
1915 	ret = 0;
1916 out:
1917 	wpabuf_free(mlbuf);
1918 	return ret;
1919 }
1920 
1921 
1922 /*
1923  * wpa_bss_parse_reconf_ml_element - Parse the Reconfiguration ML element
1924  * @wpa_s: Pointer to wpa_supplicant data
1925  * @bss: BSS table entry
1926  * Returns: The bitmap of links that are going to be removed
1927  */
wpa_bss_parse_reconf_ml_element(struct wpa_supplicant * wpa_s,struct wpa_bss * bss)1928 u16 wpa_bss_parse_reconf_ml_element(struct wpa_supplicant *wpa_s,
1929 				    struct wpa_bss *bss)
1930 {
1931 	struct ieee802_11_elems elems;
1932 	struct wpabuf *mlbuf;
1933 	const u8 *pos = wpa_bss_ie_ptr(bss);
1934 	size_t len = bss->ie_len ? bss->ie_len : bss->beacon_ie_len;
1935 	const struct ieee80211_eht_ml *ml;
1936 	const struct eht_ml_reconf_common_info *common_info;
1937 	u16 removed_links = 0;
1938 	u8 expected_ml_common_len;
1939 
1940 	if (ieee802_11_parse_elems(pos, len, &elems, 1) == ParseFailed)
1941 		return 0;
1942 
1943 	if (!elems.reconf_mle || !elems.reconf_mle_len)
1944 		return 0;
1945 
1946 	mlbuf = ieee802_11_defrag(elems.reconf_mle, elems.reconf_mle_len, true);
1947 	if (!mlbuf)
1948 		return 0;
1949 
1950 	ml = (const struct ieee80211_eht_ml *) wpabuf_head(mlbuf);
1951 	len = wpabuf_len(mlbuf);
1952 
1953 	/* There must be at least one octet for the Common Info Length subfield
1954 	 */
1955 	if (len < sizeof(*ml) + 1UL)
1956 		goto out;
1957 
1958 	expected_ml_common_len = 1;
1959 	if (le_to_host16(ml->ml_control) &
1960 	    RECONF_MULTI_LINK_CTRL_PRES_MLD_MAC_ADDR)
1961 		expected_ml_common_len += ETH_ALEN;
1962 
1963 	common_info = (const struct eht_ml_reconf_common_info *) ml->variable;
1964 	if (len < sizeof(*ml) + common_info->len) {
1965 		wpa_printf(MSG_DEBUG,
1966 			   "MLD: Unexpected Reconfiguration ML element length: (%zu < %zu)",
1967 			   len, sizeof(*ml) + common_info->len);
1968 		goto out;
1969 	}
1970 
1971 	if (common_info->len < expected_ml_common_len) {
1972 		wpa_printf(MSG_DEBUG,
1973 			   "MLD: Invalid common info len=%u; min expected=%u",
1974 			   common_info->len, expected_ml_common_len);
1975 		goto out;
1976 	}
1977 
1978 	pos = ml->variable + common_info->len;
1979 	len -= sizeof(*ml) + common_info->len;
1980 
1981 	while (len >= 2 + sizeof(struct ieee80211_eht_per_sta_profile)) {
1982 		size_t sub_elem_len = *(pos + 1);
1983 
1984 		if (2 + sub_elem_len > len) {
1985 			wpa_printf(MSG_DEBUG,
1986 				   "MLD: Invalid link info len: %zu %zu",
1987 				   2 + sub_elem_len, len);
1988 			goto out;
1989 		}
1990 
1991 		if  (*pos == EHT_ML_SUB_ELEM_PER_STA_PROFILE &&
1992 		     sub_elem_len >= 2) {
1993 			const struct ieee80211_eht_per_sta_profile *sta_prof =
1994 				(const struct ieee80211_eht_per_sta_profile *)
1995 				(pos + 2);
1996 			u16 control = le_to_host16(sta_prof->sta_control);
1997 			u8 link_id;
1998 
1999 			link_id = control & EHT_PER_STA_RECONF_CTRL_LINK_ID_MSK;
2000 			removed_links |= BIT(link_id);
2001 		}
2002 
2003 		pos += 2 + sub_elem_len;
2004 		len -= 2 + sub_elem_len;
2005 	}
2006 
2007 	wpa_printf(MSG_DEBUG, "MLD: Reconfiguration: removed_links=0x%x",
2008 		   removed_links);
2009 out:
2010 	wpabuf_free(mlbuf);
2011 	return removed_links;
2012 }
2013 
2014 
2015 #ifndef CONFIG_NO_WPA
2016 
wpa_bss_supported_cipher(struct wpa_supplicant * wpa_s,int pairwise_cipher)2017 static bool wpa_bss_supported_cipher(struct wpa_supplicant *wpa_s,
2018 				     int pairwise_cipher)
2019 {
2020 	if (!wpa_s->drv_enc)
2021 		return true;
2022 
2023 	if ((pairwise_cipher & WPA_CIPHER_CCMP) &&
2024 	    (wpa_s->drv_enc & WPA_DRIVER_CAPA_ENC_CCMP))
2025 		return true;
2026 
2027 	if ((pairwise_cipher & WPA_CIPHER_GCMP) &&
2028 	    (wpa_s->drv_enc & WPA_DRIVER_CAPA_ENC_GCMP))
2029 		return true;
2030 
2031 	if ((pairwise_cipher & WPA_CIPHER_CCMP_256) &&
2032 	    (wpa_s->drv_enc & WPA_DRIVER_CAPA_ENC_CCMP_256))
2033 		return true;
2034 
2035 	if ((pairwise_cipher & WPA_CIPHER_GCMP_256) &&
2036 	    (wpa_s->drv_enc & WPA_DRIVER_CAPA_ENC_GCMP_256))
2037 		return true;
2038 
2039 	return false;
2040 }
2041 
2042 
wpa_bss_supported_key_mgmt(struct wpa_supplicant * wpa_s,int key_mgmt)2043 static bool wpa_bss_supported_key_mgmt(struct wpa_supplicant *wpa_s,
2044 				       int key_mgmt)
2045 {
2046 	if (!wpa_s->drv_key_mgmt)
2047 		return true;
2048 
2049 	if ((key_mgmt & WPA_KEY_MGMT_IEEE8021X) &&
2050 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_WPA2))
2051 		return true;
2052 	if ((key_mgmt & WPA_KEY_MGMT_IEEE8021X_SHA256) &&
2053 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_802_1X_SHA256))
2054 		return true;
2055 	if ((key_mgmt & WPA_KEY_MGMT_FT_IEEE8021X) &&
2056 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FT))
2057 		return true;
2058 	if ((key_mgmt & WPA_KEY_MGMT_FT_IEEE8021X_SHA384) &&
2059 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FT_802_1X_SHA384))
2060 		return true;
2061 	if ((key_mgmt & WPA_KEY_MGMT_IEEE8021X_SUITE_B) &&
2062 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_SUITE_B))
2063 		return true;
2064 	if ((key_mgmt & WPA_KEY_MGMT_IEEE8021X_SUITE_B_192) &&
2065 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_SUITE_B_192))
2066 		return true;
2067 	if ((key_mgmt & WPA_KEY_MGMT_PSK) &&
2068 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_WPA2_PSK))
2069 		return true;
2070 	if ((key_mgmt & WPA_KEY_MGMT_FT_PSK) &&
2071 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FT_PSK))
2072 		return true;
2073 	if ((key_mgmt & WPA_KEY_MGMT_PSK_SHA256) &&
2074 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_PSK_SHA256))
2075 		return true;
2076 	if ((key_mgmt & WPA_KEY_MGMT_SAE) &&
2077 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_SAE))
2078 		return true;
2079 	if ((key_mgmt & WPA_KEY_MGMT_SAE_EXT_KEY) &&
2080 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_SAE_EXT_KEY))
2081 		return true;
2082 	if ((key_mgmt & WPA_KEY_MGMT_FT_SAE) &&
2083 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FT_SAE))
2084 		return true;
2085 	if ((key_mgmt & WPA_KEY_MGMT_FT_SAE_EXT_KEY) &&
2086 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FT_SAE_EXT_KEY))
2087 		return true;
2088 	if ((key_mgmt & WPA_KEY_MGMT_OWE) &&
2089 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_OWE))
2090 		return true;
2091 	if ((key_mgmt & WPA_KEY_MGMT_DPP) &&
2092 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_DPP))
2093 		return true;
2094 	if ((key_mgmt & WPA_KEY_MGMT_FILS_SHA256) &&
2095 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FILS_SHA256))
2096 		return true;
2097 	if ((key_mgmt & WPA_KEY_MGMT_FILS_SHA384) &&
2098 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FILS_SHA384))
2099 		return true;
2100 	if ((key_mgmt & WPA_KEY_MGMT_FT_FILS_SHA256) &&
2101 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FT_FILS_SHA256))
2102 		return true;
2103 	if ((key_mgmt & WPA_KEY_MGMT_FT_FILS_SHA384) &&
2104 	    (wpa_s->drv_key_mgmt & WPA_DRIVER_CAPA_KEY_MGMT_FT_FILS_SHA384))
2105 		return true;
2106 
2107 	return false;
2108 }
2109 
2110 
wpa_bss_supported_rsne(struct wpa_supplicant * wpa_s,struct wpa_ssid * ssid,const u8 * ie)2111 static bool wpa_bss_supported_rsne(struct wpa_supplicant *wpa_s,
2112 				   struct wpa_ssid *ssid, const u8 *ie)
2113 {
2114 	struct wpa_ie_data data;
2115 
2116 	if (wpa_parse_wpa_ie_rsn(ie, 2 + ie[1], &data) < 0)
2117 		return false;
2118 
2119 	/* Check that there is a supported AKM and pairwise cipher based on
2120 	 * overall capabilities */
2121 	if (!data.pairwise_cipher || !data.key_mgmt)
2122 		return false;
2123 
2124 	if (wpa_s->drv_capa_known) {
2125 		if (!wpa_bss_supported_cipher(wpa_s, data.pairwise_cipher) ||
2126 		    !wpa_bss_supported_key_mgmt(wpa_s, data.key_mgmt))
2127 			return false;
2128 	}
2129 
2130 	if (ssid) {
2131 		/* Check that there is a supported AKM and pairwise cipher
2132 		 * based on the specific network profile. */
2133 		if ((ssid->pairwise_cipher & data.pairwise_cipher) == 0)
2134 			return false;
2135 		if ((ssid->key_mgmt & data.key_mgmt) == 0)
2136 			return false;
2137 	}
2138 
2139 	return true;
2140 }
2141 
2142 #endif /* CONFIG_NO_WPA */
2143 
2144 
wpa_bss_get_rsne(struct wpa_supplicant * wpa_s,const struct wpa_bss * bss,struct wpa_ssid * ssid,bool mlo)2145 const u8 * wpa_bss_get_rsne(struct wpa_supplicant *wpa_s,
2146 			    const struct wpa_bss *bss, struct wpa_ssid *ssid,
2147 			    bool mlo)
2148 {
2149 #ifndef CONFIG_NO_WPA
2150 	const u8 *ie;
2151 
2152 	if (wpas_rsn_overriding(wpa_s, ssid)) {
2153 		if (!ssid)
2154 			ssid = wpa_s->current_ssid;
2155 
2156 		/* MLO cases for RSN overriding are required to use RSNE
2157 		 * Override 2 element and RSNXE Override element together. */
2158 		ie = wpa_bss_get_vendor_ie(bss, RSNE_OVERRIDE_2_IE_VENDOR_TYPE);
2159 		if (mlo && ie &&
2160 		    !wpa_bss_get_vendor_ie(bss,
2161 					   RSNXE_OVERRIDE_IE_VENDOR_TYPE)) {
2162 			wpa_printf(MSG_DEBUG, "BSS " MACSTR
2163 				   " advertises RSNE Override 2 element without RSNXE Override element - ignore RSNE Override 2 element for MLO",
2164 				   MAC2STR(bss->bssid));
2165 		} else if (ie && wpa_bss_supported_rsne(wpa_s, ssid, ie)) {
2166 			return ie;
2167 		}
2168 
2169 		if (!mlo) {
2170 			ie = wpa_bss_get_vendor_ie(
2171 				bss, RSNE_OVERRIDE_IE_VENDOR_TYPE);
2172 			if (ie && wpa_bss_supported_rsne(wpa_s, ssid, ie))
2173 				return ie;
2174 		}
2175 	}
2176 #endif /* CONFIG_NO_WPA */
2177 
2178 	return wpa_bss_get_ie(bss, WLAN_EID_RSN);
2179 }
2180 
2181 
wpa_bss_get_rsnxe(struct wpa_supplicant * wpa_s,const struct wpa_bss * bss,struct wpa_ssid * ssid,bool mlo)2182 const u8 * wpa_bss_get_rsnxe(struct wpa_supplicant *wpa_s,
2183 			     const struct wpa_bss *bss, struct wpa_ssid *ssid,
2184 			     bool mlo)
2185 {
2186 	const u8 *ie;
2187 
2188 	if (wpas_rsn_overriding(wpa_s, ssid)) {
2189 		ie = wpa_bss_get_vendor_ie(bss, RSNXE_OVERRIDE_IE_VENDOR_TYPE);
2190 		if (ie) {
2191 			const u8 *tmp;
2192 
2193 			tmp = wpa_bss_get_rsne(wpa_s, bss, ssid, mlo);
2194 			if (!tmp || tmp[0] == WLAN_EID_RSN) {
2195 				/* An acceptable RSNE override element was not
2196 				 * found, so need to ignore RSNXE overriding. */
2197 				goto out;
2198 			}
2199 
2200 			return ie;
2201 		}
2202 
2203 		/* MLO cases for RSN overriding are required to use RSNE
2204 		 * Override 2 element and RSNXE Override element together. */
2205 		if (mlo && wpa_bss_get_vendor_ie(
2206 			    bss, RSNE_OVERRIDE_2_IE_VENDOR_TYPE)) {
2207 			wpa_printf(MSG_DEBUG, "BSS " MACSTR
2208 				   " advertises RSNXE Override element without RSNE Override 2 element - ignore RSNXE Override element for MLO",
2209 				   MAC2STR(bss->bssid));
2210 			goto out;
2211 		}
2212 	}
2213 
2214 out:
2215 	return wpa_bss_get_ie(bss, WLAN_EID_RSNX);
2216 }
2217