1// SPDX-License-Identifier: ISC
2/* Copyright (C) 2020 MediaTek Inc. */
3
4#include <linux/firmware.h>
5#include "mt76_connac2_mac.h"
6#include "mt76_connac_mcu.h"
7
8int mt76_connac_mcu_start_firmware(struct mt76_dev *dev, u32 addr, u32 option)
9{
10 struct {
11 __le32 option;
12 __le32 addr;
13 } req = {
14 .option = cpu_to_le32(option),
15 .addr = cpu_to_le32(addr),
16 };
17
18 return mt76_mcu_send_msg(dev, MCU_CMD(FW_START_REQ), data: &req,
19 len: sizeof(req), wait_resp: true);
20}
21EXPORT_SYMBOL_GPL(mt76_connac_mcu_start_firmware);
22
23int mt76_connac_mcu_patch_sem_ctrl(struct mt76_dev *dev, bool get)
24{
25 u32 op = get ? PATCH_SEM_GET : PATCH_SEM_RELEASE;
26 struct {
27 __le32 op;
28 } req = {
29 .op = cpu_to_le32(op),
30 };
31
32 return mt76_mcu_send_msg(dev, MCU_CMD(PATCH_SEM_CONTROL),
33 data: &req, len: sizeof(req), wait_resp: true);
34}
35EXPORT_SYMBOL_GPL(mt76_connac_mcu_patch_sem_ctrl);
36
37int mt76_connac_mcu_start_patch(struct mt76_dev *dev)
38{
39 struct {
40 u8 check_crc;
41 u8 reserved[3];
42 } req = {
43 .check_crc = 0,
44 };
45
46 return mt76_mcu_send_msg(dev, MCU_CMD(PATCH_FINISH_REQ),
47 data: &req, len: sizeof(req), wait_resp: true);
48}
49EXPORT_SYMBOL_GPL(mt76_connac_mcu_start_patch);
50
51#define MCU_PATCH_ADDRESS 0x200000
52
53int mt76_connac_mcu_init_download(struct mt76_dev *dev, u32 addr, u32 len,
54 u32 mode)
55{
56 struct {
57 __le32 addr;
58 __le32 len;
59 __le32 mode;
60 } req = {
61 .addr = cpu_to_le32(addr),
62 .len = cpu_to_le32(len),
63 .mode = cpu_to_le32(mode),
64 };
65 int cmd;
66
67 if ((!is_connac_v1(dev) && addr == MCU_PATCH_ADDRESS) ||
68 (is_mt7921(dev) && addr == 0x900000) ||
69 (is_mt7925(dev) && (addr == 0x900000 || addr == 0xe0002800)) ||
70 (is_mt7996(dev) && addr == 0x900000) ||
71 (is_mt7992(dev) && addr == 0x900000))
72 cmd = MCU_CMD(PATCH_START_REQ);
73 else
74 cmd = MCU_CMD(TARGET_ADDRESS_LEN_REQ);
75
76 return mt76_mcu_send_msg(dev, cmd, data: &req, len: sizeof(req), wait_resp: true);
77}
78EXPORT_SYMBOL_GPL(mt76_connac_mcu_init_download);
79
80int mt76_connac_mcu_set_channel_domain(struct mt76_phy *phy)
81{
82 int len, i, n_max_channels, n_2ch = 0, n_5ch = 0, n_6ch = 0;
83 struct mt76_connac_mcu_channel_domain {
84 u8 alpha2[4]; /* regulatory_request.alpha2 */
85 u8 bw_2g; /* BW_20_40M 0
86 * BW_20M 1
87 * BW_20_40_80M 2
88 * BW_20_40_80_160M 3
89 * BW_20_40_80_8080M 4
90 */
91 u8 bw_5g;
92 u8 bw_6g;
93 u8 pad;
94 u8 n_2ch;
95 u8 n_5ch;
96 u8 n_6ch;
97 u8 pad2;
98 } __packed hdr = {
99 .bw_2g = 0,
100 .bw_5g = 3, /* BW_20_40_80_160M */
101 .bw_6g = 3,
102 };
103 struct mt76_connac_mcu_chan {
104 __le16 hw_value;
105 __le16 pad;
106 __le32 flags;
107 } __packed channel;
108 struct mt76_dev *dev = phy->dev;
109 struct ieee80211_channel *chan;
110 struct sk_buff *skb;
111
112 n_max_channels = phy->sband_2g.sband.n_channels +
113 phy->sband_5g.sband.n_channels +
114 phy->sband_6g.sband.n_channels;
115 len = sizeof(hdr) + n_max_channels * sizeof(channel);
116
117 skb = mt76_mcu_msg_alloc(dev, NULL, data_len: len);
118 if (!skb)
119 return -ENOMEM;
120
121 skb_reserve(skb, len: sizeof(hdr));
122
123 for (i = 0; i < phy->sband_2g.sband.n_channels; i++) {
124 chan = &phy->sband_2g.sband.channels[i];
125 if (chan->flags & IEEE80211_CHAN_DISABLED)
126 continue;
127
128 channel.hw_value = cpu_to_le16(chan->hw_value);
129 channel.flags = cpu_to_le32(chan->flags);
130 channel.pad = 0;
131
132 skb_put_data(skb, data: &channel, len: sizeof(channel));
133 n_2ch++;
134 }
135 for (i = 0; i < phy->sband_5g.sband.n_channels; i++) {
136 chan = &phy->sband_5g.sband.channels[i];
137 if (chan->flags & IEEE80211_CHAN_DISABLED)
138 continue;
139
140 channel.hw_value = cpu_to_le16(chan->hw_value);
141 channel.flags = cpu_to_le32(chan->flags);
142 channel.pad = 0;
143
144 skb_put_data(skb, data: &channel, len: sizeof(channel));
145 n_5ch++;
146 }
147 for (i = 0; i < phy->sband_6g.sband.n_channels; i++) {
148 chan = &phy->sband_6g.sband.channels[i];
149 if (chan->flags & IEEE80211_CHAN_DISABLED)
150 continue;
151
152 channel.hw_value = cpu_to_le16(chan->hw_value);
153 channel.flags = cpu_to_le32(chan->flags);
154 channel.pad = 0;
155
156 skb_put_data(skb, data: &channel, len: sizeof(channel));
157 n_6ch++;
158 }
159
160 BUILD_BUG_ON(sizeof(dev->alpha2) > sizeof(hdr.alpha2));
161 memcpy(hdr.alpha2, dev->alpha2, sizeof(dev->alpha2));
162 hdr.n_2ch = n_2ch;
163 hdr.n_5ch = n_5ch;
164 hdr.n_6ch = n_6ch;
165
166 memcpy(__skb_push(skb, sizeof(hdr)), &hdr, sizeof(hdr));
167
168 return mt76_mcu_skb_send_msg(dev, skb, MCU_CE_CMD(SET_CHAN_DOMAIN),
169 wait_resp: false);
170}
171EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_channel_domain);
172
173int mt76_connac_mcu_set_mac_enable(struct mt76_dev *dev, int band, bool enable,
174 bool hdr_trans)
175{
176 struct {
177 u8 enable;
178 u8 band;
179 u8 rsv[2];
180 } __packed req_mac = {
181 .enable = enable,
182 .band = band,
183 };
184
185 return mt76_mcu_send_msg(dev, MCU_EXT_CMD(MAC_INIT_CTRL), data: &req_mac,
186 len: sizeof(req_mac), wait_resp: true);
187}
188EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_mac_enable);
189
190int mt76_connac_mcu_set_vif_ps(struct mt76_dev *dev, struct ieee80211_vif *vif)
191{
192 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
193 struct {
194 u8 bss_idx;
195 u8 ps_state; /* 0: device awake
196 * 1: static power save
197 * 2: dynamic power saving
198 */
199 } req = {
200 .bss_idx = mvif->idx,
201 .ps_state = vif->cfg.ps ? 2 : 0,
202 };
203
204 if (vif->type != NL80211_IFTYPE_STATION)
205 return -EOPNOTSUPP;
206
207 return mt76_mcu_send_msg(dev, MCU_CE_CMD(SET_PS_PROFILE),
208 data: &req, len: sizeof(req), wait_resp: false);
209}
210EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_vif_ps);
211
212int mt76_connac_mcu_set_rts_thresh(struct mt76_dev *dev, u32 val, u8 band)
213{
214 struct {
215 u8 prot_idx;
216 u8 band;
217 u8 rsv[2];
218 __le32 len_thresh;
219 __le32 pkt_thresh;
220 } __packed req = {
221 .prot_idx = 1,
222 .band = band,
223 .len_thresh = cpu_to_le32(val),
224 .pkt_thresh = cpu_to_le32(0x2),
225 };
226
227 return mt76_mcu_send_msg(dev, MCU_EXT_CMD(PROTECT_CTRL), data: &req,
228 len: sizeof(req), wait_resp: true);
229}
230EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_rts_thresh);
231
232void mt76_connac_mcu_beacon_loss_iter(void *priv, u8 *mac,
233 struct ieee80211_vif *vif)
234{
235 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
236 struct mt76_connac_beacon_loss_event *event = priv;
237
238 if (mvif->idx != event->bss_idx)
239 return;
240
241 if (!(vif->driver_flags & IEEE80211_VIF_BEACON_FILTER))
242 return;
243
244 ieee80211_beacon_loss(vif);
245}
246EXPORT_SYMBOL_GPL(mt76_connac_mcu_beacon_loss_iter);
247
248struct tlv *
249mt76_connac_mcu_add_nested_tlv(struct sk_buff *skb, int tag, int len,
250 void *sta_ntlv, void *sta_wtbl)
251{
252 struct sta_ntlv_hdr *ntlv_hdr = sta_ntlv;
253 struct tlv *sta_hdr = sta_wtbl;
254 struct tlv *ptlv, tlv = {
255 .tag = cpu_to_le16(tag),
256 .len = cpu_to_le16(len),
257 };
258 u16 ntlv;
259
260 ptlv = skb_put(skb, len);
261 memcpy(ptlv, &tlv, sizeof(tlv));
262
263 ntlv = le16_to_cpu(ntlv_hdr->tlv_num);
264 ntlv_hdr->tlv_num = cpu_to_le16(ntlv + 1);
265
266 if (sta_hdr) {
267 len += le16_to_cpu(sta_hdr->len);
268 sta_hdr->len = cpu_to_le16(len);
269 }
270
271 return ptlv;
272}
273EXPORT_SYMBOL_GPL(mt76_connac_mcu_add_nested_tlv);
274
275struct sk_buff *
276__mt76_connac_mcu_alloc_sta_req(struct mt76_dev *dev, struct mt76_vif *mvif,
277 struct mt76_wcid *wcid, int len)
278{
279 struct sta_req_hdr hdr = {
280 .bss_idx = mvif->idx,
281 .muar_idx = wcid ? mvif->omac_idx : 0,
282 .is_tlv_append = 1,
283 };
284 struct sk_buff *skb;
285
286 if (is_mt799x(dev) && !wcid->sta)
287 hdr.muar_idx = 0xe;
288
289 mt76_connac_mcu_get_wlan_idx(dev, wcid, wlan_idx_lo: &hdr.wlan_idx_lo,
290 wlan_idx_hi: &hdr.wlan_idx_hi);
291 skb = mt76_mcu_msg_alloc(dev, NULL, data_len: len);
292 if (!skb)
293 return ERR_PTR(error: -ENOMEM);
294
295 skb_put_data(skb, data: &hdr, len: sizeof(hdr));
296
297 return skb;
298}
299EXPORT_SYMBOL_GPL(__mt76_connac_mcu_alloc_sta_req);
300
301struct wtbl_req_hdr *
302mt76_connac_mcu_alloc_wtbl_req(struct mt76_dev *dev, struct mt76_wcid *wcid,
303 int cmd, void *sta_wtbl, struct sk_buff **skb)
304{
305 struct tlv *sta_hdr = sta_wtbl;
306 struct wtbl_req_hdr hdr = {
307 .operation = cmd,
308 };
309 struct sk_buff *nskb = *skb;
310
311 mt76_connac_mcu_get_wlan_idx(dev, wcid, wlan_idx_lo: &hdr.wlan_idx_lo,
312 wlan_idx_hi: &hdr.wlan_idx_hi);
313 if (!nskb) {
314 nskb = mt76_mcu_msg_alloc(dev, NULL,
315 MT76_CONNAC_WTBL_UPDATE_MAX_SIZE);
316 if (!nskb)
317 return ERR_PTR(error: -ENOMEM);
318
319 *skb = nskb;
320 }
321
322 if (sta_hdr)
323 le16_add_cpu(var: &sta_hdr->len, val: sizeof(hdr));
324
325 return skb_put_data(skb: nskb, data: &hdr, len: sizeof(hdr));
326}
327EXPORT_SYMBOL_GPL(mt76_connac_mcu_alloc_wtbl_req);
328
329void mt76_connac_mcu_bss_omac_tlv(struct sk_buff *skb,
330 struct ieee80211_vif *vif)
331{
332 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
333 u8 omac_idx = mvif->omac_idx;
334 struct bss_info_omac *omac;
335 struct tlv *tlv;
336 u32 type = 0;
337
338 switch (vif->type) {
339 case NL80211_IFTYPE_MONITOR:
340 case NL80211_IFTYPE_MESH_POINT:
341 case NL80211_IFTYPE_AP:
342 if (vif->p2p)
343 type = CONNECTION_P2P_GO;
344 else
345 type = CONNECTION_INFRA_AP;
346 break;
347 case NL80211_IFTYPE_STATION:
348 if (vif->p2p)
349 type = CONNECTION_P2P_GC;
350 else
351 type = CONNECTION_INFRA_STA;
352 break;
353 case NL80211_IFTYPE_ADHOC:
354 type = CONNECTION_IBSS_ADHOC;
355 break;
356 default:
357 WARN_ON(1);
358 break;
359 }
360
361 tlv = mt76_connac_mcu_add_tlv(skb, tag: BSS_INFO_OMAC, len: sizeof(*omac));
362
363 omac = (struct bss_info_omac *)tlv;
364 omac->conn_type = cpu_to_le32(type);
365 omac->omac_idx = mvif->omac_idx;
366 omac->band_idx = mvif->band_idx;
367 omac->hw_bss_idx = omac_idx > EXT_BSSID_START ? HW_BSSID_0 : omac_idx;
368}
369EXPORT_SYMBOL_GPL(mt76_connac_mcu_bss_omac_tlv);
370
371void mt76_connac_mcu_sta_basic_tlv(struct mt76_dev *dev, struct sk_buff *skb,
372 struct ieee80211_vif *vif,
373 struct ieee80211_sta *sta,
374 bool enable, bool newly)
375{
376 struct sta_rec_basic *basic;
377 struct tlv *tlv;
378 int conn_type;
379
380 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_BASIC, len: sizeof(*basic));
381
382 basic = (struct sta_rec_basic *)tlv;
383 basic->extra_info = cpu_to_le16(EXTRA_INFO_VER);
384
385 if (enable) {
386 if (newly)
387 basic->extra_info |= cpu_to_le16(EXTRA_INFO_NEW);
388 basic->conn_state = CONN_STATE_PORT_SECURE;
389 } else {
390 basic->conn_state = CONN_STATE_DISCONNECT;
391 }
392
393 if (!sta) {
394 basic->conn_type = cpu_to_le32(CONNECTION_INFRA_BC);
395 eth_broadcast_addr(addr: basic->peer_addr);
396 return;
397 }
398
399 switch (vif->type) {
400 case NL80211_IFTYPE_MESH_POINT:
401 case NL80211_IFTYPE_AP:
402 if (vif->p2p && !is_mt7921(dev))
403 conn_type = CONNECTION_P2P_GC;
404 else
405 conn_type = CONNECTION_INFRA_STA;
406 basic->conn_type = cpu_to_le32(conn_type);
407 basic->aid = cpu_to_le16(sta->aid);
408 break;
409 case NL80211_IFTYPE_STATION:
410 if (vif->p2p && !is_mt7921(dev))
411 conn_type = CONNECTION_P2P_GO;
412 else
413 conn_type = CONNECTION_INFRA_AP;
414 basic->conn_type = cpu_to_le32(conn_type);
415 basic->aid = cpu_to_le16(vif->cfg.aid);
416 break;
417 case NL80211_IFTYPE_ADHOC:
418 basic->conn_type = cpu_to_le32(CONNECTION_IBSS_ADHOC);
419 basic->aid = cpu_to_le16(sta->aid);
420 break;
421 default:
422 WARN_ON(1);
423 break;
424 }
425
426 memcpy(basic->peer_addr, sta->addr, ETH_ALEN);
427 basic->qos = sta->wme;
428}
429EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_basic_tlv);
430
431void mt76_connac_mcu_sta_uapsd(struct sk_buff *skb, struct ieee80211_vif *vif,
432 struct ieee80211_sta *sta)
433{
434 struct sta_rec_uapsd *uapsd;
435 struct tlv *tlv;
436
437 if (vif->type != NL80211_IFTYPE_AP || !sta->wme)
438 return;
439
440 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_APPS, len: sizeof(*uapsd));
441 uapsd = (struct sta_rec_uapsd *)tlv;
442
443 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_VO) {
444 uapsd->dac_map |= BIT(3);
445 uapsd->tac_map |= BIT(3);
446 }
447 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_VI) {
448 uapsd->dac_map |= BIT(2);
449 uapsd->tac_map |= BIT(2);
450 }
451 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_BE) {
452 uapsd->dac_map |= BIT(1);
453 uapsd->tac_map |= BIT(1);
454 }
455 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_BK) {
456 uapsd->dac_map |= BIT(0);
457 uapsd->tac_map |= BIT(0);
458 }
459 uapsd->max_sp = sta->max_sp;
460}
461EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_uapsd);
462
463void mt76_connac_mcu_wtbl_hdr_trans_tlv(struct sk_buff *skb,
464 struct ieee80211_vif *vif,
465 struct mt76_wcid *wcid,
466 void *sta_wtbl, void *wtbl_tlv)
467{
468 struct wtbl_hdr_trans *htr;
469 struct tlv *tlv;
470
471 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_HDR_TRANS,
472 sizeof(*htr),
473 wtbl_tlv, sta_wtbl);
474 htr = (struct wtbl_hdr_trans *)tlv;
475 htr->no_rx_trans = true;
476
477 if (vif->type == NL80211_IFTYPE_STATION)
478 htr->to_ds = true;
479 else
480 htr->from_ds = true;
481
482 if (!wcid)
483 return;
484
485 htr->no_rx_trans = !test_bit(MT_WCID_FLAG_HDR_TRANS, &wcid->flags);
486 if (test_bit(MT_WCID_FLAG_4ADDR, &wcid->flags)) {
487 htr->to_ds = true;
488 htr->from_ds = true;
489 }
490}
491EXPORT_SYMBOL_GPL(mt76_connac_mcu_wtbl_hdr_trans_tlv);
492
493int mt76_connac_mcu_sta_update_hdr_trans(struct mt76_dev *dev,
494 struct ieee80211_vif *vif,
495 struct mt76_wcid *wcid, int cmd)
496{
497 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
498 struct wtbl_req_hdr *wtbl_hdr;
499 struct tlv *sta_wtbl;
500 struct sk_buff *skb;
501
502 skb = mt76_connac_mcu_alloc_sta_req(dev, mvif, wcid);
503 if (IS_ERR(ptr: skb))
504 return PTR_ERR(ptr: skb);
505
506 sta_wtbl = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_WTBL,
507 len: sizeof(struct tlv));
508
509 wtbl_hdr = mt76_connac_mcu_alloc_wtbl_req(dev, wcid, WTBL_SET,
510 sta_wtbl, &skb);
511 if (IS_ERR(ptr: wtbl_hdr))
512 return PTR_ERR(ptr: wtbl_hdr);
513
514 mt76_connac_mcu_wtbl_hdr_trans_tlv(skb, vif, wcid, sta_wtbl, wtbl_hdr);
515
516 return mt76_mcu_skb_send_msg(dev, skb, cmd, wait_resp: true);
517}
518EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_update_hdr_trans);
519
520int mt76_connac_mcu_wtbl_update_hdr_trans(struct mt76_dev *dev,
521 struct ieee80211_vif *vif,
522 struct ieee80211_sta *sta)
523{
524 struct mt76_wcid *wcid = (struct mt76_wcid *)sta->drv_priv;
525 struct wtbl_req_hdr *wtbl_hdr;
526 struct sk_buff *skb = NULL;
527
528 wtbl_hdr = mt76_connac_mcu_alloc_wtbl_req(dev, wcid, WTBL_SET, NULL,
529 &skb);
530 if (IS_ERR(ptr: wtbl_hdr))
531 return PTR_ERR(ptr: wtbl_hdr);
532
533 mt76_connac_mcu_wtbl_hdr_trans_tlv(skb, vif, wcid, NULL, wtbl_hdr);
534
535 return mt76_mcu_skb_send_msg(dev, skb, MCU_EXT_CMD(WTBL_UPDATE), wait_resp: true);
536}
537EXPORT_SYMBOL_GPL(mt76_connac_mcu_wtbl_update_hdr_trans);
538
539void mt76_connac_mcu_wtbl_generic_tlv(struct mt76_dev *dev,
540 struct sk_buff *skb,
541 struct ieee80211_vif *vif,
542 struct ieee80211_sta *sta,
543 void *sta_wtbl, void *wtbl_tlv)
544{
545 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
546 struct wtbl_generic *generic;
547 struct wtbl_rx *rx;
548 struct wtbl_spe *spe;
549 struct tlv *tlv;
550
551 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_GENERIC,
552 sizeof(*generic),
553 wtbl_tlv, sta_wtbl);
554
555 generic = (struct wtbl_generic *)tlv;
556
557 if (sta) {
558 if (vif->type == NL80211_IFTYPE_STATION)
559 generic->partial_aid = cpu_to_le16(vif->cfg.aid);
560 else
561 generic->partial_aid = cpu_to_le16(sta->aid);
562 memcpy(generic->peer_addr, sta->addr, ETH_ALEN);
563 generic->muar_idx = mvif->omac_idx;
564 generic->qos = sta->wme;
565 } else {
566 if (!is_connac_v1(dev) && vif->type == NL80211_IFTYPE_STATION)
567 memcpy(generic->peer_addr, vif->bss_conf.bssid,
568 ETH_ALEN);
569 else
570 eth_broadcast_addr(addr: generic->peer_addr);
571
572 generic->muar_idx = 0xe;
573 }
574
575 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_RX, sizeof(*rx),
576 wtbl_tlv, sta_wtbl);
577
578 rx = (struct wtbl_rx *)tlv;
579 rx->rca1 = sta ? vif->type != NL80211_IFTYPE_AP : 1;
580 rx->rca2 = 1;
581 rx->rv = 1;
582
583 if (!is_connac_v1(dev))
584 return;
585
586 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_SPE, sizeof(*spe),
587 wtbl_tlv, sta_wtbl);
588 spe = (struct wtbl_spe *)tlv;
589 spe->spe_idx = 24;
590}
591EXPORT_SYMBOL_GPL(mt76_connac_mcu_wtbl_generic_tlv);
592
593static void
594mt76_connac_mcu_sta_amsdu_tlv(struct sk_buff *skb, struct ieee80211_sta *sta,
595 struct ieee80211_vif *vif)
596{
597 struct mt76_wcid *wcid = (struct mt76_wcid *)sta->drv_priv;
598 struct sta_rec_amsdu *amsdu;
599 struct tlv *tlv;
600
601 if (vif->type != NL80211_IFTYPE_AP &&
602 vif->type != NL80211_IFTYPE_STATION)
603 return;
604
605 if (!sta->deflink.agg.max_amsdu_len)
606 return;
607
608 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_HW_AMSDU, len: sizeof(*amsdu));
609 amsdu = (struct sta_rec_amsdu *)tlv;
610 amsdu->max_amsdu_num = 8;
611 amsdu->amsdu_en = true;
612 amsdu->max_mpdu_size = sta->deflink.agg.max_amsdu_len >=
613 IEEE80211_MAX_MPDU_LEN_VHT_7991;
614
615 wcid->amsdu = true;
616}
617
618#define HE_PHY(p, c) u8_get_bits(c, IEEE80211_HE_PHY_##p)
619#define HE_MAC(m, c) u8_get_bits(c, IEEE80211_HE_MAC_##m)
620static void
621mt76_connac_mcu_sta_he_tlv(struct sk_buff *skb, struct ieee80211_sta *sta)
622{
623 struct ieee80211_sta_he_cap *he_cap = &sta->deflink.he_cap;
624 struct ieee80211_he_cap_elem *elem = &he_cap->he_cap_elem;
625 struct sta_rec_he *he;
626 struct tlv *tlv;
627 u32 cap = 0;
628
629 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_HE, len: sizeof(*he));
630
631 he = (struct sta_rec_he *)tlv;
632
633 if (elem->mac_cap_info[0] & IEEE80211_HE_MAC_CAP0_HTC_HE)
634 cap |= STA_REC_HE_CAP_HTC;
635
636 if (elem->mac_cap_info[2] & IEEE80211_HE_MAC_CAP2_BSR)
637 cap |= STA_REC_HE_CAP_BSR;
638
639 if (elem->mac_cap_info[3] & IEEE80211_HE_MAC_CAP3_OMI_CONTROL)
640 cap |= STA_REC_HE_CAP_OM;
641
642 if (elem->mac_cap_info[4] & IEEE80211_HE_MAC_CAP4_AMSDU_IN_AMPDU)
643 cap |= STA_REC_HE_CAP_AMSDU_IN_AMPDU;
644
645 if (elem->mac_cap_info[4] & IEEE80211_HE_MAC_CAP4_BQR)
646 cap |= STA_REC_HE_CAP_BQR;
647
648 if (elem->phy_cap_info[0] &
649 (IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_RU_MAPPING_IN_2G |
650 IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_RU_MAPPING_IN_5G))
651 cap |= STA_REC_HE_CAP_BW20_RU242_SUPPORT;
652
653 if (elem->phy_cap_info[1] &
654 IEEE80211_HE_PHY_CAP1_LDPC_CODING_IN_PAYLOAD)
655 cap |= STA_REC_HE_CAP_LDPC;
656
657 if (elem->phy_cap_info[1] &
658 IEEE80211_HE_PHY_CAP1_HE_LTF_AND_GI_FOR_HE_PPDUS_0_8US)
659 cap |= STA_REC_HE_CAP_SU_PPDU_1LTF_8US_GI;
660
661 if (elem->phy_cap_info[2] &
662 IEEE80211_HE_PHY_CAP2_NDP_4x_LTF_AND_3_2US)
663 cap |= STA_REC_HE_CAP_NDP_4LTF_3DOT2MS_GI;
664
665 if (elem->phy_cap_info[2] &
666 IEEE80211_HE_PHY_CAP2_STBC_TX_UNDER_80MHZ)
667 cap |= STA_REC_HE_CAP_LE_EQ_80M_TX_STBC;
668
669 if (elem->phy_cap_info[2] &
670 IEEE80211_HE_PHY_CAP2_STBC_RX_UNDER_80MHZ)
671 cap |= STA_REC_HE_CAP_LE_EQ_80M_RX_STBC;
672
673 if (elem->phy_cap_info[6] &
674 IEEE80211_HE_PHY_CAP6_PARTIAL_BW_EXT_RANGE)
675 cap |= STA_REC_HE_CAP_PARTIAL_BW_EXT_RANGE;
676
677 if (elem->phy_cap_info[7] &
678 IEEE80211_HE_PHY_CAP7_HE_SU_MU_PPDU_4XLTF_AND_08_US_GI)
679 cap |= STA_REC_HE_CAP_SU_MU_PPDU_4LTF_8US_GI;
680
681 if (elem->phy_cap_info[7] &
682 IEEE80211_HE_PHY_CAP7_STBC_TX_ABOVE_80MHZ)
683 cap |= STA_REC_HE_CAP_GT_80M_TX_STBC;
684
685 if (elem->phy_cap_info[7] &
686 IEEE80211_HE_PHY_CAP7_STBC_RX_ABOVE_80MHZ)
687 cap |= STA_REC_HE_CAP_GT_80M_RX_STBC;
688
689 if (elem->phy_cap_info[8] &
690 IEEE80211_HE_PHY_CAP8_HE_ER_SU_PPDU_4XLTF_AND_08_US_GI)
691 cap |= STA_REC_HE_CAP_ER_SU_PPDU_4LTF_8US_GI;
692
693 if (elem->phy_cap_info[8] &
694 IEEE80211_HE_PHY_CAP8_HE_ER_SU_1XLTF_AND_08_US_GI)
695 cap |= STA_REC_HE_CAP_ER_SU_PPDU_1LTF_8US_GI;
696
697 if (elem->phy_cap_info[9] &
698 IEEE80211_HE_PHY_CAP9_NON_TRIGGERED_CQI_FEEDBACK)
699 cap |= STA_REC_HE_CAP_TRIG_CQI_FK;
700
701 if (elem->phy_cap_info[9] &
702 IEEE80211_HE_PHY_CAP9_TX_1024_QAM_LESS_THAN_242_TONE_RU)
703 cap |= STA_REC_HE_CAP_TX_1024QAM_UNDER_RU242;
704
705 if (elem->phy_cap_info[9] &
706 IEEE80211_HE_PHY_CAP9_RX_1024_QAM_LESS_THAN_242_TONE_RU)
707 cap |= STA_REC_HE_CAP_RX_1024QAM_UNDER_RU242;
708
709 he->he_cap = cpu_to_le32(cap);
710
711 switch (sta->deflink.bandwidth) {
712 case IEEE80211_STA_RX_BW_160:
713 if (elem->phy_cap_info[0] &
714 IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G)
715 he->max_nss_mcs[CMD_HE_MCS_BW8080] =
716 he_cap->he_mcs_nss_supp.rx_mcs_80p80;
717
718 he->max_nss_mcs[CMD_HE_MCS_BW160] =
719 he_cap->he_mcs_nss_supp.rx_mcs_160;
720 fallthrough;
721 default:
722 he->max_nss_mcs[CMD_HE_MCS_BW80] =
723 he_cap->he_mcs_nss_supp.rx_mcs_80;
724 break;
725 }
726
727 he->t_frame_dur =
728 HE_MAC(CAP1_TF_MAC_PAD_DUR_MASK, elem->mac_cap_info[1]);
729 he->max_ampdu_exp =
730 HE_MAC(CAP3_MAX_AMPDU_LEN_EXP_MASK, elem->mac_cap_info[3]);
731
732 he->bw_set =
733 HE_PHY(CAP0_CHANNEL_WIDTH_SET_MASK, elem->phy_cap_info[0]);
734 he->device_class =
735 HE_PHY(CAP1_DEVICE_CLASS_A, elem->phy_cap_info[1]);
736 he->punc_pream_rx =
737 HE_PHY(CAP1_PREAMBLE_PUNC_RX_MASK, elem->phy_cap_info[1]);
738
739 he->dcm_tx_mode =
740 HE_PHY(CAP3_DCM_MAX_CONST_TX_MASK, elem->phy_cap_info[3]);
741 he->dcm_tx_max_nss =
742 HE_PHY(CAP3_DCM_MAX_TX_NSS_2, elem->phy_cap_info[3]);
743 he->dcm_rx_mode =
744 HE_PHY(CAP3_DCM_MAX_CONST_RX_MASK, elem->phy_cap_info[3]);
745 he->dcm_rx_max_nss =
746 HE_PHY(CAP3_DCM_MAX_RX_NSS_2, elem->phy_cap_info[3]);
747 he->dcm_rx_max_nss =
748 HE_PHY(CAP8_DCM_MAX_RU_MASK, elem->phy_cap_info[8]);
749
750 he->pkt_ext = 2;
751}
752
753void
754mt76_connac_mcu_sta_he_tlv_v2(struct sk_buff *skb, struct ieee80211_sta *sta)
755{
756 struct ieee80211_sta_he_cap *he_cap = &sta->deflink.he_cap;
757 struct ieee80211_he_cap_elem *elem = &he_cap->he_cap_elem;
758 struct sta_rec_he_v2 *he;
759 struct tlv *tlv;
760
761 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_HE_V2, len: sizeof(*he));
762
763 he = (struct sta_rec_he_v2 *)tlv;
764 memcpy(he->he_phy_cap, elem->phy_cap_info, sizeof(he->he_phy_cap));
765 memcpy(he->he_mac_cap, elem->mac_cap_info, sizeof(he->he_mac_cap));
766
767 switch (sta->deflink.bandwidth) {
768 case IEEE80211_STA_RX_BW_160:
769 if (elem->phy_cap_info[0] &
770 IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G)
771 he->max_nss_mcs[CMD_HE_MCS_BW8080] =
772 he_cap->he_mcs_nss_supp.rx_mcs_80p80;
773
774 he->max_nss_mcs[CMD_HE_MCS_BW160] =
775 he_cap->he_mcs_nss_supp.rx_mcs_160;
776 fallthrough;
777 default:
778 he->max_nss_mcs[CMD_HE_MCS_BW80] =
779 he_cap->he_mcs_nss_supp.rx_mcs_80;
780 break;
781 }
782
783 he->pkt_ext = IEEE80211_HE_PHY_CAP9_NOMINAL_PKT_PADDING_16US;
784}
785EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_he_tlv_v2);
786
787u8
788mt76_connac_get_phy_mode_v2(struct mt76_phy *mphy, struct ieee80211_vif *vif,
789 enum nl80211_band band, struct ieee80211_sta *sta)
790{
791 struct ieee80211_sta_ht_cap *ht_cap;
792 struct ieee80211_sta_vht_cap *vht_cap;
793 const struct ieee80211_sta_he_cap *he_cap;
794 const struct ieee80211_sta_eht_cap *eht_cap;
795 u8 mode = 0;
796
797 if (sta) {
798 ht_cap = &sta->deflink.ht_cap;
799 vht_cap = &sta->deflink.vht_cap;
800 he_cap = &sta->deflink.he_cap;
801 eht_cap = &sta->deflink.eht_cap;
802 } else {
803 struct ieee80211_supported_band *sband;
804
805 sband = mphy->hw->wiphy->bands[band];
806 ht_cap = &sband->ht_cap;
807 vht_cap = &sband->vht_cap;
808 he_cap = ieee80211_get_he_iftype_cap(sband, iftype: vif->type);
809 eht_cap = ieee80211_get_eht_iftype_cap(sband, iftype: vif->type);
810 }
811
812 if (band == NL80211_BAND_2GHZ) {
813 mode |= PHY_TYPE_BIT_HR_DSSS | PHY_TYPE_BIT_ERP;
814
815 if (ht_cap->ht_supported)
816 mode |= PHY_TYPE_BIT_HT;
817
818 if (he_cap && he_cap->has_he)
819 mode |= PHY_TYPE_BIT_HE;
820
821 if (eht_cap && eht_cap->has_eht)
822 mode |= PHY_TYPE_BIT_BE;
823 } else if (band == NL80211_BAND_5GHZ || band == NL80211_BAND_6GHZ) {
824 mode |= PHY_TYPE_BIT_OFDM;
825
826 if (ht_cap->ht_supported)
827 mode |= PHY_TYPE_BIT_HT;
828
829 if (vht_cap->vht_supported)
830 mode |= PHY_TYPE_BIT_VHT;
831
832 if (he_cap && he_cap->has_he)
833 mode |= PHY_TYPE_BIT_HE;
834
835 if (eht_cap && eht_cap->has_eht)
836 mode |= PHY_TYPE_BIT_BE;
837 }
838
839 return mode;
840}
841EXPORT_SYMBOL_GPL(mt76_connac_get_phy_mode_v2);
842
843void mt76_connac_mcu_sta_tlv(struct mt76_phy *mphy, struct sk_buff *skb,
844 struct ieee80211_sta *sta,
845 struct ieee80211_vif *vif,
846 u8 rcpi, u8 sta_state)
847{
848 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
849 struct cfg80211_chan_def *chandef = mvif->ctx ?
850 &mvif->ctx->def : &mphy->chandef;
851 enum nl80211_band band = chandef->chan->band;
852 struct mt76_dev *dev = mphy->dev;
853 struct sta_rec_ra_info *ra_info;
854 struct sta_rec_state *state;
855 struct sta_rec_phy *phy;
856 struct tlv *tlv;
857 u16 supp_rates;
858
859 /* starec ht */
860 if (sta->deflink.ht_cap.ht_supported) {
861 struct sta_rec_ht *ht;
862
863 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_HT, len: sizeof(*ht));
864 ht = (struct sta_rec_ht *)tlv;
865 ht->ht_cap = cpu_to_le16(sta->deflink.ht_cap.cap);
866 }
867
868 /* starec vht */
869 if (sta->deflink.vht_cap.vht_supported) {
870 struct sta_rec_vht *vht;
871 int len;
872
873 len = is_mt7921(dev) ? sizeof(*vht) : sizeof(*vht) - 4;
874 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_VHT, len);
875 vht = (struct sta_rec_vht *)tlv;
876 vht->vht_cap = cpu_to_le32(sta->deflink.vht_cap.cap);
877 vht->vht_rx_mcs_map = sta->deflink.vht_cap.vht_mcs.rx_mcs_map;
878 vht->vht_tx_mcs_map = sta->deflink.vht_cap.vht_mcs.tx_mcs_map;
879 }
880
881 /* starec uapsd */
882 mt76_connac_mcu_sta_uapsd(skb, vif, sta);
883
884 if (!is_mt7921(dev))
885 return;
886
887 if (sta->deflink.ht_cap.ht_supported || sta->deflink.he_cap.has_he)
888 mt76_connac_mcu_sta_amsdu_tlv(skb, sta, vif);
889
890 /* starec he */
891 if (sta->deflink.he_cap.has_he) {
892 mt76_connac_mcu_sta_he_tlv(skb, sta);
893 mt76_connac_mcu_sta_he_tlv_v2(skb, sta);
894 if (band == NL80211_BAND_6GHZ &&
895 sta_state == MT76_STA_INFO_STATE_ASSOC) {
896 struct sta_rec_he_6g_capa *he_6g_capa;
897
898 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_HE_6G,
899 len: sizeof(*he_6g_capa));
900 he_6g_capa = (struct sta_rec_he_6g_capa *)tlv;
901 he_6g_capa->capa = sta->deflink.he_6ghz_capa.capa;
902 }
903 }
904
905 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_PHY, len: sizeof(*phy));
906 phy = (struct sta_rec_phy *)tlv;
907 phy->phy_type = mt76_connac_get_phy_mode_v2(mphy, vif, band, sta);
908 phy->basic_rate = cpu_to_le16((u16)vif->bss_conf.basic_rates);
909 phy->rcpi = rcpi;
910 phy->ampdu = FIELD_PREP(IEEE80211_HT_AMPDU_PARM_FACTOR,
911 sta->deflink.ht_cap.ampdu_factor) |
912 FIELD_PREP(IEEE80211_HT_AMPDU_PARM_DENSITY,
913 sta->deflink.ht_cap.ampdu_density);
914
915 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_RA, len: sizeof(*ra_info));
916 ra_info = (struct sta_rec_ra_info *)tlv;
917
918 supp_rates = sta->deflink.supp_rates[band];
919 if (band == NL80211_BAND_2GHZ)
920 supp_rates = FIELD_PREP(RA_LEGACY_OFDM, supp_rates >> 4) |
921 FIELD_PREP(RA_LEGACY_CCK, supp_rates & 0xf);
922 else
923 supp_rates = FIELD_PREP(RA_LEGACY_OFDM, supp_rates);
924
925 ra_info->legacy = cpu_to_le16(supp_rates);
926
927 if (sta->deflink.ht_cap.ht_supported)
928 memcpy(ra_info->rx_mcs_bitmask,
929 sta->deflink.ht_cap.mcs.rx_mask,
930 HT_MCS_MASK_NUM);
931
932 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_STATE, len: sizeof(*state));
933 state = (struct sta_rec_state *)tlv;
934 state->state = sta_state;
935
936 if (sta->deflink.vht_cap.vht_supported) {
937 state->vht_opmode = sta->deflink.bandwidth;
938 state->vht_opmode |= (sta->deflink.rx_nss - 1) <<
939 IEEE80211_OPMODE_NOTIF_RX_NSS_SHIFT;
940 }
941}
942EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_tlv);
943
944void mt76_connac_mcu_wtbl_smps_tlv(struct sk_buff *skb,
945 struct ieee80211_sta *sta,
946 void *sta_wtbl, void *wtbl_tlv)
947{
948 struct wtbl_smps *smps;
949 struct tlv *tlv;
950
951 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_SMPS, sizeof(*smps),
952 wtbl_tlv, sta_wtbl);
953 smps = (struct wtbl_smps *)tlv;
954 smps->smps = (sta->deflink.smps_mode == IEEE80211_SMPS_DYNAMIC);
955}
956EXPORT_SYMBOL_GPL(mt76_connac_mcu_wtbl_smps_tlv);
957
958void mt76_connac_mcu_wtbl_ht_tlv(struct mt76_dev *dev, struct sk_buff *skb,
959 struct ieee80211_sta *sta, void *sta_wtbl,
960 void *wtbl_tlv, bool ht_ldpc, bool vht_ldpc)
961{
962 struct wtbl_ht *ht = NULL;
963 struct tlv *tlv;
964 u32 flags = 0;
965
966 if (sta->deflink.ht_cap.ht_supported || sta->deflink.he_6ghz_capa.capa) {
967 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_HT, sizeof(*ht),
968 wtbl_tlv, sta_wtbl);
969 ht = (struct wtbl_ht *)tlv;
970 ht->ldpc = ht_ldpc &&
971 !!(sta->deflink.ht_cap.cap & IEEE80211_HT_CAP_LDPC_CODING);
972
973 if (sta->deflink.ht_cap.ht_supported) {
974 ht->af = sta->deflink.ht_cap.ampdu_factor;
975 ht->mm = sta->deflink.ht_cap.ampdu_density;
976 } else {
977 ht->af = le16_get_bits(v: sta->deflink.he_6ghz_capa.capa,
978 IEEE80211_HE_6GHZ_CAP_MAX_AMPDU_LEN_EXP);
979 ht->mm = le16_get_bits(v: sta->deflink.he_6ghz_capa.capa,
980 IEEE80211_HE_6GHZ_CAP_MIN_MPDU_START);
981 }
982
983 ht->ht = true;
984 }
985
986 if (sta->deflink.vht_cap.vht_supported || sta->deflink.he_6ghz_capa.capa) {
987 struct wtbl_vht *vht;
988 u8 af;
989
990 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_VHT,
991 sizeof(*vht), wtbl_tlv,
992 sta_wtbl);
993 vht = (struct wtbl_vht *)tlv;
994 vht->ldpc = vht_ldpc &&
995 !!(sta->deflink.vht_cap.cap & IEEE80211_VHT_CAP_RXLDPC);
996 vht->vht = true;
997
998 af = FIELD_GET(IEEE80211_VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK,
999 sta->deflink.vht_cap.cap);
1000 if (ht)
1001 ht->af = max(ht->af, af);
1002 }
1003
1004 mt76_connac_mcu_wtbl_smps_tlv(skb, sta, sta_wtbl, wtbl_tlv);
1005
1006 if (is_connac_v1(dev) && sta->deflink.ht_cap.ht_supported) {
1007 /* sgi */
1008 u32 msk = MT_WTBL_W5_SHORT_GI_20 | MT_WTBL_W5_SHORT_GI_40 |
1009 MT_WTBL_W5_SHORT_GI_80 | MT_WTBL_W5_SHORT_GI_160;
1010 struct wtbl_raw *raw;
1011
1012 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_RAW_DATA,
1013 sizeof(*raw), wtbl_tlv,
1014 sta_wtbl);
1015
1016 if (sta->deflink.ht_cap.cap & IEEE80211_HT_CAP_SGI_20)
1017 flags |= MT_WTBL_W5_SHORT_GI_20;
1018 if (sta->deflink.ht_cap.cap & IEEE80211_HT_CAP_SGI_40)
1019 flags |= MT_WTBL_W5_SHORT_GI_40;
1020
1021 if (sta->deflink.vht_cap.vht_supported) {
1022 if (sta->deflink.vht_cap.cap & IEEE80211_VHT_CAP_SHORT_GI_80)
1023 flags |= MT_WTBL_W5_SHORT_GI_80;
1024 if (sta->deflink.vht_cap.cap & IEEE80211_VHT_CAP_SHORT_GI_160)
1025 flags |= MT_WTBL_W5_SHORT_GI_160;
1026 }
1027 raw = (struct wtbl_raw *)tlv;
1028 raw->val = cpu_to_le32(flags);
1029 raw->msk = cpu_to_le32(~msk);
1030 raw->wtbl_idx = 1;
1031 raw->dw = 5;
1032 }
1033}
1034EXPORT_SYMBOL_GPL(mt76_connac_mcu_wtbl_ht_tlv);
1035
1036int mt76_connac_mcu_sta_cmd(struct mt76_phy *phy,
1037 struct mt76_sta_cmd_info *info)
1038{
1039 struct mt76_vif *mvif = (struct mt76_vif *)info->vif->drv_priv;
1040 struct mt76_dev *dev = phy->dev;
1041 struct wtbl_req_hdr *wtbl_hdr;
1042 struct tlv *sta_wtbl;
1043 struct sk_buff *skb;
1044
1045 skb = mt76_connac_mcu_alloc_sta_req(dev, mvif, wcid: info->wcid);
1046 if (IS_ERR(ptr: skb))
1047 return PTR_ERR(ptr: skb);
1048
1049 if (info->sta || !info->offload_fw)
1050 mt76_connac_mcu_sta_basic_tlv(dev, skb, info->vif, info->sta,
1051 info->enable, info->newly);
1052 if (info->sta && info->enable)
1053 mt76_connac_mcu_sta_tlv(phy, skb, info->sta,
1054 info->vif, info->rcpi,
1055 info->state);
1056
1057 sta_wtbl = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_WTBL,
1058 len: sizeof(struct tlv));
1059
1060 wtbl_hdr = mt76_connac_mcu_alloc_wtbl_req(dev, info->wcid,
1061 WTBL_RESET_AND_SET,
1062 sta_wtbl, &skb);
1063 if (IS_ERR(ptr: wtbl_hdr))
1064 return PTR_ERR(ptr: wtbl_hdr);
1065
1066 if (info->enable) {
1067 mt76_connac_mcu_wtbl_generic_tlv(dev, skb, info->vif,
1068 info->sta, sta_wtbl,
1069 wtbl_hdr);
1070 mt76_connac_mcu_wtbl_hdr_trans_tlv(skb, info->vif, info->wcid,
1071 sta_wtbl, wtbl_hdr);
1072 if (info->sta)
1073 mt76_connac_mcu_wtbl_ht_tlv(dev, skb, info->sta,
1074 sta_wtbl, wtbl_hdr,
1075 true, true);
1076 }
1077
1078 return mt76_mcu_skb_send_msg(dev, skb, cmd: info->cmd, wait_resp: true);
1079}
1080EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_cmd);
1081
1082void mt76_connac_mcu_wtbl_ba_tlv(struct mt76_dev *dev, struct sk_buff *skb,
1083 struct ieee80211_ampdu_params *params,
1084 bool enable, bool tx, void *sta_wtbl,
1085 void *wtbl_tlv)
1086{
1087 struct wtbl_ba *ba;
1088 struct tlv *tlv;
1089
1090 tlv = mt76_connac_mcu_add_nested_tlv(skb, WTBL_BA, sizeof(*ba),
1091 wtbl_tlv, sta_wtbl);
1092
1093 ba = (struct wtbl_ba *)tlv;
1094 ba->tid = params->tid;
1095
1096 if (tx) {
1097 ba->ba_type = MT_BA_TYPE_ORIGINATOR;
1098 ba->sn = enable ? cpu_to_le16(params->ssn) : 0;
1099 ba->ba_winsize = enable ? cpu_to_le16(params->buf_size) : 0;
1100 ba->ba_en = enable;
1101 } else {
1102 memcpy(ba->peer_addr, params->sta->addr, ETH_ALEN);
1103 ba->ba_type = MT_BA_TYPE_RECIPIENT;
1104 ba->rst_ba_tid = params->tid;
1105 ba->rst_ba_sel = RST_BA_MAC_TID_MATCH;
1106 ba->rst_ba_sb = 1;
1107 }
1108
1109 if (!is_connac_v1(dev)) {
1110 ba->ba_winsize = enable ? cpu_to_le16(params->buf_size) : 0;
1111 return;
1112 }
1113
1114 if (enable && tx) {
1115 static const u8 ba_range[] = { 4, 8, 12, 24, 36, 48, 54, 64 };
1116 int i;
1117
1118 for (i = 7; i > 0; i--) {
1119 if (params->buf_size >= ba_range[i])
1120 break;
1121 }
1122 ba->ba_winsize_idx = i;
1123 }
1124}
1125EXPORT_SYMBOL_GPL(mt76_connac_mcu_wtbl_ba_tlv);
1126
1127int mt76_connac_mcu_uni_add_dev(struct mt76_phy *phy,
1128 struct ieee80211_vif *vif,
1129 struct mt76_wcid *wcid,
1130 bool enable)
1131{
1132 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
1133 struct mt76_dev *dev = phy->dev;
1134 struct {
1135 struct {
1136 u8 omac_idx;
1137 u8 band_idx;
1138 __le16 pad;
1139 } __packed hdr;
1140 struct req_tlv {
1141 __le16 tag;
1142 __le16 len;
1143 u8 active;
1144 u8 pad;
1145 u8 omac_addr[ETH_ALEN];
1146 } __packed tlv;
1147 } dev_req = {
1148 .hdr = {
1149 .omac_idx = mvif->omac_idx,
1150 .band_idx = mvif->band_idx,
1151 },
1152 .tlv = {
1153 .tag = cpu_to_le16(DEV_INFO_ACTIVE),
1154 .len = cpu_to_le16(sizeof(struct req_tlv)),
1155 .active = enable,
1156 },
1157 };
1158 struct {
1159 struct {
1160 u8 bss_idx;
1161 u8 pad[3];
1162 } __packed hdr;
1163 struct mt76_connac_bss_basic_tlv basic;
1164 } basic_req = {
1165 .hdr = {
1166 .bss_idx = mvif->idx,
1167 },
1168 .basic = {
1169 .tag = cpu_to_le16(UNI_BSS_INFO_BASIC),
1170 .len = cpu_to_le16(sizeof(struct mt76_connac_bss_basic_tlv)),
1171 .omac_idx = mvif->omac_idx,
1172 .band_idx = mvif->band_idx,
1173 .wmm_idx = mvif->wmm_idx,
1174 .active = enable,
1175 .bmc_tx_wlan_idx = cpu_to_le16(wcid->idx),
1176 .sta_idx = cpu_to_le16(wcid->idx),
1177 .conn_state = 1,
1178 },
1179 };
1180 int err, idx, cmd, len;
1181 void *data;
1182
1183 switch (vif->type) {
1184 case NL80211_IFTYPE_MESH_POINT:
1185 case NL80211_IFTYPE_MONITOR:
1186 case NL80211_IFTYPE_AP:
1187 basic_req.basic.conn_type = cpu_to_le32(CONNECTION_INFRA_AP);
1188 break;
1189 case NL80211_IFTYPE_STATION:
1190 basic_req.basic.conn_type = cpu_to_le32(CONNECTION_INFRA_STA);
1191 break;
1192 case NL80211_IFTYPE_ADHOC:
1193 basic_req.basic.conn_type = cpu_to_le32(CONNECTION_IBSS_ADHOC);
1194 break;
1195 default:
1196 WARN_ON(1);
1197 break;
1198 }
1199
1200 idx = mvif->omac_idx > EXT_BSSID_START ? HW_BSSID_0 : mvif->omac_idx;
1201 basic_req.basic.hw_bss_idx = idx;
1202
1203 memcpy(dev_req.tlv.omac_addr, vif->addr, ETH_ALEN);
1204
1205 cmd = enable ? MCU_UNI_CMD(DEV_INFO_UPDATE) : MCU_UNI_CMD(BSS_INFO_UPDATE);
1206 data = enable ? (void *)&dev_req : (void *)&basic_req;
1207 len = enable ? sizeof(dev_req) : sizeof(basic_req);
1208
1209 err = mt76_mcu_send_msg(dev, cmd, data, len, wait_resp: true);
1210 if (err < 0)
1211 return err;
1212
1213 cmd = enable ? MCU_UNI_CMD(BSS_INFO_UPDATE) : MCU_UNI_CMD(DEV_INFO_UPDATE);
1214 data = enable ? (void *)&basic_req : (void *)&dev_req;
1215 len = enable ? sizeof(basic_req) : sizeof(dev_req);
1216
1217 return mt76_mcu_send_msg(dev, cmd, data, len, wait_resp: true);
1218}
1219EXPORT_SYMBOL_GPL(mt76_connac_mcu_uni_add_dev);
1220
1221void mt76_connac_mcu_sta_ba_tlv(struct sk_buff *skb,
1222 struct ieee80211_ampdu_params *params,
1223 bool enable, bool tx)
1224{
1225 struct sta_rec_ba *ba;
1226 struct tlv *tlv;
1227
1228 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_BA, len: sizeof(*ba));
1229
1230 ba = (struct sta_rec_ba *)tlv;
1231 ba->ba_type = tx ? MT_BA_TYPE_ORIGINATOR : MT_BA_TYPE_RECIPIENT;
1232 ba->winsize = cpu_to_le16(params->buf_size);
1233 ba->ssn = cpu_to_le16(params->ssn);
1234 ba->ba_en = enable << params->tid;
1235 ba->amsdu = params->amsdu;
1236 ba->tid = params->tid;
1237}
1238EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_ba_tlv);
1239
1240int mt76_connac_mcu_sta_wed_update(struct mt76_dev *dev, struct sk_buff *skb)
1241{
1242 if (!mt76_is_mmio(dev))
1243 return 0;
1244
1245 if (!mtk_wed_device_active(&dev->mmio.wed))
1246 return 0;
1247
1248 return mtk_wed_device_update_msg(&dev->mmio.wed, WED_WO_STA_REC,
1249 skb->data, skb->len);
1250}
1251EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_wed_update);
1252
1253int mt76_connac_mcu_sta_ba(struct mt76_dev *dev, struct mt76_vif *mvif,
1254 struct ieee80211_ampdu_params *params,
1255 int cmd, bool enable, bool tx)
1256{
1257 struct mt76_wcid *wcid = (struct mt76_wcid *)params->sta->drv_priv;
1258 struct wtbl_req_hdr *wtbl_hdr;
1259 struct tlv *sta_wtbl;
1260 struct sk_buff *skb;
1261 int ret;
1262
1263 skb = mt76_connac_mcu_alloc_sta_req(dev, mvif, wcid);
1264 if (IS_ERR(ptr: skb))
1265 return PTR_ERR(ptr: skb);
1266
1267 sta_wtbl = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_WTBL,
1268 len: sizeof(struct tlv));
1269
1270 wtbl_hdr = mt76_connac_mcu_alloc_wtbl_req(dev, wcid, WTBL_SET,
1271 sta_wtbl, &skb);
1272 if (IS_ERR(ptr: wtbl_hdr))
1273 return PTR_ERR(ptr: wtbl_hdr);
1274
1275 mt76_connac_mcu_wtbl_ba_tlv(dev, skb, params, enable, tx, sta_wtbl,
1276 wtbl_hdr);
1277
1278 ret = mt76_connac_mcu_sta_wed_update(dev, skb);
1279 if (ret)
1280 return ret;
1281
1282 ret = mt76_mcu_skb_send_msg(dev, skb, cmd, wait_resp: true);
1283 if (ret)
1284 return ret;
1285
1286 skb = mt76_connac_mcu_alloc_sta_req(dev, mvif, wcid);
1287 if (IS_ERR(ptr: skb))
1288 return PTR_ERR(ptr: skb);
1289
1290 mt76_connac_mcu_sta_ba_tlv(skb, params, enable, tx);
1291
1292 ret = mt76_connac_mcu_sta_wed_update(dev, skb);
1293 if (ret)
1294 return ret;
1295
1296 return mt76_mcu_skb_send_msg(dev, skb, cmd, wait_resp: true);
1297}
1298EXPORT_SYMBOL_GPL(mt76_connac_mcu_sta_ba);
1299
1300u8 mt76_connac_get_phy_mode(struct mt76_phy *phy, struct ieee80211_vif *vif,
1301 enum nl80211_band band, struct ieee80211_sta *sta)
1302{
1303 struct mt76_dev *dev = phy->dev;
1304 const struct ieee80211_sta_he_cap *he_cap;
1305 struct ieee80211_sta_vht_cap *vht_cap;
1306 struct ieee80211_sta_ht_cap *ht_cap;
1307 u8 mode = 0;
1308
1309 if (is_connac_v1(dev))
1310 return 0x38;
1311
1312 if (sta) {
1313 ht_cap = &sta->deflink.ht_cap;
1314 vht_cap = &sta->deflink.vht_cap;
1315 he_cap = &sta->deflink.he_cap;
1316 } else {
1317 struct ieee80211_supported_band *sband;
1318
1319 sband = phy->hw->wiphy->bands[band];
1320 ht_cap = &sband->ht_cap;
1321 vht_cap = &sband->vht_cap;
1322 he_cap = ieee80211_get_he_iftype_cap(sband, iftype: vif->type);
1323 }
1324
1325 if (band == NL80211_BAND_2GHZ) {
1326 mode |= PHY_MODE_B | PHY_MODE_G;
1327
1328 if (ht_cap->ht_supported)
1329 mode |= PHY_MODE_GN;
1330
1331 if (he_cap && he_cap->has_he)
1332 mode |= PHY_MODE_AX_24G;
1333 } else if (band == NL80211_BAND_5GHZ) {
1334 mode |= PHY_MODE_A;
1335
1336 if (ht_cap->ht_supported)
1337 mode |= PHY_MODE_AN;
1338
1339 if (vht_cap->vht_supported)
1340 mode |= PHY_MODE_AC;
1341
1342 if (he_cap && he_cap->has_he)
1343 mode |= PHY_MODE_AX_5G;
1344 } else if (band == NL80211_BAND_6GHZ) {
1345 mode |= PHY_MODE_A | PHY_MODE_AN |
1346 PHY_MODE_AC | PHY_MODE_AX_5G;
1347 }
1348
1349 return mode;
1350}
1351EXPORT_SYMBOL_GPL(mt76_connac_get_phy_mode);
1352
1353u8 mt76_connac_get_phy_mode_ext(struct mt76_phy *phy, struct ieee80211_vif *vif,
1354 enum nl80211_band band)
1355{
1356 const struct ieee80211_sta_eht_cap *eht_cap;
1357 struct ieee80211_supported_band *sband;
1358 u8 mode = 0;
1359
1360 if (band == NL80211_BAND_6GHZ)
1361 mode |= PHY_MODE_AX_6G;
1362
1363 sband = phy->hw->wiphy->bands[band];
1364 eht_cap = ieee80211_get_eht_iftype_cap(sband, iftype: vif->type);
1365
1366 if (!eht_cap || !eht_cap->has_eht || !vif->bss_conf.eht_support)
1367 return mode;
1368
1369 switch (band) {
1370 case NL80211_BAND_6GHZ:
1371 mode |= PHY_MODE_BE_6G;
1372 break;
1373 case NL80211_BAND_5GHZ:
1374 mode |= PHY_MODE_BE_5G;
1375 break;
1376 case NL80211_BAND_2GHZ:
1377 mode |= PHY_MODE_BE_24G;
1378 break;
1379 default:
1380 break;
1381 }
1382
1383 return mode;
1384}
1385EXPORT_SYMBOL_GPL(mt76_connac_get_phy_mode_ext);
1386
1387const struct ieee80211_sta_he_cap *
1388mt76_connac_get_he_phy_cap(struct mt76_phy *phy, struct ieee80211_vif *vif)
1389{
1390 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
1391 struct cfg80211_chan_def *chandef = mvif->ctx ?
1392 &mvif->ctx->def : &phy->chandef;
1393 enum nl80211_band band = chandef->chan->band;
1394 struct ieee80211_supported_band *sband;
1395
1396 sband = phy->hw->wiphy->bands[band];
1397
1398 return ieee80211_get_he_iftype_cap(sband, iftype: vif->type);
1399}
1400EXPORT_SYMBOL_GPL(mt76_connac_get_he_phy_cap);
1401
1402const struct ieee80211_sta_eht_cap *
1403mt76_connac_get_eht_phy_cap(struct mt76_phy *phy, struct ieee80211_vif *vif)
1404{
1405 enum nl80211_band band = phy->chandef.chan->band;
1406 struct ieee80211_supported_band *sband;
1407
1408 sband = phy->hw->wiphy->bands[band];
1409
1410 return ieee80211_get_eht_iftype_cap(sband, iftype: vif->type);
1411}
1412EXPORT_SYMBOL_GPL(mt76_connac_get_eht_phy_cap);
1413
1414#define DEFAULT_HE_PE_DURATION 4
1415#define DEFAULT_HE_DURATION_RTS_THRES 1023
1416static void
1417mt76_connac_mcu_uni_bss_he_tlv(struct mt76_phy *phy, struct ieee80211_vif *vif,
1418 struct tlv *tlv)
1419{
1420 const struct ieee80211_sta_he_cap *cap;
1421 struct bss_info_uni_he *he;
1422
1423 cap = mt76_connac_get_he_phy_cap(phy, vif);
1424
1425 he = (struct bss_info_uni_he *)tlv;
1426 he->he_pe_duration = vif->bss_conf.htc_trig_based_pkt_ext;
1427 if (!he->he_pe_duration)
1428 he->he_pe_duration = DEFAULT_HE_PE_DURATION;
1429
1430 he->he_rts_thres = cpu_to_le16(vif->bss_conf.frame_time_rts_th);
1431 if (!he->he_rts_thres)
1432 he->he_rts_thres = cpu_to_le16(DEFAULT_HE_DURATION_RTS_THRES);
1433
1434 he->max_nss_mcs[CMD_HE_MCS_BW80] = cap->he_mcs_nss_supp.tx_mcs_80;
1435 he->max_nss_mcs[CMD_HE_MCS_BW160] = cap->he_mcs_nss_supp.tx_mcs_160;
1436 he->max_nss_mcs[CMD_HE_MCS_BW8080] = cap->he_mcs_nss_supp.tx_mcs_80p80;
1437}
1438
1439int mt76_connac_mcu_uni_set_chctx(struct mt76_phy *phy, struct mt76_vif *mvif,
1440 struct ieee80211_chanctx_conf *ctx)
1441{
1442 struct cfg80211_chan_def *chandef = ctx ? &ctx->def : &phy->chandef;
1443 int freq1 = chandef->center_freq1, freq2 = chandef->center_freq2;
1444 enum nl80211_band band = chandef->chan->band;
1445 struct mt76_dev *mdev = phy->dev;
1446 struct {
1447 struct {
1448 u8 bss_idx;
1449 u8 pad[3];
1450 } __packed hdr;
1451 struct rlm_tlv {
1452 __le16 tag;
1453 __le16 len;
1454 u8 control_channel;
1455 u8 center_chan;
1456 u8 center_chan2;
1457 u8 bw;
1458 u8 tx_streams;
1459 u8 rx_streams;
1460 u8 short_st;
1461 u8 ht_op_info;
1462 u8 sco;
1463 u8 band;
1464 u8 pad[2];
1465 } __packed rlm;
1466 } __packed rlm_req = {
1467 .hdr = {
1468 .bss_idx = mvif->idx,
1469 },
1470 .rlm = {
1471 .tag = cpu_to_le16(UNI_BSS_INFO_RLM),
1472 .len = cpu_to_le16(sizeof(struct rlm_tlv)),
1473 .control_channel = chandef->chan->hw_value,
1474 .center_chan = ieee80211_frequency_to_channel(freq: freq1),
1475 .center_chan2 = ieee80211_frequency_to_channel(freq: freq2),
1476 .tx_streams = hweight8(phy->antenna_mask),
1477 .ht_op_info = 4, /* set HT 40M allowed */
1478 .rx_streams = phy->chainmask,
1479 .short_st = true,
1480 .band = band,
1481 },
1482 };
1483
1484 switch (chandef->width) {
1485 case NL80211_CHAN_WIDTH_40:
1486 rlm_req.rlm.bw = CMD_CBW_40MHZ;
1487 break;
1488 case NL80211_CHAN_WIDTH_80:
1489 rlm_req.rlm.bw = CMD_CBW_80MHZ;
1490 break;
1491 case NL80211_CHAN_WIDTH_80P80:
1492 rlm_req.rlm.bw = CMD_CBW_8080MHZ;
1493 break;
1494 case NL80211_CHAN_WIDTH_160:
1495 rlm_req.rlm.bw = CMD_CBW_160MHZ;
1496 break;
1497 case NL80211_CHAN_WIDTH_5:
1498 rlm_req.rlm.bw = CMD_CBW_5MHZ;
1499 break;
1500 case NL80211_CHAN_WIDTH_10:
1501 rlm_req.rlm.bw = CMD_CBW_10MHZ;
1502 break;
1503 case NL80211_CHAN_WIDTH_20_NOHT:
1504 case NL80211_CHAN_WIDTH_20:
1505 default:
1506 rlm_req.rlm.bw = CMD_CBW_20MHZ;
1507 rlm_req.rlm.ht_op_info = 0;
1508 break;
1509 }
1510
1511 if (rlm_req.rlm.control_channel < rlm_req.rlm.center_chan)
1512 rlm_req.rlm.sco = 1; /* SCA */
1513 else if (rlm_req.rlm.control_channel > rlm_req.rlm.center_chan)
1514 rlm_req.rlm.sco = 3; /* SCB */
1515
1516 return mt76_mcu_send_msg(dev: mdev, MCU_UNI_CMD(BSS_INFO_UPDATE), data: &rlm_req,
1517 len: sizeof(rlm_req), wait_resp: true);
1518}
1519EXPORT_SYMBOL_GPL(mt76_connac_mcu_uni_set_chctx);
1520
1521int mt76_connac_mcu_uni_add_bss(struct mt76_phy *phy,
1522 struct ieee80211_vif *vif,
1523 struct mt76_wcid *wcid,
1524 bool enable,
1525 struct ieee80211_chanctx_conf *ctx)
1526{
1527 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
1528 struct cfg80211_chan_def *chandef = ctx ? &ctx->def : &phy->chandef;
1529 enum nl80211_band band = chandef->chan->band;
1530 struct mt76_dev *mdev = phy->dev;
1531 struct {
1532 struct {
1533 u8 bss_idx;
1534 u8 pad[3];
1535 } __packed hdr;
1536 struct mt76_connac_bss_basic_tlv basic;
1537 struct mt76_connac_bss_qos_tlv qos;
1538 } basic_req = {
1539 .hdr = {
1540 .bss_idx = mvif->idx,
1541 },
1542 .basic = {
1543 .tag = cpu_to_le16(UNI_BSS_INFO_BASIC),
1544 .len = cpu_to_le16(sizeof(struct mt76_connac_bss_basic_tlv)),
1545 .bcn_interval = cpu_to_le16(vif->bss_conf.beacon_int),
1546 .dtim_period = vif->bss_conf.dtim_period,
1547 .omac_idx = mvif->omac_idx,
1548 .band_idx = mvif->band_idx,
1549 .wmm_idx = mvif->wmm_idx,
1550 .active = true, /* keep bss deactivated */
1551 .phymode = mt76_connac_get_phy_mode(phy, vif, band, NULL),
1552 },
1553 .qos = {
1554 .tag = cpu_to_le16(UNI_BSS_INFO_QBSS),
1555 .len = cpu_to_le16(sizeof(struct mt76_connac_bss_qos_tlv)),
1556 .qos = vif->bss_conf.qos,
1557 },
1558 };
1559 int err, conn_type;
1560 u8 idx, basic_phy;
1561
1562 idx = mvif->omac_idx > EXT_BSSID_START ? HW_BSSID_0 : mvif->omac_idx;
1563 basic_req.basic.hw_bss_idx = idx;
1564 if (band == NL80211_BAND_6GHZ)
1565 basic_req.basic.phymode_ext = PHY_MODE_AX_6G;
1566
1567 basic_phy = mt76_connac_get_phy_mode_v2(phy, vif, band, NULL);
1568 basic_req.basic.nonht_basic_phy = cpu_to_le16(basic_phy);
1569
1570 switch (vif->type) {
1571 case NL80211_IFTYPE_MESH_POINT:
1572 case NL80211_IFTYPE_AP:
1573 if (vif->p2p)
1574 conn_type = CONNECTION_P2P_GO;
1575 else
1576 conn_type = CONNECTION_INFRA_AP;
1577 basic_req.basic.conn_type = cpu_to_le32(conn_type);
1578 /* Fully active/deactivate BSS network in AP mode only */
1579 basic_req.basic.active = enable;
1580 break;
1581 case NL80211_IFTYPE_STATION:
1582 if (vif->p2p)
1583 conn_type = CONNECTION_P2P_GC;
1584 else
1585 conn_type = CONNECTION_INFRA_STA;
1586 basic_req.basic.conn_type = cpu_to_le32(conn_type);
1587 break;
1588 case NL80211_IFTYPE_ADHOC:
1589 basic_req.basic.conn_type = cpu_to_le32(CONNECTION_IBSS_ADHOC);
1590 break;
1591 default:
1592 WARN_ON(1);
1593 break;
1594 }
1595
1596 memcpy(basic_req.basic.bssid, vif->bss_conf.bssid, ETH_ALEN);
1597 basic_req.basic.bmc_tx_wlan_idx = cpu_to_le16(wcid->idx);
1598 basic_req.basic.sta_idx = cpu_to_le16(wcid->idx);
1599 basic_req.basic.conn_state = !enable;
1600
1601 err = mt76_mcu_send_msg(dev: mdev, MCU_UNI_CMD(BSS_INFO_UPDATE), data: &basic_req,
1602 len: sizeof(basic_req), wait_resp: true);
1603 if (err < 0)
1604 return err;
1605
1606 if (vif->bss_conf.he_support) {
1607 struct {
1608 struct {
1609 u8 bss_idx;
1610 u8 pad[3];
1611 } __packed hdr;
1612 struct bss_info_uni_he he;
1613 struct bss_info_uni_bss_color bss_color;
1614 } he_req = {
1615 .hdr = {
1616 .bss_idx = mvif->idx,
1617 },
1618 .he = {
1619 .tag = cpu_to_le16(UNI_BSS_INFO_HE_BASIC),
1620 .len = cpu_to_le16(sizeof(struct bss_info_uni_he)),
1621 },
1622 .bss_color = {
1623 .tag = cpu_to_le16(UNI_BSS_INFO_BSS_COLOR),
1624 .len = cpu_to_le16(sizeof(struct bss_info_uni_bss_color)),
1625 .enable = 0,
1626 .bss_color = 0,
1627 },
1628 };
1629
1630 if (enable) {
1631 he_req.bss_color.enable =
1632 vif->bss_conf.he_bss_color.enabled;
1633 he_req.bss_color.bss_color =
1634 vif->bss_conf.he_bss_color.color;
1635 }
1636
1637 mt76_connac_mcu_uni_bss_he_tlv(phy, vif,
1638 tlv: (struct tlv *)&he_req.he);
1639 err = mt76_mcu_send_msg(dev: mdev, MCU_UNI_CMD(BSS_INFO_UPDATE),
1640 data: &he_req, len: sizeof(he_req), wait_resp: true);
1641 if (err < 0)
1642 return err;
1643 }
1644
1645 return mt76_connac_mcu_uni_set_chctx(phy, mvif, ctx);
1646}
1647EXPORT_SYMBOL_GPL(mt76_connac_mcu_uni_add_bss);
1648
1649#define MT76_CONNAC_SCAN_CHANNEL_TIME 60
1650int mt76_connac_mcu_hw_scan(struct mt76_phy *phy, struct ieee80211_vif *vif,
1651 struct ieee80211_scan_request *scan_req)
1652{
1653 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
1654 struct cfg80211_scan_request *sreq = &scan_req->req;
1655 int n_ssids = 0, err, i, duration;
1656 int ext_channels_num = max_t(int, sreq->n_channels - 32, 0);
1657 struct ieee80211_channel **scan_list = sreq->channels;
1658 struct mt76_dev *mdev = phy->dev;
1659 struct mt76_connac_mcu_scan_channel *chan;
1660 struct mt76_connac_hw_scan_req *req;
1661 struct sk_buff *skb;
1662
1663 if (test_bit(MT76_HW_SCANNING, &phy->state))
1664 return -EBUSY;
1665
1666 skb = mt76_mcu_msg_alloc(dev: mdev, NULL, data_len: sizeof(*req));
1667 if (!skb)
1668 return -ENOMEM;
1669
1670 set_bit(nr: MT76_HW_SCANNING, addr: &phy->state);
1671 mvif->scan_seq_num = (mvif->scan_seq_num + 1) & 0x7f;
1672
1673 req = (struct mt76_connac_hw_scan_req *)skb_put(skb, len: sizeof(*req));
1674
1675 req->seq_num = mvif->scan_seq_num | mvif->band_idx << 7;
1676 req->bss_idx = mvif->idx;
1677 req->scan_type = sreq->n_ssids ? 1 : 0;
1678 req->probe_req_num = sreq->n_ssids ? 2 : 0;
1679 req->version = 1;
1680
1681 for (i = 0; i < sreq->n_ssids; i++) {
1682 if (!sreq->ssids[i].ssid_len)
1683 continue;
1684
1685 req->ssids[i].ssid_len = cpu_to_le32(sreq->ssids[i].ssid_len);
1686 memcpy(req->ssids[i].ssid, sreq->ssids[i].ssid,
1687 sreq->ssids[i].ssid_len);
1688 n_ssids++;
1689 }
1690 req->ssid_type = n_ssids ? BIT(2) : BIT(0);
1691 req->ssid_type_ext = n_ssids ? BIT(0) : 0;
1692 req->ssids_num = n_ssids;
1693
1694 duration = is_mt7921(dev: phy->dev) ? 0 : MT76_CONNAC_SCAN_CHANNEL_TIME;
1695 /* increase channel time for passive scan */
1696 if (!sreq->n_ssids)
1697 duration *= 2;
1698 req->timeout_value = cpu_to_le16(sreq->n_channels * duration);
1699 req->channel_min_dwell_time = cpu_to_le16(duration);
1700 req->channel_dwell_time = cpu_to_le16(duration);
1701
1702 if (sreq->n_channels == 0 || sreq->n_channels > 64) {
1703 req->channel_type = 0;
1704 req->channels_num = 0;
1705 req->ext_channels_num = 0;
1706 } else {
1707 req->channel_type = 4;
1708 req->channels_num = min_t(u8, sreq->n_channels, 32);
1709 req->ext_channels_num = min_t(u8, ext_channels_num, 32);
1710 }
1711
1712 for (i = 0; i < req->channels_num + req->ext_channels_num; i++) {
1713 if (i >= 32)
1714 chan = &req->ext_channels[i - 32];
1715 else
1716 chan = &req->channels[i];
1717
1718 switch (scan_list[i]->band) {
1719 case NL80211_BAND_2GHZ:
1720 chan->band = 1;
1721 break;
1722 case NL80211_BAND_6GHZ:
1723 chan->band = 3;
1724 break;
1725 default:
1726 chan->band = 2;
1727 break;
1728 }
1729 chan->channel_num = scan_list[i]->hw_value;
1730 }
1731
1732 if (sreq->ie_len > 0) {
1733 memcpy(req->ies, sreq->ie, sreq->ie_len);
1734 req->ies_len = cpu_to_le16(sreq->ie_len);
1735 }
1736
1737 if (is_mt7921(dev: phy->dev))
1738 req->scan_func |= SCAN_FUNC_SPLIT_SCAN;
1739
1740 memcpy(req->bssid, sreq->bssid, ETH_ALEN);
1741 if (sreq->flags & NL80211_SCAN_FLAG_RANDOM_ADDR) {
1742 get_random_mask_addr(buf: req->random_mac, addr: sreq->mac_addr,
1743 mask: sreq->mac_addr_mask);
1744 req->scan_func |= SCAN_FUNC_RANDOM_MAC;
1745 }
1746
1747 err = mt76_mcu_skb_send_msg(dev: mdev, skb, MCU_CE_CMD(START_HW_SCAN),
1748 wait_resp: false);
1749 if (err < 0)
1750 clear_bit(nr: MT76_HW_SCANNING, addr: &phy->state);
1751
1752 return err;
1753}
1754EXPORT_SYMBOL_GPL(mt76_connac_mcu_hw_scan);
1755
1756int mt76_connac_mcu_cancel_hw_scan(struct mt76_phy *phy,
1757 struct ieee80211_vif *vif)
1758{
1759 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
1760 struct {
1761 u8 seq_num;
1762 u8 is_ext_channel;
1763 u8 rsv[2];
1764 } __packed req = {
1765 .seq_num = mvif->scan_seq_num,
1766 };
1767
1768 if (test_and_clear_bit(nr: MT76_HW_SCANNING, addr: &phy->state)) {
1769 struct cfg80211_scan_info info = {
1770 .aborted = true,
1771 };
1772
1773 ieee80211_scan_completed(hw: phy->hw, info: &info);
1774 }
1775
1776 return mt76_mcu_send_msg(dev: phy->dev, MCU_CE_CMD(CANCEL_HW_SCAN),
1777 data: &req, len: sizeof(req), wait_resp: false);
1778}
1779EXPORT_SYMBOL_GPL(mt76_connac_mcu_cancel_hw_scan);
1780
1781int mt76_connac_mcu_sched_scan_req(struct mt76_phy *phy,
1782 struct ieee80211_vif *vif,
1783 struct cfg80211_sched_scan_request *sreq)
1784{
1785 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
1786 struct ieee80211_channel **scan_list = sreq->channels;
1787 struct mt76_connac_mcu_scan_channel *chan;
1788 struct mt76_connac_sched_scan_req *req;
1789 struct mt76_dev *mdev = phy->dev;
1790 struct cfg80211_match_set *match;
1791 struct cfg80211_ssid *ssid;
1792 struct sk_buff *skb;
1793 int i;
1794
1795 skb = mt76_mcu_msg_alloc(dev: mdev, NULL, data_len: sizeof(*req) + sreq->ie_len);
1796 if (!skb)
1797 return -ENOMEM;
1798
1799 mvif->scan_seq_num = (mvif->scan_seq_num + 1) & 0x7f;
1800
1801 req = (struct mt76_connac_sched_scan_req *)skb_put(skb, len: sizeof(*req));
1802 req->version = 1;
1803 req->seq_num = mvif->scan_seq_num | mvif->band_idx << 7;
1804
1805 if (sreq->flags & NL80211_SCAN_FLAG_RANDOM_ADDR) {
1806 u8 *addr = is_mt7663(dev: phy->dev) ? req->mt7663.random_mac
1807 : req->mt7921.random_mac;
1808
1809 req->scan_func = 1;
1810 get_random_mask_addr(buf: addr, addr: sreq->mac_addr,
1811 mask: sreq->mac_addr_mask);
1812 }
1813 if (is_mt7921(dev: phy->dev)) {
1814 req->mt7921.bss_idx = mvif->idx;
1815 req->mt7921.delay = cpu_to_le32(sreq->delay);
1816 }
1817
1818 req->ssids_num = sreq->n_ssids;
1819 for (i = 0; i < req->ssids_num; i++) {
1820 ssid = &sreq->ssids[i];
1821 memcpy(req->ssids[i].ssid, ssid->ssid, ssid->ssid_len);
1822 req->ssids[i].ssid_len = cpu_to_le32(ssid->ssid_len);
1823 }
1824
1825 req->match_num = sreq->n_match_sets;
1826 for (i = 0; i < req->match_num; i++) {
1827 match = &sreq->match_sets[i];
1828 memcpy(req->match[i].ssid, match->ssid.ssid,
1829 match->ssid.ssid_len);
1830 req->match[i].rssi_th = cpu_to_le32(match->rssi_thold);
1831 req->match[i].ssid_len = match->ssid.ssid_len;
1832 }
1833
1834 req->channel_type = sreq->n_channels ? 4 : 0;
1835 req->channels_num = min_t(u8, sreq->n_channels, 64);
1836 for (i = 0; i < req->channels_num; i++) {
1837 chan = &req->channels[i];
1838
1839 switch (scan_list[i]->band) {
1840 case NL80211_BAND_2GHZ:
1841 chan->band = 1;
1842 break;
1843 case NL80211_BAND_6GHZ:
1844 chan->band = 3;
1845 break;
1846 default:
1847 chan->band = 2;
1848 break;
1849 }
1850 chan->channel_num = scan_list[i]->hw_value;
1851 }
1852
1853 req->intervals_num = sreq->n_scan_plans;
1854 for (i = 0; i < req->intervals_num; i++)
1855 req->intervals[i] = cpu_to_le16(sreq->scan_plans[i].interval);
1856
1857 if (sreq->ie_len > 0) {
1858 req->ie_len = cpu_to_le16(sreq->ie_len);
1859 memcpy(skb_put(skb, sreq->ie_len), sreq->ie, sreq->ie_len);
1860 }
1861
1862 return mt76_mcu_skb_send_msg(dev: mdev, skb, MCU_CE_CMD(SCHED_SCAN_REQ),
1863 wait_resp: false);
1864}
1865EXPORT_SYMBOL_GPL(mt76_connac_mcu_sched_scan_req);
1866
1867int mt76_connac_mcu_sched_scan_enable(struct mt76_phy *phy,
1868 struct ieee80211_vif *vif,
1869 bool enable)
1870{
1871 struct {
1872 u8 active; /* 0: enabled 1: disabled */
1873 u8 rsv[3];
1874 } __packed req = {
1875 .active = !enable,
1876 };
1877
1878 if (enable)
1879 set_bit(nr: MT76_HW_SCHED_SCANNING, addr: &phy->state);
1880 else
1881 clear_bit(nr: MT76_HW_SCHED_SCANNING, addr: &phy->state);
1882
1883 return mt76_mcu_send_msg(dev: phy->dev, MCU_CE_CMD(SCHED_SCAN_ENABLE),
1884 data: &req, len: sizeof(req), wait_resp: false);
1885}
1886EXPORT_SYMBOL_GPL(mt76_connac_mcu_sched_scan_enable);
1887
1888int mt76_connac_mcu_chip_config(struct mt76_dev *dev)
1889{
1890 struct mt76_connac_config req = {
1891 .resp_type = 0,
1892 };
1893
1894 memcpy(req.data, "assert", 7);
1895
1896 return mt76_mcu_send_msg(dev, MCU_CE_CMD(CHIP_CONFIG),
1897 data: &req, len: sizeof(req), wait_resp: false);
1898}
1899EXPORT_SYMBOL_GPL(mt76_connac_mcu_chip_config);
1900
1901int mt76_connac_mcu_set_deep_sleep(struct mt76_dev *dev, bool enable)
1902{
1903 struct mt76_connac_config req = {
1904 .resp_type = 0,
1905 };
1906
1907 snprintf(buf: req.data, size: sizeof(req.data), fmt: "KeepFullPwr %d", !enable);
1908
1909 return mt76_mcu_send_msg(dev, MCU_CE_CMD(CHIP_CONFIG),
1910 data: &req, len: sizeof(req), wait_resp: false);
1911}
1912EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_deep_sleep);
1913
1914int mt76_connac_sta_state_dp(struct mt76_dev *dev,
1915 enum ieee80211_sta_state old_state,
1916 enum ieee80211_sta_state new_state)
1917{
1918 if ((old_state == IEEE80211_STA_ASSOC &&
1919 new_state == IEEE80211_STA_AUTHORIZED) ||
1920 (old_state == IEEE80211_STA_NONE &&
1921 new_state == IEEE80211_STA_NOTEXIST))
1922 mt76_connac_mcu_set_deep_sleep(dev, true);
1923
1924 if ((old_state == IEEE80211_STA_NOTEXIST &&
1925 new_state == IEEE80211_STA_NONE) ||
1926 (old_state == IEEE80211_STA_AUTHORIZED &&
1927 new_state == IEEE80211_STA_ASSOC))
1928 mt76_connac_mcu_set_deep_sleep(dev, false);
1929
1930 return 0;
1931}
1932EXPORT_SYMBOL_GPL(mt76_connac_sta_state_dp);
1933
1934void mt76_connac_mcu_coredump_event(struct mt76_dev *dev, struct sk_buff *skb,
1935 struct mt76_connac_coredump *coredump)
1936{
1937 spin_lock_bh(lock: &dev->lock);
1938 __skb_queue_tail(list: &coredump->msg_list, newsk: skb);
1939 spin_unlock_bh(lock: &dev->lock);
1940
1941 coredump->last_activity = jiffies;
1942
1943 queue_delayed_work(wq: dev->wq, dwork: &coredump->work,
1944 MT76_CONNAC_COREDUMP_TIMEOUT);
1945}
1946EXPORT_SYMBOL_GPL(mt76_connac_mcu_coredump_event);
1947
1948static void
1949mt76_connac_mcu_build_sku(struct mt76_dev *dev, s8 *sku,
1950 struct mt76_power_limits *limits,
1951 enum nl80211_band band)
1952{
1953 int max_power = is_mt7921(dev) ? 127 : 63;
1954 int i, offset = sizeof(limits->cck);
1955
1956 memset(sku, max_power, MT_SKU_POWER_LIMIT);
1957
1958 if (band == NL80211_BAND_2GHZ) {
1959 /* cck */
1960 memcpy(sku, limits->cck, sizeof(limits->cck));
1961 }
1962
1963 /* ofdm */
1964 memcpy(&sku[offset], limits->ofdm, sizeof(limits->ofdm));
1965 offset += sizeof(limits->ofdm);
1966
1967 /* ht */
1968 for (i = 0; i < 2; i++) {
1969 memcpy(&sku[offset], limits->mcs[i], 8);
1970 offset += 8;
1971 }
1972 sku[offset++] = limits->mcs[0][0];
1973
1974 /* vht */
1975 for (i = 0; i < ARRAY_SIZE(limits->mcs); i++) {
1976 memcpy(&sku[offset], limits->mcs[i],
1977 ARRAY_SIZE(limits->mcs[i]));
1978 offset += 12;
1979 }
1980
1981 if (!is_mt7921(dev))
1982 return;
1983
1984 /* he */
1985 for (i = 0; i < ARRAY_SIZE(limits->ru); i++) {
1986 memcpy(&sku[offset], limits->ru[i], ARRAY_SIZE(limits->ru[i]));
1987 offset += ARRAY_SIZE(limits->ru[i]);
1988 }
1989}
1990
1991s8 mt76_connac_get_ch_power(struct mt76_phy *phy,
1992 struct ieee80211_channel *chan,
1993 s8 target_power)
1994{
1995 struct mt76_dev *dev = phy->dev;
1996 struct ieee80211_supported_band *sband;
1997 int i;
1998
1999 switch (chan->band) {
2000 case NL80211_BAND_2GHZ:
2001 sband = &phy->sband_2g.sband;
2002 break;
2003 case NL80211_BAND_5GHZ:
2004 sband = &phy->sband_5g.sband;
2005 break;
2006 case NL80211_BAND_6GHZ:
2007 sband = &phy->sband_6g.sband;
2008 break;
2009 default:
2010 return target_power;
2011 }
2012
2013 for (i = 0; i < sband->n_channels; i++) {
2014 struct ieee80211_channel *ch = &sband->channels[i];
2015
2016 if (ch->hw_value == chan->hw_value) {
2017 if (!(ch->flags & IEEE80211_CHAN_DISABLED)) {
2018 int power = 2 * ch->max_reg_power;
2019
2020 if (is_mt7663(dev) && (power > 63 || power < -64))
2021 power = 63;
2022 target_power = min_t(s8, power, target_power);
2023 }
2024 break;
2025 }
2026 }
2027
2028 return target_power;
2029}
2030EXPORT_SYMBOL_GPL(mt76_connac_get_ch_power);
2031
2032static int
2033mt76_connac_mcu_rate_txpower_band(struct mt76_phy *phy,
2034 enum nl80211_band band)
2035{
2036 struct mt76_dev *dev = phy->dev;
2037 int sku_len, batch_len = is_mt7921(dev) ? 8 : 16;
2038 static const u8 chan_list_2ghz[] = {
2039 1, 2, 3, 4, 5, 6, 7,
2040 8, 9, 10, 11, 12, 13, 14
2041 };
2042 static const u8 chan_list_5ghz[] = {
2043 36, 38, 40, 42, 44, 46, 48,
2044 50, 52, 54, 56, 58, 60, 62,
2045 64, 100, 102, 104, 106, 108, 110,
2046 112, 114, 116, 118, 120, 122, 124,
2047 126, 128, 132, 134, 136, 138, 140,
2048 142, 144, 149, 151, 153, 155, 157,
2049 159, 161, 165, 169, 173, 177
2050 };
2051 static const u8 chan_list_6ghz[] = {
2052 1, 3, 5, 7, 9, 11, 13,
2053 15, 17, 19, 21, 23, 25, 27,
2054 29, 33, 35, 37, 39, 41, 43,
2055 45, 47, 49, 51, 53, 55, 57,
2056 59, 61, 65, 67, 69, 71, 73,
2057 75, 77, 79, 81, 83, 85, 87,
2058 89, 91, 93, 97, 99, 101, 103,
2059 105, 107, 109, 111, 113, 115, 117,
2060 119, 121, 123, 125, 129, 131, 133,
2061 135, 137, 139, 141, 143, 145, 147,
2062 149, 151, 153, 155, 157, 161, 163,
2063 165, 167, 169, 171, 173, 175, 177,
2064 179, 181, 183, 185, 187, 189, 193,
2065 195, 197, 199, 201, 203, 205, 207,
2066 209, 211, 213, 215, 217, 219, 221,
2067 225, 227, 229, 233
2068 };
2069 int i, n_chan, batch_size, idx = 0, tx_power, last_ch, err = 0;
2070 struct mt76_connac_sku_tlv sku_tlbv;
2071 struct mt76_power_limits *limits;
2072 const u8 *ch_list;
2073
2074 limits = devm_kmalloc(dev: dev->dev, size: sizeof(*limits), GFP_KERNEL);
2075 if (!limits)
2076 return -ENOMEM;
2077
2078 sku_len = is_mt7921(dev) ? sizeof(sku_tlbv) : sizeof(sku_tlbv) - 92;
2079 tx_power = 2 * phy->hw->conf.power_level;
2080 if (!tx_power)
2081 tx_power = 127;
2082
2083 if (band == NL80211_BAND_2GHZ) {
2084 n_chan = ARRAY_SIZE(chan_list_2ghz);
2085 ch_list = chan_list_2ghz;
2086 } else if (band == NL80211_BAND_6GHZ) {
2087 n_chan = ARRAY_SIZE(chan_list_6ghz);
2088 ch_list = chan_list_6ghz;
2089 } else {
2090 n_chan = ARRAY_SIZE(chan_list_5ghz);
2091 ch_list = chan_list_5ghz;
2092 }
2093 batch_size = DIV_ROUND_UP(n_chan, batch_len);
2094
2095 if (phy->cap.has_6ghz)
2096 last_ch = chan_list_6ghz[ARRAY_SIZE(chan_list_6ghz) - 1];
2097 else if (phy->cap.has_5ghz)
2098 last_ch = chan_list_5ghz[ARRAY_SIZE(chan_list_5ghz) - 1];
2099 else
2100 last_ch = chan_list_2ghz[ARRAY_SIZE(chan_list_2ghz) - 1];
2101
2102 for (i = 0; i < batch_size; i++) {
2103 struct mt76_connac_tx_power_limit_tlv tx_power_tlv = {};
2104 int j, msg_len, num_ch;
2105 struct sk_buff *skb;
2106
2107 num_ch = i == batch_size - 1 ? n_chan - i * batch_len : batch_len;
2108 msg_len = sizeof(tx_power_tlv) + num_ch * sizeof(sku_tlbv);
2109 skb = mt76_mcu_msg_alloc(dev, NULL, data_len: msg_len);
2110 if (!skb) {
2111 err = -ENOMEM;
2112 goto out;
2113 }
2114
2115 skb_reserve(skb, len: sizeof(tx_power_tlv));
2116
2117 BUILD_BUG_ON(sizeof(dev->alpha2) > sizeof(tx_power_tlv.alpha2));
2118 memcpy(tx_power_tlv.alpha2, dev->alpha2, sizeof(dev->alpha2));
2119 tx_power_tlv.n_chan = num_ch;
2120
2121 switch (band) {
2122 case NL80211_BAND_2GHZ:
2123 tx_power_tlv.band = 1;
2124 break;
2125 case NL80211_BAND_6GHZ:
2126 tx_power_tlv.band = 3;
2127 break;
2128 default:
2129 tx_power_tlv.band = 2;
2130 break;
2131 }
2132
2133 for (j = 0; j < num_ch; j++, idx++) {
2134 struct ieee80211_channel chan = {
2135 .hw_value = ch_list[idx],
2136 .band = band,
2137 };
2138 s8 reg_power, sar_power;
2139
2140 reg_power = mt76_connac_get_ch_power(phy, &chan,
2141 tx_power);
2142 sar_power = mt76_get_sar_power(phy, chan: &chan, power: reg_power);
2143
2144 mt76_get_rate_power_limits(phy, chan: &chan, dest: limits,
2145 target_power: sar_power);
2146
2147 tx_power_tlv.last_msg = ch_list[idx] == last_ch;
2148 sku_tlbv.channel = ch_list[idx];
2149
2150 mt76_connac_mcu_build_sku(dev, sku: sku_tlbv.pwr_limit,
2151 limits, band);
2152 skb_put_data(skb, data: &sku_tlbv, len: sku_len);
2153 }
2154 __skb_push(skb, len: sizeof(tx_power_tlv));
2155 memcpy(skb->data, &tx_power_tlv, sizeof(tx_power_tlv));
2156
2157 err = mt76_mcu_skb_send_msg(dev, skb,
2158 MCU_CE_CMD(SET_RATE_TX_POWER),
2159 wait_resp: false);
2160 if (err < 0)
2161 goto out;
2162 }
2163
2164out:
2165 devm_kfree(dev: dev->dev, p: limits);
2166 return err;
2167}
2168
2169int mt76_connac_mcu_set_rate_txpower(struct mt76_phy *phy)
2170{
2171 int err;
2172
2173 if (phy->cap.has_2ghz) {
2174 err = mt76_connac_mcu_rate_txpower_band(phy,
2175 band: NL80211_BAND_2GHZ);
2176 if (err < 0)
2177 return err;
2178 }
2179 if (phy->cap.has_5ghz) {
2180 err = mt76_connac_mcu_rate_txpower_band(phy,
2181 band: NL80211_BAND_5GHZ);
2182 if (err < 0)
2183 return err;
2184 }
2185 if (phy->cap.has_6ghz) {
2186 err = mt76_connac_mcu_rate_txpower_band(phy,
2187 band: NL80211_BAND_6GHZ);
2188 if (err < 0)
2189 return err;
2190 }
2191
2192 return 0;
2193}
2194EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_rate_txpower);
2195
2196int mt76_connac_mcu_update_arp_filter(struct mt76_dev *dev,
2197 struct mt76_vif *vif,
2198 struct ieee80211_bss_conf *info)
2199{
2200 struct ieee80211_vif *mvif = container_of(info, struct ieee80211_vif,
2201 bss_conf);
2202 struct sk_buff *skb;
2203 int i, len = min_t(int, mvif->cfg.arp_addr_cnt,
2204 IEEE80211_BSS_ARP_ADDR_LIST_LEN);
2205 struct {
2206 struct {
2207 u8 bss_idx;
2208 u8 pad[3];
2209 } __packed hdr;
2210 struct mt76_connac_arpns_tlv arp;
2211 } req_hdr = {
2212 .hdr = {
2213 .bss_idx = vif->idx,
2214 },
2215 .arp = {
2216 .tag = cpu_to_le16(UNI_OFFLOAD_OFFLOAD_ARP),
2217 .len = cpu_to_le16(sizeof(struct mt76_connac_arpns_tlv)),
2218 .ips_num = len,
2219 .mode = 2, /* update */
2220 .option = 1,
2221 },
2222 };
2223
2224 skb = mt76_mcu_msg_alloc(dev, NULL,
2225 data_len: sizeof(req_hdr) + len * sizeof(__be32));
2226 if (!skb)
2227 return -ENOMEM;
2228
2229 skb_put_data(skb, data: &req_hdr, len: sizeof(req_hdr));
2230 for (i = 0; i < len; i++)
2231 skb_put_data(skb, data: &mvif->cfg.arp_addr_list[i], len: sizeof(__be32));
2232
2233 return mt76_mcu_skb_send_msg(dev, skb, MCU_UNI_CMD(OFFLOAD), wait_resp: true);
2234}
2235EXPORT_SYMBOL_GPL(mt76_connac_mcu_update_arp_filter);
2236
2237int mt76_connac_mcu_set_p2p_oppps(struct ieee80211_hw *hw,
2238 struct ieee80211_vif *vif)
2239{
2240 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2241 int ct_window = vif->bss_conf.p2p_noa_attr.oppps_ctwindow;
2242 struct mt76_phy *phy = hw->priv;
2243 struct {
2244 __le32 ct_win;
2245 u8 bss_idx;
2246 u8 rsv[3];
2247 } __packed req = {
2248 .ct_win = cpu_to_le32(ct_window),
2249 .bss_idx = mvif->idx,
2250 };
2251
2252 return mt76_mcu_send_msg(dev: phy->dev, MCU_CE_CMD(SET_P2P_OPPPS),
2253 data: &req, len: sizeof(req), wait_resp: false);
2254}
2255EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_p2p_oppps);
2256
2257#ifdef CONFIG_PM
2258
2259const struct wiphy_wowlan_support mt76_connac_wowlan_support = {
2260 .flags = WIPHY_WOWLAN_MAGIC_PKT | WIPHY_WOWLAN_DISCONNECT |
2261 WIPHY_WOWLAN_SUPPORTS_GTK_REKEY | WIPHY_WOWLAN_NET_DETECT,
2262 .n_patterns = 1,
2263 .pattern_min_len = 1,
2264 .pattern_max_len = MT76_CONNAC_WOW_PATTEN_MAX_LEN,
2265 .max_nd_match_sets = 10,
2266};
2267EXPORT_SYMBOL_GPL(mt76_connac_wowlan_support);
2268
2269static void
2270mt76_connac_mcu_key_iter(struct ieee80211_hw *hw,
2271 struct ieee80211_vif *vif,
2272 struct ieee80211_sta *sta,
2273 struct ieee80211_key_conf *key,
2274 void *data)
2275{
2276 struct mt76_connac_gtk_rekey_tlv *gtk_tlv = data;
2277 u32 cipher;
2278
2279 if (key->cipher != WLAN_CIPHER_SUITE_AES_CMAC &&
2280 key->cipher != WLAN_CIPHER_SUITE_CCMP &&
2281 key->cipher != WLAN_CIPHER_SUITE_TKIP)
2282 return;
2283
2284 if (key->cipher == WLAN_CIPHER_SUITE_TKIP)
2285 cipher = BIT(3);
2286 else
2287 cipher = BIT(4);
2288
2289 /* we are assuming here to have a single pairwise key */
2290 if (key->flags & IEEE80211_KEY_FLAG_PAIRWISE) {
2291 if (key->cipher == WLAN_CIPHER_SUITE_TKIP)
2292 gtk_tlv->proto = cpu_to_le32(NL80211_WPA_VERSION_1);
2293 else
2294 gtk_tlv->proto = cpu_to_le32(NL80211_WPA_VERSION_2);
2295
2296 gtk_tlv->pairwise_cipher = cpu_to_le32(cipher);
2297 gtk_tlv->keyid = key->keyidx;
2298 } else {
2299 gtk_tlv->group_cipher = cpu_to_le32(cipher);
2300 }
2301}
2302
2303int mt76_connac_mcu_update_gtk_rekey(struct ieee80211_hw *hw,
2304 struct ieee80211_vif *vif,
2305 struct cfg80211_gtk_rekey_data *key)
2306{
2307 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2308 struct mt76_connac_gtk_rekey_tlv *gtk_tlv;
2309 struct mt76_phy *phy = hw->priv;
2310 struct sk_buff *skb;
2311 struct {
2312 u8 bss_idx;
2313 u8 pad[3];
2314 } __packed hdr = {
2315 .bss_idx = mvif->idx,
2316 };
2317
2318 skb = mt76_mcu_msg_alloc(dev: phy->dev, NULL,
2319 data_len: sizeof(hdr) + sizeof(*gtk_tlv));
2320 if (!skb)
2321 return -ENOMEM;
2322
2323 skb_put_data(skb, data: &hdr, len: sizeof(hdr));
2324 gtk_tlv = (struct mt76_connac_gtk_rekey_tlv *)skb_put(skb,
2325 len: sizeof(*gtk_tlv));
2326 gtk_tlv->tag = cpu_to_le16(UNI_OFFLOAD_OFFLOAD_GTK_REKEY);
2327 gtk_tlv->len = cpu_to_le16(sizeof(*gtk_tlv));
2328 gtk_tlv->rekey_mode = 2;
2329 gtk_tlv->option = 1;
2330
2331 rcu_read_lock();
2332 ieee80211_iter_keys_rcu(hw, vif, iter: mt76_connac_mcu_key_iter, iter_data: gtk_tlv);
2333 rcu_read_unlock();
2334
2335 memcpy(gtk_tlv->kek, key->kek, NL80211_KEK_LEN);
2336 memcpy(gtk_tlv->kck, key->kck, NL80211_KCK_LEN);
2337 memcpy(gtk_tlv->replay_ctr, key->replay_ctr, NL80211_REPLAY_CTR_LEN);
2338
2339 return mt76_mcu_skb_send_msg(dev: phy->dev, skb,
2340 MCU_UNI_CMD(OFFLOAD), wait_resp: true);
2341}
2342EXPORT_SYMBOL_GPL(mt76_connac_mcu_update_gtk_rekey);
2343
2344static int
2345mt76_connac_mcu_set_arp_filter(struct mt76_dev *dev, struct ieee80211_vif *vif,
2346 bool suspend)
2347{
2348 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2349 struct {
2350 struct {
2351 u8 bss_idx;
2352 u8 pad[3];
2353 } __packed hdr;
2354 struct mt76_connac_arpns_tlv arpns;
2355 } req = {
2356 .hdr = {
2357 .bss_idx = mvif->idx,
2358 },
2359 .arpns = {
2360 .tag = cpu_to_le16(UNI_OFFLOAD_OFFLOAD_ARP),
2361 .len = cpu_to_le16(sizeof(struct mt76_connac_arpns_tlv)),
2362 .mode = suspend,
2363 },
2364 };
2365
2366 return mt76_mcu_send_msg(dev, MCU_UNI_CMD(OFFLOAD), data: &req,
2367 len: sizeof(req), wait_resp: true);
2368}
2369
2370int
2371mt76_connac_mcu_set_gtk_rekey(struct mt76_dev *dev, struct ieee80211_vif *vif,
2372 bool suspend)
2373{
2374 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2375 struct {
2376 struct {
2377 u8 bss_idx;
2378 u8 pad[3];
2379 } __packed hdr;
2380 struct mt76_connac_gtk_rekey_tlv gtk_tlv;
2381 } __packed req = {
2382 .hdr = {
2383 .bss_idx = mvif->idx,
2384 },
2385 .gtk_tlv = {
2386 .tag = cpu_to_le16(UNI_OFFLOAD_OFFLOAD_GTK_REKEY),
2387 .len = cpu_to_le16(sizeof(struct mt76_connac_gtk_rekey_tlv)),
2388 .rekey_mode = !suspend,
2389 },
2390 };
2391
2392 return mt76_mcu_send_msg(dev, MCU_UNI_CMD(OFFLOAD), data: &req,
2393 len: sizeof(req), wait_resp: true);
2394}
2395EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_gtk_rekey);
2396
2397int
2398mt76_connac_mcu_set_suspend_mode(struct mt76_dev *dev,
2399 struct ieee80211_vif *vif,
2400 bool enable, u8 mdtim,
2401 bool wow_suspend)
2402{
2403 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2404 struct {
2405 struct {
2406 u8 bss_idx;
2407 u8 pad[3];
2408 } __packed hdr;
2409 struct mt76_connac_suspend_tlv suspend_tlv;
2410 } req = {
2411 .hdr = {
2412 .bss_idx = mvif->idx,
2413 },
2414 .suspend_tlv = {
2415 .tag = cpu_to_le16(UNI_SUSPEND_MODE_SETTING),
2416 .len = cpu_to_le16(sizeof(struct mt76_connac_suspend_tlv)),
2417 .enable = enable,
2418 .mdtim = mdtim,
2419 .wow_suspend = wow_suspend,
2420 },
2421 };
2422
2423 return mt76_mcu_send_msg(dev, MCU_UNI_CMD(SUSPEND), data: &req,
2424 len: sizeof(req), wait_resp: true);
2425}
2426EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_suspend_mode);
2427
2428static int
2429mt76_connac_mcu_set_wow_pattern(struct mt76_dev *dev,
2430 struct ieee80211_vif *vif,
2431 u8 index, bool enable,
2432 struct cfg80211_pkt_pattern *pattern)
2433{
2434 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2435 struct mt76_connac_wow_pattern_tlv *ptlv;
2436 struct sk_buff *skb;
2437 struct req_hdr {
2438 u8 bss_idx;
2439 u8 pad[3];
2440 } __packed hdr = {
2441 .bss_idx = mvif->idx,
2442 };
2443
2444 skb = mt76_mcu_msg_alloc(dev, NULL, data_len: sizeof(hdr) + sizeof(*ptlv));
2445 if (!skb)
2446 return -ENOMEM;
2447
2448 skb_put_data(skb, data: &hdr, len: sizeof(hdr));
2449 ptlv = (struct mt76_connac_wow_pattern_tlv *)skb_put(skb, len: sizeof(*ptlv));
2450 ptlv->tag = cpu_to_le16(UNI_SUSPEND_WOW_PATTERN);
2451 ptlv->len = cpu_to_le16(sizeof(*ptlv));
2452 ptlv->data_len = pattern->pattern_len;
2453 ptlv->enable = enable;
2454 ptlv->index = index;
2455
2456 memcpy(ptlv->pattern, pattern->pattern, pattern->pattern_len);
2457 memcpy(ptlv->mask, pattern->mask, DIV_ROUND_UP(pattern->pattern_len, 8));
2458
2459 return mt76_mcu_skb_send_msg(dev, skb, MCU_UNI_CMD(SUSPEND), wait_resp: true);
2460}
2461
2462int
2463mt76_connac_mcu_set_wow_ctrl(struct mt76_phy *phy, struct ieee80211_vif *vif,
2464 bool suspend, struct cfg80211_wowlan *wowlan)
2465{
2466 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2467 struct mt76_dev *dev = phy->dev;
2468 struct {
2469 struct {
2470 u8 bss_idx;
2471 u8 pad[3];
2472 } __packed hdr;
2473 struct mt76_connac_wow_ctrl_tlv wow_ctrl_tlv;
2474 struct mt76_connac_wow_gpio_param_tlv gpio_tlv;
2475 } req = {
2476 .hdr = {
2477 .bss_idx = mvif->idx,
2478 },
2479 .wow_ctrl_tlv = {
2480 .tag = cpu_to_le16(UNI_SUSPEND_WOW_CTRL),
2481 .len = cpu_to_le16(sizeof(struct mt76_connac_wow_ctrl_tlv)),
2482 .cmd = suspend ? 1 : 2,
2483 },
2484 .gpio_tlv = {
2485 .tag = cpu_to_le16(UNI_SUSPEND_WOW_GPIO_PARAM),
2486 .len = cpu_to_le16(sizeof(struct mt76_connac_wow_gpio_param_tlv)),
2487 .gpio_pin = 0xff, /* follow fw about GPIO pin */
2488 },
2489 };
2490
2491 if (wowlan->magic_pkt)
2492 req.wow_ctrl_tlv.trigger |= UNI_WOW_DETECT_TYPE_MAGIC;
2493 if (wowlan->disconnect)
2494 req.wow_ctrl_tlv.trigger |= (UNI_WOW_DETECT_TYPE_DISCONNECT |
2495 UNI_WOW_DETECT_TYPE_BCN_LOST);
2496 if (wowlan->nd_config) {
2497 mt76_connac_mcu_sched_scan_req(phy, vif, wowlan->nd_config);
2498 req.wow_ctrl_tlv.trigger |= UNI_WOW_DETECT_TYPE_SCH_SCAN_HIT;
2499 mt76_connac_mcu_sched_scan_enable(phy, vif, suspend);
2500 }
2501 if (wowlan->n_patterns)
2502 req.wow_ctrl_tlv.trigger |= UNI_WOW_DETECT_TYPE_BITMAP;
2503
2504 if (mt76_is_mmio(dev))
2505 req.wow_ctrl_tlv.wakeup_hif = WOW_PCIE;
2506 else if (mt76_is_usb(dev))
2507 req.wow_ctrl_tlv.wakeup_hif = WOW_USB;
2508 else if (mt76_is_sdio(dev))
2509 req.wow_ctrl_tlv.wakeup_hif = WOW_GPIO;
2510
2511 return mt76_mcu_send_msg(dev, MCU_UNI_CMD(SUSPEND), data: &req,
2512 len: sizeof(req), wait_resp: true);
2513}
2514EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_wow_ctrl);
2515
2516int mt76_connac_mcu_set_hif_suspend(struct mt76_dev *dev, bool suspend)
2517{
2518 struct {
2519 struct {
2520 u8 hif_type; /* 0x0: HIF_SDIO
2521 * 0x1: HIF_USB
2522 * 0x2: HIF_PCIE
2523 */
2524 u8 pad[3];
2525 } __packed hdr;
2526 struct hif_suspend_tlv {
2527 __le16 tag;
2528 __le16 len;
2529 u8 suspend;
2530 } __packed hif_suspend;
2531 } req = {
2532 .hif_suspend = {
2533 .tag = cpu_to_le16(0), /* 0: UNI_HIF_CTRL_BASIC */
2534 .len = cpu_to_le16(sizeof(struct hif_suspend_tlv)),
2535 .suspend = suspend,
2536 },
2537 };
2538
2539 if (mt76_is_mmio(dev))
2540 req.hdr.hif_type = 2;
2541 else if (mt76_is_usb(dev))
2542 req.hdr.hif_type = 1;
2543 else if (mt76_is_sdio(dev))
2544 req.hdr.hif_type = 0;
2545
2546 return mt76_mcu_send_msg(dev, MCU_UNI_CMD(HIF_CTRL), data: &req,
2547 len: sizeof(req), wait_resp: true);
2548}
2549EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_hif_suspend);
2550
2551void mt76_connac_mcu_set_suspend_iter(void *priv, u8 *mac,
2552 struct ieee80211_vif *vif)
2553{
2554 struct mt76_phy *phy = priv;
2555 bool suspend = !test_bit(MT76_STATE_RUNNING, &phy->state);
2556 struct ieee80211_hw *hw = phy->hw;
2557 struct cfg80211_wowlan *wowlan = hw->wiphy->wowlan_config;
2558 int i;
2559
2560 mt76_connac_mcu_set_gtk_rekey(phy->dev, vif, suspend);
2561 mt76_connac_mcu_set_arp_filter(dev: phy->dev, vif, suspend);
2562
2563 mt76_connac_mcu_set_suspend_mode(phy->dev, vif, suspend, 1, true);
2564
2565 for (i = 0; i < wowlan->n_patterns; i++)
2566 mt76_connac_mcu_set_wow_pattern(dev: phy->dev, vif, index: i, enable: suspend,
2567 pattern: &wowlan->patterns[i]);
2568 mt76_connac_mcu_set_wow_ctrl(phy, vif, suspend, wowlan);
2569}
2570EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_suspend_iter);
2571#endif /* CONFIG_PM */
2572
2573u32 mt76_connac_mcu_reg_rr(struct mt76_dev *dev, u32 offset)
2574{
2575 struct {
2576 __le32 addr;
2577 __le32 val;
2578 } __packed req = {
2579 .addr = cpu_to_le32(offset),
2580 };
2581
2582 return mt76_mcu_send_msg(dev, MCU_CE_QUERY(REG_READ), data: &req,
2583 len: sizeof(req), wait_resp: true);
2584}
2585EXPORT_SYMBOL_GPL(mt76_connac_mcu_reg_rr);
2586
2587void mt76_connac_mcu_reg_wr(struct mt76_dev *dev, u32 offset, u32 val)
2588{
2589 struct {
2590 __le32 addr;
2591 __le32 val;
2592 } __packed req = {
2593 .addr = cpu_to_le32(offset),
2594 .val = cpu_to_le32(val),
2595 };
2596
2597 mt76_mcu_send_msg(dev, MCU_CE_CMD(REG_WRITE), data: &req,
2598 len: sizeof(req), wait_resp: false);
2599}
2600EXPORT_SYMBOL_GPL(mt76_connac_mcu_reg_wr);
2601
2602static int
2603mt76_connac_mcu_sta_key_tlv(struct mt76_connac_sta_key_conf *sta_key_conf,
2604 struct sk_buff *skb,
2605 struct ieee80211_key_conf *key,
2606 enum set_key_cmd cmd)
2607{
2608 struct sta_rec_sec *sec;
2609 u32 len = sizeof(*sec);
2610 struct tlv *tlv;
2611
2612 tlv = mt76_connac_mcu_add_tlv(skb, tag: STA_REC_KEY_V2, len: sizeof(*sec));
2613 sec = (struct sta_rec_sec *)tlv;
2614 sec->add = cmd;
2615
2616 if (cmd == SET_KEY) {
2617 struct sec_key *sec_key;
2618 u8 cipher;
2619
2620 cipher = mt76_connac_mcu_get_cipher(cipher: key->cipher);
2621 if (cipher == MCU_CIPHER_NONE)
2622 return -EOPNOTSUPP;
2623
2624 sec_key = &sec->key[0];
2625 sec_key->cipher_len = sizeof(*sec_key);
2626
2627 if (cipher == MCU_CIPHER_BIP_CMAC_128) {
2628 sec_key->cipher_id = MCU_CIPHER_AES_CCMP;
2629 sec_key->key_id = sta_key_conf->keyidx;
2630 sec_key->key_len = 16;
2631 memcpy(sec_key->key, sta_key_conf->key, 16);
2632
2633 sec_key = &sec->key[1];
2634 sec_key->cipher_id = MCU_CIPHER_BIP_CMAC_128;
2635 sec_key->cipher_len = sizeof(*sec_key);
2636 sec_key->key_len = 16;
2637 memcpy(sec_key->key, key->key, 16);
2638 sec->n_cipher = 2;
2639 } else {
2640 sec_key->cipher_id = cipher;
2641 sec_key->key_id = key->keyidx;
2642 sec_key->key_len = key->keylen;
2643 memcpy(sec_key->key, key->key, key->keylen);
2644
2645 if (cipher == MCU_CIPHER_TKIP) {
2646 /* Rx/Tx MIC keys are swapped */
2647 memcpy(sec_key->key + 16, key->key + 24, 8);
2648 memcpy(sec_key->key + 24, key->key + 16, 8);
2649 }
2650
2651 /* store key_conf for BIP batch update */
2652 if (cipher == MCU_CIPHER_AES_CCMP) {
2653 memcpy(sta_key_conf->key, key->key, key->keylen);
2654 sta_key_conf->keyidx = key->keyidx;
2655 }
2656
2657 len -= sizeof(*sec_key);
2658 sec->n_cipher = 1;
2659 }
2660 } else {
2661 len -= sizeof(sec->key);
2662 sec->n_cipher = 0;
2663 }
2664 sec->len = cpu_to_le16(len);
2665
2666 return 0;
2667}
2668
2669int mt76_connac_mcu_add_key(struct mt76_dev *dev, struct ieee80211_vif *vif,
2670 struct mt76_connac_sta_key_conf *sta_key_conf,
2671 struct ieee80211_key_conf *key, int mcu_cmd,
2672 struct mt76_wcid *wcid, enum set_key_cmd cmd)
2673{
2674 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2675 struct sk_buff *skb;
2676 int ret;
2677
2678 skb = mt76_connac_mcu_alloc_sta_req(dev, mvif, wcid);
2679 if (IS_ERR(ptr: skb))
2680 return PTR_ERR(ptr: skb);
2681
2682 ret = mt76_connac_mcu_sta_key_tlv(sta_key_conf, skb, key, cmd);
2683 if (ret)
2684 return ret;
2685
2686 ret = mt76_connac_mcu_sta_wed_update(dev, skb);
2687 if (ret)
2688 return ret;
2689
2690 return mt76_mcu_skb_send_msg(dev, skb, cmd: mcu_cmd, wait_resp: true);
2691}
2692EXPORT_SYMBOL_GPL(mt76_connac_mcu_add_key);
2693
2694/* SIFS 20us + 512 byte beacon transmitted by 1Mbps (3906us) */
2695#define BCN_TX_ESTIMATE_TIME (4096 + 20)
2696void mt76_connac_mcu_bss_ext_tlv(struct sk_buff *skb, struct mt76_vif *mvif)
2697{
2698 struct bss_info_ext_bss *ext;
2699 int ext_bss_idx, tsf_offset;
2700 struct tlv *tlv;
2701
2702 ext_bss_idx = mvif->omac_idx - EXT_BSSID_START;
2703 if (ext_bss_idx < 0)
2704 return;
2705
2706 tlv = mt76_connac_mcu_add_tlv(skb, tag: BSS_INFO_EXT_BSS, len: sizeof(*ext));
2707
2708 ext = (struct bss_info_ext_bss *)tlv;
2709 tsf_offset = ext_bss_idx * BCN_TX_ESTIMATE_TIME;
2710 ext->mbss_tsf_offset = cpu_to_le32(tsf_offset);
2711}
2712EXPORT_SYMBOL_GPL(mt76_connac_mcu_bss_ext_tlv);
2713
2714int mt76_connac_mcu_bss_basic_tlv(struct sk_buff *skb,
2715 struct ieee80211_vif *vif,
2716 struct ieee80211_sta *sta,
2717 struct mt76_phy *phy, u16 wlan_idx,
2718 bool enable)
2719{
2720 struct mt76_vif *mvif = (struct mt76_vif *)vif->drv_priv;
2721 u32 type = vif->p2p ? NETWORK_P2P : NETWORK_INFRA;
2722 struct bss_info_basic *bss;
2723 struct tlv *tlv;
2724
2725 tlv = mt76_connac_mcu_add_tlv(skb, tag: BSS_INFO_BASIC, len: sizeof(*bss));
2726 bss = (struct bss_info_basic *)tlv;
2727
2728 switch (vif->type) {
2729 case NL80211_IFTYPE_MESH_POINT:
2730 case NL80211_IFTYPE_MONITOR:
2731 break;
2732 case NL80211_IFTYPE_AP:
2733 if (ieee80211_hw_check(phy->hw, SUPPORTS_MULTI_BSSID)) {
2734 u8 bssid_id = vif->bss_conf.bssid_indicator;
2735 struct wiphy *wiphy = phy->hw->wiphy;
2736
2737 if (bssid_id > ilog2(wiphy->mbssid_max_interfaces))
2738 return -EINVAL;
2739
2740 bss->non_tx_bssid = vif->bss_conf.bssid_index;
2741 bss->max_bssid = bssid_id;
2742 }
2743 break;
2744 case NL80211_IFTYPE_STATION:
2745 if (enable) {
2746 rcu_read_lock();
2747 if (!sta)
2748 sta = ieee80211_find_sta(vif,
2749 addr: vif->bss_conf.bssid);
2750 /* TODO: enable BSS_INFO_UAPSD & BSS_INFO_PM */
2751 if (sta) {
2752 struct mt76_wcid *wcid;
2753
2754 wcid = (struct mt76_wcid *)sta->drv_priv;
2755 wlan_idx = wcid->idx;
2756 }
2757 rcu_read_unlock();
2758 }
2759 break;
2760 case NL80211_IFTYPE_ADHOC:
2761 type = NETWORK_IBSS;
2762 break;
2763 default:
2764 WARN_ON(1);
2765 break;
2766 }
2767
2768 bss->network_type = cpu_to_le32(type);
2769 bss->bmc_wcid_lo = to_wcid_lo(wlan_idx);
2770 bss->bmc_wcid_hi = to_wcid_hi(wlan_idx);
2771 bss->wmm_idx = mvif->wmm_idx;
2772 bss->active = enable;
2773 bss->cipher = mvif->cipher;
2774
2775 if (vif->type != NL80211_IFTYPE_MONITOR) {
2776 struct cfg80211_chan_def *chandef = &phy->chandef;
2777
2778 memcpy(bss->bssid, vif->bss_conf.bssid, ETH_ALEN);
2779 bss->bcn_interval = cpu_to_le16(vif->bss_conf.beacon_int);
2780 bss->dtim_period = vif->bss_conf.dtim_period;
2781 bss->phy_mode = mt76_connac_get_phy_mode(phy, vif,
2782 chandef->chan->band, NULL);
2783 } else {
2784 memcpy(bss->bssid, phy->macaddr, ETH_ALEN);
2785 }
2786
2787 return 0;
2788}
2789EXPORT_SYMBOL_GPL(mt76_connac_mcu_bss_basic_tlv);
2790
2791#define ENTER_PM_STATE 1
2792#define EXIT_PM_STATE 2
2793int mt76_connac_mcu_set_pm(struct mt76_dev *dev, int band, int enter)
2794{
2795 struct {
2796 u8 pm_number;
2797 u8 pm_state;
2798 u8 bssid[ETH_ALEN];
2799 u8 dtim_period;
2800 u8 wlan_idx_lo;
2801 __le16 bcn_interval;
2802 __le32 aid;
2803 __le32 rx_filter;
2804 u8 band_idx;
2805 u8 wlan_idx_hi;
2806 u8 rsv[2];
2807 __le32 feature;
2808 u8 omac_idx;
2809 u8 wmm_idx;
2810 u8 bcn_loss_cnt;
2811 u8 bcn_sp_duration;
2812 } __packed req = {
2813 .pm_number = 5,
2814 .pm_state = enter ? ENTER_PM_STATE : EXIT_PM_STATE,
2815 .band_idx = band,
2816 };
2817
2818 return mt76_mcu_send_msg(dev, MCU_EXT_CMD(PM_STATE_CTRL), data: &req,
2819 len: sizeof(req), wait_resp: true);
2820}
2821EXPORT_SYMBOL_GPL(mt76_connac_mcu_set_pm);
2822
2823int mt76_connac_mcu_restart(struct mt76_dev *dev)
2824{
2825 struct {
2826 u8 power_mode;
2827 u8 rsv[3];
2828 } req = {
2829 .power_mode = 1,
2830 };
2831
2832 return mt76_mcu_send_msg(dev, MCU_CMD(NIC_POWER_CTRL), data: &req,
2833 len: sizeof(req), wait_resp: false);
2834}
2835EXPORT_SYMBOL_GPL(mt76_connac_mcu_restart);
2836
2837int mt76_connac_mcu_rdd_cmd(struct mt76_dev *dev, int cmd, u8 index,
2838 u8 rx_sel, u8 val)
2839{
2840 struct {
2841 u8 ctrl;
2842 u8 rdd_idx;
2843 u8 rdd_rx_sel;
2844 u8 val;
2845 u8 rsv[4];
2846 } __packed req = {
2847 .ctrl = cmd,
2848 .rdd_idx = index,
2849 .rdd_rx_sel = rx_sel,
2850 .val = val,
2851 };
2852
2853 return mt76_mcu_send_msg(dev, MCU_EXT_CMD(SET_RDD_CTRL), data: &req,
2854 len: sizeof(req), wait_resp: true);
2855}
2856EXPORT_SYMBOL_GPL(mt76_connac_mcu_rdd_cmd);
2857
2858static int
2859mt76_connac_mcu_send_ram_firmware(struct mt76_dev *dev,
2860 const struct mt76_connac2_fw_trailer *hdr,
2861 const u8 *data, bool is_wa)
2862{
2863 int i, offset = 0, max_len = mt76_is_sdio(dev) ? 2048 : 4096;
2864 u32 override = 0, option = 0;
2865
2866 for (i = 0; i < hdr->n_region; i++) {
2867 const struct mt76_connac2_fw_region *region;
2868 u32 len, addr, mode;
2869 int err;
2870
2871 region = (const void *)((const u8 *)hdr -
2872 (hdr->n_region - i) * sizeof(*region));
2873 mode = mt76_connac_mcu_gen_dl_mode(dev, feature_set: region->feature_set,
2874 is_wa);
2875 len = le32_to_cpu(region->len);
2876 addr = le32_to_cpu(region->addr);
2877
2878 if (region->feature_set & FW_FEATURE_NON_DL)
2879 goto next;
2880
2881 if (region->feature_set & FW_FEATURE_OVERRIDE_ADDR)
2882 override = addr;
2883
2884 err = mt76_connac_mcu_init_download(dev, addr, len, mode);
2885 if (err) {
2886 dev_err(dev->dev, "Download request failed\n");
2887 return err;
2888 }
2889
2890 err = __mt76_mcu_send_firmware(dev, MCU_CMD(FW_SCATTER),
2891 data: data + offset, len, max_len);
2892 if (err) {
2893 dev_err(dev->dev, "Failed to send firmware.\n");
2894 return err;
2895 }
2896
2897next:
2898 offset += len;
2899 }
2900
2901 if (override)
2902 option |= FW_START_OVERRIDE;
2903 if (is_wa)
2904 option |= FW_START_WORKING_PDA_CR4;
2905
2906 return mt76_connac_mcu_start_firmware(dev, override, option);
2907}
2908
2909int mt76_connac2_load_ram(struct mt76_dev *dev, const char *fw_wm,
2910 const char *fw_wa)
2911{
2912 const struct mt76_connac2_fw_trailer *hdr;
2913 const struct firmware *fw;
2914 int ret;
2915
2916 ret = request_firmware(fw: &fw, name: fw_wm, device: dev->dev);
2917 if (ret)
2918 return ret;
2919
2920 if (!fw || !fw->data || fw->size < sizeof(*hdr)) {
2921 dev_err(dev->dev, "Invalid firmware\n");
2922 ret = -EINVAL;
2923 goto out;
2924 }
2925
2926 hdr = (const void *)(fw->data + fw->size - sizeof(*hdr));
2927 dev_info(dev->dev, "WM Firmware Version: %.10s, Build Time: %.15s\n",
2928 hdr->fw_ver, hdr->build_date);
2929
2930 ret = mt76_connac_mcu_send_ram_firmware(dev, hdr, data: fw->data, is_wa: false);
2931 if (ret) {
2932 dev_err(dev->dev, "Failed to start WM firmware\n");
2933 goto out;
2934 }
2935
2936 snprintf(buf: dev->hw->wiphy->fw_version,
2937 size: sizeof(dev->hw->wiphy->fw_version),
2938 fmt: "%.10s-%.15s", hdr->fw_ver, hdr->build_date);
2939
2940 release_firmware(fw);
2941
2942 if (!fw_wa)
2943 return 0;
2944
2945 ret = request_firmware(fw: &fw, name: fw_wa, device: dev->dev);
2946 if (ret)
2947 return ret;
2948
2949 if (!fw || !fw->data || fw->size < sizeof(*hdr)) {
2950 dev_err(dev->dev, "Invalid firmware\n");
2951 ret = -EINVAL;
2952 goto out;
2953 }
2954
2955 hdr = (const void *)(fw->data + fw->size - sizeof(*hdr));
2956 dev_info(dev->dev, "WA Firmware Version: %.10s, Build Time: %.15s\n",
2957 hdr->fw_ver, hdr->build_date);
2958
2959 ret = mt76_connac_mcu_send_ram_firmware(dev, hdr, data: fw->data, is_wa: true);
2960 if (ret) {
2961 dev_err(dev->dev, "Failed to start WA firmware\n");
2962 goto out;
2963 }
2964
2965 snprintf(buf: dev->hw->wiphy->fw_version,
2966 size: sizeof(dev->hw->wiphy->fw_version),
2967 fmt: "%.10s-%.15s", hdr->fw_ver, hdr->build_date);
2968
2969out:
2970 release_firmware(fw);
2971
2972 return ret;
2973}
2974EXPORT_SYMBOL_GPL(mt76_connac2_load_ram);
2975
2976static u32 mt76_connac2_get_data_mode(struct mt76_dev *dev, u32 info)
2977{
2978 u32 mode = DL_MODE_NEED_RSP;
2979
2980 if ((!is_mt7921(dev) && !is_mt7925(dev)) || info == PATCH_SEC_NOT_SUPPORT)
2981 return mode;
2982
2983 switch (FIELD_GET(PATCH_SEC_ENC_TYPE_MASK, info)) {
2984 case PATCH_SEC_ENC_TYPE_PLAIN:
2985 break;
2986 case PATCH_SEC_ENC_TYPE_AES:
2987 mode |= DL_MODE_ENCRYPT;
2988 mode |= FIELD_PREP(DL_MODE_KEY_IDX,
2989 (info & PATCH_SEC_ENC_AES_KEY_MASK)) & DL_MODE_KEY_IDX;
2990 mode |= DL_MODE_RESET_SEC_IV;
2991 break;
2992 case PATCH_SEC_ENC_TYPE_SCRAMBLE:
2993 mode |= DL_MODE_ENCRYPT;
2994 mode |= DL_CONFIG_ENCRY_MODE_SEL;
2995 mode |= DL_MODE_RESET_SEC_IV;
2996 break;
2997 default:
2998 dev_err(dev->dev, "Encryption type not support!\n");
2999 }
3000
3001 return mode;
3002}
3003
3004int mt76_connac2_load_patch(struct mt76_dev *dev, const char *fw_name)
3005{
3006 int i, ret, sem, max_len = mt76_is_sdio(dev) ? 2048 : 4096;
3007 const struct mt76_connac2_patch_hdr *hdr;
3008 const struct firmware *fw = NULL;
3009
3010 sem = mt76_connac_mcu_patch_sem_ctrl(dev, true);
3011 switch (sem) {
3012 case PATCH_IS_DL:
3013 return 0;
3014 case PATCH_NOT_DL_SEM_SUCCESS:
3015 break;
3016 default:
3017 dev_err(dev->dev, "Failed to get patch semaphore\n");
3018 return -EAGAIN;
3019 }
3020
3021 ret = request_firmware(fw: &fw, name: fw_name, device: dev->dev);
3022 if (ret)
3023 goto out;
3024
3025 if (!fw || !fw->data || fw->size < sizeof(*hdr)) {
3026 dev_err(dev->dev, "Invalid firmware\n");
3027 ret = -EINVAL;
3028 goto out;
3029 }
3030
3031 hdr = (const void *)fw->data;
3032 dev_info(dev->dev, "HW/SW Version: 0x%x, Build Time: %.16s\n",
3033 be32_to_cpu(hdr->hw_sw_ver), hdr->build_date);
3034
3035 for (i = 0; i < be32_to_cpu(hdr->desc.n_region); i++) {
3036 struct mt76_connac2_patch_sec *sec;
3037 u32 len, addr, mode;
3038 const u8 *dl;
3039 u32 sec_info;
3040
3041 sec = (void *)(fw->data + sizeof(*hdr) + i * sizeof(*sec));
3042 if ((be32_to_cpu(sec->type) & PATCH_SEC_TYPE_MASK) !=
3043 PATCH_SEC_TYPE_INFO) {
3044 ret = -EINVAL;
3045 goto out;
3046 }
3047
3048 addr = be32_to_cpu(sec->info.addr);
3049 len = be32_to_cpu(sec->info.len);
3050 dl = fw->data + be32_to_cpu(sec->offs);
3051 sec_info = be32_to_cpu(sec->info.sec_key_idx);
3052 mode = mt76_connac2_get_data_mode(dev, info: sec_info);
3053
3054 ret = mt76_connac_mcu_init_download(dev, addr, len, mode);
3055 if (ret) {
3056 dev_err(dev->dev, "Download request failed\n");
3057 goto out;
3058 }
3059
3060 ret = __mt76_mcu_send_firmware(dev, MCU_CMD(FW_SCATTER),
3061 data: dl, len, max_len);
3062 if (ret) {
3063 dev_err(dev->dev, "Failed to send patch\n");
3064 goto out;
3065 }
3066 }
3067
3068 ret = mt76_connac_mcu_start_patch(dev);
3069 if (ret)
3070 dev_err(dev->dev, "Failed to start patch\n");
3071
3072out:
3073 sem = mt76_connac_mcu_patch_sem_ctrl(dev, false);
3074 switch (sem) {
3075 case PATCH_REL_SEM_SUCCESS:
3076 break;
3077 default:
3078 ret = -EAGAIN;
3079 dev_err(dev->dev, "Failed to release patch semaphore\n");
3080 break;
3081 }
3082
3083 release_firmware(fw);
3084
3085 return ret;
3086}
3087EXPORT_SYMBOL_GPL(mt76_connac2_load_patch);
3088
3089int mt76_connac2_mcu_fill_message(struct mt76_dev *dev, struct sk_buff *skb,
3090 int cmd, int *wait_seq)
3091{
3092 int txd_len, mcu_cmd = FIELD_GET(__MCU_CMD_FIELD_ID, cmd);
3093 struct mt76_connac2_mcu_uni_txd *uni_txd;
3094 struct mt76_connac2_mcu_txd *mcu_txd;
3095 __le32 *txd;
3096 u32 val;
3097 u8 seq;
3098
3099 /* TODO: make dynamic based on msg type */
3100 dev->mcu.timeout = 20 * HZ;
3101
3102 seq = ++dev->mcu.msg_seq & 0xf;
3103 if (!seq)
3104 seq = ++dev->mcu.msg_seq & 0xf;
3105
3106 if (cmd == MCU_CMD(FW_SCATTER))
3107 goto exit;
3108
3109 txd_len = cmd & __MCU_CMD_FIELD_UNI ? sizeof(*uni_txd) : sizeof(*mcu_txd);
3110 txd = (__le32 *)skb_push(skb, len: txd_len);
3111
3112 val = FIELD_PREP(MT_TXD0_TX_BYTES, skb->len) |
3113 FIELD_PREP(MT_TXD0_PKT_FMT, MT_TX_TYPE_CMD) |
3114 FIELD_PREP(MT_TXD0_Q_IDX, MT_TX_MCU_PORT_RX_Q0);
3115 txd[0] = cpu_to_le32(val);
3116
3117 val = MT_TXD1_LONG_FORMAT |
3118 FIELD_PREP(MT_TXD1_HDR_FORMAT, MT_HDR_FORMAT_CMD);
3119 txd[1] = cpu_to_le32(val);
3120
3121 if (cmd & __MCU_CMD_FIELD_UNI) {
3122 uni_txd = (struct mt76_connac2_mcu_uni_txd *)txd;
3123 uni_txd->len = cpu_to_le16(skb->len - sizeof(uni_txd->txd));
3124 uni_txd->option = MCU_CMD_UNI_EXT_ACK;
3125 uni_txd->cid = cpu_to_le16(mcu_cmd);
3126 uni_txd->s2d_index = MCU_S2D_H2N;
3127 uni_txd->pkt_type = MCU_PKT_ID;
3128 uni_txd->seq = seq;
3129
3130 goto exit;
3131 }
3132
3133 mcu_txd = (struct mt76_connac2_mcu_txd *)txd;
3134 mcu_txd->len = cpu_to_le16(skb->len - sizeof(mcu_txd->txd));
3135 mcu_txd->pq_id = cpu_to_le16(MCU_PQ_ID(MT_TX_PORT_IDX_MCU,
3136 MT_TX_MCU_PORT_RX_Q0));
3137 mcu_txd->pkt_type = MCU_PKT_ID;
3138 mcu_txd->seq = seq;
3139 mcu_txd->cid = mcu_cmd;
3140 mcu_txd->ext_cid = FIELD_GET(__MCU_CMD_FIELD_EXT_ID, cmd);
3141
3142 if (mcu_txd->ext_cid || (cmd & __MCU_CMD_FIELD_CE)) {
3143 if (cmd & __MCU_CMD_FIELD_QUERY)
3144 mcu_txd->set_query = MCU_Q_QUERY;
3145 else
3146 mcu_txd->set_query = MCU_Q_SET;
3147 mcu_txd->ext_cid_ack = !!mcu_txd->ext_cid;
3148 } else {
3149 mcu_txd->set_query = MCU_Q_NA;
3150 }
3151
3152 if (cmd & __MCU_CMD_FIELD_WA)
3153 mcu_txd->s2d_index = MCU_S2D_H2C;
3154 else
3155 mcu_txd->s2d_index = MCU_S2D_H2N;
3156
3157exit:
3158 if (wait_seq)
3159 *wait_seq = seq;
3160
3161 return 0;
3162}
3163EXPORT_SYMBOL_GPL(mt76_connac2_mcu_fill_message);
3164
3165MODULE_AUTHOR("Lorenzo Bianconi <lorenzo@kernel.org>");
3166MODULE_DESCRIPTION("MediaTek MT76x connac layer helpers");
3167MODULE_LICENSE("Dual BSD/GPL");
3168

source code of linux/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c