blob: 9a38681b525b182461328f0f9457a8620e1a522a [file] [log] [blame]
developer7e2761e2023-10-12 08:11:13 +08001From a20311a499edde8f5b8e6b4bced55bd5e0f25884 Mon Sep 17 00:00:00 2001
developerc2cfe0f2023-09-22 04:11:09 +08002From: mtk23510 <rudra.shahi@mediatek.com>
3Date: Wed, 26 Apr 2023 20:08:10 +0800
developer7e2761e2023-10-12 08:11:13 +08004Subject: [PATCH 46/98] wifi: mt76: mt7996: Beacon protection feature added
developerc2cfe0f2023-09-22 04:11:09 +08005
6Signed-off-by: mtk23510 <rudra.shahi@mediatek.com>
7Signed-off-by: Allen.Ye <allen.ye@mediatek.com>
8---
9 mt76_connac_mcu.h | 24 ++++++++
10 mt7996/main.c | 14 +++--
11 mt7996/mcu.c | 138 +++++++++++++++++++++++++++++++++-------------
12 mt7996/mcu.h | 17 ++++++
13 mt7996/mt7996.h | 3 +-
14 5 files changed, 153 insertions(+), 43 deletions(-)
15
16diff --git a/mt76_connac_mcu.h b/mt76_connac_mcu.h
developer7e2761e2023-10-12 08:11:13 +080017index 762ac29..42eb64c 100644
developerc2cfe0f2023-09-22 04:11:09 +080018--- a/mt76_connac_mcu.h
19+++ b/mt76_connac_mcu.h
developer7e2761e2023-10-12 08:11:13 +080020@@ -418,6 +418,14 @@ struct sta_rec_he_6g_capa {
developerc2cfe0f2023-09-22 04:11:09 +080021 u8 rsv[2];
22 } __packed;
23
24+struct sta_rec_pn_info {
25+ __le16 tag;
26+ __le16 len;
27+ u8 pn[6];
28+ u8 tsc_type;
29+ u8 rsv;
30+} __packed;
31+
32 struct sec_key {
33 u8 cipher_id;
34 u8 cipher_len;
developer7e2761e2023-10-12 08:11:13 +080035@@ -770,6 +778,7 @@ struct wtbl_raw {
developerc2cfe0f2023-09-22 04:11:09 +080036 sizeof(struct sta_rec_sec) + \
37 sizeof(struct sta_rec_ra_fixed) + \
38 sizeof(struct sta_rec_he_6g_capa) + \
39+ sizeof(struct sta_rec_pn_info) + \
40 sizeof(struct tlv) + \
41 MT76_CONNAC_WTBL_UPDATE_MAX_SIZE)
42
developer7e2761e2023-10-12 08:11:13 +080043@@ -800,6 +809,7 @@ enum {
developerc2cfe0f2023-09-22 04:11:09 +080044 STA_REC_HE_V2 = 0x19,
45 STA_REC_MLD = 0x20,
46 STA_REC_EHT = 0x22,
47+ STA_REC_PN_INFO = 0x26,
48 STA_REC_HDRT = 0x28,
49 STA_REC_HDR_TRANS = 0x2B,
50 STA_REC_MAX_NUM
developer7e2761e2023-10-12 08:11:13 +080051@@ -1093,6 +1103,13 @@ enum mcu_cipher_type {
developerc2cfe0f2023-09-22 04:11:09 +080052 MCU_CIPHER_GCMP_256,
53 MCU_CIPHER_WAPI,
54 MCU_CIPHER_BIP_CMAC_128,
55+ MCU_CIPHER_BIP_CMAC_256,
56+ MCU_CIPHER_BCN_PROT_CMAC_128,
57+ MCU_CIPHER_BCN_PROT_CMAC_256,
58+ MCU_CIPHER_BCN_PROT_GMAC_128,
59+ MCU_CIPHER_BCN_PROT_GMAC_256,
60+ MCU_CIPHER_BIP_GMAC_128,
61+ MCU_CIPHER_BIP_GMAC_256,
62 };
63
64 enum {
developer7e2761e2023-10-12 08:11:13 +080065@@ -1319,6 +1336,7 @@ enum {
developerc2cfe0f2023-09-22 04:11:09 +080066 UNI_BSS_INFO_RATE = 11,
67 UNI_BSS_INFO_QBSS = 15,
68 UNI_BSS_INFO_SEC = 16,
69+ UNI_BSS_INFO_BCN_PROT = 17,
70 UNI_BSS_INFO_TXCMD = 18,
71 UNI_BSS_INFO_UAPSD = 19,
72 UNI_BSS_INFO_PS = 21,
developer7e2761e2023-10-12 08:11:13 +080073@@ -1779,6 +1797,12 @@ mt76_connac_mcu_get_cipher(int cipher)
developerc2cfe0f2023-09-22 04:11:09 +080074 return MCU_CIPHER_GCMP;
75 case WLAN_CIPHER_SUITE_GCMP_256:
76 return MCU_CIPHER_GCMP_256;
77+ case WLAN_CIPHER_SUITE_BIP_GMAC_128:
78+ return MCU_CIPHER_BIP_GMAC_128;
79+ case WLAN_CIPHER_SUITE_BIP_GMAC_256:
80+ return MCU_CIPHER_BIP_GMAC_256;
81+ case WLAN_CIPHER_SUITE_BIP_CMAC_256:
82+ return MCU_CIPHER_BIP_CMAC_256;
83 case WLAN_CIPHER_SUITE_SMS4:
84 return MCU_CIPHER_WAPI;
85 default:
86diff --git a/mt7996/main.c b/mt7996/main.c
developer7e2761e2023-10-12 08:11:13 +080087index 7d1bd42..0ea006c 100644
developerc2cfe0f2023-09-22 04:11:09 +080088--- a/mt7996/main.c
89+++ b/mt7996/main.c
90@@ -368,8 +368,10 @@ static int mt7996_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd,
91 /* fall back to sw encryption for unsupported ciphers */
92 switch (key->cipher) {
93 case WLAN_CIPHER_SUITE_AES_CMAC:
94- wcid_keyidx = &wcid->hw_key_idx2;
95 key->flags |= IEEE80211_KEY_FLAG_GENERATE_MMIE;
96+ case WLAN_CIPHER_SUITE_BIP_GMAC_128:
97+ case WLAN_CIPHER_SUITE_BIP_GMAC_256:
98+ wcid_keyidx = &wcid->hw_key_idx2;
99 break;
100 case WLAN_CIPHER_SUITE_TKIP:
101 case WLAN_CIPHER_SUITE_CCMP:
102@@ -400,9 +402,13 @@ static int mt7996_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd,
103 }
104
105 mt76_wcid_key_setup(&dev->mt76, wcid, key);
106- err = mt7996_mcu_add_key(&dev->mt76, vif, &msta->bip,
107- key, MCU_WMWA_UNI_CMD(STA_REC_UPDATE),
108- &msta->wcid, cmd);
109+
110+ if (key->keyidx == 6 || key->keyidx == 7)
111+ err = mt7996_mcu_bcn_prot_enable(dev, vif, key);
112+ else
113+ err = mt7996_mcu_add_key(&dev->mt76, vif, key,
114+ MCU_WMWA_UNI_CMD(STA_REC_UPDATE),
115+ &msta->wcid, cmd);
116 out:
117 mutex_unlock(&dev->mt76.mutex);
118
119diff --git a/mt7996/mcu.c b/mt7996/mcu.c
developer7e2761e2023-10-12 08:11:13 +0800120index 695d5f0..1a1c732 100644
developerc2cfe0f2023-09-22 04:11:09 +0800121--- a/mt7996/mcu.c
122+++ b/mt7996/mcu.c
developer7e2761e2023-10-12 08:11:13 +0800123@@ -2118,7 +2118,6 @@ out:
developerc2cfe0f2023-09-22 04:11:09 +0800124
125 static int
126 mt7996_mcu_sta_key_tlv(struct mt76_wcid *wcid,
127- struct mt76_connac_sta_key_conf *sta_key_conf,
128 struct sk_buff *skb,
129 struct ieee80211_key_conf *key,
130 enum set_key_cmd cmd)
developer7e2761e2023-10-12 08:11:13 +0800131@@ -2139,43 +2138,22 @@ mt7996_mcu_sta_key_tlv(struct mt76_wcid *wcid,
developerc2cfe0f2023-09-22 04:11:09 +0800132 return -EOPNOTSUPP;
133
134 sec_key = &sec->key[0];
135+ sec_key->wlan_idx = cpu_to_le16(wcid->idx);
136+ sec_key->mgmt_prot = 0;
137+ sec_key->cipher_id = cipher;
138 sec_key->cipher_len = sizeof(*sec_key);
139-
140- if (cipher == MCU_CIPHER_BIP_CMAC_128) {
141- sec_key->wlan_idx = cpu_to_le16(wcid->idx);
142- sec_key->cipher_id = MCU_CIPHER_AES_CCMP;
143- sec_key->key_id = sta_key_conf->keyidx;
144- sec_key->key_len = 16;
145- memcpy(sec_key->key, sta_key_conf->key, 16);
146-
147- sec_key = &sec->key[1];
148- sec_key->wlan_idx = cpu_to_le16(wcid->idx);
149- sec_key->cipher_id = MCU_CIPHER_BIP_CMAC_128;
150- sec_key->cipher_len = sizeof(*sec_key);
151- sec_key->key_len = 16;
152- memcpy(sec_key->key, key->key, 16);
153- sec->n_cipher = 2;
154- } else {
155- sec_key->wlan_idx = cpu_to_le16(wcid->idx);
156- sec_key->cipher_id = cipher;
157- sec_key->key_id = key->keyidx;
158- sec_key->key_len = key->keylen;
159- memcpy(sec_key->key, key->key, key->keylen);
160-
161- if (cipher == MCU_CIPHER_TKIP) {
162- /* Rx/Tx MIC keys are swapped */
163- memcpy(sec_key->key + 16, key->key + 24, 8);
164- memcpy(sec_key->key + 24, key->key + 16, 8);
165- }
166-
167- /* store key_conf for BIP batch update */
168- if (cipher == MCU_CIPHER_AES_CCMP) {
169- memcpy(sta_key_conf->key, key->key, key->keylen);
170- sta_key_conf->keyidx = key->keyidx;
171- }
172-
173- sec->n_cipher = 1;
174+ sec_key->key_id = key->keyidx;
175+ sec_key->key_len = key->keylen;
176+ sec_key->need_resp = 0;
177+ memcpy(sec_key->key, key->key, key->keylen);
178+
179+ if (cipher == MCU_CIPHER_TKIP) {
180+ /* Rx/Tx MIC keys are swapped */
181+ memcpy(sec_key->key + 16, key->key + 24, 8);
182+ memcpy(sec_key->key + 24, key->key + 16, 8);
183 }
184+
185+ sec->n_cipher = 1;
186 } else {
187 sec->n_cipher = 0;
188 }
developer7e2761e2023-10-12 08:11:13 +0800189@@ -2184,7 +2162,6 @@ mt7996_mcu_sta_key_tlv(struct mt76_wcid *wcid,
developerc2cfe0f2023-09-22 04:11:09 +0800190 }
191
192 int mt7996_mcu_add_key(struct mt76_dev *dev, struct ieee80211_vif *vif,
193- struct mt76_connac_sta_key_conf *sta_key_conf,
194 struct ieee80211_key_conf *key, int mcu_cmd,
195 struct mt76_wcid *wcid, enum set_key_cmd cmd)
196 {
developer7e2761e2023-10-12 08:11:13 +0800197@@ -2197,13 +2174,98 @@ int mt7996_mcu_add_key(struct mt76_dev *dev, struct ieee80211_vif *vif,
developerc2cfe0f2023-09-22 04:11:09 +0800198 if (IS_ERR(skb))
199 return PTR_ERR(skb);
200
201- ret = mt7996_mcu_sta_key_tlv(wcid, sta_key_conf, skb, key, cmd);
202+ ret = mt7996_mcu_sta_key_tlv(wcid, skb, key, cmd);
203 if (ret)
204 return ret;
205
206 return mt76_mcu_skb_send_msg(dev, skb, mcu_cmd, true);
207 }
208
209+static int mt7996_mcu_get_pn(struct mt7996_dev *dev, struct ieee80211_vif *vif,
210+ u8 *pn)
211+{
212+#define TSC_TYPE_BIGTK_PN 2
213+ struct mt7996_vif *mvif = (struct mt7996_vif *)vif->drv_priv;
214+ struct sta_rec_pn_info *pn_info;
215+ struct sk_buff *skb, *rskb;
216+ struct tlv *tlv;
217+ int ret;
218+
219+ skb = mt76_connac_mcu_alloc_sta_req(&dev->mt76, &mvif->mt76, &mvif->sta.wcid);
220+ if (IS_ERR(skb))
221+ return PTR_ERR(skb);
222+
223+ tlv = mt76_connac_mcu_add_tlv(skb, STA_REC_PN_INFO, sizeof(*pn_info));
224+ pn_info = (struct sta_rec_pn_info *)tlv;
225+
226+ pn_info->tsc_type = TSC_TYPE_BIGTK_PN;
227+ ret = mt76_mcu_skb_send_and_get_msg(&dev->mt76, skb,
228+ MCU_WM_UNI_CMD_QUERY(STA_REC_UPDATE), true, &rskb);
229+ if (ret)
230+ return ret;
231+
232+ skb_pull(rskb, 4);
233+
234+ pn_info = (struct sta_rec_pn_info *)rskb->data;
235+ if (le16_to_cpu(pn_info->tag) == STA_REC_PN_INFO)
236+ memcpy(pn, pn_info->pn, 6);
237+
238+ dev_kfree_skb(rskb);
239+ return 0;
240+}
241+
242+int mt7996_mcu_bcn_prot_enable(struct mt7996_dev *dev, struct ieee80211_vif *vif,
243+ struct ieee80211_key_conf *key)
244+{
245+ int len = sizeof(struct bss_req_hdr) + sizeof(struct mt7996_mcu_bcn_prot_tlv);
246+ struct mt7996_vif *mvif = (struct mt7996_vif *)vif->drv_priv;
247+ int ret;
248+ struct mt7996_mcu_bcn_prot_tlv *bcn_prot;
249+ struct sk_buff *skb;
250+ struct tlv *tlv;
251+ u8 pn[6] = {0};
252+
253+ skb = __mt7996_mcu_alloc_bss_req(&dev->mt76, &mvif->mt76, len);
254+ if (IS_ERR(skb))
255+ return PTR_ERR(skb);
256+
257+ tlv = mt76_connac_mcu_add_tlv(skb, UNI_BSS_INFO_BCN_PROT,
258+ sizeof(*bcn_prot));
259+
260+ bcn_prot = (struct mt7996_mcu_bcn_prot_tlv *)tlv;
261+
262+ ret = mt7996_mcu_get_pn(dev, vif, pn);
263+ if (ret) {
264+ dev_kfree_skb(skb);
265+ return ret;
266+ }
267+
268+ switch (key->cipher) {
269+ case WLAN_CIPHER_SUITE_AES_CMAC:
270+ bcn_prot->cipher_id = MCU_CIPHER_BCN_PROT_CMAC_128;
271+ break;
272+ case WLAN_CIPHER_SUITE_BIP_GMAC_128:
273+ bcn_prot->cipher_id = MCU_CIPHER_BCN_PROT_GMAC_128;
274+ break;
275+ case WLAN_CIPHER_SUITE_BIP_GMAC_256:
276+ bcn_prot->cipher_id = MCU_CIPHER_BCN_PROT_GMAC_256;
277+ break;
278+ case WLAN_CIPHER_SUITE_BIP_CMAC_256:
279+ default:
280+ dev_err(dev->mt76.dev, "Not supported Bigtk Cipher\n");
281+ dev_kfree_skb(skb);
282+ return -EOPNOTSUPP;
283+ }
284+
285+ pn[0]++;
286+ memcpy(bcn_prot->pn, pn, 6);
287+ bcn_prot->enable = BP_SW_MODE;
288+ memcpy(bcn_prot->key, key->key, WLAN_MAX_KEY_LEN);
289+ bcn_prot->key_id = key->keyidx;
290+
291+ return mt76_mcu_skb_send_msg(&dev->mt76, skb,
292+ MCU_WMWA_UNI_CMD(BSS_INFO_UPDATE), true);
293+}
294 int mt7996_mcu_add_dev_info(struct mt7996_phy *phy,
295 struct ieee80211_vif *vif, bool enable)
296 {
297diff --git a/mt7996/mcu.h b/mt7996/mcu.h
developer7e2761e2023-10-12 08:11:13 +0800298index c5c0a44..7808c35 100644
developerc2cfe0f2023-09-22 04:11:09 +0800299--- a/mt7996/mcu.h
300+++ b/mt7996/mcu.h
developer7e2761e2023-10-12 08:11:13 +0800301@@ -310,6 +310,23 @@ struct bss_rate_tlv {
developerc2cfe0f2023-09-22 04:11:09 +0800302 u8 __rsv2[9];
303 } __packed;
304
305+enum {
306+ BP_DISABLE,
307+ BP_SW_MODE,
308+ BP_HW_MODE,
309+};
310+
311+struct mt7996_mcu_bcn_prot_tlv {
312+ __le16 tag;
313+ __le16 len;
314+ u8 pn[6];
315+ u8 enable;
316+ u8 cipher_id;
317+ u8 key[WLAN_MAX_KEY_LEN];
318+ u8 key_id;
319+ u8 __rsv[3];
320+} __packed;
321+
322 struct bss_ra_tlv {
323 __le16 tag;
324 __le16 len;
325diff --git a/mt7996/mt7996.h b/mt7996/mt7996.h
developer7e2761e2023-10-12 08:11:13 +0800326index 80a10bf..9f99d13 100644
developerc2cfe0f2023-09-22 04:11:09 +0800327--- a/mt7996/mt7996.h
328+++ b/mt7996/mt7996.h
developer7e2761e2023-10-12 08:11:13 +0800329@@ -712,9 +712,10 @@ int mt7996_init_debugfs(struct mt7996_phy *phy);
developerc2cfe0f2023-09-22 04:11:09 +0800330 void mt7996_debugfs_rx_fw_monitor(struct mt7996_dev *dev, const void *data, int len);
331 bool mt7996_debugfs_rx_log(struct mt7996_dev *dev, const void *data, int len);
332 int mt7996_mcu_add_key(struct mt76_dev *dev, struct ieee80211_vif *vif,
333- struct mt76_connac_sta_key_conf *sta_key_conf,
334 struct ieee80211_key_conf *key, int mcu_cmd,
335 struct mt76_wcid *wcid, enum set_key_cmd cmd);
336+int mt7996_mcu_bcn_prot_enable(struct mt7996_dev *dev, struct ieee80211_vif *vif,
337+ struct ieee80211_key_conf *key);
338 int mt7996_mcu_wtbl_update_hdr_trans(struct mt7996_dev *dev,
339 struct ieee80211_vif *vif,
340 struct ieee80211_sta *sta);
341--
developer7e2761e2023-10-12 08:11:13 +08003422.18.0
developerc2cfe0f2023-09-22 04:11:09 +0800343