1
2
3
4
5
6
7
8
9
10
11
12
13
14#include <net/mac80211.h>
15#include <linux/netdevice.h>
16#include <linux/export.h>
17#include <linux/types.h>
18#include <linux/slab.h>
19#include <linux/skbuff.h>
20#include <linux/etherdevice.h>
21#include <linux/if_arp.h>
22#include <linux/bitmap.h>
23#include <linux/crc32.h>
24#include <net/net_namespace.h>
25#include <net/cfg80211.h>
26#include <net/rtnetlink.h>
27
28#include "ieee80211_i.h"
29#include "driver-ops.h"
30#include "rate.h"
31#include "mesh.h"
32#include "wme.h"
33#include "led.h"
34#include "wep.h"
35
36
37const void *const mac80211_wiphy_privid = &mac80211_wiphy_privid;
38
39struct ieee80211_hw *wiphy_to_ieee80211_hw(struct wiphy *wiphy)
40{
41 struct ieee80211_local *local;
42
43 local = wiphy_priv(wiphy);
44 return &local->hw;
45}
46EXPORT_SYMBOL(wiphy_to_ieee80211_hw);
47
48u8 *ieee80211_get_bssid(struct ieee80211_hdr *hdr, size_t len,
49 enum nl80211_iftype type)
50{
51 __le16 fc = hdr->frame_control;
52
53 if (ieee80211_is_data(fc)) {
54 if (len < 24)
55 return NULL;
56
57 if (ieee80211_has_a4(fc))
58 return NULL;
59 if (ieee80211_has_tods(fc))
60 return hdr->addr1;
61 if (ieee80211_has_fromds(fc))
62 return hdr->addr2;
63
64 return hdr->addr3;
65 }
66
67 if (ieee80211_is_s1g_beacon(fc)) {
68 struct ieee80211_ext *ext = (void *) hdr;
69
70 return ext->u.s1g_beacon.sa;
71 }
72
73 if (ieee80211_is_mgmt(fc)) {
74 if (len < 24)
75 return NULL;
76 return hdr->addr3;
77 }
78
79 if (ieee80211_is_ctl(fc)) {
80 if (ieee80211_is_pspoll(fc))
81 return hdr->addr1;
82
83 if (ieee80211_is_back_req(fc)) {
84 switch (type) {
85 case NL80211_IFTYPE_STATION:
86 return hdr->addr2;
87 case NL80211_IFTYPE_AP:
88 case NL80211_IFTYPE_AP_VLAN:
89 return hdr->addr1;
90 default:
91 break;
92 }
93 }
94 }
95
96 return NULL;
97}
98EXPORT_SYMBOL(ieee80211_get_bssid);
99
100void ieee80211_tx_set_protected(struct ieee80211_tx_data *tx)
101{
102 struct sk_buff *skb;
103 struct ieee80211_hdr *hdr;
104
105 skb_queue_walk(&tx->skbs, skb) {
106 hdr = (struct ieee80211_hdr *) skb->data;
107 hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED);
108 }
109}
110
111int ieee80211_frame_duration(enum nl80211_band band, size_t len,
112 int rate, int erp, int short_preamble,
113 int shift)
114{
115 int dur;
116
117
118
119
120
121
122
123
124
125
126
127
128
129 if (band == NL80211_BAND_5GHZ || erp) {
130
131
132
133
134
135
136
137
138
139
140
141
142
143 dur = 16;
144 dur += 16;
145 dur += 4;
146
147
148
149
150
151 dur *= 1 << shift;
152
153
154
155
156 dur += 4 * DIV_ROUND_UP((16 + 8 * (len + 4) + 6) * 10,
157 4 * rate);
158 } else {
159
160
161
162
163
164
165
166
167
168
169 dur = 10;
170 dur += short_preamble ? (72 + 24) : (144 + 48);
171
172 dur += DIV_ROUND_UP(8 * (len + 4) * 10, rate);
173 }
174
175 return dur;
176}
177
178
179__le16 ieee80211_generic_frame_duration(struct ieee80211_hw *hw,
180 struct ieee80211_vif *vif,
181 enum nl80211_band band,
182 size_t frame_len,
183 struct ieee80211_rate *rate)
184{
185 struct ieee80211_sub_if_data *sdata;
186 u16 dur;
187 int erp, shift = 0;
188 bool short_preamble = false;
189
190 erp = 0;
191 if (vif) {
192 sdata = vif_to_sdata(vif);
193 short_preamble = sdata->vif.bss_conf.use_short_preamble;
194 if (sdata->flags & IEEE80211_SDATA_OPERATING_GMODE)
195 erp = rate->flags & IEEE80211_RATE_ERP_G;
196 shift = ieee80211_vif_get_shift(vif);
197 }
198
199 dur = ieee80211_frame_duration(band, frame_len, rate->bitrate, erp,
200 short_preamble, shift);
201
202 return cpu_to_le16(dur);
203}
204EXPORT_SYMBOL(ieee80211_generic_frame_duration);
205
206__le16 ieee80211_rts_duration(struct ieee80211_hw *hw,
207 struct ieee80211_vif *vif, size_t frame_len,
208 const struct ieee80211_tx_info *frame_txctl)
209{
210 struct ieee80211_local *local = hw_to_local(hw);
211 struct ieee80211_rate *rate;
212 struct ieee80211_sub_if_data *sdata;
213 bool short_preamble;
214 int erp, shift = 0, bitrate;
215 u16 dur;
216 struct ieee80211_supported_band *sband;
217
218 sband = local->hw.wiphy->bands[frame_txctl->band];
219
220 short_preamble = false;
221
222 rate = &sband->bitrates[frame_txctl->control.rts_cts_rate_idx];
223
224 erp = 0;
225 if (vif) {
226 sdata = vif_to_sdata(vif);
227 short_preamble = sdata->vif.bss_conf.use_short_preamble;
228 if (sdata->flags & IEEE80211_SDATA_OPERATING_GMODE)
229 erp = rate->flags & IEEE80211_RATE_ERP_G;
230 shift = ieee80211_vif_get_shift(vif);
231 }
232
233 bitrate = DIV_ROUND_UP(rate->bitrate, 1 << shift);
234
235
236 dur = ieee80211_frame_duration(sband->band, 10, bitrate,
237 erp, short_preamble, shift);
238
239 dur += ieee80211_frame_duration(sband->band, frame_len, bitrate,
240 erp, short_preamble, shift);
241
242 dur += ieee80211_frame_duration(sband->band, 10, bitrate,
243 erp, short_preamble, shift);
244
245 return cpu_to_le16(dur);
246}
247EXPORT_SYMBOL(ieee80211_rts_duration);
248
249__le16 ieee80211_ctstoself_duration(struct ieee80211_hw *hw,
250 struct ieee80211_vif *vif,
251 size_t frame_len,
252 const struct ieee80211_tx_info *frame_txctl)
253{
254 struct ieee80211_local *local = hw_to_local(hw);
255 struct ieee80211_rate *rate;
256 struct ieee80211_sub_if_data *sdata;
257 bool short_preamble;
258 int erp, shift = 0, bitrate;
259 u16 dur;
260 struct ieee80211_supported_band *sband;
261
262 sband = local->hw.wiphy->bands[frame_txctl->band];
263
264 short_preamble = false;
265
266 rate = &sband->bitrates[frame_txctl->control.rts_cts_rate_idx];
267 erp = 0;
268 if (vif) {
269 sdata = vif_to_sdata(vif);
270 short_preamble = sdata->vif.bss_conf.use_short_preamble;
271 if (sdata->flags & IEEE80211_SDATA_OPERATING_GMODE)
272 erp = rate->flags & IEEE80211_RATE_ERP_G;
273 shift = ieee80211_vif_get_shift(vif);
274 }
275
276 bitrate = DIV_ROUND_UP(rate->bitrate, 1 << shift);
277
278
279 dur = ieee80211_frame_duration(sband->band, frame_len, bitrate,
280 erp, short_preamble, shift);
281 if (!(frame_txctl->flags & IEEE80211_TX_CTL_NO_ACK)) {
282
283 dur += ieee80211_frame_duration(sband->band, 10, bitrate,
284 erp, short_preamble, shift);
285 }
286
287 return cpu_to_le16(dur);
288}
289EXPORT_SYMBOL(ieee80211_ctstoself_duration);
290
291static void __ieee80211_wake_txqs(struct ieee80211_sub_if_data *sdata, int ac)
292{
293 struct ieee80211_local *local = sdata->local;
294 struct ieee80211_vif *vif = &sdata->vif;
295 struct fq *fq = &local->fq;
296 struct ps_data *ps = NULL;
297 struct txq_info *txqi;
298 struct sta_info *sta;
299 int i;
300
301 local_bh_disable();
302 spin_lock(&fq->lock);
303
304 if (sdata->vif.type == NL80211_IFTYPE_AP)
305 ps = &sdata->bss->ps;
306
307 sdata->vif.txqs_stopped[ac] = false;
308
309 list_for_each_entry_rcu(sta, &local->sta_list, list) {
310 if (sdata != sta->sdata)
311 continue;
312
313 for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) {
314 struct ieee80211_txq *txq = sta->sta.txq[i];
315
316 if (!txq)
317 continue;
318
319 txqi = to_txq_info(txq);
320
321 if (ac != txq->ac)
322 continue;
323
324 if (!test_and_clear_bit(IEEE80211_TXQ_STOP_NETIF_TX,
325 &txqi->flags))
326 continue;
327
328 spin_unlock(&fq->lock);
329 drv_wake_tx_queue(local, txqi);
330 spin_lock(&fq->lock);
331 }
332 }
333
334 if (!vif->txq)
335 goto out;
336
337 txqi = to_txq_info(vif->txq);
338
339 if (!test_and_clear_bit(IEEE80211_TXQ_STOP_NETIF_TX, &txqi->flags) ||
340 (ps && atomic_read(&ps->num_sta_ps)) || ac != vif->txq->ac)
341 goto out;
342
343 spin_unlock(&fq->lock);
344
345 drv_wake_tx_queue(local, txqi);
346 local_bh_enable();
347 return;
348out:
349 spin_unlock(&fq->lock);
350 local_bh_enable();
351}
352
353static void
354__releases(&local->queue_stop_reason_lock)
355__acquires(&local->queue_stop_reason_lock)
356_ieee80211_wake_txqs(struct ieee80211_local *local, unsigned long *flags)
357{
358 struct ieee80211_sub_if_data *sdata;
359 int n_acs = IEEE80211_NUM_ACS;
360 int i;
361
362 rcu_read_lock();
363
364 if (local->hw.queues < IEEE80211_NUM_ACS)
365 n_acs = 1;
366
367 for (i = 0; i < local->hw.queues; i++) {
368 if (local->queue_stop_reasons[i])
369 continue;
370
371 spin_unlock_irqrestore(&local->queue_stop_reason_lock, *flags);
372 list_for_each_entry_rcu(sdata, &local->interfaces, list) {
373 int ac;
374
375 for (ac = 0; ac < n_acs; ac++) {
376 int ac_queue = sdata->vif.hw_queue[ac];
377
378 if (ac_queue == i ||
379 sdata->vif.cab_queue == i)
380 __ieee80211_wake_txqs(sdata, ac);
381 }
382 }
383 spin_lock_irqsave(&local->queue_stop_reason_lock, *flags);
384 }
385
386 rcu_read_unlock();
387}
388
389void ieee80211_wake_txqs(struct tasklet_struct *t)
390{
391 struct ieee80211_local *local = from_tasklet(local, t,
392 wake_txqs_tasklet);
393 unsigned long flags;
394
395 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
396 _ieee80211_wake_txqs(local, &flags);
397 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
398}
399
400void ieee80211_propagate_queue_wake(struct ieee80211_local *local, int queue)
401{
402 struct ieee80211_sub_if_data *sdata;
403 int n_acs = IEEE80211_NUM_ACS;
404
405 if (local->ops->wake_tx_queue)
406 return;
407
408 if (local->hw.queues < IEEE80211_NUM_ACS)
409 n_acs = 1;
410
411 list_for_each_entry_rcu(sdata, &local->interfaces, list) {
412 int ac;
413
414 if (!sdata->dev)
415 continue;
416
417 if (sdata->vif.cab_queue != IEEE80211_INVAL_HW_QUEUE &&
418 local->queue_stop_reasons[sdata->vif.cab_queue] != 0)
419 continue;
420
421 for (ac = 0; ac < n_acs; ac++) {
422 int ac_queue = sdata->vif.hw_queue[ac];
423
424 if (ac_queue == queue ||
425 (sdata->vif.cab_queue == queue &&
426 local->queue_stop_reasons[ac_queue] == 0 &&
427 skb_queue_empty(&local->pending[ac_queue])))
428 netif_wake_subqueue(sdata->dev, ac);
429 }
430 }
431}
432
433static void __ieee80211_wake_queue(struct ieee80211_hw *hw, int queue,
434 enum queue_stop_reason reason,
435 bool refcounted,
436 unsigned long *flags)
437{
438 struct ieee80211_local *local = hw_to_local(hw);
439
440 trace_wake_queue(local, queue, reason);
441
442 if (WARN_ON(queue >= hw->queues))
443 return;
444
445 if (!test_bit(reason, &local->queue_stop_reasons[queue]))
446 return;
447
448 if (!refcounted) {
449 local->q_stop_reasons[queue][reason] = 0;
450 } else {
451 local->q_stop_reasons[queue][reason]--;
452 if (WARN_ON(local->q_stop_reasons[queue][reason] < 0))
453 local->q_stop_reasons[queue][reason] = 0;
454 }
455
456 if (local->q_stop_reasons[queue][reason] == 0)
457 __clear_bit(reason, &local->queue_stop_reasons[queue]);
458
459 if (local->queue_stop_reasons[queue] != 0)
460
461 return;
462
463 if (skb_queue_empty(&local->pending[queue])) {
464 rcu_read_lock();
465 ieee80211_propagate_queue_wake(local, queue);
466 rcu_read_unlock();
467 } else
468 tasklet_schedule(&local->tx_pending_tasklet);
469
470
471
472
473
474
475
476
477 if (local->ops->wake_tx_queue) {
478 if (reason == IEEE80211_QUEUE_STOP_REASON_DRIVER)
479 tasklet_schedule(&local->wake_txqs_tasklet);
480 else
481 _ieee80211_wake_txqs(local, flags);
482 }
483}
484
485void ieee80211_wake_queue_by_reason(struct ieee80211_hw *hw, int queue,
486 enum queue_stop_reason reason,
487 bool refcounted)
488{
489 struct ieee80211_local *local = hw_to_local(hw);
490 unsigned long flags;
491
492 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
493 __ieee80211_wake_queue(hw, queue, reason, refcounted, &flags);
494 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
495}
496
497void ieee80211_wake_queue(struct ieee80211_hw *hw, int queue)
498{
499 ieee80211_wake_queue_by_reason(hw, queue,
500 IEEE80211_QUEUE_STOP_REASON_DRIVER,
501 false);
502}
503EXPORT_SYMBOL(ieee80211_wake_queue);
504
505static void __ieee80211_stop_queue(struct ieee80211_hw *hw, int queue,
506 enum queue_stop_reason reason,
507 bool refcounted)
508{
509 struct ieee80211_local *local = hw_to_local(hw);
510 struct ieee80211_sub_if_data *sdata;
511 int n_acs = IEEE80211_NUM_ACS;
512
513 trace_stop_queue(local, queue, reason);
514
515 if (WARN_ON(queue >= hw->queues))
516 return;
517
518 if (!refcounted)
519 local->q_stop_reasons[queue][reason] = 1;
520 else
521 local->q_stop_reasons[queue][reason]++;
522
523 if (__test_and_set_bit(reason, &local->queue_stop_reasons[queue]))
524 return;
525
526 if (local->hw.queues < IEEE80211_NUM_ACS)
527 n_acs = 1;
528
529 rcu_read_lock();
530 list_for_each_entry_rcu(sdata, &local->interfaces, list) {
531 int ac;
532
533 if (!sdata->dev)
534 continue;
535
536 for (ac = 0; ac < n_acs; ac++) {
537 if (sdata->vif.hw_queue[ac] == queue ||
538 sdata->vif.cab_queue == queue) {
539 if (!local->ops->wake_tx_queue) {
540 netif_stop_subqueue(sdata->dev, ac);
541 continue;
542 }
543 spin_lock(&local->fq.lock);
544 sdata->vif.txqs_stopped[ac] = true;
545 spin_unlock(&local->fq.lock);
546 }
547 }
548 }
549 rcu_read_unlock();
550}
551
552void ieee80211_stop_queue_by_reason(struct ieee80211_hw *hw, int queue,
553 enum queue_stop_reason reason,
554 bool refcounted)
555{
556 struct ieee80211_local *local = hw_to_local(hw);
557 unsigned long flags;
558
559 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
560 __ieee80211_stop_queue(hw, queue, reason, refcounted);
561 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
562}
563
564void ieee80211_stop_queue(struct ieee80211_hw *hw, int queue)
565{
566 ieee80211_stop_queue_by_reason(hw, queue,
567 IEEE80211_QUEUE_STOP_REASON_DRIVER,
568 false);
569}
570EXPORT_SYMBOL(ieee80211_stop_queue);
571
572void ieee80211_add_pending_skb(struct ieee80211_local *local,
573 struct sk_buff *skb)
574{
575 struct ieee80211_hw *hw = &local->hw;
576 unsigned long flags;
577 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
578 int queue = info->hw_queue;
579
580 if (WARN_ON(!info->control.vif)) {
581 ieee80211_free_txskb(&local->hw, skb);
582 return;
583 }
584
585 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
586 __ieee80211_stop_queue(hw, queue, IEEE80211_QUEUE_STOP_REASON_SKB_ADD,
587 false);
588 __skb_queue_tail(&local->pending[queue], skb);
589 __ieee80211_wake_queue(hw, queue, IEEE80211_QUEUE_STOP_REASON_SKB_ADD,
590 false, &flags);
591 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
592}
593
594void ieee80211_add_pending_skbs(struct ieee80211_local *local,
595 struct sk_buff_head *skbs)
596{
597 struct ieee80211_hw *hw = &local->hw;
598 struct sk_buff *skb;
599 unsigned long flags;
600 int queue, i;
601
602 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
603 while ((skb = skb_dequeue(skbs))) {
604 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
605
606 if (WARN_ON(!info->control.vif)) {
607 ieee80211_free_txskb(&local->hw, skb);
608 continue;
609 }
610
611 queue = info->hw_queue;
612
613 __ieee80211_stop_queue(hw, queue,
614 IEEE80211_QUEUE_STOP_REASON_SKB_ADD,
615 false);
616
617 __skb_queue_tail(&local->pending[queue], skb);
618 }
619
620 for (i = 0; i < hw->queues; i++)
621 __ieee80211_wake_queue(hw, i,
622 IEEE80211_QUEUE_STOP_REASON_SKB_ADD,
623 false, &flags);
624 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
625}
626
627void ieee80211_stop_queues_by_reason(struct ieee80211_hw *hw,
628 unsigned long queues,
629 enum queue_stop_reason reason,
630 bool refcounted)
631{
632 struct ieee80211_local *local = hw_to_local(hw);
633 unsigned long flags;
634 int i;
635
636 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
637
638 for_each_set_bit(i, &queues, hw->queues)
639 __ieee80211_stop_queue(hw, i, reason, refcounted);
640
641 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
642}
643
644void ieee80211_stop_queues(struct ieee80211_hw *hw)
645{
646 ieee80211_stop_queues_by_reason(hw, IEEE80211_MAX_QUEUE_MAP,
647 IEEE80211_QUEUE_STOP_REASON_DRIVER,
648 false);
649}
650EXPORT_SYMBOL(ieee80211_stop_queues);
651
652int ieee80211_queue_stopped(struct ieee80211_hw *hw, int queue)
653{
654 struct ieee80211_local *local = hw_to_local(hw);
655 unsigned long flags;
656 int ret;
657
658 if (WARN_ON(queue >= hw->queues))
659 return true;
660
661 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
662 ret = test_bit(IEEE80211_QUEUE_STOP_REASON_DRIVER,
663 &local->queue_stop_reasons[queue]);
664 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
665 return ret;
666}
667EXPORT_SYMBOL(ieee80211_queue_stopped);
668
669void ieee80211_wake_queues_by_reason(struct ieee80211_hw *hw,
670 unsigned long queues,
671 enum queue_stop_reason reason,
672 bool refcounted)
673{
674 struct ieee80211_local *local = hw_to_local(hw);
675 unsigned long flags;
676 int i;
677
678 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
679
680 for_each_set_bit(i, &queues, hw->queues)
681 __ieee80211_wake_queue(hw, i, reason, refcounted, &flags);
682
683 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
684}
685
686void ieee80211_wake_queues(struct ieee80211_hw *hw)
687{
688 ieee80211_wake_queues_by_reason(hw, IEEE80211_MAX_QUEUE_MAP,
689 IEEE80211_QUEUE_STOP_REASON_DRIVER,
690 false);
691}
692EXPORT_SYMBOL(ieee80211_wake_queues);
693
694static unsigned int
695ieee80211_get_vif_queues(struct ieee80211_local *local,
696 struct ieee80211_sub_if_data *sdata)
697{
698 unsigned int queues;
699
700 if (sdata && ieee80211_hw_check(&local->hw, QUEUE_CONTROL)) {
701 int ac;
702
703 queues = 0;
704
705 for (ac = 0; ac < IEEE80211_NUM_ACS; ac++)
706 queues |= BIT(sdata->vif.hw_queue[ac]);
707 if (sdata->vif.cab_queue != IEEE80211_INVAL_HW_QUEUE)
708 queues |= BIT(sdata->vif.cab_queue);
709 } else {
710
711 queues = BIT(local->hw.queues) - 1;
712 }
713
714 return queues;
715}
716
717void __ieee80211_flush_queues(struct ieee80211_local *local,
718 struct ieee80211_sub_if_data *sdata,
719 unsigned int queues, bool drop)
720{
721 if (!local->ops->flush)
722 return;
723
724
725
726
727
728 if (!queues || !ieee80211_hw_check(&local->hw, QUEUE_CONTROL))
729 queues = ieee80211_get_vif_queues(local, sdata);
730
731 ieee80211_stop_queues_by_reason(&local->hw, queues,
732 IEEE80211_QUEUE_STOP_REASON_FLUSH,
733 false);
734
735 drv_flush(local, sdata, queues, drop);
736
737 ieee80211_wake_queues_by_reason(&local->hw, queues,
738 IEEE80211_QUEUE_STOP_REASON_FLUSH,
739 false);
740}
741
742void ieee80211_flush_queues(struct ieee80211_local *local,
743 struct ieee80211_sub_if_data *sdata, bool drop)
744{
745 __ieee80211_flush_queues(local, sdata, 0, drop);
746}
747
748void ieee80211_stop_vif_queues(struct ieee80211_local *local,
749 struct ieee80211_sub_if_data *sdata,
750 enum queue_stop_reason reason)
751{
752 ieee80211_stop_queues_by_reason(&local->hw,
753 ieee80211_get_vif_queues(local, sdata),
754 reason, true);
755}
756
757void ieee80211_wake_vif_queues(struct ieee80211_local *local,
758 struct ieee80211_sub_if_data *sdata,
759 enum queue_stop_reason reason)
760{
761 ieee80211_wake_queues_by_reason(&local->hw,
762 ieee80211_get_vif_queues(local, sdata),
763 reason, true);
764}
765
766static void __iterate_interfaces(struct ieee80211_local *local,
767 u32 iter_flags,
768 void (*iterator)(void *data, u8 *mac,
769 struct ieee80211_vif *vif),
770 void *data)
771{
772 struct ieee80211_sub_if_data *sdata;
773 bool active_only = iter_flags & IEEE80211_IFACE_ITER_ACTIVE;
774
775 list_for_each_entry_rcu(sdata, &local->interfaces, list) {
776 switch (sdata->vif.type) {
777 case NL80211_IFTYPE_MONITOR:
778 if (!(sdata->u.mntr.flags & MONITOR_FLAG_ACTIVE))
779 continue;
780 break;
781 case NL80211_IFTYPE_AP_VLAN:
782 continue;
783 default:
784 break;
785 }
786 if (!(iter_flags & IEEE80211_IFACE_ITER_RESUME_ALL) &&
787 active_only && !(sdata->flags & IEEE80211_SDATA_IN_DRIVER))
788 continue;
789 if ((iter_flags & IEEE80211_IFACE_SKIP_SDATA_NOT_IN_DRIVER) &&
790 !(sdata->flags & IEEE80211_SDATA_IN_DRIVER))
791 continue;
792 if (ieee80211_sdata_running(sdata) || !active_only)
793 iterator(data, sdata->vif.addr,
794 &sdata->vif);
795 }
796
797 sdata = rcu_dereference_check(local->monitor_sdata,
798 lockdep_is_held(&local->iflist_mtx) ||
799 lockdep_is_held(&local->hw.wiphy->mtx));
800 if (sdata &&
801 (iter_flags & IEEE80211_IFACE_ITER_RESUME_ALL || !active_only ||
802 sdata->flags & IEEE80211_SDATA_IN_DRIVER))
803 iterator(data, sdata->vif.addr, &sdata->vif);
804}
805
806void ieee80211_iterate_interfaces(
807 struct ieee80211_hw *hw, u32 iter_flags,
808 void (*iterator)(void *data, u8 *mac,
809 struct ieee80211_vif *vif),
810 void *data)
811{
812 struct ieee80211_local *local = hw_to_local(hw);
813
814 mutex_lock(&local->iflist_mtx);
815 __iterate_interfaces(local, iter_flags, iterator, data);
816 mutex_unlock(&local->iflist_mtx);
817}
818EXPORT_SYMBOL_GPL(ieee80211_iterate_interfaces);
819
820void ieee80211_iterate_active_interfaces_atomic(
821 struct ieee80211_hw *hw, u32 iter_flags,
822 void (*iterator)(void *data, u8 *mac,
823 struct ieee80211_vif *vif),
824 void *data)
825{
826 struct ieee80211_local *local = hw_to_local(hw);
827
828 rcu_read_lock();
829 __iterate_interfaces(local, iter_flags | IEEE80211_IFACE_ITER_ACTIVE,
830 iterator, data);
831 rcu_read_unlock();
832}
833EXPORT_SYMBOL_GPL(ieee80211_iterate_active_interfaces_atomic);
834
835void ieee80211_iterate_active_interfaces_mtx(
836 struct ieee80211_hw *hw, u32 iter_flags,
837 void (*iterator)(void *data, u8 *mac,
838 struct ieee80211_vif *vif),
839 void *data)
840{
841 struct ieee80211_local *local = hw_to_local(hw);
842
843 lockdep_assert_wiphy(hw->wiphy);
844
845 __iterate_interfaces(local, iter_flags | IEEE80211_IFACE_ITER_ACTIVE,
846 iterator, data);
847}
848EXPORT_SYMBOL_GPL(ieee80211_iterate_active_interfaces_mtx);
849
850static void __iterate_stations(struct ieee80211_local *local,
851 void (*iterator)(void *data,
852 struct ieee80211_sta *sta),
853 void *data)
854{
855 struct sta_info *sta;
856
857 list_for_each_entry_rcu(sta, &local->sta_list, list) {
858 if (!sta->uploaded)
859 continue;
860
861 iterator(data, &sta->sta);
862 }
863}
864
865void ieee80211_iterate_stations(struct ieee80211_hw *hw,
866 void (*iterator)(void *data,
867 struct ieee80211_sta *sta),
868 void *data)
869{
870 struct ieee80211_local *local = hw_to_local(hw);
871
872 mutex_lock(&local->sta_mtx);
873 __iterate_stations(local, iterator, data);
874 mutex_unlock(&local->sta_mtx);
875}
876EXPORT_SYMBOL_GPL(ieee80211_iterate_stations);
877
878void ieee80211_iterate_stations_atomic(struct ieee80211_hw *hw,
879 void (*iterator)(void *data,
880 struct ieee80211_sta *sta),
881 void *data)
882{
883 struct ieee80211_local *local = hw_to_local(hw);
884
885 rcu_read_lock();
886 __iterate_stations(local, iterator, data);
887 rcu_read_unlock();
888}
889EXPORT_SYMBOL_GPL(ieee80211_iterate_stations_atomic);
890
891struct ieee80211_vif *wdev_to_ieee80211_vif(struct wireless_dev *wdev)
892{
893 struct ieee80211_sub_if_data *sdata = IEEE80211_WDEV_TO_SUB_IF(wdev);
894
895 if (!ieee80211_sdata_running(sdata) ||
896 !(sdata->flags & IEEE80211_SDATA_IN_DRIVER))
897 return NULL;
898 return &sdata->vif;
899}
900EXPORT_SYMBOL_GPL(wdev_to_ieee80211_vif);
901
902struct wireless_dev *ieee80211_vif_to_wdev(struct ieee80211_vif *vif)
903{
904 if (!vif)
905 return NULL;
906
907 return &vif_to_sdata(vif)->wdev;
908}
909EXPORT_SYMBOL_GPL(ieee80211_vif_to_wdev);
910
911
912
913
914
915
916
917
918
919
920static bool ieee80211_can_queue_work(struct ieee80211_local *local)
921{
922 if (local->quiescing || (local->suspended && !local->resuming)) {
923 pr_warn("queueing ieee80211 work while going to suspend\n");
924 return false;
925 }
926
927 return true;
928}
929
930void ieee80211_queue_work(struct ieee80211_hw *hw, struct work_struct *work)
931{
932 struct ieee80211_local *local = hw_to_local(hw);
933
934 if (!ieee80211_can_queue_work(local))
935 return;
936
937 queue_work(local->workqueue, work);
938}
939EXPORT_SYMBOL(ieee80211_queue_work);
940
941void ieee80211_queue_delayed_work(struct ieee80211_hw *hw,
942 struct delayed_work *dwork,
943 unsigned long delay)
944{
945 struct ieee80211_local *local = hw_to_local(hw);
946
947 if (!ieee80211_can_queue_work(local))
948 return;
949
950 queue_delayed_work(local->workqueue, dwork, delay);
951}
952EXPORT_SYMBOL(ieee80211_queue_delayed_work);
953
954static void ieee80211_parse_extension_element(u32 *crc,
955 const struct element *elem,
956 struct ieee802_11_elems *elems)
957{
958 const void *data = elem->data + 1;
959 u8 len;
960
961 if (!elem->datalen)
962 return;
963
964 len = elem->datalen - 1;
965
966 switch (elem->data[0]) {
967 case WLAN_EID_EXT_HE_MU_EDCA:
968 if (len >= sizeof(*elems->mu_edca_param_set)) {
969 elems->mu_edca_param_set = data;
970 if (crc)
971 *crc = crc32_be(*crc, (void *)elem,
972 elem->datalen + 2);
973 }
974 break;
975 case WLAN_EID_EXT_HE_CAPABILITY:
976 if (ieee80211_he_capa_size_ok(data, len)) {
977 elems->he_cap = data;
978 elems->he_cap_len = len;
979 }
980 break;
981 case WLAN_EID_EXT_HE_OPERATION:
982 if (len >= sizeof(*elems->he_operation) &&
983 len >= ieee80211_he_oper_size(data) - 1) {
984 if (crc)
985 *crc = crc32_be(*crc, (void *)elem,
986 elem->datalen + 2);
987 elems->he_operation = data;
988 }
989 break;
990 case WLAN_EID_EXT_UORA:
991 if (len >= 1)
992 elems->uora_element = data;
993 break;
994 case WLAN_EID_EXT_MAX_CHANNEL_SWITCH_TIME:
995 if (len == 3)
996 elems->max_channel_switch_time = data;
997 break;
998 case WLAN_EID_EXT_MULTIPLE_BSSID_CONFIGURATION:
999 if (len >= sizeof(*elems->mbssid_config_ie))
1000 elems->mbssid_config_ie = data;
1001 break;
1002 case WLAN_EID_EXT_HE_SPR:
1003 if (len >= sizeof(*elems->he_spr) &&
1004 len >= ieee80211_he_spr_size(data))
1005 elems->he_spr = data;
1006 break;
1007 case WLAN_EID_EXT_HE_6GHZ_CAPA:
1008 if (len >= sizeof(*elems->he_6ghz_capa))
1009 elems->he_6ghz_capa = data;
1010 break;
1011 case WLAN_EID_EXT_EHT_CAPABILITY:
1012 if (ieee80211_eht_capa_size_ok(elems->he_cap,
1013 data, len)) {
1014 elems->eht_cap = data;
1015 elems->eht_cap_len = len;
1016 }
1017 break;
1018 case WLAN_EID_EXT_EHT_OPERATION:
1019 if (ieee80211_eht_oper_size_ok(data, len))
1020 elems->eht_operation = data;
1021 break;
1022 }
1023}
1024
1025static u32
1026_ieee802_11_parse_elems_crc(const u8 *start, size_t len, bool action,
1027 struct ieee802_11_elems *elems,
1028 u64 filter, u32 crc,
1029 const struct element *check_inherit)
1030{
1031 const struct element *elem;
1032 bool calc_crc = filter != 0;
1033 DECLARE_BITMAP(seen_elems, 256);
1034 const u8 *ie;
1035
1036 bitmap_zero(seen_elems, 256);
1037
1038 for_each_element(elem, start, len) {
1039 bool elem_parse_failed;
1040 u8 id = elem->id;
1041 u8 elen = elem->datalen;
1042 const u8 *pos = elem->data;
1043
1044 if (check_inherit &&
1045 !cfg80211_is_element_inherited(elem,
1046 check_inherit))
1047 continue;
1048
1049 switch (id) {
1050 case WLAN_EID_SSID:
1051 case WLAN_EID_SUPP_RATES:
1052 case WLAN_EID_FH_PARAMS:
1053 case WLAN_EID_DS_PARAMS:
1054 case WLAN_EID_CF_PARAMS:
1055 case WLAN_EID_TIM:
1056 case WLAN_EID_IBSS_PARAMS:
1057 case WLAN_EID_CHALLENGE:
1058 case WLAN_EID_RSN:
1059 case WLAN_EID_ERP_INFO:
1060 case WLAN_EID_EXT_SUPP_RATES:
1061 case WLAN_EID_HT_CAPABILITY:
1062 case WLAN_EID_HT_OPERATION:
1063 case WLAN_EID_VHT_CAPABILITY:
1064 case WLAN_EID_VHT_OPERATION:
1065 case WLAN_EID_MESH_ID:
1066 case WLAN_EID_MESH_CONFIG:
1067 case WLAN_EID_PEER_MGMT:
1068 case WLAN_EID_PREQ:
1069 case WLAN_EID_PREP:
1070 case WLAN_EID_PERR:
1071 case WLAN_EID_RANN:
1072 case WLAN_EID_CHANNEL_SWITCH:
1073 case WLAN_EID_EXT_CHANSWITCH_ANN:
1074 case WLAN_EID_COUNTRY:
1075 case WLAN_EID_PWR_CONSTRAINT:
1076 case WLAN_EID_TIMEOUT_INTERVAL:
1077 case WLAN_EID_SECONDARY_CHANNEL_OFFSET:
1078 case WLAN_EID_WIDE_BW_CHANNEL_SWITCH:
1079 case WLAN_EID_CHAN_SWITCH_PARAM:
1080 case WLAN_EID_EXT_CAPABILITY:
1081 case WLAN_EID_CHAN_SWITCH_TIMING:
1082 case WLAN_EID_LINK_ID:
1083 case WLAN_EID_BSS_MAX_IDLE_PERIOD:
1084 case WLAN_EID_RSNX:
1085 case WLAN_EID_S1G_BCN_COMPAT:
1086 case WLAN_EID_S1G_CAPABILITIES:
1087 case WLAN_EID_S1G_OPERATION:
1088 case WLAN_EID_AID_RESPONSE:
1089 case WLAN_EID_S1G_SHORT_BCN_INTERVAL:
1090
1091
1092
1093
1094 if (test_bit(id, seen_elems)) {
1095 elems->parse_error = true;
1096 continue;
1097 }
1098 break;
1099 }
1100
1101 if (calc_crc && id < 64 && (filter & (1ULL << id)))
1102 crc = crc32_be(crc, pos - 2, elen + 2);
1103
1104 elem_parse_failed = false;
1105
1106 switch (id) {
1107 case WLAN_EID_LINK_ID:
1108 if (elen + 2 < sizeof(struct ieee80211_tdls_lnkie)) {
1109 elem_parse_failed = true;
1110 break;
1111 }
1112 elems->lnk_id = (void *)(pos - 2);
1113 break;
1114 case WLAN_EID_CHAN_SWITCH_TIMING:
1115 if (elen < sizeof(struct ieee80211_ch_switch_timing)) {
1116 elem_parse_failed = true;
1117 break;
1118 }
1119 elems->ch_sw_timing = (void *)pos;
1120 break;
1121 case WLAN_EID_EXT_CAPABILITY:
1122 elems->ext_capab = pos;
1123 elems->ext_capab_len = elen;
1124 break;
1125 case WLAN_EID_SSID:
1126 elems->ssid = pos;
1127 elems->ssid_len = elen;
1128 break;
1129 case WLAN_EID_SUPP_RATES:
1130 elems->supp_rates = pos;
1131 elems->supp_rates_len = elen;
1132 break;
1133 case WLAN_EID_DS_PARAMS:
1134 if (elen >= 1)
1135 elems->ds_params = pos;
1136 else
1137 elem_parse_failed = true;
1138 break;
1139 case WLAN_EID_TIM:
1140 if (elen >= sizeof(struct ieee80211_tim_ie)) {
1141 elems->tim = (void *)pos;
1142 elems->tim_len = elen;
1143 } else
1144 elem_parse_failed = true;
1145 break;
1146 case WLAN_EID_VENDOR_SPECIFIC:
1147 if (elen >= 4 && pos[0] == 0x00 && pos[1] == 0x50 &&
1148 pos[2] == 0xf2) {
1149
1150
1151 if (calc_crc)
1152 crc = crc32_be(crc, pos - 2, elen + 2);
1153
1154 if (elen >= 5 && pos[3] == 2) {
1155
1156 if (pos[4] == 0) {
1157 elems->wmm_info = pos;
1158 elems->wmm_info_len = elen;
1159 } else if (pos[4] == 1) {
1160 elems->wmm_param = pos;
1161 elems->wmm_param_len = elen;
1162 }
1163 }
1164 }
1165 break;
1166 case WLAN_EID_RSN:
1167 elems->rsn = pos;
1168 elems->rsn_len = elen;
1169 break;
1170 case WLAN_EID_ERP_INFO:
1171 if (elen >= 1)
1172 elems->erp_info = pos;
1173 else
1174 elem_parse_failed = true;
1175 break;
1176 case WLAN_EID_EXT_SUPP_RATES:
1177 elems->ext_supp_rates = pos;
1178 elems->ext_supp_rates_len = elen;
1179 break;
1180 case WLAN_EID_HT_CAPABILITY:
1181 if (elen >= sizeof(struct ieee80211_ht_cap))
1182 elems->ht_cap_elem = (void *)pos;
1183 else
1184 elem_parse_failed = true;
1185 break;
1186 case WLAN_EID_HT_OPERATION:
1187 if (elen >= sizeof(struct ieee80211_ht_operation))
1188 elems->ht_operation = (void *)pos;
1189 else
1190 elem_parse_failed = true;
1191 break;
1192 case WLAN_EID_VHT_CAPABILITY:
1193 if (elen >= sizeof(struct ieee80211_vht_cap))
1194 elems->vht_cap_elem = (void *)pos;
1195 else
1196 elem_parse_failed = true;
1197 break;
1198 case WLAN_EID_VHT_OPERATION:
1199 if (elen >= sizeof(struct ieee80211_vht_operation)) {
1200 elems->vht_operation = (void *)pos;
1201 if (calc_crc)
1202 crc = crc32_be(crc, pos - 2, elen + 2);
1203 break;
1204 }
1205 elem_parse_failed = true;
1206 break;
1207 case WLAN_EID_OPMODE_NOTIF:
1208 if (elen > 0) {
1209 elems->opmode_notif = pos;
1210 if (calc_crc)
1211 crc = crc32_be(crc, pos - 2, elen + 2);
1212 break;
1213 }
1214 elem_parse_failed = true;
1215 break;
1216 case WLAN_EID_MESH_ID:
1217 elems->mesh_id = pos;
1218 elems->mesh_id_len = elen;
1219 break;
1220 case WLAN_EID_MESH_CONFIG:
1221 if (elen >= sizeof(struct ieee80211_meshconf_ie))
1222 elems->mesh_config = (void *)pos;
1223 else
1224 elem_parse_failed = true;
1225 break;
1226 case WLAN_EID_PEER_MGMT:
1227 elems->peering = pos;
1228 elems->peering_len = elen;
1229 break;
1230 case WLAN_EID_MESH_AWAKE_WINDOW:
1231 if (elen >= 2)
1232 elems->awake_window = (void *)pos;
1233 break;
1234 case WLAN_EID_PREQ:
1235 elems->preq = pos;
1236 elems->preq_len = elen;
1237 break;
1238 case WLAN_EID_PREP:
1239 elems->prep = pos;
1240 elems->prep_len = elen;
1241 break;
1242 case WLAN_EID_PERR:
1243 elems->perr = pos;
1244 elems->perr_len = elen;
1245 break;
1246 case WLAN_EID_RANN:
1247 if (elen >= sizeof(struct ieee80211_rann_ie))
1248 elems->rann = (void *)pos;
1249 else
1250 elem_parse_failed = true;
1251 break;
1252 case WLAN_EID_CHANNEL_SWITCH:
1253 if (elen != sizeof(struct ieee80211_channel_sw_ie)) {
1254 elem_parse_failed = true;
1255 break;
1256 }
1257 elems->ch_switch_ie = (void *)pos;
1258 break;
1259 case WLAN_EID_EXT_CHANSWITCH_ANN:
1260 if (elen != sizeof(struct ieee80211_ext_chansw_ie)) {
1261 elem_parse_failed = true;
1262 break;
1263 }
1264 elems->ext_chansw_ie = (void *)pos;
1265 break;
1266 case WLAN_EID_SECONDARY_CHANNEL_OFFSET:
1267 if (elen != sizeof(struct ieee80211_sec_chan_offs_ie)) {
1268 elem_parse_failed = true;
1269 break;
1270 }
1271 elems->sec_chan_offs = (void *)pos;
1272 break;
1273 case WLAN_EID_CHAN_SWITCH_PARAM:
1274 if (elen <
1275 sizeof(*elems->mesh_chansw_params_ie)) {
1276 elem_parse_failed = true;
1277 break;
1278 }
1279 elems->mesh_chansw_params_ie = (void *)pos;
1280 break;
1281 case WLAN_EID_WIDE_BW_CHANNEL_SWITCH:
1282 if (!action ||
1283 elen < sizeof(*elems->wide_bw_chansw_ie)) {
1284 elem_parse_failed = true;
1285 break;
1286 }
1287 elems->wide_bw_chansw_ie = (void *)pos;
1288 break;
1289 case WLAN_EID_CHANNEL_SWITCH_WRAPPER:
1290 if (action) {
1291 elem_parse_failed = true;
1292 break;
1293 }
1294
1295
1296
1297
1298
1299 ie = cfg80211_find_ie(WLAN_EID_WIDE_BW_CHANNEL_SWITCH,
1300 pos, elen);
1301 if (ie) {
1302 if (ie[1] >= sizeof(*elems->wide_bw_chansw_ie))
1303 elems->wide_bw_chansw_ie =
1304 (void *)(ie + 2);
1305 else
1306 elem_parse_failed = true;
1307 }
1308 break;
1309 case WLAN_EID_COUNTRY:
1310 elems->country_elem = pos;
1311 elems->country_elem_len = elen;
1312 break;
1313 case WLAN_EID_PWR_CONSTRAINT:
1314 if (elen != 1) {
1315 elem_parse_failed = true;
1316 break;
1317 }
1318 elems->pwr_constr_elem = pos;
1319 break;
1320 case WLAN_EID_CISCO_VENDOR_SPECIFIC:
1321
1322
1323
1324
1325
1326 if (elen < 4) {
1327 elem_parse_failed = true;
1328 break;
1329 }
1330
1331 if (pos[0] != 0x00 || pos[1] != 0x40 ||
1332 pos[2] != 0x96 || pos[3] != 0x00)
1333 break;
1334
1335 if (elen != 6) {
1336 elem_parse_failed = true;
1337 break;
1338 }
1339
1340 if (calc_crc)
1341 crc = crc32_be(crc, pos - 2, elen + 2);
1342
1343 elems->cisco_dtpc_elem = pos;
1344 break;
1345 case WLAN_EID_ADDBA_EXT:
1346 if (elen < sizeof(struct ieee80211_addba_ext_ie)) {
1347 elem_parse_failed = true;
1348 break;
1349 }
1350 elems->addba_ext_ie = (void *)pos;
1351 break;
1352 case WLAN_EID_TIMEOUT_INTERVAL:
1353 if (elen >= sizeof(struct ieee80211_timeout_interval_ie))
1354 elems->timeout_int = (void *)pos;
1355 else
1356 elem_parse_failed = true;
1357 break;
1358 case WLAN_EID_BSS_MAX_IDLE_PERIOD:
1359 if (elen >= sizeof(*elems->max_idle_period_ie))
1360 elems->max_idle_period_ie = (void *)pos;
1361 break;
1362 case WLAN_EID_RSNX:
1363 elems->rsnx = pos;
1364 elems->rsnx_len = elen;
1365 break;
1366 case WLAN_EID_TX_POWER_ENVELOPE:
1367 if (elen < 1 ||
1368 elen > sizeof(struct ieee80211_tx_pwr_env))
1369 break;
1370
1371 if (elems->tx_pwr_env_num >= ARRAY_SIZE(elems->tx_pwr_env))
1372 break;
1373
1374 elems->tx_pwr_env[elems->tx_pwr_env_num] = (void *)pos;
1375 elems->tx_pwr_env_len[elems->tx_pwr_env_num] = elen;
1376 elems->tx_pwr_env_num++;
1377 break;
1378 case WLAN_EID_EXTENSION:
1379 ieee80211_parse_extension_element(calc_crc ?
1380 &crc : NULL,
1381 elem, elems);
1382 break;
1383 case WLAN_EID_S1G_CAPABILITIES:
1384 if (elen >= sizeof(*elems->s1g_capab))
1385 elems->s1g_capab = (void *)pos;
1386 else
1387 elem_parse_failed = true;
1388 break;
1389 case WLAN_EID_S1G_OPERATION:
1390 if (elen == sizeof(*elems->s1g_oper))
1391 elems->s1g_oper = (void *)pos;
1392 else
1393 elem_parse_failed = true;
1394 break;
1395 case WLAN_EID_S1G_BCN_COMPAT:
1396 if (elen == sizeof(*elems->s1g_bcn_compat))
1397 elems->s1g_bcn_compat = (void *)pos;
1398 else
1399 elem_parse_failed = true;
1400 break;
1401 case WLAN_EID_AID_RESPONSE:
1402 if (elen == sizeof(struct ieee80211_aid_response_ie))
1403 elems->aid_resp = (void *)pos;
1404 else
1405 elem_parse_failed = true;
1406 break;
1407 default:
1408 break;
1409 }
1410
1411 if (elem_parse_failed)
1412 elems->parse_error = true;
1413 else
1414 __set_bit(id, seen_elems);
1415 }
1416
1417 if (!for_each_element_completed(elem, start, len))
1418 elems->parse_error = true;
1419
1420 return crc;
1421}
1422
1423static size_t ieee802_11_find_bssid_profile(const u8 *start, size_t len,
1424 struct ieee802_11_elems *elems,
1425 const u8 *transmitter_bssid,
1426 const u8 *bss_bssid,
1427 u8 *nontransmitted_profile)
1428{
1429 const struct element *elem, *sub;
1430 size_t profile_len = 0;
1431 bool found = false;
1432
1433 if (!bss_bssid || !transmitter_bssid)
1434 return profile_len;
1435
1436 for_each_element_id(elem, WLAN_EID_MULTIPLE_BSSID, start, len) {
1437 if (elem->datalen < 2)
1438 continue;
1439
1440 for_each_element(sub, elem->data + 1, elem->datalen - 1) {
1441 u8 new_bssid[ETH_ALEN];
1442 const u8 *index;
1443
1444 if (sub->id != 0 || sub->datalen < 4) {
1445
1446 continue;
1447 }
1448
1449 if (sub->data[0] != WLAN_EID_NON_TX_BSSID_CAP ||
1450 sub->data[1] != 2) {
1451
1452
1453
1454
1455
1456 continue;
1457 }
1458
1459 memset(nontransmitted_profile, 0, len);
1460 profile_len = cfg80211_merge_profile(start, len,
1461 elem,
1462 sub,
1463 nontransmitted_profile,
1464 len);
1465
1466
1467 index = cfg80211_find_ie(WLAN_EID_MULTI_BSSID_IDX,
1468 nontransmitted_profile,
1469 profile_len);
1470 if (!index || index[1] < 1 || index[2] == 0) {
1471
1472 continue;
1473 }
1474
1475 cfg80211_gen_new_bssid(transmitter_bssid,
1476 elem->data[0],
1477 index[2],
1478 new_bssid);
1479 if (ether_addr_equal(new_bssid, bss_bssid)) {
1480 found = true;
1481 elems->bssid_index_len = index[1];
1482 elems->bssid_index = (void *)&index[2];
1483 break;
1484 }
1485 }
1486 }
1487
1488 return found ? profile_len : 0;
1489}
1490
1491struct ieee802_11_elems *ieee802_11_parse_elems_crc(const u8 *start, size_t len,
1492 bool action, u64 filter,
1493 u32 crc,
1494 const u8 *transmitter_bssid,
1495 const u8 *bss_bssid)
1496{
1497 struct ieee802_11_elems *elems;
1498 const struct element *non_inherit = NULL;
1499 u8 *nontransmitted_profile;
1500 int nontransmitted_profile_len = 0;
1501
1502 elems = kzalloc(sizeof(*elems), GFP_ATOMIC);
1503 if (!elems)
1504 return NULL;
1505 elems->ie_start = start;
1506 elems->total_len = len;
1507
1508 nontransmitted_profile = kmalloc(len, GFP_ATOMIC);
1509 if (nontransmitted_profile) {
1510 nontransmitted_profile_len =
1511 ieee802_11_find_bssid_profile(start, len, elems,
1512 transmitter_bssid,
1513 bss_bssid,
1514 nontransmitted_profile);
1515 non_inherit =
1516 cfg80211_find_ext_elem(WLAN_EID_EXT_NON_INHERITANCE,
1517 nontransmitted_profile,
1518 nontransmitted_profile_len);
1519 }
1520
1521 crc = _ieee802_11_parse_elems_crc(start, len, action, elems, filter,
1522 crc, non_inherit);
1523
1524
1525 if (nontransmitted_profile_len)
1526 _ieee802_11_parse_elems_crc(nontransmitted_profile,
1527 nontransmitted_profile_len,
1528 action, elems, 0, 0, NULL);
1529
1530 if (elems->tim && !elems->parse_error) {
1531 const struct ieee80211_tim_ie *tim_ie = elems->tim;
1532
1533 elems->dtim_period = tim_ie->dtim_period;
1534 elems->dtim_count = tim_ie->dtim_count;
1535 }
1536
1537
1538 if (elems->bssid_index &&
1539 elems->bssid_index_len >=
1540 offsetofend(struct ieee80211_bssid_index, dtim_period))
1541 elems->dtim_period = elems->bssid_index->dtim_period;
1542
1543 if (elems->bssid_index &&
1544 elems->bssid_index_len >=
1545 offsetofend(struct ieee80211_bssid_index, dtim_count))
1546 elems->dtim_count = elems->bssid_index->dtim_count;
1547
1548 kfree(nontransmitted_profile);
1549
1550 elems->crc = crc;
1551
1552 return elems;
1553}
1554
1555void ieee80211_regulatory_limit_wmm_params(struct ieee80211_sub_if_data *sdata,
1556 struct ieee80211_tx_queue_params
1557 *qparam, int ac)
1558{
1559 struct ieee80211_chanctx_conf *chanctx_conf;
1560 const struct ieee80211_reg_rule *rrule;
1561 const struct ieee80211_wmm_ac *wmm_ac;
1562 u16 center_freq = 0;
1563
1564 if (sdata->vif.type != NL80211_IFTYPE_AP &&
1565 sdata->vif.type != NL80211_IFTYPE_STATION)
1566 return;
1567
1568 rcu_read_lock();
1569 chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf);
1570 if (chanctx_conf)
1571 center_freq = chanctx_conf->def.chan->center_freq;
1572
1573 if (!center_freq) {
1574 rcu_read_unlock();
1575 return;
1576 }
1577
1578 rrule = freq_reg_info(sdata->wdev.wiphy, MHZ_TO_KHZ(center_freq));
1579
1580 if (IS_ERR_OR_NULL(rrule) || !rrule->has_wmm) {
1581 rcu_read_unlock();
1582 return;
1583 }
1584
1585 if (sdata->vif.type == NL80211_IFTYPE_AP)
1586 wmm_ac = &rrule->wmm_rule.ap[ac];
1587 else
1588 wmm_ac = &rrule->wmm_rule.client[ac];
1589 qparam->cw_min = max_t(u16, qparam->cw_min, wmm_ac->cw_min);
1590 qparam->cw_max = max_t(u16, qparam->cw_max, wmm_ac->cw_max);
1591 qparam->aifs = max_t(u8, qparam->aifs, wmm_ac->aifsn);
1592 qparam->txop = min_t(u16, qparam->txop, wmm_ac->cot / 32);
1593 rcu_read_unlock();
1594}
1595
1596void ieee80211_set_wmm_default(struct ieee80211_sub_if_data *sdata,
1597 bool bss_notify, bool enable_qos)
1598{
1599 struct ieee80211_local *local = sdata->local;
1600 struct ieee80211_tx_queue_params qparam;
1601 struct ieee80211_chanctx_conf *chanctx_conf;
1602 int ac;
1603 bool use_11b;
1604 bool is_ocb;
1605 int aCWmin, aCWmax;
1606
1607 if (!local->ops->conf_tx)
1608 return;
1609
1610 if (local->hw.queues < IEEE80211_NUM_ACS)
1611 return;
1612
1613 memset(&qparam, 0, sizeof(qparam));
1614
1615 rcu_read_lock();
1616 chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf);
1617 use_11b = (chanctx_conf &&
1618 chanctx_conf->def.chan->band == NL80211_BAND_2GHZ) &&
1619 !(sdata->flags & IEEE80211_SDATA_OPERATING_GMODE);
1620 rcu_read_unlock();
1621
1622 is_ocb = (sdata->vif.type == NL80211_IFTYPE_OCB);
1623
1624
1625 aCWmax = 1023;
1626 if (use_11b)
1627 aCWmin = 31;
1628 else
1629 aCWmin = 15;
1630
1631
1632 qparam.cw_max = aCWmax;
1633 qparam.cw_min = aCWmin;
1634 qparam.txop = 0;
1635 qparam.aifs = 2;
1636
1637 for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) {
1638
1639 if (enable_qos) {
1640 switch (ac) {
1641 case IEEE80211_AC_BK:
1642 qparam.cw_max = aCWmax;
1643 qparam.cw_min = aCWmin;
1644 qparam.txop = 0;
1645 if (is_ocb)
1646 qparam.aifs = 9;
1647 else
1648 qparam.aifs = 7;
1649 break;
1650
1651 default:
1652 case IEEE80211_AC_BE:
1653 qparam.cw_max = aCWmax;
1654 qparam.cw_min = aCWmin;
1655 qparam.txop = 0;
1656 if (is_ocb)
1657 qparam.aifs = 6;
1658 else
1659 qparam.aifs = 3;
1660 break;
1661 case IEEE80211_AC_VI:
1662 qparam.cw_max = aCWmin;
1663 qparam.cw_min = (aCWmin + 1) / 2 - 1;
1664 if (is_ocb)
1665 qparam.txop = 0;
1666 else if (use_11b)
1667 qparam.txop = 6016/32;
1668 else
1669 qparam.txop = 3008/32;
1670
1671 if (is_ocb)
1672 qparam.aifs = 3;
1673 else
1674 qparam.aifs = 2;
1675 break;
1676 case IEEE80211_AC_VO:
1677 qparam.cw_max = (aCWmin + 1) / 2 - 1;
1678 qparam.cw_min = (aCWmin + 1) / 4 - 1;
1679 if (is_ocb)
1680 qparam.txop = 0;
1681 else if (use_11b)
1682 qparam.txop = 3264/32;
1683 else
1684 qparam.txop = 1504/32;
1685 qparam.aifs = 2;
1686 break;
1687 }
1688 }
1689 ieee80211_regulatory_limit_wmm_params(sdata, &qparam, ac);
1690
1691 qparam.uapsd = false;
1692
1693 sdata->tx_conf[ac] = qparam;
1694 drv_conf_tx(local, sdata, ac, &qparam);
1695 }
1696
1697 if (sdata->vif.type != NL80211_IFTYPE_MONITOR &&
1698 sdata->vif.type != NL80211_IFTYPE_P2P_DEVICE &&
1699 sdata->vif.type != NL80211_IFTYPE_NAN) {
1700 sdata->vif.bss_conf.qos = enable_qos;
1701 if (bss_notify)
1702 ieee80211_bss_info_change_notify(sdata,
1703 BSS_CHANGED_QOS);
1704 }
1705}
1706
1707void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata,
1708 u16 transaction, u16 auth_alg, u16 status,
1709 const u8 *extra, size_t extra_len, const u8 *da,
1710 const u8 *bssid, const u8 *key, u8 key_len, u8 key_idx,
1711 u32 tx_flags)
1712{
1713 struct ieee80211_local *local = sdata->local;
1714 struct sk_buff *skb;
1715 struct ieee80211_mgmt *mgmt;
1716 int err;
1717
1718
1719 skb = dev_alloc_skb(local->hw.extra_tx_headroom + IEEE80211_WEP_IV_LEN +
1720 24 + 6 + extra_len + IEEE80211_WEP_ICV_LEN);
1721 if (!skb)
1722 return;
1723
1724 skb_reserve(skb, local->hw.extra_tx_headroom + IEEE80211_WEP_IV_LEN);
1725
1726 mgmt = skb_put_zero(skb, 24 + 6);
1727 mgmt->frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
1728 IEEE80211_STYPE_AUTH);
1729 memcpy(mgmt->da, da, ETH_ALEN);
1730 memcpy(mgmt->sa, sdata->vif.addr, ETH_ALEN);
1731 memcpy(mgmt->bssid, bssid, ETH_ALEN);
1732 mgmt->u.auth.auth_alg = cpu_to_le16(auth_alg);
1733 mgmt->u.auth.auth_transaction = cpu_to_le16(transaction);
1734 mgmt->u.auth.status_code = cpu_to_le16(status);
1735 if (extra)
1736 skb_put_data(skb, extra, extra_len);
1737
1738 if (auth_alg == WLAN_AUTH_SHARED_KEY && transaction == 3) {
1739 mgmt->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED);
1740 err = ieee80211_wep_encrypt(local, skb, key, key_len, key_idx);
1741 if (WARN_ON(err)) {
1742 kfree_skb(skb);
1743 return;
1744 }
1745 }
1746
1747 IEEE80211_SKB_CB(skb)->flags |= IEEE80211_TX_INTFL_DONT_ENCRYPT |
1748 tx_flags;
1749 ieee80211_tx_skb(sdata, skb);
1750}
1751
1752void ieee80211_send_deauth_disassoc(struct ieee80211_sub_if_data *sdata,
1753 const u8 *da, const u8 *bssid,
1754 u16 stype, u16 reason,
1755 bool send_frame, u8 *frame_buf)
1756{
1757 struct ieee80211_local *local = sdata->local;
1758 struct sk_buff *skb;
1759 struct ieee80211_mgmt *mgmt = (void *)frame_buf;
1760
1761
1762 mgmt->frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT | stype);
1763 mgmt->duration = 0;
1764 mgmt->seq_ctrl = 0;
1765 memcpy(mgmt->da, da, ETH_ALEN);
1766 memcpy(mgmt->sa, sdata->vif.addr, ETH_ALEN);
1767 memcpy(mgmt->bssid, bssid, ETH_ALEN);
1768
1769 mgmt->u.deauth.reason_code = cpu_to_le16(reason);
1770
1771 if (send_frame) {
1772 skb = dev_alloc_skb(local->hw.extra_tx_headroom +
1773 IEEE80211_DEAUTH_FRAME_LEN);
1774 if (!skb)
1775 return;
1776
1777 skb_reserve(skb, local->hw.extra_tx_headroom);
1778
1779
1780 skb_put_data(skb, mgmt, IEEE80211_DEAUTH_FRAME_LEN);
1781
1782 if (sdata->vif.type != NL80211_IFTYPE_STATION ||
1783 !(sdata->u.mgd.flags & IEEE80211_STA_MFP_ENABLED))
1784 IEEE80211_SKB_CB(skb)->flags |=
1785 IEEE80211_TX_INTFL_DONT_ENCRYPT;
1786
1787 ieee80211_tx_skb(sdata, skb);
1788 }
1789}
1790
1791static u8 *ieee80211_write_he_6ghz_cap(u8 *pos, __le16 cap, u8 *end)
1792{
1793 if ((end - pos) < 5)
1794 return pos;
1795
1796 *pos++ = WLAN_EID_EXTENSION;
1797 *pos++ = 1 + sizeof(cap);
1798 *pos++ = WLAN_EID_EXT_HE_6GHZ_CAPA;
1799 memcpy(pos, &cap, sizeof(cap));
1800
1801 return pos + 2;
1802}
1803
1804static int ieee80211_build_preq_ies_band(struct ieee80211_sub_if_data *sdata,
1805 u8 *buffer, size_t buffer_len,
1806 const u8 *ie, size_t ie_len,
1807 enum nl80211_band band,
1808 u32 rate_mask,
1809 struct cfg80211_chan_def *chandef,
1810 size_t *offset, u32 flags)
1811{
1812 struct ieee80211_local *local = sdata->local;
1813 struct ieee80211_supported_band *sband;
1814 const struct ieee80211_sta_he_cap *he_cap;
1815 const struct ieee80211_sta_eht_cap *eht_cap;
1816 u8 *pos = buffer, *end = buffer + buffer_len;
1817 size_t noffset;
1818 int supp_rates_len, i;
1819 u8 rates[32];
1820 int num_rates;
1821 int ext_rates_len;
1822 int shift;
1823 u32 rate_flags;
1824 bool have_80mhz = false;
1825
1826 *offset = 0;
1827
1828 sband = local->hw.wiphy->bands[band];
1829 if (WARN_ON_ONCE(!sband))
1830 return 0;
1831
1832 rate_flags = ieee80211_chandef_rate_flags(chandef);
1833 shift = ieee80211_chandef_get_shift(chandef);
1834
1835 num_rates = 0;
1836 for (i = 0; i < sband->n_bitrates; i++) {
1837 if ((BIT(i) & rate_mask) == 0)
1838 continue;
1839 if ((rate_flags & sband->bitrates[i].flags) != rate_flags)
1840 continue;
1841
1842 rates[num_rates++] =
1843 (u8) DIV_ROUND_UP(sband->bitrates[i].bitrate,
1844 (1 << shift) * 5);
1845 }
1846
1847 supp_rates_len = min_t(int, num_rates, 8);
1848
1849 if (end - pos < 2 + supp_rates_len)
1850 goto out_err;
1851 *pos++ = WLAN_EID_SUPP_RATES;
1852 *pos++ = supp_rates_len;
1853 memcpy(pos, rates, supp_rates_len);
1854 pos += supp_rates_len;
1855
1856
1857 if (ie && ie_len) {
1858 static const u8 before_extrates[] = {
1859 WLAN_EID_SSID,
1860 WLAN_EID_SUPP_RATES,
1861 WLAN_EID_REQUEST,
1862 };
1863 noffset = ieee80211_ie_split(ie, ie_len,
1864 before_extrates,
1865 ARRAY_SIZE(before_extrates),
1866 *offset);
1867 if (end - pos < noffset - *offset)
1868 goto out_err;
1869 memcpy(pos, ie + *offset, noffset - *offset);
1870 pos += noffset - *offset;
1871 *offset = noffset;
1872 }
1873
1874 ext_rates_len = num_rates - supp_rates_len;
1875 if (ext_rates_len > 0) {
1876 if (end - pos < 2 + ext_rates_len)
1877 goto out_err;
1878 *pos++ = WLAN_EID_EXT_SUPP_RATES;
1879 *pos++ = ext_rates_len;
1880 memcpy(pos, rates + supp_rates_len, ext_rates_len);
1881 pos += ext_rates_len;
1882 }
1883
1884 if (chandef->chan && sband->band == NL80211_BAND_2GHZ) {
1885 if (end - pos < 3)
1886 goto out_err;
1887 *pos++ = WLAN_EID_DS_PARAMS;
1888 *pos++ = 1;
1889 *pos++ = ieee80211_frequency_to_channel(
1890 chandef->chan->center_freq);
1891 }
1892
1893 if (flags & IEEE80211_PROBE_FLAG_MIN_CONTENT)
1894 goto done;
1895
1896
1897 if (ie && ie_len) {
1898 static const u8 before_ht[] = {
1899
1900
1901
1902
1903 WLAN_EID_DS_PARAMS,
1904 WLAN_EID_SUPPORTED_REGULATORY_CLASSES,
1905 };
1906 noffset = ieee80211_ie_split(ie, ie_len,
1907 before_ht, ARRAY_SIZE(before_ht),
1908 *offset);
1909 if (end - pos < noffset - *offset)
1910 goto out_err;
1911 memcpy(pos, ie + *offset, noffset - *offset);
1912 pos += noffset - *offset;
1913 *offset = noffset;
1914 }
1915
1916 if (sband->ht_cap.ht_supported) {
1917 if (end - pos < 2 + sizeof(struct ieee80211_ht_cap))
1918 goto out_err;
1919 pos = ieee80211_ie_build_ht_cap(pos, &sband->ht_cap,
1920 sband->ht_cap.cap);
1921 }
1922
1923
1924 if (ie && ie_len) {
1925 static const u8 before_vht[] = {
1926
1927
1928
1929
1930 WLAN_EID_BSS_COEX_2040,
1931 WLAN_EID_EXT_CAPABILITY,
1932 WLAN_EID_SSID_LIST,
1933 WLAN_EID_CHANNEL_USAGE,
1934 WLAN_EID_INTERWORKING,
1935 WLAN_EID_MESH_ID,
1936
1937 };
1938 noffset = ieee80211_ie_split(ie, ie_len,
1939 before_vht, ARRAY_SIZE(before_vht),
1940 *offset);
1941 if (end - pos < noffset - *offset)
1942 goto out_err;
1943 memcpy(pos, ie + *offset, noffset - *offset);
1944 pos += noffset - *offset;
1945 *offset = noffset;
1946 }
1947
1948
1949 for (i = 0; i < sband->n_channels; i++) {
1950 if (sband->channels[i].flags & (IEEE80211_CHAN_DISABLED |
1951 IEEE80211_CHAN_NO_80MHZ))
1952 continue;
1953
1954 have_80mhz = true;
1955 break;
1956 }
1957
1958 if (sband->vht_cap.vht_supported && have_80mhz) {
1959 if (end - pos < 2 + sizeof(struct ieee80211_vht_cap))
1960 goto out_err;
1961 pos = ieee80211_ie_build_vht_cap(pos, &sband->vht_cap,
1962 sband->vht_cap.cap);
1963 }
1964
1965
1966 if (ie && ie_len) {
1967 static const u8 before_he[] = {
1968
1969
1970
1971
1972 WLAN_EID_EXTENSION, WLAN_EID_EXT_FILS_REQ_PARAMS,
1973 WLAN_EID_AP_CSN,
1974
1975 };
1976 noffset = ieee80211_ie_split(ie, ie_len,
1977 before_he, ARRAY_SIZE(before_he),
1978 *offset);
1979 if (end - pos < noffset - *offset)
1980 goto out_err;
1981 memcpy(pos, ie + *offset, noffset - *offset);
1982 pos += noffset - *offset;
1983 *offset = noffset;
1984 }
1985
1986 he_cap = ieee80211_get_he_iftype_cap(sband,
1987 ieee80211_vif_type_p2p(&sdata->vif));
1988 if (he_cap &&
1989 cfg80211_any_usable_channels(local->hw.wiphy, BIT(sband->band),
1990 IEEE80211_CHAN_NO_HE)) {
1991 pos = ieee80211_ie_build_he_cap(0, pos, he_cap, end);
1992 if (!pos)
1993 goto out_err;
1994 }
1995
1996 eht_cap = ieee80211_get_eht_iftype_cap(sband,
1997 ieee80211_vif_type_p2p(&sdata->vif));
1998
1999 if (eht_cap &&
2000 cfg80211_any_usable_channels(local->hw.wiphy, BIT(sband->band),
2001 IEEE80211_CHAN_NO_HE |
2002 IEEE80211_CHAN_NO_EHT)) {
2003 pos = ieee80211_ie_build_eht_cap(pos, he_cap, eht_cap, end);
2004 if (!pos)
2005 goto out_err;
2006 }
2007
2008 if (cfg80211_any_usable_channels(local->hw.wiphy,
2009 BIT(NL80211_BAND_6GHZ),
2010 IEEE80211_CHAN_NO_HE)) {
2011 struct ieee80211_supported_band *sband6;
2012
2013 sband6 = local->hw.wiphy->bands[NL80211_BAND_6GHZ];
2014 he_cap = ieee80211_get_he_iftype_cap(sband6,
2015 ieee80211_vif_type_p2p(&sdata->vif));
2016
2017 if (he_cap) {
2018 enum nl80211_iftype iftype =
2019 ieee80211_vif_type_p2p(&sdata->vif);
2020 __le16 cap = ieee80211_get_he_6ghz_capa(sband, iftype);
2021
2022 pos = ieee80211_write_he_6ghz_cap(pos, cap, end);
2023 }
2024 }
2025
2026
2027
2028
2029
2030
2031 return pos - buffer;
2032 out_err:
2033 WARN_ONCE(1, "not enough space for preq IEs\n");
2034 done:
2035 return pos - buffer;
2036}
2037
2038int ieee80211_build_preq_ies(struct ieee80211_sub_if_data *sdata, u8 *buffer,
2039 size_t buffer_len,
2040 struct ieee80211_scan_ies *ie_desc,
2041 const u8 *ie, size_t ie_len,
2042 u8 bands_used, u32 *rate_masks,
2043 struct cfg80211_chan_def *chandef,
2044 u32 flags)
2045{
2046 size_t pos = 0, old_pos = 0, custom_ie_offset = 0;
2047 int i;
2048
2049 memset(ie_desc, 0, sizeof(*ie_desc));
2050
2051 for (i = 0; i < NUM_NL80211_BANDS; i++) {
2052 if (bands_used & BIT(i)) {
2053 pos += ieee80211_build_preq_ies_band(sdata,
2054 buffer + pos,
2055 buffer_len - pos,
2056 ie, ie_len, i,
2057 rate_masks[i],
2058 chandef,
2059 &custom_ie_offset,
2060 flags);
2061 ie_desc->ies[i] = buffer + old_pos;
2062 ie_desc->len[i] = pos - old_pos;
2063 old_pos = pos;
2064 }
2065 }
2066
2067
2068 if (ie && ie_len) {
2069 if (WARN_ONCE(buffer_len - pos < ie_len - custom_ie_offset,
2070 "not enough space for preq custom IEs\n"))
2071 return pos;
2072 memcpy(buffer + pos, ie + custom_ie_offset,
2073 ie_len - custom_ie_offset);
2074 ie_desc->common_ies = buffer + pos;
2075 ie_desc->common_ie_len = ie_len - custom_ie_offset;
2076 pos += ie_len - custom_ie_offset;
2077 }
2078
2079 return pos;
2080};
2081
2082struct sk_buff *ieee80211_build_probe_req(struct ieee80211_sub_if_data *sdata,
2083 const u8 *src, const u8 *dst,
2084 u32 ratemask,
2085 struct ieee80211_channel *chan,
2086 const u8 *ssid, size_t ssid_len,
2087 const u8 *ie, size_t ie_len,
2088 u32 flags)
2089{
2090 struct ieee80211_local *local = sdata->local;
2091 struct cfg80211_chan_def chandef;
2092 struct sk_buff *skb;
2093 struct ieee80211_mgmt *mgmt;
2094 int ies_len;
2095 u32 rate_masks[NUM_NL80211_BANDS] = {};
2096 struct ieee80211_scan_ies dummy_ie_desc;
2097
2098
2099
2100
2101
2102
2103 chandef.width = sdata->vif.bss_conf.chandef.width;
2104 if (flags & IEEE80211_PROBE_FLAG_DIRECTED)
2105 chandef.chan = NULL;
2106 else
2107 chandef.chan = chan;
2108
2109 skb = ieee80211_probereq_get(&local->hw, src, ssid, ssid_len,
2110 local->scan_ies_len + ie_len);
2111 if (!skb)
2112 return NULL;
2113
2114 rate_masks[chan->band] = ratemask;
2115 ies_len = ieee80211_build_preq_ies(sdata, skb_tail_pointer(skb),
2116 skb_tailroom(skb), &dummy_ie_desc,
2117 ie, ie_len, BIT(chan->band),
2118 rate_masks, &chandef, flags);
2119 skb_put(skb, ies_len);
2120
2121 if (dst) {
2122 mgmt = (struct ieee80211_mgmt *) skb->data;
2123 memcpy(mgmt->da, dst, ETH_ALEN);
2124 memcpy(mgmt->bssid, dst, ETH_ALEN);
2125 }
2126
2127 IEEE80211_SKB_CB(skb)->flags |= IEEE80211_TX_INTFL_DONT_ENCRYPT;
2128
2129 return skb;
2130}
2131
2132u32 ieee80211_sta_get_rates(struct ieee80211_sub_if_data *sdata,
2133 struct ieee802_11_elems *elems,
2134 enum nl80211_band band, u32 *basic_rates)
2135{
2136 struct ieee80211_supported_band *sband;
2137 size_t num_rates;
2138 u32 supp_rates, rate_flags;
2139 int i, j, shift;
2140
2141 sband = sdata->local->hw.wiphy->bands[band];
2142 if (WARN_ON(!sband))
2143 return 1;
2144
2145 rate_flags = ieee80211_chandef_rate_flags(&sdata->vif.bss_conf.chandef);
2146 shift = ieee80211_vif_get_shift(&sdata->vif);
2147
2148 num_rates = sband->n_bitrates;
2149 supp_rates = 0;
2150 for (i = 0; i < elems->supp_rates_len +
2151 elems->ext_supp_rates_len; i++) {
2152 u8 rate = 0;
2153 int own_rate;
2154 bool is_basic;
2155 if (i < elems->supp_rates_len)
2156 rate = elems->supp_rates[i];
2157 else if (elems->ext_supp_rates)
2158 rate = elems->ext_supp_rates
2159 [i - elems->supp_rates_len];
2160 own_rate = 5 * (rate & 0x7f);
2161 is_basic = !!(rate & 0x80);
2162
2163 if (is_basic && (rate & 0x7f) == BSS_MEMBERSHIP_SELECTOR_HT_PHY)
2164 continue;
2165
2166 for (j = 0; j < num_rates; j++) {
2167 int brate;
2168 if ((rate_flags & sband->bitrates[j].flags)
2169 != rate_flags)
2170 continue;
2171
2172 brate = DIV_ROUND_UP(sband->bitrates[j].bitrate,
2173 1 << shift);
2174
2175 if (brate == own_rate) {
2176 supp_rates |= BIT(j);
2177 if (basic_rates && is_basic)
2178 *basic_rates |= BIT(j);
2179 }
2180 }
2181 }
2182 return supp_rates;
2183}
2184
2185void ieee80211_stop_device(struct ieee80211_local *local)
2186{
2187 ieee80211_led_radio(local, false);
2188 ieee80211_mod_tpt_led_trig(local, 0, IEEE80211_TPT_LEDTRIG_FL_RADIO);
2189
2190 cancel_work_sync(&local->reconfig_filter);
2191
2192 flush_workqueue(local->workqueue);
2193 drv_stop(local);
2194}
2195
2196static void ieee80211_flush_completed_scan(struct ieee80211_local *local,
2197 bool aborted)
2198{
2199
2200
2201
2202
2203
2204
2205
2206 if (test_bit(SCAN_COMPLETED, &local->scanning)) {
2207
2208
2209
2210
2211
2212 if (aborted)
2213 set_bit(SCAN_ABORTED, &local->scanning);
2214 ieee80211_queue_delayed_work(&local->hw, &local->scan_work, 0);
2215 flush_delayed_work(&local->scan_work);
2216 }
2217}
2218
2219static void ieee80211_handle_reconfig_failure(struct ieee80211_local *local)
2220{
2221 struct ieee80211_sub_if_data *sdata;
2222 struct ieee80211_chanctx *ctx;
2223
2224
2225
2226
2227
2228
2229
2230
2231
2232
2233
2234 local->resuming = false;
2235 local->suspended = false;
2236 local->in_reconfig = false;
2237
2238 ieee80211_flush_completed_scan(local, true);
2239
2240
2241
2242
2243 ieee80211_sched_scan_end(local);
2244
2245 list_for_each_entry(sdata, &local->interfaces, list)
2246 sdata->flags &= ~IEEE80211_SDATA_IN_DRIVER;
2247
2248
2249
2250
2251 mutex_lock(&local->chanctx_mtx);
2252 list_for_each_entry(ctx, &local->chanctx_list, list)
2253 ctx->driver_present = false;
2254 mutex_unlock(&local->chanctx_mtx);
2255}
2256
2257static void ieee80211_assign_chanctx(struct ieee80211_local *local,
2258 struct ieee80211_sub_if_data *sdata)
2259{
2260 struct ieee80211_chanctx_conf *conf;
2261 struct ieee80211_chanctx *ctx;
2262
2263 if (!local->use_chanctx)
2264 return;
2265
2266 mutex_lock(&local->chanctx_mtx);
2267 conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
2268 lockdep_is_held(&local->chanctx_mtx));
2269 if (conf) {
2270 ctx = container_of(conf, struct ieee80211_chanctx, conf);
2271 drv_assign_vif_chanctx(local, sdata, ctx);
2272 }
2273 mutex_unlock(&local->chanctx_mtx);
2274}
2275
2276static void ieee80211_reconfig_stations(struct ieee80211_sub_if_data *sdata)
2277{
2278 struct ieee80211_local *local = sdata->local;
2279 struct sta_info *sta;
2280
2281
2282 mutex_lock(&local->sta_mtx);
2283 list_for_each_entry(sta, &local->sta_list, list) {
2284 enum ieee80211_sta_state state;
2285
2286 if (!sta->uploaded || sta->sdata != sdata)
2287 continue;
2288
2289 for (state = IEEE80211_STA_NOTEXIST;
2290 state < sta->sta_state; state++)
2291 WARN_ON(drv_sta_state(local, sta->sdata, sta, state,
2292 state + 1));
2293 }
2294 mutex_unlock(&local->sta_mtx);
2295}
2296
2297static int ieee80211_reconfig_nan(struct ieee80211_sub_if_data *sdata)
2298{
2299 struct cfg80211_nan_func *func, **funcs;
2300 int res, id, i = 0;
2301
2302 res = drv_start_nan(sdata->local, sdata,
2303 &sdata->u.nan.conf);
2304 if (WARN_ON(res))
2305 return res;
2306
2307 funcs = kcalloc(sdata->local->hw.max_nan_de_entries + 1,
2308 sizeof(*funcs),
2309 GFP_KERNEL);
2310 if (!funcs)
2311 return -ENOMEM;
2312
2313
2314
2315
2316
2317 spin_lock_bh(&sdata->u.nan.func_lock);
2318
2319 idr_for_each_entry(&sdata->u.nan.function_inst_ids, func, id)
2320 funcs[i++] = func;
2321
2322 spin_unlock_bh(&sdata->u.nan.func_lock);
2323
2324 for (i = 0; funcs[i]; i++) {
2325 res = drv_add_nan_func(sdata->local, sdata, funcs[i]);
2326 if (WARN_ON(res))
2327 ieee80211_nan_func_terminated(&sdata->vif,
2328 funcs[i]->instance_id,
2329 NL80211_NAN_FUNC_TERM_REASON_ERROR,
2330 GFP_KERNEL);
2331 }
2332
2333 kfree(funcs);
2334
2335 return 0;
2336}
2337
2338int ieee80211_reconfig(struct ieee80211_local *local)
2339{
2340 struct ieee80211_hw *hw = &local->hw;
2341 struct ieee80211_sub_if_data *sdata;
2342 struct ieee80211_chanctx *ctx;
2343 struct sta_info *sta;
2344 int res, i;
2345 bool reconfig_due_to_wowlan = false;
2346 struct ieee80211_sub_if_data *sched_scan_sdata;
2347 struct cfg80211_sched_scan_request *sched_scan_req;
2348 bool sched_scan_stopped = false;
2349 bool suspended = local->suspended;
2350 bool in_reconfig = false;
2351
2352
2353 if (!local->open_count)
2354 goto wake_up;
2355
2356#ifdef CONFIG_PM
2357 if (suspended)
2358 local->resuming = true;
2359
2360 if (local->wowlan) {
2361
2362
2363
2364
2365
2366
2367 local->suspended = false;
2368 res = drv_resume(local);
2369 local->wowlan = false;
2370 if (res < 0) {
2371 local->resuming = false;
2372 return res;
2373 }
2374 if (res == 0)
2375 goto wake_up;
2376 WARN_ON(res > 1);
2377
2378
2379
2380
2381
2382 reconfig_due_to_wowlan = true;
2383 local->suspended = true;
2384 }
2385#endif
2386
2387
2388
2389
2390
2391
2392
2393
2394 if (suspended && local->in_reconfig && !reconfig_due_to_wowlan)
2395 cancel_work_sync(&local->restart_work);
2396
2397 local->started = false;
2398
2399
2400
2401
2402
2403
2404
2405 res = drv_start(local);
2406 if (res) {
2407 if (suspended)
2408 WARN(1, "Hardware became unavailable upon resume. This could be a software issue prior to suspend or a hardware issue.\n");
2409 else
2410 WARN(1, "Hardware became unavailable during restart.\n");
2411 ieee80211_handle_reconfig_failure(local);
2412 return res;
2413 }
2414
2415
2416 drv_set_frag_threshold(local, hw->wiphy->frag_threshold);
2417
2418
2419 drv_set_rts_threshold(local, hw->wiphy->rts_threshold);
2420
2421
2422 drv_set_coverage_class(local, hw->wiphy->coverage_class);
2423
2424 ieee80211_led_radio(local, true);
2425 ieee80211_mod_tpt_led_trig(local,
2426 IEEE80211_TPT_LEDTRIG_FL_RADIO, 0);
2427
2428
2429 sdata = wiphy_dereference(local->hw.wiphy, local->monitor_sdata);
2430 if (sdata) {
2431
2432 WARN_ON(local->resuming);
2433 res = drv_add_interface(local, sdata);
2434 if (WARN_ON(res)) {
2435 RCU_INIT_POINTER(local->monitor_sdata, NULL);
2436 synchronize_net();
2437 kfree(sdata);
2438 }
2439 }
2440
2441 list_for_each_entry(sdata, &local->interfaces, list) {
2442 if (sdata->vif.type != NL80211_IFTYPE_AP_VLAN &&
2443 sdata->vif.type != NL80211_IFTYPE_MONITOR &&
2444 ieee80211_sdata_running(sdata)) {
2445 res = drv_add_interface(local, sdata);
2446 if (WARN_ON(res))
2447 break;
2448 }
2449 }
2450
2451
2452
2453
2454 if (res) {
2455 list_for_each_entry_continue_reverse(sdata, &local->interfaces,
2456 list)
2457 if (sdata->vif.type != NL80211_IFTYPE_AP_VLAN &&
2458 sdata->vif.type != NL80211_IFTYPE_MONITOR &&
2459 ieee80211_sdata_running(sdata))
2460 drv_remove_interface(local, sdata);
2461 ieee80211_handle_reconfig_failure(local);
2462 return res;
2463 }
2464
2465
2466 if (local->use_chanctx) {
2467 mutex_lock(&local->chanctx_mtx);
2468 list_for_each_entry(ctx, &local->chanctx_list, list)
2469 if (ctx->replace_state !=
2470 IEEE80211_CHANCTX_REPLACES_OTHER)
2471 WARN_ON(drv_add_chanctx(local, ctx));
2472 mutex_unlock(&local->chanctx_mtx);
2473
2474 sdata = wiphy_dereference(local->hw.wiphy,
2475 local->monitor_sdata);
2476 if (sdata && ieee80211_sdata_running(sdata))
2477 ieee80211_assign_chanctx(local, sdata);
2478 }
2479
2480
2481 ieee80211_hw_config(local, ~0);
2482
2483 ieee80211_configure_filter(local);
2484
2485
2486 list_for_each_entry(sdata, &local->interfaces, list) {
2487 u32 changed;
2488
2489 if (!ieee80211_sdata_running(sdata))
2490 continue;
2491
2492 ieee80211_assign_chanctx(local, sdata);
2493
2494 switch (sdata->vif.type) {
2495 case NL80211_IFTYPE_AP_VLAN:
2496 case NL80211_IFTYPE_MONITOR:
2497 break;
2498 case NL80211_IFTYPE_ADHOC:
2499 if (sdata->vif.bss_conf.ibss_joined)
2500 WARN_ON(drv_join_ibss(local, sdata));
2501 fallthrough;
2502 default:
2503 ieee80211_reconfig_stations(sdata);
2504 fallthrough;
2505 case NL80211_IFTYPE_AP:
2506 for (i = 0; i < IEEE80211_NUM_ACS; i++)
2507 drv_conf_tx(local, sdata, i,
2508 &sdata->tx_conf[i]);
2509 break;
2510 }
2511
2512
2513 changed = BSS_CHANGED_ERP_CTS_PROT |
2514 BSS_CHANGED_ERP_PREAMBLE |
2515 BSS_CHANGED_ERP_SLOT |
2516 BSS_CHANGED_HT |
2517 BSS_CHANGED_BASIC_RATES |
2518 BSS_CHANGED_BEACON_INT |
2519 BSS_CHANGED_BSSID |
2520 BSS_CHANGED_CQM |
2521 BSS_CHANGED_QOS |
2522 BSS_CHANGED_IDLE |
2523 BSS_CHANGED_TXPOWER |
2524 BSS_CHANGED_MCAST_RATE;
2525
2526 if (sdata->vif.mu_mimo_owner)
2527 changed |= BSS_CHANGED_MU_GROUPS;
2528
2529 switch (sdata->vif.type) {
2530 case NL80211_IFTYPE_STATION:
2531 changed |= BSS_CHANGED_ASSOC |
2532 BSS_CHANGED_ARP_FILTER |
2533 BSS_CHANGED_PS;
2534
2535
2536 if (sdata->u.mgd.have_beacon)
2537 changed |= BSS_CHANGED_BEACON_INFO;
2538
2539 if (sdata->vif.bss_conf.max_idle_period ||
2540 sdata->vif.bss_conf.protected_keep_alive)
2541 changed |= BSS_CHANGED_KEEP_ALIVE;
2542
2543 sdata_lock(sdata);
2544 ieee80211_bss_info_change_notify(sdata, changed);
2545 sdata_unlock(sdata);
2546 break;
2547 case NL80211_IFTYPE_OCB:
2548 changed |= BSS_CHANGED_OCB;
2549 ieee80211_bss_info_change_notify(sdata, changed);
2550 break;
2551 case NL80211_IFTYPE_ADHOC:
2552 changed |= BSS_CHANGED_IBSS;
2553 fallthrough;
2554 case NL80211_IFTYPE_AP:
2555 changed |= BSS_CHANGED_SSID | BSS_CHANGED_P2P_PS;
2556
2557 if (sdata->vif.bss_conf.ftm_responder == 1 &&
2558 wiphy_ext_feature_isset(sdata->local->hw.wiphy,
2559 NL80211_EXT_FEATURE_ENABLE_FTM_RESPONDER))
2560 changed |= BSS_CHANGED_FTM_RESPONDER;
2561
2562 if (sdata->vif.type == NL80211_IFTYPE_AP) {
2563 changed |= BSS_CHANGED_AP_PROBE_RESP;
2564
2565 if (rcu_access_pointer(sdata->u.ap.beacon))
2566 drv_start_ap(local, sdata);
2567 }
2568 fallthrough;
2569 case NL80211_IFTYPE_MESH_POINT:
2570 if (sdata->vif.bss_conf.enable_beacon) {
2571 changed |= BSS_CHANGED_BEACON |
2572 BSS_CHANGED_BEACON_ENABLED;
2573 ieee80211_bss_info_change_notify(sdata, changed);
2574 }
2575 break;
2576 case NL80211_IFTYPE_NAN:
2577 res = ieee80211_reconfig_nan(sdata);
2578 if (res < 0) {
2579 ieee80211_handle_reconfig_failure(local);
2580 return res;
2581 }
2582 break;
2583 case NL80211_IFTYPE_AP_VLAN:
2584 case NL80211_IFTYPE_MONITOR:
2585 case NL80211_IFTYPE_P2P_DEVICE:
2586
2587 break;
2588 case NL80211_IFTYPE_UNSPECIFIED:
2589 case NUM_NL80211_IFTYPES:
2590 case NL80211_IFTYPE_P2P_CLIENT:
2591 case NL80211_IFTYPE_P2P_GO:
2592 case NL80211_IFTYPE_WDS:
2593 WARN_ON(1);
2594 break;
2595 }
2596 }
2597
2598 ieee80211_recalc_ps(local);
2599
2600
2601
2602
2603
2604
2605
2606 if (!(local->hw.conf.flags & IEEE80211_CONF_PS)) {
2607 list_for_each_entry(sdata, &local->interfaces, list) {
2608 if (sdata->vif.type != NL80211_IFTYPE_STATION)
2609 continue;
2610 if (!sdata->u.mgd.associated)
2611 continue;
2612
2613 ieee80211_send_nullfunc(local, sdata, false);
2614 }
2615 }
2616
2617
2618 mutex_lock(&local->sta_mtx);
2619 list_for_each_entry(sta, &local->sta_list, list) {
2620 enum ieee80211_sta_state state;
2621
2622 if (!sta->uploaded)
2623 continue;
2624
2625 if (sta->sdata->vif.type != NL80211_IFTYPE_AP &&
2626 sta->sdata->vif.type != NL80211_IFTYPE_AP_VLAN)
2627 continue;
2628
2629 for (state = IEEE80211_STA_NOTEXIST;
2630 state < sta->sta_state; state++)
2631 WARN_ON(drv_sta_state(local, sta->sdata, sta, state,
2632 state + 1));
2633 }
2634 mutex_unlock(&local->sta_mtx);
2635
2636
2637 list_for_each_entry(sdata, &local->interfaces, list)
2638 ieee80211_reenable_keys(sdata);
2639
2640
2641 mutex_lock(&local->mtx);
2642 sched_scan_sdata = rcu_dereference_protected(local->sched_scan_sdata,
2643 lockdep_is_held(&local->mtx));
2644 sched_scan_req = rcu_dereference_protected(local->sched_scan_req,
2645 lockdep_is_held(&local->mtx));
2646 if (sched_scan_sdata && sched_scan_req)
2647
2648
2649
2650
2651
2652
2653
2654 if (sched_scan_req->n_scan_plans > 1 ||
2655 __ieee80211_request_sched_scan_start(sched_scan_sdata,
2656 sched_scan_req)) {
2657 RCU_INIT_POINTER(local->sched_scan_sdata, NULL);
2658 RCU_INIT_POINTER(local->sched_scan_req, NULL);
2659 sched_scan_stopped = true;
2660 }
2661 mutex_unlock(&local->mtx);
2662
2663 if (sched_scan_stopped)
2664 cfg80211_sched_scan_stopped_locked(local->hw.wiphy, 0);
2665
2666 wake_up:
2667
2668 if (local->monitors == local->open_count && local->monitors > 0)
2669 ieee80211_add_virtual_monitor(local);
2670
2671
2672
2673
2674
2675
2676
2677
2678
2679
2680
2681 if (ieee80211_hw_check(hw, AMPDU_AGGREGATION)) {
2682 mutex_lock(&local->sta_mtx);
2683
2684 list_for_each_entry(sta, &local->sta_list, list) {
2685 if (!local->resuming)
2686 ieee80211_sta_tear_down_BA_sessions(
2687 sta, AGG_STOP_LOCAL_REQUEST);
2688 clear_sta_flag(sta, WLAN_STA_BLOCK_BA);
2689 }
2690
2691 mutex_unlock(&local->sta_mtx);
2692 }
2693
2694
2695
2696
2697
2698 if (local->open_count && (!suspended || reconfig_due_to_wowlan))
2699 drv_reconfig_complete(local, IEEE80211_RECONFIG_TYPE_RESTART);
2700
2701 if (local->in_reconfig) {
2702 in_reconfig = local->in_reconfig;
2703 local->in_reconfig = false;
2704 barrier();
2705
2706
2707 mutex_lock(&local->mtx);
2708 ieee80211_start_next_roc(local);
2709 mutex_unlock(&local->mtx);
2710
2711
2712 list_for_each_entry(sdata, &local->interfaces, list)
2713 ieee80211_queue_work(&local->hw, &sdata->work);
2714 }
2715
2716 ieee80211_wake_queues_by_reason(hw, IEEE80211_MAX_QUEUE_MAP,
2717 IEEE80211_QUEUE_STOP_REASON_SUSPEND,
2718 false);
2719
2720 if (in_reconfig) {
2721 list_for_each_entry(sdata, &local->interfaces, list) {
2722 if (!ieee80211_sdata_running(sdata))
2723 continue;
2724 if (sdata->vif.type == NL80211_IFTYPE_STATION)
2725 ieee80211_sta_restart(sdata);
2726 }
2727 }
2728
2729 if (!suspended)
2730 return 0;
2731
2732#ifdef CONFIG_PM
2733
2734 local->suspended = false;
2735 mb();
2736 local->resuming = false;
2737
2738 ieee80211_flush_completed_scan(local, false);
2739
2740 if (local->open_count && !reconfig_due_to_wowlan)
2741 drv_reconfig_complete(local, IEEE80211_RECONFIG_TYPE_SUSPEND);
2742
2743 list_for_each_entry(sdata, &local->interfaces, list) {
2744 if (!ieee80211_sdata_running(sdata))
2745 continue;
2746 if (sdata->vif.type == NL80211_IFTYPE_STATION)
2747 ieee80211_sta_restart(sdata);
2748 }
2749
2750 mod_timer(&local->sta_cleanup, jiffies + 1);
2751#else
2752 WARN_ON(1);
2753#endif
2754
2755 return 0;
2756}
2757
2758static void ieee80211_reconfig_disconnect(struct ieee80211_vif *vif, u8 flag)
2759{
2760 struct ieee80211_sub_if_data *sdata;
2761 struct ieee80211_local *local;
2762 struct ieee80211_key *key;
2763
2764 if (WARN_ON(!vif))
2765 return;
2766
2767 sdata = vif_to_sdata(vif);
2768 local = sdata->local;
2769
2770 if (WARN_ON(flag & IEEE80211_SDATA_DISCONNECT_RESUME &&
2771 !local->resuming))
2772 return;
2773
2774 if (WARN_ON(flag & IEEE80211_SDATA_DISCONNECT_HW_RESTART &&
2775 !local->in_reconfig))
2776 return;
2777
2778 if (WARN_ON(vif->type != NL80211_IFTYPE_STATION))
2779 return;
2780
2781 sdata->flags |= flag;
2782
2783 mutex_lock(&local->key_mtx);
2784 list_for_each_entry(key, &sdata->key_list, list)
2785 key->flags |= KEY_FLAG_TAINTED;
2786 mutex_unlock(&local->key_mtx);
2787}
2788
2789void ieee80211_hw_restart_disconnect(struct ieee80211_vif *vif)
2790{
2791 ieee80211_reconfig_disconnect(vif, IEEE80211_SDATA_DISCONNECT_HW_RESTART);
2792}
2793EXPORT_SYMBOL_GPL(ieee80211_hw_restart_disconnect);
2794
2795void ieee80211_resume_disconnect(struct ieee80211_vif *vif)
2796{
2797 ieee80211_reconfig_disconnect(vif, IEEE80211_SDATA_DISCONNECT_RESUME);
2798}
2799EXPORT_SYMBOL_GPL(ieee80211_resume_disconnect);
2800
2801void ieee80211_recalc_smps(struct ieee80211_sub_if_data *sdata)
2802{
2803 struct ieee80211_local *local = sdata->local;
2804 struct ieee80211_chanctx_conf *chanctx_conf;
2805 struct ieee80211_chanctx *chanctx;
2806
2807 mutex_lock(&local->chanctx_mtx);
2808
2809 chanctx_conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
2810 lockdep_is_held(&local->chanctx_mtx));
2811
2812
2813
2814
2815
2816
2817
2818 if (!chanctx_conf)
2819 goto unlock;
2820
2821 chanctx = container_of(chanctx_conf, struct ieee80211_chanctx, conf);
2822 ieee80211_recalc_smps_chanctx(local, chanctx);
2823 unlock:
2824 mutex_unlock(&local->chanctx_mtx);
2825}
2826
2827void ieee80211_recalc_min_chandef(struct ieee80211_sub_if_data *sdata)
2828{
2829 struct ieee80211_local *local = sdata->local;
2830 struct ieee80211_chanctx_conf *chanctx_conf;
2831 struct ieee80211_chanctx *chanctx;
2832
2833 mutex_lock(&local->chanctx_mtx);
2834
2835 chanctx_conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
2836 lockdep_is_held(&local->chanctx_mtx));
2837
2838 if (WARN_ON_ONCE(!chanctx_conf))
2839 goto unlock;
2840
2841 chanctx = container_of(chanctx_conf, struct ieee80211_chanctx, conf);
2842 ieee80211_recalc_chanctx_min_def(local, chanctx);
2843 unlock:
2844 mutex_unlock(&local->chanctx_mtx);
2845}
2846
2847size_t ieee80211_ie_split_vendor(const u8 *ies, size_t ielen, size_t offset)
2848{
2849 size_t pos = offset;
2850
2851 while (pos < ielen && ies[pos] != WLAN_EID_VENDOR_SPECIFIC)
2852 pos += 2 + ies[pos + 1];
2853
2854 return pos;
2855}
2856
2857static void _ieee80211_enable_rssi_reports(struct ieee80211_sub_if_data *sdata,
2858 int rssi_min_thold,
2859 int rssi_max_thold)
2860{
2861 trace_api_enable_rssi_reports(sdata, rssi_min_thold, rssi_max_thold);
2862
2863 if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_STATION))
2864 return;
2865
2866
2867
2868
2869
2870
2871 sdata->u.mgd.rssi_min_thold = rssi_min_thold*16;
2872 sdata->u.mgd.rssi_max_thold = rssi_max_thold*16;
2873}
2874
2875void ieee80211_enable_rssi_reports(struct ieee80211_vif *vif,
2876 int rssi_min_thold,
2877 int rssi_max_thold)
2878{
2879 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
2880
2881 WARN_ON(rssi_min_thold == rssi_max_thold ||
2882 rssi_min_thold > rssi_max_thold);
2883
2884 _ieee80211_enable_rssi_reports(sdata, rssi_min_thold,
2885 rssi_max_thold);
2886}
2887EXPORT_SYMBOL(ieee80211_enable_rssi_reports);
2888
2889void ieee80211_disable_rssi_reports(struct ieee80211_vif *vif)
2890{
2891 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
2892
2893 _ieee80211_enable_rssi_reports(sdata, 0, 0);
2894}
2895EXPORT_SYMBOL(ieee80211_disable_rssi_reports);
2896
2897u8 *ieee80211_ie_build_ht_cap(u8 *pos, struct ieee80211_sta_ht_cap *ht_cap,
2898 u16 cap)
2899{
2900 __le16 tmp;
2901
2902 *pos++ = WLAN_EID_HT_CAPABILITY;
2903 *pos++ = sizeof(struct ieee80211_ht_cap);
2904 memset(pos, 0, sizeof(struct ieee80211_ht_cap));
2905
2906
2907 tmp = cpu_to_le16(cap);
2908 memcpy(pos, &tmp, sizeof(u16));
2909 pos += sizeof(u16);
2910
2911
2912 *pos++ = ht_cap->ampdu_factor |
2913 (ht_cap->ampdu_density <<
2914 IEEE80211_HT_AMPDU_PARM_DENSITY_SHIFT);
2915
2916
2917 memcpy(pos, &ht_cap->mcs, sizeof(ht_cap->mcs));
2918 pos += sizeof(ht_cap->mcs);
2919
2920
2921 pos += sizeof(__le16);
2922
2923
2924 pos += sizeof(__le32);
2925
2926
2927 pos += sizeof(u8);
2928
2929 return pos;
2930}
2931
2932u8 *ieee80211_ie_build_vht_cap(u8 *pos, struct ieee80211_sta_vht_cap *vht_cap,
2933 u32 cap)
2934{
2935 __le32 tmp;
2936
2937 *pos++ = WLAN_EID_VHT_CAPABILITY;
2938 *pos++ = sizeof(struct ieee80211_vht_cap);
2939 memset(pos, 0, sizeof(struct ieee80211_vht_cap));
2940
2941
2942 tmp = cpu_to_le32(cap);
2943 memcpy(pos, &tmp, sizeof(u32));
2944 pos += sizeof(u32);
2945
2946
2947 memcpy(pos, &vht_cap->vht_mcs, sizeof(vht_cap->vht_mcs));
2948 pos += sizeof(vht_cap->vht_mcs);
2949
2950 return pos;
2951}
2952
2953u8 ieee80211_ie_len_he_cap(struct ieee80211_sub_if_data *sdata, u8 iftype)
2954{
2955 const struct ieee80211_sta_he_cap *he_cap;
2956 struct ieee80211_supported_band *sband;
2957 u8 n;
2958
2959 sband = ieee80211_get_sband(sdata);
2960 if (!sband)
2961 return 0;
2962
2963 he_cap = ieee80211_get_he_iftype_cap(sband, iftype);
2964 if (!he_cap)
2965 return 0;
2966
2967 n = ieee80211_he_mcs_nss_size(&he_cap->he_cap_elem);
2968 return 2 + 1 +
2969 sizeof(he_cap->he_cap_elem) + n +
2970 ieee80211_he_ppe_size(he_cap->ppe_thres[0],
2971 he_cap->he_cap_elem.phy_cap_info);
2972}
2973
2974u8 *ieee80211_ie_build_he_cap(u32 disable_flags, u8 *pos,
2975 const struct ieee80211_sta_he_cap *he_cap,
2976 u8 *end)
2977{
2978 struct ieee80211_he_cap_elem elem;
2979 u8 n;
2980 u8 ie_len;
2981 u8 *orig_pos = pos;
2982
2983
2984
2985
2986
2987
2988 if (!he_cap)
2989 return orig_pos;
2990
2991
2992 elem = he_cap->he_cap_elem;
2993
2994 if (disable_flags & IEEE80211_STA_DISABLE_40MHZ)
2995 elem.phy_cap_info[0] &=
2996 ~(IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_80MHZ_IN_5G |
2997 IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_IN_2G);
2998
2999 if (disable_flags & IEEE80211_STA_DISABLE_160MHZ)
3000 elem.phy_cap_info[0] &=
3001 ~IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G;
3002
3003 if (disable_flags & IEEE80211_STA_DISABLE_80P80MHZ)
3004 elem.phy_cap_info[0] &=
3005 ~IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G;
3006
3007 n = ieee80211_he_mcs_nss_size(&elem);
3008 ie_len = 2 + 1 +
3009 sizeof(he_cap->he_cap_elem) + n +
3010 ieee80211_he_ppe_size(he_cap->ppe_thres[0],
3011 he_cap->he_cap_elem.phy_cap_info);
3012
3013 if ((end - pos) < ie_len)
3014 return orig_pos;
3015
3016 *pos++ = WLAN_EID_EXTENSION;
3017 pos++;
3018 *pos++ = WLAN_EID_EXT_HE_CAPABILITY;
3019
3020
3021 memcpy(pos, &elem, sizeof(elem));
3022 pos += sizeof(elem);
3023
3024 memcpy(pos, &he_cap->he_mcs_nss_supp, n);
3025 pos += n;
3026
3027
3028 if ((he_cap->he_cap_elem.phy_cap_info[6] &
3029 IEEE80211_HE_PHY_CAP6_PPE_THRESHOLD_PRESENT) == 0)
3030 goto end;
3031
3032
3033
3034
3035
3036 n = hweight8(he_cap->ppe_thres[0] &
3037 IEEE80211_PPE_THRES_RU_INDEX_BITMASK_MASK);
3038 n *= (1 + ((he_cap->ppe_thres[0] & IEEE80211_PPE_THRES_NSS_MASK) >>
3039 IEEE80211_PPE_THRES_NSS_POS));
3040
3041
3042
3043
3044
3045 n = (n * IEEE80211_PPE_THRES_INFO_PPET_SIZE * 2) + 7;
3046 n = DIV_ROUND_UP(n, 8);
3047
3048
3049 memcpy(pos, &he_cap->ppe_thres, n);
3050 pos += n;
3051
3052end:
3053 orig_pos[1] = (pos - orig_pos) - 2;
3054 return pos;
3055}
3056
3057void ieee80211_ie_build_he_6ghz_cap(struct ieee80211_sub_if_data *sdata,
3058 struct sk_buff *skb)
3059{
3060 struct ieee80211_supported_band *sband;
3061 const struct ieee80211_sband_iftype_data *iftd;
3062 enum nl80211_iftype iftype = ieee80211_vif_type_p2p(&sdata->vif);
3063 u8 *pos;
3064 u16 cap;
3065
3066 if (!cfg80211_any_usable_channels(sdata->local->hw.wiphy,
3067 BIT(NL80211_BAND_6GHZ),
3068 IEEE80211_CHAN_NO_HE))
3069 return;
3070
3071 sband = sdata->local->hw.wiphy->bands[NL80211_BAND_6GHZ];
3072
3073 iftd = ieee80211_get_sband_iftype_data(sband, iftype);
3074 if (!iftd)
3075 return;
3076
3077
3078 if (!iftd->he_6ghz_capa.capa)
3079 return;
3080
3081 cap = le16_to_cpu(iftd->he_6ghz_capa.capa);
3082 cap &= ~IEEE80211_HE_6GHZ_CAP_SM_PS;
3083
3084 switch (sdata->smps_mode) {
3085 case IEEE80211_SMPS_AUTOMATIC:
3086 case IEEE80211_SMPS_NUM_MODES:
3087 WARN_ON(1);
3088 fallthrough;
3089 case IEEE80211_SMPS_OFF:
3090 cap |= u16_encode_bits(WLAN_HT_CAP_SM_PS_DISABLED,
3091 IEEE80211_HE_6GHZ_CAP_SM_PS);
3092 break;
3093 case IEEE80211_SMPS_STATIC:
3094 cap |= u16_encode_bits(WLAN_HT_CAP_SM_PS_STATIC,
3095 IEEE80211_HE_6GHZ_CAP_SM_PS);
3096 break;
3097 case IEEE80211_SMPS_DYNAMIC:
3098 cap |= u16_encode_bits(WLAN_HT_CAP_SM_PS_DYNAMIC,
3099 IEEE80211_HE_6GHZ_CAP_SM_PS);
3100 break;
3101 }
3102
3103 pos = skb_put(skb, 2 + 1 + sizeof(cap));
3104 ieee80211_write_he_6ghz_cap(pos, cpu_to_le16(cap),
3105 pos + 2 + 1 + sizeof(cap));
3106}
3107
3108u8 *ieee80211_ie_build_ht_oper(u8 *pos, struct ieee80211_sta_ht_cap *ht_cap,
3109 const struct cfg80211_chan_def *chandef,
3110 u16 prot_mode, bool rifs_mode)
3111{
3112 struct ieee80211_ht_operation *ht_oper;
3113
3114 *pos++ = WLAN_EID_HT_OPERATION;
3115 *pos++ = sizeof(struct ieee80211_ht_operation);
3116 ht_oper = (struct ieee80211_ht_operation *)pos;
3117 ht_oper->primary_chan = ieee80211_frequency_to_channel(
3118 chandef->chan->center_freq);
3119 switch (chandef->width) {
3120 case NL80211_CHAN_WIDTH_160:
3121 case NL80211_CHAN_WIDTH_80P80:
3122 case NL80211_CHAN_WIDTH_80:
3123 case NL80211_CHAN_WIDTH_40:
3124 if (chandef->center_freq1 > chandef->chan->center_freq)
3125 ht_oper->ht_param = IEEE80211_HT_PARAM_CHA_SEC_ABOVE;
3126 else
3127 ht_oper->ht_param = IEEE80211_HT_PARAM_CHA_SEC_BELOW;
3128 break;
3129 case NL80211_CHAN_WIDTH_320:
3130
3131 WARN_ON(1);
3132 return pos;
3133 default:
3134 ht_oper->ht_param = IEEE80211_HT_PARAM_CHA_SEC_NONE;
3135 break;
3136 }
3137 if (ht_cap->cap & IEEE80211_HT_CAP_SUP_WIDTH_20_40 &&
3138 chandef->width != NL80211_CHAN_WIDTH_20_NOHT &&
3139 chandef->width != NL80211_CHAN_WIDTH_20)
3140 ht_oper->ht_param |= IEEE80211_HT_PARAM_CHAN_WIDTH_ANY;
3141
3142 if (rifs_mode)
3143 ht_oper->ht_param |= IEEE80211_HT_PARAM_RIFS_MODE;
3144
3145 ht_oper->operation_mode = cpu_to_le16(prot_mode);
3146 ht_oper->stbc_param = 0x0000;
3147
3148
3149
3150 memset(&ht_oper->basic_set, 0, 16);
3151 memcpy(&ht_oper->basic_set, &ht_cap->mcs, 10);
3152
3153 return pos + sizeof(struct ieee80211_ht_operation);
3154}
3155
3156void ieee80211_ie_build_wide_bw_cs(u8 *pos,
3157 const struct cfg80211_chan_def *chandef)
3158{
3159 *pos++ = WLAN_EID_WIDE_BW_CHANNEL_SWITCH;
3160 *pos++ = 3;
3161
3162 switch (chandef->width) {
3163 case NL80211_CHAN_WIDTH_80:
3164 *pos++ = IEEE80211_VHT_CHANWIDTH_80MHZ;
3165 break;
3166 case NL80211_CHAN_WIDTH_160:
3167 *pos++ = IEEE80211_VHT_CHANWIDTH_160MHZ;
3168 break;
3169 case NL80211_CHAN_WIDTH_80P80:
3170 *pos++ = IEEE80211_VHT_CHANWIDTH_80P80MHZ;
3171 break;
3172 case NL80211_CHAN_WIDTH_320:
3173
3174 WARN_ON(1);
3175 fallthrough;
3176 default:
3177 *pos++ = IEEE80211_VHT_CHANWIDTH_USE_HT;
3178 }
3179
3180
3181 *pos++ = ieee80211_frequency_to_channel(chandef->center_freq1);
3182
3183 if (chandef->center_freq2)
3184 *pos++ = ieee80211_frequency_to_channel(chandef->center_freq2);
3185 else
3186 *pos++ = 0;
3187}
3188
3189u8 *ieee80211_ie_build_vht_oper(u8 *pos, struct ieee80211_sta_vht_cap *vht_cap,
3190 const struct cfg80211_chan_def *chandef)
3191{
3192 struct ieee80211_vht_operation *vht_oper;
3193
3194 *pos++ = WLAN_EID_VHT_OPERATION;
3195 *pos++ = sizeof(struct ieee80211_vht_operation);
3196 vht_oper = (struct ieee80211_vht_operation *)pos;
3197 vht_oper->center_freq_seg0_idx = ieee80211_frequency_to_channel(
3198 chandef->center_freq1);
3199 if (chandef->center_freq2)
3200 vht_oper->center_freq_seg1_idx =
3201 ieee80211_frequency_to_channel(chandef->center_freq2);
3202 else
3203 vht_oper->center_freq_seg1_idx = 0x00;
3204
3205 switch (chandef->width) {
3206 case NL80211_CHAN_WIDTH_160:
3207
3208
3209
3210
3211 vht_oper->chan_width = IEEE80211_VHT_CHANWIDTH_80MHZ;
3212 vht_oper->center_freq_seg1_idx = vht_oper->center_freq_seg0_idx;
3213 if (chandef->chan->center_freq < chandef->center_freq1)
3214 vht_oper->center_freq_seg0_idx -= 8;
3215 else
3216 vht_oper->center_freq_seg0_idx += 8;
3217 break;
3218 case NL80211_CHAN_WIDTH_80P80:
3219
3220
3221
3222
3223 vht_oper->chan_width = IEEE80211_VHT_CHANWIDTH_80MHZ;
3224 break;
3225 case NL80211_CHAN_WIDTH_80:
3226 vht_oper->chan_width = IEEE80211_VHT_CHANWIDTH_80MHZ;
3227 break;
3228 case NL80211_CHAN_WIDTH_320:
3229
3230 WARN_ON(1);
3231 return pos;
3232 default:
3233 vht_oper->chan_width = IEEE80211_VHT_CHANWIDTH_USE_HT;
3234 break;
3235 }
3236
3237
3238 vht_oper->basic_mcs_set = cpu_to_le16(0xffff);
3239
3240 return pos + sizeof(struct ieee80211_vht_operation);
3241}
3242
3243u8 *ieee80211_ie_build_he_oper(u8 *pos, struct cfg80211_chan_def *chandef)
3244{
3245 struct ieee80211_he_operation *he_oper;
3246 struct ieee80211_he_6ghz_oper *he_6ghz_op;
3247 u32 he_oper_params;
3248 u8 ie_len = 1 + sizeof(struct ieee80211_he_operation);
3249
3250 if (chandef->chan->band == NL80211_BAND_6GHZ)
3251 ie_len += sizeof(struct ieee80211_he_6ghz_oper);
3252
3253 *pos++ = WLAN_EID_EXTENSION;
3254 *pos++ = ie_len;
3255 *pos++ = WLAN_EID_EXT_HE_OPERATION;
3256
3257 he_oper_params = 0;
3258 he_oper_params |= u32_encode_bits(1023,
3259 IEEE80211_HE_OPERATION_RTS_THRESHOLD_MASK);
3260 he_oper_params |= u32_encode_bits(1,
3261 IEEE80211_HE_OPERATION_ER_SU_DISABLE);
3262 he_oper_params |= u32_encode_bits(1,
3263 IEEE80211_HE_OPERATION_BSS_COLOR_DISABLED);
3264 if (chandef->chan->band == NL80211_BAND_6GHZ)
3265 he_oper_params |= u32_encode_bits(1,
3266 IEEE80211_HE_OPERATION_6GHZ_OP_INFO);
3267
3268 he_oper = (struct ieee80211_he_operation *)pos;
3269 he_oper->he_oper_params = cpu_to_le32(he_oper_params);
3270
3271
3272 he_oper->he_mcs_nss_set = cpu_to_le16(0xffff);
3273 pos += sizeof(struct ieee80211_he_operation);
3274
3275 if (chandef->chan->band != NL80211_BAND_6GHZ)
3276 goto out;
3277
3278
3279 he_6ghz_op = (struct ieee80211_he_6ghz_oper *)pos;
3280 he_6ghz_op->minrate = 6;
3281 he_6ghz_op->primary =
3282 ieee80211_frequency_to_channel(chandef->chan->center_freq);
3283 he_6ghz_op->ccfs0 =
3284 ieee80211_frequency_to_channel(chandef->center_freq1);
3285 if (chandef->center_freq2)
3286 he_6ghz_op->ccfs1 =
3287 ieee80211_frequency_to_channel(chandef->center_freq2);
3288 else
3289 he_6ghz_op->ccfs1 = 0;
3290
3291 switch (chandef->width) {
3292 case NL80211_CHAN_WIDTH_320:
3293
3294
3295
3296
3297 WARN_ON(1);
3298 break;
3299 case NL80211_CHAN_WIDTH_160:
3300
3301
3302
3303 he_6ghz_op->control =
3304 IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_160MHZ;
3305 he_6ghz_op->ccfs1 = he_6ghz_op->ccfs0;
3306 if (chandef->chan->center_freq < chandef->center_freq1)
3307 he_6ghz_op->ccfs0 -= 8;
3308 else
3309 he_6ghz_op->ccfs0 += 8;
3310 fallthrough;
3311 case NL80211_CHAN_WIDTH_80P80:
3312 he_6ghz_op->control =
3313 IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_160MHZ;
3314 break;
3315 case NL80211_CHAN_WIDTH_80:
3316 he_6ghz_op->control =
3317 IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_80MHZ;
3318 break;
3319 case NL80211_CHAN_WIDTH_40:
3320 he_6ghz_op->control =
3321 IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_40MHZ;
3322 break;
3323 default:
3324 he_6ghz_op->control =
3325 IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_20MHZ;
3326 break;
3327 }
3328
3329 pos += sizeof(struct ieee80211_he_6ghz_oper);
3330
3331out:
3332 return pos;
3333}
3334
3335bool ieee80211_chandef_ht_oper(const struct ieee80211_ht_operation *ht_oper,
3336 struct cfg80211_chan_def *chandef)
3337{
3338 enum nl80211_channel_type channel_type;
3339
3340 if (!ht_oper)
3341 return false;
3342
3343 switch (ht_oper->ht_param & IEEE80211_HT_PARAM_CHA_SEC_OFFSET) {
3344 case IEEE80211_HT_PARAM_CHA_SEC_NONE:
3345 channel_type = NL80211_CHAN_HT20;
3346 break;
3347 case IEEE80211_HT_PARAM_CHA_SEC_ABOVE:
3348 channel_type = NL80211_CHAN_HT40PLUS;
3349 break;
3350 case IEEE80211_HT_PARAM_CHA_SEC_BELOW:
3351 channel_type = NL80211_CHAN_HT40MINUS;
3352 break;
3353 default:
3354 return false;
3355 }
3356
3357 cfg80211_chandef_create(chandef, chandef->chan, channel_type);
3358 return true;
3359}
3360
3361bool ieee80211_chandef_vht_oper(struct ieee80211_hw *hw, u32 vht_cap_info,
3362 const struct ieee80211_vht_operation *oper,
3363 const struct ieee80211_ht_operation *htop,
3364 struct cfg80211_chan_def *chandef)
3365{
3366 struct cfg80211_chan_def new = *chandef;
3367 int cf0, cf1;
3368 int ccfs0, ccfs1, ccfs2;
3369 int ccf0, ccf1;
3370 u32 vht_cap;
3371 bool support_80_80 = false;
3372 bool support_160 = false;
3373 u8 ext_nss_bw_supp = u32_get_bits(vht_cap_info,
3374 IEEE80211_VHT_CAP_EXT_NSS_BW_MASK);
3375 u8 supp_chwidth = u32_get_bits(vht_cap_info,
3376 IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_MASK);
3377
3378 if (!oper || !htop)
3379 return false;
3380
3381 vht_cap = hw->wiphy->bands[chandef->chan->band]->vht_cap.cap;
3382 support_160 = (vht_cap & (IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_MASK |
3383 IEEE80211_VHT_CAP_EXT_NSS_BW_MASK));
3384 support_80_80 = ((vht_cap &
3385 IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ) ||
3386 (vht_cap & IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ &&
3387 vht_cap & IEEE80211_VHT_CAP_EXT_NSS_BW_MASK) ||
3388 ((vht_cap & IEEE80211_VHT_CAP_EXT_NSS_BW_MASK) >>
3389 IEEE80211_VHT_CAP_EXT_NSS_BW_SHIFT > 1));
3390 ccfs0 = oper->center_freq_seg0_idx;
3391 ccfs1 = oper->center_freq_seg1_idx;
3392 ccfs2 = (le16_to_cpu(htop->operation_mode) &
3393 IEEE80211_HT_OP_MODE_CCFS2_MASK)
3394 >> IEEE80211_HT_OP_MODE_CCFS2_SHIFT;
3395
3396 ccf0 = ccfs0;
3397
3398
3399 if (!ieee80211_hw_check(hw, SUPPORTS_VHT_EXT_NSS_BW))
3400 ext_nss_bw_supp = 0;
3401
3402
3403
3404
3405
3406
3407
3408 switch ((supp_chwidth << 4) | ext_nss_bw_supp) {
3409 default:
3410 case 0x00:
3411 ccf1 = 0;
3412 support_160 = false;
3413 support_80_80 = false;
3414 break;
3415 case 0x01:
3416 support_80_80 = false;
3417 fallthrough;
3418 case 0x02:
3419 case 0x03:
3420 ccf1 = ccfs2;
3421 break;
3422 case 0x10:
3423 ccf1 = ccfs1;
3424 break;
3425 case 0x11:
3426 case 0x12:
3427 if (!ccfs1)
3428 ccf1 = ccfs2;
3429 else
3430 ccf1 = ccfs1;
3431 break;
3432 case 0x13:
3433 case 0x20:
3434 case 0x23:
3435 ccf1 = ccfs1;
3436 break;
3437 }
3438
3439 cf0 = ieee80211_channel_to_frequency(ccf0, chandef->chan->band);
3440 cf1 = ieee80211_channel_to_frequency(ccf1, chandef->chan->band);
3441
3442 switch (oper->chan_width) {
3443 case IEEE80211_VHT_CHANWIDTH_USE_HT:
3444
3445 break;
3446 case IEEE80211_VHT_CHANWIDTH_80MHZ:
3447 new.width = NL80211_CHAN_WIDTH_80;
3448 new.center_freq1 = cf0;
3449
3450 if (ccf1) {
3451 unsigned int diff;
3452
3453 diff = abs(ccf1 - ccf0);
3454 if ((diff == 8) && support_160) {
3455 new.width = NL80211_CHAN_WIDTH_160;
3456 new.center_freq1 = cf1;
3457 } else if ((diff > 8) && support_80_80) {
3458 new.width = NL80211_CHAN_WIDTH_80P80;
3459 new.center_freq2 = cf1;
3460 }
3461 }
3462 break;
3463 case IEEE80211_VHT_CHANWIDTH_160MHZ:
3464
3465 new.width = NL80211_CHAN_WIDTH_160;
3466 new.center_freq1 = cf0;
3467 break;
3468 case IEEE80211_VHT_CHANWIDTH_80P80MHZ:
3469
3470 new.width = NL80211_CHAN_WIDTH_80P80;
3471 new.center_freq1 = cf0;
3472 new.center_freq2 = cf1;
3473 break;
3474 default:
3475 return false;
3476 }
3477
3478 if (!cfg80211_chandef_valid(&new))
3479 return false;
3480
3481 *chandef = new;
3482 return true;
3483}
3484
3485bool ieee80211_chandef_he_6ghz_oper(struct ieee80211_sub_if_data *sdata,
3486 const struct ieee80211_he_operation *he_oper,
3487 const struct ieee80211_eht_operation *eht_oper,
3488 struct cfg80211_chan_def *chandef)
3489{
3490 struct ieee80211_local *local = sdata->local;
3491 struct ieee80211_supported_band *sband;
3492 enum nl80211_iftype iftype = ieee80211_vif_type_p2p(&sdata->vif);
3493 const struct ieee80211_sta_he_cap *he_cap;
3494 const struct ieee80211_sta_eht_cap *eht_cap;
3495 struct cfg80211_chan_def he_chandef = *chandef;
3496 const struct ieee80211_he_6ghz_oper *he_6ghz_oper;
3497 struct ieee80211_bss_conf *bss_conf = &sdata->vif.bss_conf;
3498 bool support_80_80, support_160, support_320;
3499 u8 he_phy_cap, eht_phy_cap;
3500 u32 freq;
3501
3502 if (chandef->chan->band != NL80211_BAND_6GHZ)
3503 return true;
3504
3505 sband = local->hw.wiphy->bands[NL80211_BAND_6GHZ];
3506
3507 he_cap = ieee80211_get_he_iftype_cap(sband, iftype);
3508 if (!he_cap) {
3509 sdata_info(sdata, "Missing iftype sband data/HE cap");
3510 return false;
3511 }
3512
3513 he_phy_cap = he_cap->he_cap_elem.phy_cap_info[0];
3514 support_160 =
3515 he_phy_cap &
3516 IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G;
3517 support_80_80 =
3518 he_phy_cap &
3519 IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G;
3520
3521 if (!he_oper) {
3522 sdata_info(sdata,
3523 "HE is not advertised on (on %d MHz), expect issues\n",
3524 chandef->chan->center_freq);
3525 return false;
3526 }
3527
3528 eht_cap = ieee80211_get_eht_iftype_cap(sband, iftype);
3529 if (!eht_cap) {
3530 sdata_info(sdata, "Missing iftype sband data/EHT cap");
3531 eht_oper = NULL;
3532 }
3533
3534 he_6ghz_oper = ieee80211_he_6ghz_oper(he_oper);
3535
3536 if (!he_6ghz_oper) {
3537 sdata_info(sdata,
3538 "HE 6GHz operation missing (on %d MHz), expect issues\n",
3539 chandef->chan->center_freq);
3540 return false;
3541 }
3542
3543
3544
3545
3546
3547
3548 freq = ieee80211_channel_to_frequency(he_6ghz_oper->primary,
3549 NL80211_BAND_6GHZ);
3550 he_chandef.chan = ieee80211_get_channel(sdata->local->hw.wiphy, freq);
3551
3552 switch (u8_get_bits(he_6ghz_oper->control,
3553 IEEE80211_HE_6GHZ_OPER_CTRL_REG_INFO)) {
3554 case IEEE80211_6GHZ_CTRL_REG_LPI_AP:
3555 bss_conf->power_type = IEEE80211_REG_LPI_AP;
3556 break;
3557 case IEEE80211_6GHZ_CTRL_REG_SP_AP:
3558 bss_conf->power_type = IEEE80211_REG_SP_AP;
3559 break;
3560 default:
3561 bss_conf->power_type = IEEE80211_REG_UNSET_AP;
3562 break;
3563 }
3564
3565 if (!eht_oper) {
3566 switch (u8_get_bits(he_6ghz_oper->control,
3567 IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH)) {
3568 case IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_20MHZ:
3569 he_chandef.width = NL80211_CHAN_WIDTH_20;
3570 break;
3571 case IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_40MHZ:
3572 he_chandef.width = NL80211_CHAN_WIDTH_40;
3573 break;
3574 case IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_80MHZ:
3575 he_chandef.width = NL80211_CHAN_WIDTH_80;
3576 break;
3577 case IEEE80211_HE_6GHZ_OPER_CTRL_CHANWIDTH_160MHZ:
3578 he_chandef.width = NL80211_CHAN_WIDTH_80;
3579 if (!he_6ghz_oper->ccfs1)
3580 break;
3581 if (abs(he_6ghz_oper->ccfs1 - he_6ghz_oper->ccfs0) == 8) {
3582 if (support_160)
3583 he_chandef.width = NL80211_CHAN_WIDTH_160;
3584 } else {
3585 if (support_80_80)
3586 he_chandef.width = NL80211_CHAN_WIDTH_80P80;
3587 }
3588 break;
3589 }
3590
3591 if (he_chandef.width == NL80211_CHAN_WIDTH_160) {
3592 he_chandef.center_freq1 =
3593 ieee80211_channel_to_frequency(he_6ghz_oper->ccfs1,
3594 NL80211_BAND_6GHZ);
3595 } else {
3596 he_chandef.center_freq1 =
3597 ieee80211_channel_to_frequency(he_6ghz_oper->ccfs0,
3598 NL80211_BAND_6GHZ);
3599 if (support_80_80 || support_160)
3600 he_chandef.center_freq2 =
3601 ieee80211_channel_to_frequency(he_6ghz_oper->ccfs1,
3602 NL80211_BAND_6GHZ);
3603 }
3604 } else {
3605 eht_phy_cap = eht_cap->eht_cap_elem.phy_cap_info[0];
3606 support_320 =
3607 eht_phy_cap & IEEE80211_EHT_PHY_CAP0_320MHZ_IN_6GHZ;
3608
3609 switch (u8_get_bits(eht_oper->chan_width,
3610 IEEE80211_EHT_OPER_CHAN_WIDTH)) {
3611 case IEEE80211_EHT_OPER_CHAN_WIDTH_20MHZ:
3612 he_chandef.width = NL80211_CHAN_WIDTH_20;
3613 break;
3614 case IEEE80211_EHT_OPER_CHAN_WIDTH_40MHZ:
3615 he_chandef.width = NL80211_CHAN_WIDTH_40;
3616 break;
3617 case IEEE80211_EHT_OPER_CHAN_WIDTH_80MHZ:
3618 he_chandef.width = NL80211_CHAN_WIDTH_80;
3619 break;
3620 case IEEE80211_EHT_OPER_CHAN_WIDTH_160MHZ:
3621 if (support_160)
3622 he_chandef.width = NL80211_CHAN_WIDTH_160;
3623 else
3624 he_chandef.width = NL80211_CHAN_WIDTH_80;
3625 break;
3626 case IEEE80211_EHT_OPER_CHAN_WIDTH_320MHZ:
3627 if (support_320)
3628 he_chandef.width = NL80211_CHAN_WIDTH_320;
3629 else if (support_160)
3630 he_chandef.width = NL80211_CHAN_WIDTH_160;
3631 else
3632 he_chandef.width = NL80211_CHAN_WIDTH_80;
3633 break;
3634 }
3635
3636 he_chandef.center_freq1 =
3637 ieee80211_channel_to_frequency(eht_oper->ccfs,
3638 NL80211_BAND_6GHZ);
3639 }
3640
3641 if (!cfg80211_chandef_valid(&he_chandef)) {
3642 sdata_info(sdata,
3643 "HE 6GHz operation resulted in invalid chandef: %d MHz/%d/%d MHz/%d MHz\n",
3644 he_chandef.chan ? he_chandef.chan->center_freq : 0,
3645 he_chandef.width,
3646 he_chandef.center_freq1,
3647 he_chandef.center_freq2);
3648 return false;
3649 }
3650
3651 *chandef = he_chandef;
3652
3653 return true;
3654}
3655
3656bool ieee80211_chandef_s1g_oper(const struct ieee80211_s1g_oper_ie *oper,
3657 struct cfg80211_chan_def *chandef)
3658{
3659 u32 oper_freq;
3660
3661 if (!oper)
3662 return false;
3663
3664 switch (FIELD_GET(S1G_OPER_CH_WIDTH_OPER, oper->ch_width)) {
3665 case IEEE80211_S1G_CHANWIDTH_1MHZ:
3666 chandef->width = NL80211_CHAN_WIDTH_1;
3667 break;
3668 case IEEE80211_S1G_CHANWIDTH_2MHZ:
3669 chandef->width = NL80211_CHAN_WIDTH_2;
3670 break;
3671 case IEEE80211_S1G_CHANWIDTH_4MHZ:
3672 chandef->width = NL80211_CHAN_WIDTH_4;
3673 break;
3674 case IEEE80211_S1G_CHANWIDTH_8MHZ:
3675 chandef->width = NL80211_CHAN_WIDTH_8;
3676 break;
3677 case IEEE80211_S1G_CHANWIDTH_16MHZ:
3678 chandef->width = NL80211_CHAN_WIDTH_16;
3679 break;
3680 default:
3681 return false;
3682 }
3683
3684 oper_freq = ieee80211_channel_to_freq_khz(oper->oper_ch,
3685 NL80211_BAND_S1GHZ);
3686 chandef->center_freq1 = KHZ_TO_MHZ(oper_freq);
3687 chandef->freq1_offset = oper_freq % 1000;
3688
3689 return true;
3690}
3691
3692int ieee80211_parse_bitrates(struct cfg80211_chan_def *chandef,
3693 const struct ieee80211_supported_band *sband,
3694 const u8 *srates, int srates_len, u32 *rates)
3695{
3696 u32 rate_flags = ieee80211_chandef_rate_flags(chandef);
3697 int shift = ieee80211_chandef_get_shift(chandef);
3698 struct ieee80211_rate *br;
3699 int brate, rate, i, j, count = 0;
3700
3701 *rates = 0;
3702
3703 for (i = 0; i < srates_len; i++) {
3704 rate = srates[i] & 0x7f;
3705
3706 for (j = 0; j < sband->n_bitrates; j++) {
3707 br = &sband->bitrates[j];
3708 if ((rate_flags & br->flags) != rate_flags)
3709 continue;
3710
3711 brate = DIV_ROUND_UP(br->bitrate, (1 << shift) * 5);
3712 if (brate == rate) {
3713 *rates |= BIT(j);
3714 count++;
3715 break;
3716 }
3717 }
3718 }
3719 return count;
3720}
3721
3722int ieee80211_add_srates_ie(struct ieee80211_sub_if_data *sdata,
3723 struct sk_buff *skb, bool need_basic,
3724 enum nl80211_band band)
3725{
3726 struct ieee80211_local *local = sdata->local;
3727 struct ieee80211_supported_band *sband;
3728 int rate, shift;
3729 u8 i, rates, *pos;
3730 u32 basic_rates = sdata->vif.bss_conf.basic_rates;
3731 u32 rate_flags;
3732
3733 shift = ieee80211_vif_get_shift(&sdata->vif);
3734 rate_flags = ieee80211_chandef_rate_flags(&sdata->vif.bss_conf.chandef);
3735 sband = local->hw.wiphy->bands[band];
3736 rates = 0;
3737 for (i = 0; i < sband->n_bitrates; i++) {
3738 if ((rate_flags & sband->bitrates[i].flags) != rate_flags)
3739 continue;
3740 rates++;
3741 }
3742 if (rates > 8)
3743 rates = 8;
3744
3745 if (skb_tailroom(skb) < rates + 2)
3746 return -ENOMEM;
3747
3748 pos = skb_put(skb, rates + 2);
3749 *pos++ = WLAN_EID_SUPP_RATES;
3750 *pos++ = rates;
3751 for (i = 0; i < rates; i++) {
3752 u8 basic = 0;
3753 if ((rate_flags & sband->bitrates[i].flags) != rate_flags)
3754 continue;
3755
3756 if (need_basic && basic_rates & BIT(i))
3757 basic = 0x80;
3758 rate = DIV_ROUND_UP(sband->bitrates[i].bitrate,
3759 5 * (1 << shift));
3760 *pos++ = basic | (u8) rate;
3761 }
3762
3763 return 0;
3764}
3765
3766int ieee80211_add_ext_srates_ie(struct ieee80211_sub_if_data *sdata,
3767 struct sk_buff *skb, bool need_basic,
3768 enum nl80211_band band)
3769{
3770 struct ieee80211_local *local = sdata->local;
3771 struct ieee80211_supported_band *sband;
3772 int rate, shift;
3773 u8 i, exrates, *pos;
3774 u32 basic_rates = sdata->vif.bss_conf.basic_rates;
3775 u32 rate_flags;
3776
3777 rate_flags = ieee80211_chandef_rate_flags(&sdata->vif.bss_conf.chandef);
3778 shift = ieee80211_vif_get_shift(&sdata->vif);
3779
3780 sband = local->hw.wiphy->bands[band];
3781 exrates = 0;
3782 for (i = 0; i < sband->n_bitrates; i++) {
3783 if ((rate_flags & sband->bitrates[i].flags) != rate_flags)
3784 continue;
3785 exrates++;
3786 }
3787
3788 if (exrates > 8)
3789 exrates -= 8;
3790 else
3791 exrates = 0;
3792
3793 if (skb_tailroom(skb) < exrates + 2)
3794 return -ENOMEM;
3795
3796 if (exrates) {
3797 pos = skb_put(skb, exrates + 2);
3798 *pos++ = WLAN_EID_EXT_SUPP_RATES;
3799 *pos++ = exrates;
3800 for (i = 8; i < sband->n_bitrates; i++) {
3801 u8 basic = 0;
3802 if ((rate_flags & sband->bitrates[i].flags)
3803 != rate_flags)
3804 continue;
3805 if (need_basic && basic_rates & BIT(i))
3806 basic = 0x80;
3807 rate = DIV_ROUND_UP(sband->bitrates[i].bitrate,
3808 5 * (1 << shift));
3809 *pos++ = basic | (u8) rate;
3810 }
3811 }
3812 return 0;
3813}
3814
3815int ieee80211_ave_rssi(struct ieee80211_vif *vif)
3816{
3817 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
3818 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
3819
3820 if (WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION)) {
3821
3822 return 0;
3823 }
3824 return -ewma_beacon_signal_read(&ifmgd->ave_beacon_signal);
3825}
3826EXPORT_SYMBOL_GPL(ieee80211_ave_rssi);
3827
3828u8 ieee80211_mcs_to_chains(const struct ieee80211_mcs_info *mcs)
3829{
3830 if (!mcs)
3831 return 1;
3832
3833
3834
3835 if (mcs->rx_mask[3])
3836 return 4;
3837 if (mcs->rx_mask[2])
3838 return 3;
3839 if (mcs->rx_mask[1])
3840 return 2;
3841 return 1;
3842}
3843
3844
3845
3846
3847
3848
3849
3850
3851
3852
3853
3854
3855u64 ieee80211_calculate_rx_timestamp(struct ieee80211_local *local,
3856 struct ieee80211_rx_status *status,
3857 unsigned int mpdu_len,
3858 unsigned int mpdu_offset)
3859{
3860 u64 ts = status->mactime;
3861 struct rate_info ri;
3862 u16 rate;
3863 u8 n_ltf;
3864
3865 if (WARN_ON(!ieee80211_have_rx_timestamp(status)))
3866 return 0;
3867
3868 memset(&ri, 0, sizeof(ri));
3869
3870 ri.bw = status->bw;
3871
3872
3873 switch (status->encoding) {
3874 case RX_ENC_HE:
3875 ri.flags |= RATE_INFO_FLAGS_HE_MCS;
3876 ri.mcs = status->rate_idx;
3877 ri.nss = status->nss;
3878 ri.he_ru_alloc = status->he_ru;
3879 if (status->enc_flags & RX_ENC_FLAG_SHORT_GI)
3880 ri.flags |= RATE_INFO_FLAGS_SHORT_GI;
3881
3882
3883
3884
3885
3886 if (status->flag & RX_FLAG_MACTIME_PLCP_START) {
3887 mpdu_offset += 2;
3888 ts += 36;
3889
3890
3891
3892
3893
3894
3895
3896
3897 }
3898
3899 break;
3900 case RX_ENC_HT:
3901 ri.mcs = status->rate_idx;
3902 ri.flags |= RATE_INFO_FLAGS_MCS;
3903 if (status->enc_flags & RX_ENC_FLAG_SHORT_GI)
3904 ri.flags |= RATE_INFO_FLAGS_SHORT_GI;
3905
3906
3907
3908
3909
3910 if (status->flag & RX_FLAG_MACTIME_PLCP_START) {
3911 mpdu_offset += 2;
3912 if (status->enc_flags & RX_ENC_FLAG_HT_GF)
3913 ts += 24;
3914 else
3915 ts += 32;
3916
3917
3918
3919
3920
3921 n_ltf = ((ri.mcs >> 3) & 3) + 1;
3922 n_ltf = n_ltf == 3 ? 4 : n_ltf;
3923 ts += n_ltf * 4;
3924 }
3925
3926 break;
3927 case RX_ENC_VHT:
3928 ri.flags |= RATE_INFO_FLAGS_VHT_MCS;
3929 ri.mcs = status->rate_idx;
3930 ri.nss = status->nss;
3931 if (status->enc_flags & RX_ENC_FLAG_SHORT_GI)
3932 ri.flags |= RATE_INFO_FLAGS_SHORT_GI;
3933
3934
3935
3936
3937
3938 if (status->flag & RX_FLAG_MACTIME_PLCP_START) {
3939 mpdu_offset += 2;
3940 ts += 36;
3941
3942
3943
3944
3945 n_ltf = (ri.nss != 1) && (ri.nss % 2) ?
3946 ri.nss + 1 : ri.nss;
3947 ts += 4 * n_ltf;
3948 }
3949
3950 break;
3951 default:
3952 WARN_ON(1);
3953 fallthrough;
3954 case RX_ENC_LEGACY: {
3955 struct ieee80211_supported_band *sband;
3956 int shift = 0;
3957 int bitrate;
3958
3959 switch (status->bw) {
3960 case RATE_INFO_BW_10:
3961 shift = 1;
3962 break;
3963 case RATE_INFO_BW_5:
3964 shift = 2;
3965 break;
3966 }
3967
3968 sband = local->hw.wiphy->bands[status->band];
3969 bitrate = sband->bitrates[status->rate_idx].bitrate;
3970 ri.legacy = DIV_ROUND_UP(bitrate, (1 << shift));
3971
3972 if (status->flag & RX_FLAG_MACTIME_PLCP_START) {
3973 if (status->band == NL80211_BAND_5GHZ) {
3974 ts += 20 << shift;
3975 mpdu_offset += 2;
3976 } else if (status->enc_flags & RX_ENC_FLAG_SHORTPRE) {
3977 ts += 96;
3978 } else {
3979 ts += 192;
3980 }
3981 }
3982 break;
3983 }
3984 }
3985
3986 rate = cfg80211_calculate_bitrate(&ri);
3987 if (WARN_ONCE(!rate,
3988 "Invalid bitrate: flags=0x%llx, idx=%d, vht_nss=%d\n",
3989 (unsigned long long)status->flag, status->rate_idx,
3990 status->nss))
3991 return 0;
3992
3993
3994 if (status->flag & RX_FLAG_MACTIME_END)
3995 ts -= mpdu_len * 8 * 10 / rate;
3996
3997 ts += mpdu_offset * 8 * 10 / rate;
3998
3999 return ts;
4000}
4001
4002void ieee80211_dfs_cac_cancel(struct ieee80211_local *local)
4003{
4004 struct ieee80211_sub_if_data *sdata;
4005 struct cfg80211_chan_def chandef;
4006
4007
4008 lockdep_assert_wiphy(local->hw.wiphy);
4009
4010 mutex_lock(&local->mtx);
4011 list_for_each_entry(sdata, &local->interfaces, list) {
4012
4013
4014
4015
4016 cancel_delayed_work(&sdata->dfs_cac_timer_work);
4017
4018 if (sdata->wdev.cac_started) {
4019 chandef = sdata->vif.bss_conf.chandef;
4020 ieee80211_vif_release_channel(sdata);
4021 cfg80211_cac_event(sdata->dev,
4022 &chandef,
4023 NL80211_RADAR_CAC_ABORTED,
4024 GFP_KERNEL);
4025 }
4026 }
4027 mutex_unlock(&local->mtx);
4028}
4029
4030void ieee80211_dfs_radar_detected_work(struct work_struct *work)
4031{
4032 struct ieee80211_local *local =
4033 container_of(work, struct ieee80211_local, radar_detected_work);
4034 struct cfg80211_chan_def chandef = local->hw.conf.chandef;
4035 struct ieee80211_chanctx *ctx;
4036 int num_chanctx = 0;
4037
4038 mutex_lock(&local->chanctx_mtx);
4039 list_for_each_entry(ctx, &local->chanctx_list, list) {
4040 if (ctx->replace_state == IEEE80211_CHANCTX_REPLACES_OTHER)
4041 continue;
4042
4043 num_chanctx++;
4044 chandef = ctx->conf.def;
4045 }
4046 mutex_unlock(&local->chanctx_mtx);
4047
4048 wiphy_lock(local->hw.wiphy);
4049 ieee80211_dfs_cac_cancel(local);
4050 wiphy_unlock(local->hw.wiphy);
4051
4052 if (num_chanctx > 1)
4053
4054 WARN_ON(1);
4055 else
4056 cfg80211_radar_event(local->hw.wiphy, &chandef, GFP_KERNEL);
4057}
4058
4059void ieee80211_radar_detected(struct ieee80211_hw *hw)
4060{
4061 struct ieee80211_local *local = hw_to_local(hw);
4062
4063 trace_api_radar_detected(local);
4064
4065 schedule_work(&local->radar_detected_work);
4066}
4067EXPORT_SYMBOL(ieee80211_radar_detected);
4068
4069u32 ieee80211_chandef_downgrade(struct cfg80211_chan_def *c)
4070{
4071 u32 ret;
4072 int tmp;
4073
4074 switch (c->width) {
4075 case NL80211_CHAN_WIDTH_20:
4076 c->width = NL80211_CHAN_WIDTH_20_NOHT;
4077 ret = IEEE80211_STA_DISABLE_HT | IEEE80211_STA_DISABLE_VHT;
4078 break;
4079 case NL80211_CHAN_WIDTH_40:
4080 c->width = NL80211_CHAN_WIDTH_20;
4081 c->center_freq1 = c->chan->center_freq;
4082 ret = IEEE80211_STA_DISABLE_40MHZ |
4083 IEEE80211_STA_DISABLE_VHT;
4084 break;
4085 case NL80211_CHAN_WIDTH_80:
4086 tmp = (30 + c->chan->center_freq - c->center_freq1)/20;
4087
4088 tmp /= 2;
4089
4090 c->center_freq1 = c->center_freq1 - 20 + 40 * tmp;
4091 c->width = NL80211_CHAN_WIDTH_40;
4092 ret = IEEE80211_STA_DISABLE_VHT;
4093 break;
4094 case NL80211_CHAN_WIDTH_80P80:
4095 c->center_freq2 = 0;
4096 c->width = NL80211_CHAN_WIDTH_80;
4097 ret = IEEE80211_STA_DISABLE_80P80MHZ |
4098 IEEE80211_STA_DISABLE_160MHZ;
4099 break;
4100 case NL80211_CHAN_WIDTH_160:
4101
4102 tmp = (70 + c->chan->center_freq - c->center_freq1)/20;
4103
4104 tmp /= 4;
4105 c->center_freq1 = c->center_freq1 - 40 + 80 * tmp;
4106 c->width = NL80211_CHAN_WIDTH_80;
4107 ret = IEEE80211_STA_DISABLE_80P80MHZ |
4108 IEEE80211_STA_DISABLE_160MHZ;
4109 break;
4110 case NL80211_CHAN_WIDTH_320:
4111
4112 tmp = (150 + c->chan->center_freq - c->center_freq1) / 20;
4113
4114 tmp /= 80;
4115 c->center_freq1 = c->center_freq1 - 80 + 160 * tmp;
4116 c->width = NL80211_CHAN_WIDTH_160;
4117 ret = IEEE80211_STA_DISABLE_320MHZ;
4118 break;
4119 default:
4120 case NL80211_CHAN_WIDTH_20_NOHT:
4121 WARN_ON_ONCE(1);
4122 c->width = NL80211_CHAN_WIDTH_20_NOHT;
4123 ret = IEEE80211_STA_DISABLE_HT | IEEE80211_STA_DISABLE_VHT;
4124 break;
4125 case NL80211_CHAN_WIDTH_1:
4126 case NL80211_CHAN_WIDTH_2:
4127 case NL80211_CHAN_WIDTH_4:
4128 case NL80211_CHAN_WIDTH_8:
4129 case NL80211_CHAN_WIDTH_16:
4130 case NL80211_CHAN_WIDTH_5:
4131 case NL80211_CHAN_WIDTH_10:
4132 WARN_ON_ONCE(1);
4133
4134 ret = IEEE80211_STA_DISABLE_HT | IEEE80211_STA_DISABLE_VHT;
4135 break;
4136 }
4137
4138 WARN_ON_ONCE(!cfg80211_chandef_valid(c));
4139
4140 return ret;
4141}
4142
4143
4144
4145
4146
4147bool ieee80211_smps_is_restrictive(enum ieee80211_smps_mode smps_mode_old,
4148 enum ieee80211_smps_mode smps_mode_new)
4149{
4150 if (WARN_ON_ONCE(smps_mode_old == IEEE80211_SMPS_AUTOMATIC ||
4151 smps_mode_new == IEEE80211_SMPS_AUTOMATIC))
4152 return false;
4153
4154 switch (smps_mode_old) {
4155 case IEEE80211_SMPS_STATIC:
4156 return false;
4157 case IEEE80211_SMPS_DYNAMIC:
4158 return smps_mode_new == IEEE80211_SMPS_STATIC;
4159 case IEEE80211_SMPS_OFF:
4160 return smps_mode_new != IEEE80211_SMPS_OFF;
4161 default:
4162 WARN_ON(1);
4163 }
4164
4165 return false;
4166}
4167
4168int ieee80211_send_action_csa(struct ieee80211_sub_if_data *sdata,
4169 struct cfg80211_csa_settings *csa_settings)
4170{
4171 struct sk_buff *skb;
4172 struct ieee80211_mgmt *mgmt;
4173 struct ieee80211_local *local = sdata->local;
4174 int freq;
4175 int hdr_len = offsetofend(struct ieee80211_mgmt,
4176 u.action.u.chan_switch);
4177 u8 *pos;
4178
4179 if (sdata->vif.type != NL80211_IFTYPE_ADHOC &&
4180 sdata->vif.type != NL80211_IFTYPE_MESH_POINT)
4181 return -EOPNOTSUPP;
4182
4183 skb = dev_alloc_skb(local->tx_headroom + hdr_len +
4184 5 +
4185 3 +
4186 5 +
4187 8);
4188 if (!skb)
4189 return -ENOMEM;
4190
4191 skb_reserve(skb, local->tx_headroom);
4192 mgmt = skb_put_zero(skb, hdr_len);
4193 mgmt->frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
4194 IEEE80211_STYPE_ACTION);
4195
4196 eth_broadcast_addr(mgmt->da);
4197 memcpy(mgmt->sa, sdata->vif.addr, ETH_ALEN);
4198 if (ieee80211_vif_is_mesh(&sdata->vif)) {
4199 memcpy(mgmt->bssid, sdata->vif.addr, ETH_ALEN);
4200 } else {
4201 struct ieee80211_if_ibss *ifibss = &sdata->u.ibss;
4202 memcpy(mgmt->bssid, ifibss->bssid, ETH_ALEN);
4203 }
4204 mgmt->u.action.category = WLAN_CATEGORY_SPECTRUM_MGMT;
4205 mgmt->u.action.u.chan_switch.action_code = WLAN_ACTION_SPCT_CHL_SWITCH;
4206 pos = skb_put(skb, 5);
4207 *pos++ = WLAN_EID_CHANNEL_SWITCH;
4208 *pos++ = 3;
4209 *pos++ = csa_settings->block_tx ? 1 : 0;
4210 freq = csa_settings->chandef.chan->center_freq;
4211 *pos++ = ieee80211_frequency_to_channel(freq);
4212 *pos++ = csa_settings->count;
4213
4214 if (csa_settings->chandef.width == NL80211_CHAN_WIDTH_40) {
4215 enum nl80211_channel_type ch_type;
4216
4217 skb_put(skb, 3);
4218 *pos++ = WLAN_EID_SECONDARY_CHANNEL_OFFSET;
4219 *pos++ = 1;
4220 ch_type = cfg80211_get_chandef_type(&csa_settings->chandef);
4221 if (ch_type == NL80211_CHAN_HT40PLUS)
4222 *pos++ = IEEE80211_HT_PARAM_CHA_SEC_ABOVE;
4223 else
4224 *pos++ = IEEE80211_HT_PARAM_CHA_SEC_BELOW;
4225 }
4226
4227 if (ieee80211_vif_is_mesh(&sdata->vif)) {
4228 struct ieee80211_if_mesh *ifmsh = &sdata->u.mesh;
4229
4230 skb_put(skb, 8);
4231 *pos++ = WLAN_EID_CHAN_SWITCH_PARAM;
4232 *pos++ = 6;
4233 *pos++ = sdata->u.mesh.mshcfg.dot11MeshTTL;
4234 *pos = 0x00;
4235 *pos |= WLAN_EID_CHAN_SWITCH_PARAM_INITIATOR;
4236 *pos++ |= csa_settings->block_tx ?
4237 WLAN_EID_CHAN_SWITCH_PARAM_TX_RESTRICT : 0x00;
4238 put_unaligned_le16(WLAN_REASON_MESH_CHAN, pos);
4239 pos += 2;
4240 put_unaligned_le16(ifmsh->pre_value, pos);
4241 pos += 2;
4242 }
4243
4244 if (csa_settings->chandef.width == NL80211_CHAN_WIDTH_80 ||
4245 csa_settings->chandef.width == NL80211_CHAN_WIDTH_80P80 ||
4246 csa_settings->chandef.width == NL80211_CHAN_WIDTH_160) {
4247 skb_put(skb, 5);
4248 ieee80211_ie_build_wide_bw_cs(pos, &csa_settings->chandef);
4249 }
4250
4251 ieee80211_tx_skb(sdata, skb);
4252 return 0;
4253}
4254
4255bool ieee80211_cs_valid(const struct ieee80211_cipher_scheme *cs)
4256{
4257 return !(cs == NULL || cs->cipher == 0 ||
4258 cs->hdr_len < cs->pn_len + cs->pn_off ||
4259 cs->hdr_len <= cs->key_idx_off ||
4260 cs->key_idx_shift > 7 ||
4261 cs->key_idx_mask == 0);
4262}
4263
4264bool ieee80211_cs_list_valid(const struct ieee80211_cipher_scheme *cs, int n)
4265{
4266 int i;
4267
4268
4269 WARN_ON((NUM_NL80211_IFTYPES / 8 + 1) > sizeof(cs[0].iftype));
4270
4271 for (i = 0; i < n; i++)
4272 if (!ieee80211_cs_valid(&cs[i]))
4273 return false;
4274
4275 return true;
4276}
4277
4278const struct ieee80211_cipher_scheme *
4279ieee80211_cs_get(struct ieee80211_local *local, u32 cipher,
4280 enum nl80211_iftype iftype)
4281{
4282 const struct ieee80211_cipher_scheme *l = local->hw.cipher_schemes;
4283 int n = local->hw.n_cipher_schemes;
4284 int i;
4285 const struct ieee80211_cipher_scheme *cs = NULL;
4286
4287 for (i = 0; i < n; i++) {
4288 if (l[i].cipher == cipher) {
4289 cs = &l[i];
4290 break;
4291 }
4292 }
4293
4294 if (!cs || !(cs->iftype & BIT(iftype)))
4295 return NULL;
4296
4297 return cs;
4298}
4299
4300int ieee80211_cs_headroom(struct ieee80211_local *local,
4301 struct cfg80211_crypto_settings *crypto,
4302 enum nl80211_iftype iftype)
4303{
4304 const struct ieee80211_cipher_scheme *cs;
4305 int headroom = IEEE80211_ENCRYPT_HEADROOM;
4306 int i;
4307
4308 for (i = 0; i < crypto->n_ciphers_pairwise; i++) {
4309 cs = ieee80211_cs_get(local, crypto->ciphers_pairwise[i],
4310 iftype);
4311
4312 if (cs && headroom < cs->hdr_len)
4313 headroom = cs->hdr_len;
4314 }
4315
4316 cs = ieee80211_cs_get(local, crypto->cipher_group, iftype);
4317 if (cs && headroom < cs->hdr_len)
4318 headroom = cs->hdr_len;
4319
4320 return headroom;
4321}
4322
4323static bool
4324ieee80211_extend_noa_desc(struct ieee80211_noa_data *data, u32 tsf, int i)
4325{
4326 s32 end = data->desc[i].start + data->desc[i].duration - (tsf + 1);
4327 int skip;
4328
4329 if (end > 0)
4330 return false;
4331
4332
4333 if (data->count[i] == 1)
4334 return false;
4335
4336 if (data->desc[i].interval == 0)
4337 return false;
4338
4339
4340 skip = DIV_ROUND_UP(-end, data->desc[i].interval);
4341 if (data->count[i] < 255) {
4342 if (data->count[i] <= skip) {
4343 data->count[i] = 0;
4344 return false;
4345 }
4346
4347 data->count[i] -= skip;
4348 }
4349
4350 data->desc[i].start += skip * data->desc[i].interval;
4351
4352 return true;
4353}
4354
4355static bool
4356ieee80211_extend_absent_time(struct ieee80211_noa_data *data, u32 tsf,
4357 s32 *offset)
4358{
4359 bool ret = false;
4360 int i;
4361
4362 for (i = 0; i < IEEE80211_P2P_NOA_DESC_MAX; i++) {
4363 s32 cur;
4364
4365 if (!data->count[i])
4366 continue;
4367
4368 if (ieee80211_extend_noa_desc(data, tsf + *offset, i))
4369 ret = true;
4370
4371 cur = data->desc[i].start - tsf;
4372 if (cur > *offset)
4373 continue;
4374
4375 cur = data->desc[i].start + data->desc[i].duration - tsf;
4376 if (cur > *offset)
4377 *offset = cur;
4378 }
4379
4380 return ret;
4381}
4382
4383static u32
4384ieee80211_get_noa_absent_time(struct ieee80211_noa_data *data, u32 tsf)
4385{
4386 s32 offset = 0;
4387 int tries = 0;
4388
4389
4390
4391
4392 int max_tries = 5;
4393
4394 ieee80211_extend_absent_time(data, tsf, &offset);
4395 do {
4396 if (!ieee80211_extend_absent_time(data, tsf, &offset))
4397 break;
4398
4399 tries++;
4400 } while (tries < max_tries);
4401
4402 return offset;
4403}
4404
4405void ieee80211_update_p2p_noa(struct ieee80211_noa_data *data, u32 tsf)
4406{
4407 u32 next_offset = BIT(31) - 1;
4408 int i;
4409
4410 data->absent = 0;
4411 data->has_next_tsf = false;
4412 for (i = 0; i < IEEE80211_P2P_NOA_DESC_MAX; i++) {
4413 s32 start;
4414
4415 if (!data->count[i])
4416 continue;
4417
4418 ieee80211_extend_noa_desc(data, tsf, i);
4419 start = data->desc[i].start - tsf;
4420 if (start <= 0)
4421 data->absent |= BIT(i);
4422
4423 if (next_offset > start)
4424 next_offset = start;
4425
4426 data->has_next_tsf = true;
4427 }
4428
4429 if (data->absent)
4430 next_offset = ieee80211_get_noa_absent_time(data, tsf);
4431
4432 data->next_tsf = tsf + next_offset;
4433}
4434EXPORT_SYMBOL(ieee80211_update_p2p_noa);
4435
4436int ieee80211_parse_p2p_noa(const struct ieee80211_p2p_noa_attr *attr,
4437 struct ieee80211_noa_data *data, u32 tsf)
4438{
4439 int ret = 0;
4440 int i;
4441
4442 memset(data, 0, sizeof(*data));
4443
4444 for (i = 0; i < IEEE80211_P2P_NOA_DESC_MAX; i++) {
4445 const struct ieee80211_p2p_noa_desc *desc = &attr->desc[i];
4446
4447 if (!desc->count || !desc->duration)
4448 continue;
4449
4450 data->count[i] = desc->count;
4451 data->desc[i].start = le32_to_cpu(desc->start_time);
4452 data->desc[i].duration = le32_to_cpu(desc->duration);
4453 data->desc[i].interval = le32_to_cpu(desc->interval);
4454
4455 if (data->count[i] > 1 &&
4456 data->desc[i].interval < data->desc[i].duration)
4457 continue;
4458
4459 ieee80211_extend_noa_desc(data, tsf, i);
4460 ret++;
4461 }
4462
4463 if (ret)
4464 ieee80211_update_p2p_noa(data, tsf);
4465
4466 return ret;
4467}
4468EXPORT_SYMBOL(ieee80211_parse_p2p_noa);
4469
4470void ieee80211_recalc_dtim(struct ieee80211_local *local,
4471 struct ieee80211_sub_if_data *sdata)
4472{
4473 u64 tsf = drv_get_tsf(local, sdata);
4474 u64 dtim_count = 0;
4475 u16 beacon_int = sdata->vif.bss_conf.beacon_int * 1024;
4476 u8 dtim_period = sdata->vif.bss_conf.dtim_period;
4477 struct ps_data *ps;
4478 u8 bcns_from_dtim;
4479
4480 if (tsf == -1ULL || !beacon_int || !dtim_period)
4481 return;
4482
4483 if (sdata->vif.type == NL80211_IFTYPE_AP ||
4484 sdata->vif.type == NL80211_IFTYPE_AP_VLAN) {
4485 if (!sdata->bss)
4486 return;
4487
4488 ps = &sdata->bss->ps;
4489 } else if (ieee80211_vif_is_mesh(&sdata->vif)) {
4490 ps = &sdata->u.mesh.ps;
4491 } else {
4492 return;
4493 }
4494
4495
4496
4497
4498
4499
4500 do_div(tsf, beacon_int);
4501 bcns_from_dtim = do_div(tsf, dtim_period);
4502
4503 if (!bcns_from_dtim)
4504 dtim_count = 0;
4505 else
4506 dtim_count = dtim_period - bcns_from_dtim;
4507
4508 ps->dtim_count = dtim_count;
4509}
4510
4511static u8 ieee80211_chanctx_radar_detect(struct ieee80211_local *local,
4512 struct ieee80211_chanctx *ctx)
4513{
4514 struct ieee80211_sub_if_data *sdata;
4515 u8 radar_detect = 0;
4516
4517 lockdep_assert_held(&local->chanctx_mtx);
4518
4519 if (WARN_ON(ctx->replace_state == IEEE80211_CHANCTX_WILL_BE_REPLACED))
4520 return 0;
4521
4522 list_for_each_entry(sdata, &ctx->reserved_vifs, reserved_chanctx_list)
4523 if (sdata->reserved_radar_required)
4524 radar_detect |= BIT(sdata->reserved_chandef.width);
4525
4526
4527
4528
4529
4530 WARN_ON(ctx->replace_state == IEEE80211_CHANCTX_REPLACES_OTHER &&
4531 !list_empty(&ctx->assigned_vifs));
4532
4533 list_for_each_entry(sdata, &ctx->assigned_vifs, assigned_chanctx_list)
4534 if (sdata->radar_required)
4535 radar_detect |= BIT(sdata->vif.bss_conf.chandef.width);
4536
4537 return radar_detect;
4538}
4539
4540int ieee80211_check_combinations(struct ieee80211_sub_if_data *sdata,
4541 const struct cfg80211_chan_def *chandef,
4542 enum ieee80211_chanctx_mode chanmode,
4543 u8 radar_detect)
4544{
4545 struct ieee80211_local *local = sdata->local;
4546 struct ieee80211_sub_if_data *sdata_iter;
4547 enum nl80211_iftype iftype = sdata->wdev.iftype;
4548 struct ieee80211_chanctx *ctx;
4549 int total = 1;
4550 struct iface_combination_params params = {
4551 .radar_detect = radar_detect,
4552 };
4553
4554 lockdep_assert_held(&local->chanctx_mtx);
4555
4556 if (WARN_ON(hweight32(radar_detect) > 1))
4557 return -EINVAL;
4558
4559 if (WARN_ON(chandef && chanmode == IEEE80211_CHANCTX_SHARED &&
4560 !chandef->chan))
4561 return -EINVAL;
4562
4563 if (WARN_ON(iftype >= NUM_NL80211_IFTYPES))
4564 return -EINVAL;
4565
4566 if (sdata->vif.type == NL80211_IFTYPE_AP ||
4567 sdata->vif.type == NL80211_IFTYPE_MESH_POINT) {
4568
4569
4570
4571
4572
4573 params.new_beacon_int = sdata->vif.bss_conf.beacon_int;
4574 }
4575
4576
4577 if (cfg80211_iftype_allowed(local->hw.wiphy, iftype, 0, 1)) {
4578 if (radar_detect)
4579 return -EINVAL;
4580 return 0;
4581 }
4582
4583 if (chandef)
4584 params.num_different_channels = 1;
4585
4586 if (iftype != NL80211_IFTYPE_UNSPECIFIED)
4587 params.iftype_num[iftype] = 1;
4588
4589 list_for_each_entry(ctx, &local->chanctx_list, list) {
4590 if (ctx->replace_state == IEEE80211_CHANCTX_WILL_BE_REPLACED)
4591 continue;
4592 params.radar_detect |=
4593 ieee80211_chanctx_radar_detect(local, ctx);
4594 if (ctx->mode == IEEE80211_CHANCTX_EXCLUSIVE) {
4595 params.num_different_channels++;
4596 continue;
4597 }
4598 if (chandef && chanmode == IEEE80211_CHANCTX_SHARED &&
4599 cfg80211_chandef_compatible(chandef,
4600 &ctx->conf.def))
4601 continue;
4602 params.num_different_channels++;
4603 }
4604
4605 list_for_each_entry_rcu(sdata_iter, &local->interfaces, list) {
4606 struct wireless_dev *wdev_iter;
4607
4608 wdev_iter = &sdata_iter->wdev;
4609
4610 if (sdata_iter == sdata ||
4611 !ieee80211_sdata_running(sdata_iter) ||
4612 cfg80211_iftype_allowed(local->hw.wiphy,
4613 wdev_iter->iftype, 0, 1))
4614 continue;
4615
4616 params.iftype_num[wdev_iter->iftype]++;
4617 total++;
4618 }
4619
4620 if (total == 1 && !params.radar_detect)
4621 return 0;
4622
4623 return cfg80211_check_combinations(local->hw.wiphy, ¶ms);
4624}
4625
4626static void
4627ieee80211_iter_max_chans(const struct ieee80211_iface_combination *c,
4628 void *data)
4629{
4630 u32 *max_num_different_channels = data;
4631
4632 *max_num_different_channels = max(*max_num_different_channels,
4633 c->num_different_channels);
4634}
4635
4636int ieee80211_max_num_channels(struct ieee80211_local *local)
4637{
4638 struct ieee80211_sub_if_data *sdata;
4639 struct ieee80211_chanctx *ctx;
4640 u32 max_num_different_channels = 1;
4641 int err;
4642 struct iface_combination_params params = {0};
4643
4644 lockdep_assert_held(&local->chanctx_mtx);
4645
4646 list_for_each_entry(ctx, &local->chanctx_list, list) {
4647 if (ctx->replace_state == IEEE80211_CHANCTX_WILL_BE_REPLACED)
4648 continue;
4649
4650 params.num_different_channels++;
4651
4652 params.radar_detect |=
4653 ieee80211_chanctx_radar_detect(local, ctx);
4654 }
4655
4656 list_for_each_entry_rcu(sdata, &local->interfaces, list)
4657 params.iftype_num[sdata->wdev.iftype]++;
4658
4659 err = cfg80211_iter_combinations(local->hw.wiphy, ¶ms,
4660 ieee80211_iter_max_chans,
4661 &max_num_different_channels);
4662 if (err < 0)
4663 return err;
4664
4665 return max_num_different_channels;
4666}
4667
4668void ieee80211_add_s1g_capab_ie(struct ieee80211_sub_if_data *sdata,
4669 struct ieee80211_sta_s1g_cap *caps,
4670 struct sk_buff *skb)
4671{
4672 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
4673 struct ieee80211_s1g_cap s1g_capab;
4674 u8 *pos;
4675 int i;
4676
4677 if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_STATION))
4678 return;
4679
4680 if (!caps->s1g)
4681 return;
4682
4683 memcpy(s1g_capab.capab_info, caps->cap, sizeof(caps->cap));
4684 memcpy(s1g_capab.supp_mcs_nss, caps->nss_mcs, sizeof(caps->nss_mcs));
4685
4686
4687 for (i = 0; i < sizeof(ifmgd->s1g_capa.capab_info); i++) {
4688 u8 mask = ifmgd->s1g_capa_mask.capab_info[i];
4689
4690 s1g_capab.capab_info[i] &= ~mask;
4691 s1g_capab.capab_info[i] |= ifmgd->s1g_capa.capab_info[i] & mask;
4692 }
4693
4694
4695 for (i = 0; i < sizeof(ifmgd->s1g_capa.supp_mcs_nss); i++) {
4696 u8 mask = ifmgd->s1g_capa_mask.supp_mcs_nss[i];
4697
4698 s1g_capab.supp_mcs_nss[i] &= ~mask;
4699 s1g_capab.supp_mcs_nss[i] |=
4700 ifmgd->s1g_capa.supp_mcs_nss[i] & mask;
4701 }
4702
4703 pos = skb_put(skb, 2 + sizeof(s1g_capab));
4704 *pos++ = WLAN_EID_S1G_CAPABILITIES;
4705 *pos++ = sizeof(s1g_capab);
4706
4707 memcpy(pos, &s1g_capab, sizeof(s1g_capab));
4708}
4709
4710void ieee80211_add_aid_request_ie(struct ieee80211_sub_if_data *sdata,
4711 struct sk_buff *skb)
4712{
4713 u8 *pos = skb_put(skb, 3);
4714
4715 *pos++ = WLAN_EID_AID_REQUEST;
4716 *pos++ = 1;
4717 *pos++ = 0;
4718}
4719
4720u8 *ieee80211_add_wmm_info_ie(u8 *buf, u8 qosinfo)
4721{
4722 *buf++ = WLAN_EID_VENDOR_SPECIFIC;
4723 *buf++ = 7;
4724 *buf++ = 0x00;
4725 *buf++ = 0x50;
4726 *buf++ = 0xf2;
4727 *buf++ = 2;
4728 *buf++ = 0;
4729 *buf++ = 1;
4730 *buf++ = qosinfo;
4731
4732 return buf;
4733}
4734
4735void ieee80211_txq_get_depth(struct ieee80211_txq *txq,
4736 unsigned long *frame_cnt,
4737 unsigned long *byte_cnt)
4738{
4739 struct txq_info *txqi = to_txq_info(txq);
4740 u32 frag_cnt = 0, frag_bytes = 0;
4741 struct sk_buff *skb;
4742
4743 skb_queue_walk(&txqi->frags, skb) {
4744 frag_cnt++;
4745 frag_bytes += skb->len;
4746 }
4747
4748 if (frame_cnt)
4749 *frame_cnt = txqi->tin.backlog_packets + frag_cnt;
4750
4751 if (byte_cnt)
4752 *byte_cnt = txqi->tin.backlog_bytes + frag_bytes;
4753}
4754EXPORT_SYMBOL(ieee80211_txq_get_depth);
4755
4756const u8 ieee80211_ac_to_qos_mask[IEEE80211_NUM_ACS] = {
4757 IEEE80211_WMM_IE_STA_QOSINFO_AC_VO,
4758 IEEE80211_WMM_IE_STA_QOSINFO_AC_VI,
4759 IEEE80211_WMM_IE_STA_QOSINFO_AC_BE,
4760 IEEE80211_WMM_IE_STA_QOSINFO_AC_BK
4761};
4762
4763u16 ieee80211_encode_usf(int listen_interval)
4764{
4765 static const int listen_int_usf[] = { 1, 10, 1000, 10000 };
4766 u16 ui, usf = 0;
4767
4768
4769 while (usf < IEEE80211_MAX_USF) {
4770 if (listen_interval % listen_int_usf[usf + 1])
4771 break;
4772 usf += 1;
4773 }
4774 ui = listen_interval / listen_int_usf[usf];
4775
4776
4777 WARN_ON_ONCE(ui > IEEE80211_MAX_UI);
4778 listen_interval = FIELD_PREP(LISTEN_INT_USF, usf) |
4779 FIELD_PREP(LISTEN_INT_UI, ui);
4780
4781 return (u16) listen_interval;
4782}
4783
4784u8 ieee80211_ie_len_eht_cap(struct ieee80211_sub_if_data *sdata, u8 iftype)
4785{
4786 const struct ieee80211_sta_he_cap *he_cap;
4787 const struct ieee80211_sta_eht_cap *eht_cap;
4788 struct ieee80211_supported_band *sband;
4789 u8 n;
4790
4791 sband = ieee80211_get_sband(sdata);
4792 if (!sband)
4793 return 0;
4794
4795 he_cap = ieee80211_get_he_iftype_cap(sband, iftype);
4796 eht_cap = ieee80211_get_eht_iftype_cap(sband, iftype);
4797 if (!he_cap || !eht_cap)
4798 return 0;
4799
4800 n = ieee80211_eht_mcs_nss_size(&he_cap->he_cap_elem,
4801 &eht_cap->eht_cap_elem);
4802 return 2 + 1 +
4803 sizeof(he_cap->he_cap_elem) + n +
4804 ieee80211_eht_ppe_size(eht_cap->eht_ppe_thres[0],
4805 eht_cap->eht_cap_elem.phy_cap_info);
4806 return 0;
4807}
4808
4809u8 *ieee80211_ie_build_eht_cap(u8 *pos,
4810 const struct ieee80211_sta_he_cap *he_cap,
4811 const struct ieee80211_sta_eht_cap *eht_cap,
4812 u8 *end)
4813{
4814 u8 mcs_nss_len, ppet_len;
4815 u8 ie_len;
4816 u8 *orig_pos = pos;
4817
4818
4819 if (!he_cap || !eht_cap)
4820 return orig_pos;
4821
4822 mcs_nss_len = ieee80211_eht_mcs_nss_size(&he_cap->he_cap_elem,
4823 &eht_cap->eht_cap_elem);
4824 ppet_len = ieee80211_eht_ppe_size(eht_cap->eht_ppe_thres[0],
4825 eht_cap->eht_cap_elem.phy_cap_info);
4826
4827 ie_len = 2 + 1 + sizeof(eht_cap->eht_cap_elem) + mcs_nss_len + ppet_len;
4828 if ((end - pos) < ie_len)
4829 return orig_pos;
4830
4831 *pos++ = WLAN_EID_EXTENSION;
4832 *pos++ = ie_len - 2;
4833 *pos++ = WLAN_EID_EXT_EHT_CAPABILITY;
4834
4835
4836 memcpy(pos, &eht_cap->eht_cap_elem, sizeof(eht_cap->eht_cap_elem));
4837 pos += sizeof(eht_cap->eht_cap_elem);
4838
4839 memcpy(pos, &eht_cap->eht_mcs_nss_supp, mcs_nss_len);
4840 pos += mcs_nss_len;
4841
4842 if (ppet_len) {
4843 memcpy(pos, &eht_cap->eht_ppe_thres, ppet_len);
4844 pos += ppet_len;
4845 }
4846
4847 return pos;
4848}
4849