]> git.proxmox.com Git - mirror_ubuntu-jammy-kernel.git/blob - drivers/net/wireless/realtek/rtlwifi/rtl8821ae/phy.c
slip: Fix use-after-free Read in slip_open
[mirror_ubuntu-jammy-kernel.git] / drivers / net / wireless / realtek / rtlwifi / rtl8821ae / phy.c
1 // SPDX-License-Identifier: GPL-2.0
2 /* Copyright(c) 2009-2010 Realtek Corporation.*/
3
4 #include "../wifi.h"
5 #include "../pci.h"
6 #include "../ps.h"
7 #include "reg.h"
8 #include "def.h"
9 #include "phy.h"
10 #include "rf.h"
11 #include "dm.h"
12 #include "table.h"
13 #include "trx.h"
14 #include "../btcoexist/halbt_precomp.h"
15 #include "hw.h"
16 #include "../efuse.h"
17
18 #define READ_NEXT_PAIR(array_table, v1, v2, i) \
19 do { \
20 i += 2; \
21 v1 = array_table[i]; \
22 v2 = array_table[i+1]; \
23 } while (0)
24
25 static u32 _rtl8821ae_phy_rf_serial_read(struct ieee80211_hw *hw,
26 enum radio_path rfpath, u32 offset);
27 static void _rtl8821ae_phy_rf_serial_write(struct ieee80211_hw *hw,
28 enum radio_path rfpath, u32 offset,
29 u32 data);
30 static u32 _rtl8821ae_phy_calculate_bit_shift(u32 bitmask);
31 static bool _rtl8821ae_phy_bb8821a_config_parafile(struct ieee80211_hw *hw);
32 /*static bool _rtl8812ae_phy_config_mac_with_headerfile(struct ieee80211_hw *hw);*/
33 static bool _rtl8821ae_phy_config_mac_with_headerfile(struct ieee80211_hw *hw);
34 static bool _rtl8821ae_phy_config_bb_with_headerfile(struct ieee80211_hw *hw,
35 u8 configtype);
36 static bool _rtl8821ae_phy_config_bb_with_pgheaderfile(struct ieee80211_hw *hw,
37 u8 configtype);
38 static void phy_init_bb_rf_register_definition(struct ieee80211_hw *hw);
39
40 static long _rtl8821ae_phy_txpwr_idx_to_dbm(struct ieee80211_hw *hw,
41 enum wireless_mode wirelessmode,
42 u8 txpwridx);
43 static void rtl8821ae_phy_set_rf_on(struct ieee80211_hw *hw);
44 static void rtl8821ae_phy_set_io(struct ieee80211_hw *hw);
45
46 static void rtl8812ae_fixspur(struct ieee80211_hw *hw,
47 enum ht_channel_width band_width, u8 channel)
48 {
49 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
50
51 /*C cut Item12 ADC FIFO CLOCK*/
52 if (IS_VENDOR_8812A_C_CUT(rtlhal->version)) {
53 if (band_width == HT_CHANNEL_WIDTH_20_40 && channel == 11)
54 rtl_set_bbreg(hw, RRFMOD, 0xC00, 0x3);
55 /* 0x8AC[11:10] = 2'b11*/
56 else
57 rtl_set_bbreg(hw, RRFMOD, 0xC00, 0x2);
58 /* 0x8AC[11:10] = 2'b10*/
59
60 /* <20120914, Kordan> A workarould to resolve
61 * 2480Mhz spur by setting ADC clock as 160M. (Asked by Binson)
62 */
63 if (band_width == HT_CHANNEL_WIDTH_20 &&
64 (channel == 13 || channel == 14)) {
65 rtl_set_bbreg(hw, RRFMOD, 0x300, 0x3);
66 /*0x8AC[9:8] = 2'b11*/
67 rtl_set_bbreg(hw, RADC_BUF_CLK, BIT(30), 1);
68 /* 0x8C4[30] = 1*/
69 } else if (band_width == HT_CHANNEL_WIDTH_20_40 &&
70 channel == 11) {
71 rtl_set_bbreg(hw, RADC_BUF_CLK, BIT(30), 1);
72 /*0x8C4[30] = 1*/
73 } else if (band_width != HT_CHANNEL_WIDTH_80) {
74 rtl_set_bbreg(hw, RRFMOD, 0x300, 0x2);
75 /*0x8AC[9:8] = 2'b10*/
76 rtl_set_bbreg(hw, RADC_BUF_CLK, BIT(30), 0);
77 /*0x8C4[30] = 0*/
78 }
79 } else if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
80 /* <20120914, Kordan> A workarould to resolve
81 * 2480Mhz spur by setting ADC clock as 160M.
82 */
83 if (band_width == HT_CHANNEL_WIDTH_20 &&
84 (channel == 13 || channel == 14))
85 rtl_set_bbreg(hw, RRFMOD, 0x300, 0x3);
86 /*0x8AC[9:8] = 11*/
87 else if (channel <= 14) /*2.4G only*/
88 rtl_set_bbreg(hw, RRFMOD, 0x300, 0x2);
89 /*0x8AC[9:8] = 10*/
90 }
91 }
92
93 u32 rtl8821ae_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr,
94 u32 bitmask)
95 {
96 struct rtl_priv *rtlpriv = rtl_priv(hw);
97 u32 returnvalue, originalvalue, bitshift;
98
99 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
100 "regaddr(%#x), bitmask(%#x)\n",
101 regaddr, bitmask);
102 originalvalue = rtl_read_dword(rtlpriv, regaddr);
103 bitshift = _rtl8821ae_phy_calculate_bit_shift(bitmask);
104 returnvalue = (originalvalue & bitmask) >> bitshift;
105
106 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
107 "BBR MASK=0x%x Addr[0x%x]=0x%x\n",
108 bitmask, regaddr, originalvalue);
109 return returnvalue;
110 }
111
112 void rtl8821ae_phy_set_bb_reg(struct ieee80211_hw *hw,
113 u32 regaddr, u32 bitmask, u32 data)
114 {
115 struct rtl_priv *rtlpriv = rtl_priv(hw);
116 u32 originalvalue, bitshift;
117
118 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
119 "regaddr(%#x), bitmask(%#x), data(%#x)\n",
120 regaddr, bitmask, data);
121
122 if (bitmask != MASKDWORD) {
123 originalvalue = rtl_read_dword(rtlpriv, regaddr);
124 bitshift = _rtl8821ae_phy_calculate_bit_shift(bitmask);
125 data = ((originalvalue & (~bitmask)) |
126 ((data << bitshift) & bitmask));
127 }
128
129 rtl_write_dword(rtlpriv, regaddr, data);
130
131 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
132 "regaddr(%#x), bitmask(%#x), data(%#x)\n",
133 regaddr, bitmask, data);
134 }
135
136 u32 rtl8821ae_phy_query_rf_reg(struct ieee80211_hw *hw,
137 enum radio_path rfpath, u32 regaddr,
138 u32 bitmask)
139 {
140 struct rtl_priv *rtlpriv = rtl_priv(hw);
141 u32 original_value, readback_value, bitshift;
142 unsigned long flags;
143
144 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
145 "regaddr(%#x), rfpath(%#x), bitmask(%#x)\n",
146 regaddr, rfpath, bitmask);
147
148 spin_lock_irqsave(&rtlpriv->locks.rf_lock, flags);
149
150 original_value = _rtl8821ae_phy_rf_serial_read(hw, rfpath, regaddr);
151 bitshift = _rtl8821ae_phy_calculate_bit_shift(bitmask);
152 readback_value = (original_value & bitmask) >> bitshift;
153
154 spin_unlock_irqrestore(&rtlpriv->locks.rf_lock, flags);
155
156 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
157 "regaddr(%#x), rfpath(%#x), bitmask(%#x), original_value(%#x)\n",
158 regaddr, rfpath, bitmask, original_value);
159
160 return readback_value;
161 }
162
163 void rtl8821ae_phy_set_rf_reg(struct ieee80211_hw *hw,
164 enum radio_path rfpath,
165 u32 regaddr, u32 bitmask, u32 data)
166 {
167 struct rtl_priv *rtlpriv = rtl_priv(hw);
168 u32 original_value, bitshift;
169 unsigned long flags;
170
171 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
172 "regaddr(%#x), bitmask(%#x), data(%#x), rfpath(%#x)\n",
173 regaddr, bitmask, data, rfpath);
174
175 spin_lock_irqsave(&rtlpriv->locks.rf_lock, flags);
176
177 if (bitmask != RFREG_OFFSET_MASK) {
178 original_value =
179 _rtl8821ae_phy_rf_serial_read(hw, rfpath, regaddr);
180 bitshift = _rtl8821ae_phy_calculate_bit_shift(bitmask);
181 data = ((original_value & (~bitmask)) | (data << bitshift));
182 }
183
184 _rtl8821ae_phy_rf_serial_write(hw, rfpath, regaddr, data);
185
186 spin_unlock_irqrestore(&rtlpriv->locks.rf_lock, flags);
187
188 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
189 "regaddr(%#x), bitmask(%#x), data(%#x), rfpath(%#x)\n",
190 regaddr, bitmask, data, rfpath);
191 }
192
193 static u32 _rtl8821ae_phy_rf_serial_read(struct ieee80211_hw *hw,
194 enum radio_path rfpath, u32 offset)
195 {
196 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
197 bool is_pi_mode = false;
198 u32 retvalue = 0;
199
200 /* 2009/06/17 MH We can not execute IO for power
201 save or other accident mode.*/
202 if (RT_CANNOT_IO(hw)) {
203 pr_err("return all one\n");
204 return 0xFFFFFFFF;
205 }
206 /* <20120809, Kordan> CCA OFF(when entering),
207 asked by James to avoid reading the wrong value.
208 <20120828, Kordan> Toggling CCA would affect RF 0x0, skip it!*/
209 if (offset != 0x0 &&
210 !((rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) ||
211 (IS_VENDOR_8812A_C_CUT(rtlhal->version))))
212 rtl_set_bbreg(hw, RCCAONSEC, 0x8, 1);
213 offset &= 0xff;
214
215 if (rfpath == RF90_PATH_A)
216 is_pi_mode = (bool)rtl_get_bbreg(hw, 0xC00, 0x4);
217 else if (rfpath == RF90_PATH_B)
218 is_pi_mode = (bool)rtl_get_bbreg(hw, 0xE00, 0x4);
219
220 rtl_set_bbreg(hw, RHSSIREAD_8821AE, 0xff, offset);
221
222 if ((rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) ||
223 (IS_VENDOR_8812A_C_CUT(rtlhal->version)))
224 udelay(20);
225
226 if (is_pi_mode) {
227 if (rfpath == RF90_PATH_A)
228 retvalue =
229 rtl_get_bbreg(hw, RA_PIREAD_8821A, BLSSIREADBACKDATA);
230 else if (rfpath == RF90_PATH_B)
231 retvalue =
232 rtl_get_bbreg(hw, RB_PIREAD_8821A, BLSSIREADBACKDATA);
233 } else {
234 if (rfpath == RF90_PATH_A)
235 retvalue =
236 rtl_get_bbreg(hw, RA_SIREAD_8821A, BLSSIREADBACKDATA);
237 else if (rfpath == RF90_PATH_B)
238 retvalue =
239 rtl_get_bbreg(hw, RB_SIREAD_8821A, BLSSIREADBACKDATA);
240 }
241
242 /*<20120809, Kordan> CCA ON(when exiting),
243 * asked by James to avoid reading the wrong value.
244 * <20120828, Kordan> Toggling CCA would affect RF 0x0, skip it!
245 */
246 if (offset != 0x0 &&
247 !((rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) ||
248 (IS_VENDOR_8812A_C_CUT(rtlhal->version))))
249 rtl_set_bbreg(hw, RCCAONSEC, 0x8, 0);
250 return retvalue;
251 }
252
253 static void _rtl8821ae_phy_rf_serial_write(struct ieee80211_hw *hw,
254 enum radio_path rfpath, u32 offset,
255 u32 data)
256 {
257 struct rtl_priv *rtlpriv = rtl_priv(hw);
258 struct rtl_phy *rtlphy = &rtlpriv->phy;
259 struct bb_reg_def *pphyreg = &rtlphy->phyreg_def[rfpath];
260 u32 data_and_addr;
261 u32 newoffset;
262
263 if (RT_CANNOT_IO(hw)) {
264 pr_err("stop\n");
265 return;
266 }
267 offset &= 0xff;
268 newoffset = offset;
269 data_and_addr = ((newoffset << 20) |
270 (data & 0x000fffff)) & 0x0fffffff;
271 rtl_set_bbreg(hw, pphyreg->rf3wire_offset, MASKDWORD, data_and_addr);
272 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
273 "RFW-%d Addr[0x%x]=0x%x\n",
274 rfpath, pphyreg->rf3wire_offset, data_and_addr);
275 }
276
277 static u32 _rtl8821ae_phy_calculate_bit_shift(u32 bitmask)
278 {
279 u32 i;
280
281 for (i = 0; i <= 31; i++) {
282 if (((bitmask >> i) & 0x1) == 1)
283 break;
284 }
285 return i;
286 }
287
288 bool rtl8821ae_phy_mac_config(struct ieee80211_hw *hw)
289 {
290 bool rtstatus = 0;
291
292 rtstatus = _rtl8821ae_phy_config_mac_with_headerfile(hw);
293
294 return rtstatus;
295 }
296
297 bool rtl8821ae_phy_bb_config(struct ieee80211_hw *hw)
298 {
299 bool rtstatus = true;
300 struct rtl_priv *rtlpriv = rtl_priv(hw);
301 struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
302 struct rtl_phy *rtlphy = &rtlpriv->phy;
303 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
304 u8 regval;
305 u8 crystal_cap;
306
307 phy_init_bb_rf_register_definition(hw);
308
309 regval = rtl_read_byte(rtlpriv, REG_SYS_FUNC_EN);
310 regval |= FEN_PCIEA;
311 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, regval);
312 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN,
313 regval | FEN_BB_GLB_RSTN | FEN_BBRSTB);
314
315 rtl_write_byte(rtlpriv, REG_RF_CTRL, 0x7);
316 rtl_write_byte(rtlpriv, REG_OPT_CTRL + 2, 0x7);
317
318 rtstatus = _rtl8821ae_phy_bb8821a_config_parafile(hw);
319
320 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
321 crystal_cap = rtlefuse->crystalcap & 0x3F;
322 rtl_set_bbreg(hw, REG_MAC_PHY_CTRL, 0x7FF80000,
323 (crystal_cap | (crystal_cap << 6)));
324 } else {
325 crystal_cap = rtlefuse->crystalcap & 0x3F;
326 rtl_set_bbreg(hw, REG_MAC_PHY_CTRL, 0xFFF000,
327 (crystal_cap | (crystal_cap << 6)));
328 }
329 rtlphy->reg_837 = rtl_read_byte(rtlpriv, 0x837);
330
331 return rtstatus;
332 }
333
334 bool rtl8821ae_phy_rf_config(struct ieee80211_hw *hw)
335 {
336 return rtl8821ae_phy_rf6052_config(hw);
337 }
338
339 static void _rtl8812ae_phy_set_rfe_reg_24g(struct ieee80211_hw *hw)
340 {
341 struct rtl_priv *rtlpriv = rtl_priv(hw);
342 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
343 u8 tmp;
344
345 switch (rtlhal->rfe_type) {
346 case 3:
347 rtl_set_bbreg(hw, RA_RFE_PINMUX, BMASKDWORD, 0x54337770);
348 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x54337770);
349 rtl_set_bbreg(hw, RA_RFE_INV, BMASKRFEINV, 0x010);
350 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x010);
351 rtl_set_bbreg(hw, 0x900, 0x00000303, 0x1);
352 break;
353 case 4:
354 rtl_set_bbreg(hw, RA_RFE_PINMUX, BMASKDWORD, 0x77777777);
355 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x77777777);
356 rtl_set_bbreg(hw, RA_RFE_INV, BMASKRFEINV, 0x001);
357 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x001);
358 break;
359 case 5:
360 rtl_write_byte(rtlpriv, RA_RFE_PINMUX + 2, 0x77);
361 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x77777777);
362 tmp = rtl_read_byte(rtlpriv, RA_RFE_INV + 3);
363 rtl_write_byte(rtlpriv, RA_RFE_INV + 3, tmp & ~0x1);
364 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x000);
365 break;
366 case 1:
367 if (rtlpriv->btcoexist.bt_coexistence) {
368 rtl_set_bbreg(hw, RA_RFE_PINMUX, 0xffffff, 0x777777);
369 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD,
370 0x77777777);
371 rtl_set_bbreg(hw, RA_RFE_INV, 0x33f00000, 0x000);
372 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x000);
373 break;
374 }
375 /* fall through */
376 case 0:
377 case 2:
378 default:
379 rtl_set_bbreg(hw, RA_RFE_PINMUX, BMASKDWORD, 0x77777777);
380 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x77777777);
381 rtl_set_bbreg(hw, RA_RFE_INV, BMASKRFEINV, 0x000);
382 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x000);
383 break;
384 }
385 }
386
387 static void _rtl8812ae_phy_set_rfe_reg_5g(struct ieee80211_hw *hw)
388 {
389 struct rtl_priv *rtlpriv = rtl_priv(hw);
390 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
391 u8 tmp;
392
393 switch (rtlhal->rfe_type) {
394 case 0:
395 rtl_set_bbreg(hw, RA_RFE_PINMUX, BMASKDWORD, 0x77337717);
396 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x77337717);
397 rtl_set_bbreg(hw, RA_RFE_INV, BMASKRFEINV, 0x010);
398 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x010);
399 break;
400 case 1:
401 if (rtlpriv->btcoexist.bt_coexistence) {
402 rtl_set_bbreg(hw, RA_RFE_PINMUX, 0xffffff, 0x337717);
403 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD,
404 0x77337717);
405 rtl_set_bbreg(hw, RA_RFE_INV, 0x33f00000, 0x000);
406 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x000);
407 } else {
408 rtl_set_bbreg(hw, RA_RFE_PINMUX, BMASKDWORD,
409 0x77337717);
410 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD,
411 0x77337717);
412 rtl_set_bbreg(hw, RA_RFE_INV, BMASKRFEINV, 0x000);
413 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x000);
414 }
415 break;
416 case 3:
417 rtl_set_bbreg(hw, RA_RFE_PINMUX, BMASKDWORD, 0x54337717);
418 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x54337717);
419 rtl_set_bbreg(hw, RA_RFE_INV, BMASKRFEINV, 0x010);
420 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x010);
421 rtl_set_bbreg(hw, 0x900, 0x00000303, 0x1);
422 break;
423 case 5:
424 rtl_write_byte(rtlpriv, RA_RFE_PINMUX + 2, 0x33);
425 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x77337777);
426 tmp = rtl_read_byte(rtlpriv, RA_RFE_INV + 3);
427 rtl_write_byte(rtlpriv, RA_RFE_INV + 3, tmp | 0x1);
428 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x010);
429 break;
430 case 2:
431 case 4:
432 default:
433 rtl_set_bbreg(hw, RA_RFE_PINMUX, BMASKDWORD, 0x77337777);
434 rtl_set_bbreg(hw, RB_RFE_PINMUX, BMASKDWORD, 0x77337777);
435 rtl_set_bbreg(hw, RA_RFE_INV, BMASKRFEINV, 0x010);
436 rtl_set_bbreg(hw, RB_RFE_INV, BMASKRFEINV, 0x010);
437 break;
438 }
439 }
440
441 u32 phy_get_tx_swing_8812A(struct ieee80211_hw *hw, u8 band,
442 u8 rf_path)
443 {
444 struct rtl_priv *rtlpriv = rtl_priv(hw);
445 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
446 struct rtl_dm *rtldm = rtl_dm(rtlpriv);
447 struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
448 s8 reg_swing_2g = -1;/* 0xff; */
449 s8 reg_swing_5g = -1;/* 0xff; */
450 s8 swing_2g = -1 * reg_swing_2g;
451 s8 swing_5g = -1 * reg_swing_5g;
452 u32 out = 0x200;
453 const s8 auto_temp = -1;
454
455 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD,
456 "===> PHY_GetTXBBSwing_8812A, bbSwing_2G: %d, bbSwing_5G: %d,autoload_failflag=%d.\n",
457 (int)swing_2g, (int)swing_5g,
458 (int)rtlefuse->autoload_failflag);
459
460 if (rtlefuse->autoload_failflag) {
461 if (band == BAND_ON_2_4G) {
462 rtldm->swing_diff_2g = swing_2g;
463 if (swing_2g == 0) {
464 out = 0x200; /* 0 dB */
465 } else if (swing_2g == -3) {
466 out = 0x16A; /* -3 dB */
467 } else if (swing_2g == -6) {
468 out = 0x101; /* -6 dB */
469 } else if (swing_2g == -9) {
470 out = 0x0B6; /* -9 dB */
471 } else {
472 rtldm->swing_diff_2g = 0;
473 out = 0x200;
474 }
475 } else if (band == BAND_ON_5G) {
476 rtldm->swing_diff_5g = swing_5g;
477 if (swing_5g == 0) {
478 out = 0x200; /* 0 dB */
479 } else if (swing_5g == -3) {
480 out = 0x16A; /* -3 dB */
481 } else if (swing_5g == -6) {
482 out = 0x101; /* -6 dB */
483 } else if (swing_5g == -9) {
484 out = 0x0B6; /* -9 dB */
485 } else {
486 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
487 rtldm->swing_diff_5g = -3;
488 out = 0x16A;
489 } else {
490 rtldm->swing_diff_5g = 0;
491 out = 0x200;
492 }
493 }
494 } else {
495 rtldm->swing_diff_2g = -3;
496 rtldm->swing_diff_5g = -3;
497 out = 0x16A; /* -3 dB */
498 }
499 } else {
500 u32 swing = 0, swing_a = 0, swing_b = 0;
501
502 if (band == BAND_ON_2_4G) {
503 if (reg_swing_2g == auto_temp) {
504 efuse_shadow_read(hw, 1, 0xC6, (u32 *)&swing);
505 swing = (swing == 0xFF) ? 0x00 : swing;
506 } else if (swing_2g == 0) {
507 swing = 0x00; /* 0 dB */
508 } else if (swing_2g == -3) {
509 swing = 0x05; /* -3 dB */
510 } else if (swing_2g == -6) {
511 swing = 0x0A; /* -6 dB */
512 } else if (swing_2g == -9) {
513 swing = 0xFF; /* -9 dB */
514 } else {
515 swing = 0x00;
516 }
517 } else {
518 if (reg_swing_5g == auto_temp) {
519 efuse_shadow_read(hw, 1, 0xC7, (u32 *)&swing);
520 swing = (swing == 0xFF) ? 0x00 : swing;
521 } else if (swing_5g == 0) {
522 swing = 0x00; /* 0 dB */
523 } else if (swing_5g == -3) {
524 swing = 0x05; /* -3 dB */
525 } else if (swing_5g == -6) {
526 swing = 0x0A; /* -6 dB */
527 } else if (swing_5g == -9) {
528 swing = 0xFF; /* -9 dB */
529 } else {
530 swing = 0x00;
531 }
532 }
533
534 swing_a = (swing & 0x3) >> 0; /* 0xC6/C7[1:0] */
535 swing_b = (swing & 0xC) >> 2; /* 0xC6/C7[3:2] */
536 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD,
537 "===> PHY_GetTXBBSwing_8812A, swingA: 0x%X, swingB: 0x%X\n",
538 swing_a, swing_b);
539
540 /* 3 Path-A */
541 if (swing_a == 0x0) {
542 if (band == BAND_ON_2_4G)
543 rtldm->swing_diff_2g = 0;
544 else
545 rtldm->swing_diff_5g = 0;
546 out = 0x200; /* 0 dB */
547 } else if (swing_a == 0x1) {
548 if (band == BAND_ON_2_4G)
549 rtldm->swing_diff_2g = -3;
550 else
551 rtldm->swing_diff_5g = -3;
552 out = 0x16A; /* -3 dB */
553 } else if (swing_a == 0x2) {
554 if (band == BAND_ON_2_4G)
555 rtldm->swing_diff_2g = -6;
556 else
557 rtldm->swing_diff_5g = -6;
558 out = 0x101; /* -6 dB */
559 } else if (swing_a == 0x3) {
560 if (band == BAND_ON_2_4G)
561 rtldm->swing_diff_2g = -9;
562 else
563 rtldm->swing_diff_5g = -9;
564 out = 0x0B6; /* -9 dB */
565 }
566 /* 3 Path-B */
567 if (swing_b == 0x0) {
568 if (band == BAND_ON_2_4G)
569 rtldm->swing_diff_2g = 0;
570 else
571 rtldm->swing_diff_5g = 0;
572 out = 0x200; /* 0 dB */
573 } else if (swing_b == 0x1) {
574 if (band == BAND_ON_2_4G)
575 rtldm->swing_diff_2g = -3;
576 else
577 rtldm->swing_diff_5g = -3;
578 out = 0x16A; /* -3 dB */
579 } else if (swing_b == 0x2) {
580 if (band == BAND_ON_2_4G)
581 rtldm->swing_diff_2g = -6;
582 else
583 rtldm->swing_diff_5g = -6;
584 out = 0x101; /* -6 dB */
585 } else if (swing_b == 0x3) {
586 if (band == BAND_ON_2_4G)
587 rtldm->swing_diff_2g = -9;
588 else
589 rtldm->swing_diff_5g = -9;
590 out = 0x0B6; /* -9 dB */
591 }
592 }
593
594 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD,
595 "<=== PHY_GetTXBBSwing_8812A, out = 0x%X\n", out);
596 return out;
597 }
598
599 void rtl8821ae_phy_switch_wirelessband(struct ieee80211_hw *hw, u8 band)
600 {
601 struct rtl_priv *rtlpriv = rtl_priv(hw);
602 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
603 struct rtl_dm *rtldm = rtl_dm(rtlpriv);
604 u8 current_band = rtlhal->current_bandtype;
605 u32 txpath, rxpath;
606 s8 bb_diff_between_band;
607
608 txpath = rtl8821ae_phy_query_bb_reg(hw, RTXPATH, 0xf0);
609 rxpath = rtl8821ae_phy_query_bb_reg(hw, RCCK_RX, 0x0f000000);
610 rtlhal->current_bandtype = (enum band_type) band;
611 /* reconfig BB/RF according to wireless mode */
612 if (rtlhal->current_bandtype == BAND_ON_2_4G) {
613 /* BB & RF Config */
614 rtl_set_bbreg(hw, ROFDMCCKEN, BOFDMEN|BCCKEN, 0x03);
615
616 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
617 /* 0xCB0[15:12] = 0x7 (LNA_On)*/
618 rtl_set_bbreg(hw, RA_RFE_PINMUX, 0xF000, 0x7);
619 /* 0xCB0[7:4] = 0x7 (PAPE_A)*/
620 rtl_set_bbreg(hw, RA_RFE_PINMUX, 0xF0, 0x7);
621 }
622
623 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
624 /*0x834[1:0] = 0x1*/
625 rtl_set_bbreg(hw, 0x834, 0x3, 0x1);
626 }
627
628 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
629 /* 0xC1C[11:8] = 0 */
630 rtl_set_bbreg(hw, RA_TXSCALE, 0xF00, 0);
631 } else {
632 /* 0x82C[1:0] = 2b'00 */
633 rtl_set_bbreg(hw, 0x82c, 0x3, 0);
634 }
635
636 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE)
637 _rtl8812ae_phy_set_rfe_reg_24g(hw);
638
639 rtl_set_bbreg(hw, RTXPATH, 0xf0, 0x1);
640 rtl_set_bbreg(hw, RCCK_RX, 0x0f000000, 0x1);
641
642 rtl_write_byte(rtlpriv, REG_CCK_CHECK, 0x0);
643 } else {/* 5G band */
644 u16 count, reg_41a;
645
646 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
647 /*0xCB0[15:12] = 0x5 (LNA_On)*/
648 rtl_set_bbreg(hw, RA_RFE_PINMUX, 0xF000, 0x5);
649 /*0xCB0[7:4] = 0x4 (PAPE_A)*/
650 rtl_set_bbreg(hw, RA_RFE_PINMUX, 0xF0, 0x4);
651 }
652 /*CCK_CHECK_en*/
653 rtl_write_byte(rtlpriv, REG_CCK_CHECK, 0x80);
654
655 count = 0;
656 reg_41a = rtl_read_word(rtlpriv, REG_TXPKT_EMPTY);
657 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD,
658 "Reg41A value %d\n", reg_41a);
659 reg_41a &= 0x30;
660 while ((reg_41a != 0x30) && (count < 50)) {
661 udelay(50);
662 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD, "Delay 50us\n");
663
664 reg_41a = rtl_read_word(rtlpriv, REG_TXPKT_EMPTY);
665 reg_41a &= 0x30;
666 count++;
667 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD,
668 "Reg41A value %d\n", reg_41a);
669 }
670 if (count != 0)
671 RT_TRACE(rtlpriv, COMP_MLME, DBG_LOUD,
672 "PHY_SwitchWirelessBand8812(): Switch to 5G Band. Count = %d reg41A=0x%x\n",
673 count, reg_41a);
674
675 /* 2012/02/01, Sinda add registry to switch workaround
676 without long-run verification for scan issue. */
677 rtl_set_bbreg(hw, ROFDMCCKEN, BOFDMEN|BCCKEN, 0x03);
678
679 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
680 /*0x834[1:0] = 0x2*/
681 rtl_set_bbreg(hw, 0x834, 0x3, 0x2);
682 }
683
684 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
685 /* AGC table select */
686 /* 0xC1C[11:8] = 1*/
687 rtl_set_bbreg(hw, RA_TXSCALE, 0xF00, 1);
688 } else
689 /* 0x82C[1:0] = 2'b00 */
690 rtl_set_bbreg(hw, 0x82c, 0x3, 1);
691
692 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE)
693 _rtl8812ae_phy_set_rfe_reg_5g(hw);
694
695 rtl_set_bbreg(hw, RTXPATH, 0xf0, 0);
696 rtl_set_bbreg(hw, RCCK_RX, 0x0f000000, 0xf);
697
698 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD,
699 "==>PHY_SwitchWirelessBand8812() BAND_ON_5G settings OFDM index 0x%x\n",
700 rtlpriv->dm.ofdm_index[RF90_PATH_A]);
701 }
702
703 if ((rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) ||
704 (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE)) {
705 /* 0xC1C[31:21] */
706 rtl_set_bbreg(hw, RA_TXSCALE, 0xFFE00000,
707 phy_get_tx_swing_8812A(hw, band, RF90_PATH_A));
708 /* 0xE1C[31:21] */
709 rtl_set_bbreg(hw, RB_TXSCALE, 0xFFE00000,
710 phy_get_tx_swing_8812A(hw, band, RF90_PATH_B));
711
712 /* <20121005, Kordan> When TxPowerTrack is ON,
713 * we should take care of the change of BB swing.
714 * That is, reset all info to trigger Tx power tracking.
715 */
716 if (band != current_band) {
717 bb_diff_between_band =
718 (rtldm->swing_diff_2g - rtldm->swing_diff_5g);
719 bb_diff_between_band = (band == BAND_ON_2_4G) ?
720 bb_diff_between_band :
721 (-1 * bb_diff_between_band);
722 rtldm->default_ofdm_index += bb_diff_between_band * 2;
723 }
724 rtl8821ae_dm_clear_txpower_tracking_state(hw);
725 }
726
727 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
728 "<==rtl8821ae_phy_switch_wirelessband():Switch Band OK.\n");
729 return;
730 }
731
732 static bool _rtl8821ae_check_positive(struct ieee80211_hw *hw,
733 const u32 condition1,
734 const u32 condition2)
735 {
736 struct rtl_priv *rtlpriv = rtl_priv(hw);
737 struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
738 u32 cut_ver = ((rtlhal->version & CHIP_VER_RTL_MASK)
739 >> CHIP_VER_RTL_SHIFT);
740 u32 intf = (rtlhal->interface == INTF_USB ? BIT(1) : BIT(0));
741
742 u8 board_type = ((rtlhal->board_type & BIT(4)) >> 4) << 0 | /* _GLNA */
743 ((rtlhal->board_type & BIT(3)) >> 3) << 1 | /* _GPA */
744 ((rtlhal->board_type & BIT(7)) >> 7) << 2 | /* _ALNA */
745 ((rtlhal->board_type & BIT(6)) >> 6) << 3 | /* _APA */
746 ((rtlhal->board_type & BIT(2)) >> 2) << 4; /* _BT */
747
748 u32 cond1 = condition1, cond2 = condition2;
749 u32 driver1 = cut_ver << 24 | /* CUT ver */
750 0 << 20 | /* interface 2/2 */
751 0x04 << 16 | /* platform */
752 rtlhal->package_type << 12 |
753 intf << 8 | /* interface 1/2 */
754 board_type;
755
756 u32 driver2 = rtlhal->type_glna << 0 |
757 rtlhal->type_gpa << 8 |
758 rtlhal->type_alna << 16 |
759 rtlhal->type_apa << 24;
760
761 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
762 "===> [8812A] CheckPositive (cond1, cond2) = (0x%X 0x%X)\n",
763 cond1, cond2);
764 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
765 "===> [8812A] CheckPositive (driver1, driver2) = (0x%X 0x%X)\n",
766 driver1, driver2);
767
768 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
769 " (Platform, Interface) = (0x%X, 0x%X)\n", 0x04, intf);
770 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
771 " (Board, Package) = (0x%X, 0x%X)\n",
772 rtlhal->board_type, rtlhal->package_type);
773
774 /*============== Value Defined Check ===============*/
775 /*QFN Type [15:12] and Cut Version [27:24] need to do value check*/
776
777 if (((cond1 & 0x0000F000) != 0) && ((cond1 & 0x0000F000) !=
778 (driver1 & 0x0000F000)))
779 return false;
780 if (((cond1 & 0x0F000000) != 0) && ((cond1 & 0x0F000000) !=
781 (driver1 & 0x0F000000)))
782 return false;
783
784 /*=============== Bit Defined Check ================*/
785 /* We don't care [31:28] */
786
787 cond1 &= 0x00FF0FFF;
788 driver1 &= 0x00FF0FFF;
789
790 if ((cond1 & driver1) == cond1) {
791 u32 mask = 0;
792
793 if ((cond1 & 0x0F) == 0) /* BoardType is DONTCARE*/
794 return true;
795
796 if ((cond1 & BIT(0)) != 0) /*GLNA*/
797 mask |= 0x000000FF;
798 if ((cond1 & BIT(1)) != 0) /*GPA*/
799 mask |= 0x0000FF00;
800 if ((cond1 & BIT(2)) != 0) /*ALNA*/
801 mask |= 0x00FF0000;
802 if ((cond1 & BIT(3)) != 0) /*APA*/
803 mask |= 0xFF000000;
804
805 /* BoardType of each RF path is matched*/
806 if ((cond2 & mask) == (driver2 & mask))
807 return true;
808 else
809 return false;
810 } else
811 return false;
812 }
813
814 static bool _rtl8821ae_check_condition(struct ieee80211_hw *hw,
815 const u32 condition)
816 {
817 struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
818 u32 _board = rtlefuse->board_type; /*need efuse define*/
819 u32 _interface = 0x01; /* ODM_ITRF_PCIE */
820 u32 _platform = 0x08;/* ODM_WIN */
821 u32 cond = condition;
822
823 if (condition == 0xCDCDCDCD)
824 return true;
825
826 cond = condition & 0xFF;
827 if ((_board != cond) && cond != 0xFF)
828 return false;
829
830 cond = condition & 0xFF00;
831 cond = cond >> 8;
832 if ((_interface & cond) == 0 && cond != 0x07)
833 return false;
834
835 cond = condition & 0xFF0000;
836 cond = cond >> 16;
837 if ((_platform & cond) == 0 && cond != 0x0F)
838 return false;
839 return true;
840 }
841
842 static void _rtl8821ae_config_rf_reg(struct ieee80211_hw *hw,
843 u32 addr, u32 data,
844 enum radio_path rfpath, u32 regaddr)
845 {
846 if (addr == 0xfe || addr == 0xffe) {
847 /* In order not to disturb BT music when
848 * wifi init.(1ant NIC only)
849 */
850 mdelay(50);
851 } else {
852 rtl_set_rfreg(hw, rfpath, regaddr, RFREG_OFFSET_MASK, data);
853 udelay(1);
854 }
855 }
856
857 static void _rtl8821ae_config_rf_radio_a(struct ieee80211_hw *hw,
858 u32 addr, u32 data)
859 {
860 u32 content = 0x1000; /*RF Content: radio_a_txt*/
861 u32 maskforphyset = (u32)(content & 0xE000);
862
863 _rtl8821ae_config_rf_reg(hw, addr, data,
864 RF90_PATH_A, addr | maskforphyset);
865 }
866
867 static void _rtl8821ae_config_rf_radio_b(struct ieee80211_hw *hw,
868 u32 addr, u32 data)
869 {
870 u32 content = 0x1001; /*RF Content: radio_b_txt*/
871 u32 maskforphyset = (u32)(content & 0xE000);
872
873 _rtl8821ae_config_rf_reg(hw, addr, data,
874 RF90_PATH_B, addr | maskforphyset);
875 }
876
877 static void _rtl8821ae_config_bb_reg(struct ieee80211_hw *hw,
878 u32 addr, u32 data)
879 {
880 if (addr == 0xfe)
881 mdelay(50);
882 else if (addr == 0xfd)
883 mdelay(5);
884 else if (addr == 0xfc)
885 mdelay(1);
886 else if (addr == 0xfb)
887 udelay(50);
888 else if (addr == 0xfa)
889 udelay(5);
890 else if (addr == 0xf9)
891 udelay(1);
892 else
893 rtl_set_bbreg(hw, addr, MASKDWORD, data);
894
895 udelay(1);
896 }
897
898 static void _rtl8821ae_phy_init_tx_power_by_rate(struct ieee80211_hw *hw)
899 {
900 struct rtl_priv *rtlpriv = rtl_priv(hw);
901 struct rtl_phy *rtlphy = &rtlpriv->phy;
902 u8 band, rfpath, txnum, rate_section;
903
904 for (band = BAND_ON_2_4G; band <= BAND_ON_5G; ++band)
905 for (rfpath = 0; rfpath < TX_PWR_BY_RATE_NUM_RF; ++rfpath)
906 for (txnum = 0; txnum < TX_PWR_BY_RATE_NUM_RF; ++txnum)
907 for (rate_section = 0;
908 rate_section < TX_PWR_BY_RATE_NUM_SECTION;
909 ++rate_section)
910 rtlphy->tx_power_by_rate_offset[band]
911 [rfpath][txnum][rate_section] = 0;
912 }
913
914 static void _rtl8821ae_phy_set_txpower_by_rate_base(struct ieee80211_hw *hw,
915 u8 band, u8 path,
916 u8 rate_section,
917 u8 txnum, u8 value)
918 {
919 struct rtl_priv *rtlpriv = rtl_priv(hw);
920 struct rtl_phy *rtlphy = &rtlpriv->phy;
921
922 if (path > RF90_PATH_D) {
923 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
924 "Invalid Rf Path %d in phy_SetTxPowerByRatBase()\n", path);
925 return;
926 }
927
928 if (band == BAND_ON_2_4G) {
929 switch (rate_section) {
930 case CCK:
931 rtlphy->txpwr_by_rate_base_24g[path][txnum][0] = value;
932 break;
933 case OFDM:
934 rtlphy->txpwr_by_rate_base_24g[path][txnum][1] = value;
935 break;
936 case HT_MCS0_MCS7:
937 rtlphy->txpwr_by_rate_base_24g[path][txnum][2] = value;
938 break;
939 case HT_MCS8_MCS15:
940 rtlphy->txpwr_by_rate_base_24g[path][txnum][3] = value;
941 break;
942 case VHT_1SSMCS0_1SSMCS9:
943 rtlphy->txpwr_by_rate_base_24g[path][txnum][4] = value;
944 break;
945 case VHT_2SSMCS0_2SSMCS9:
946 rtlphy->txpwr_by_rate_base_24g[path][txnum][5] = value;
947 break;
948 default:
949 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
950 "Invalid RateSection %d in Band 2.4G,Rf Path %d, %dTx in PHY_SetTxPowerByRateBase()\n",
951 rate_section, path, txnum);
952 break;
953 }
954 } else if (band == BAND_ON_5G) {
955 switch (rate_section) {
956 case OFDM:
957 rtlphy->txpwr_by_rate_base_5g[path][txnum][0] = value;
958 break;
959 case HT_MCS0_MCS7:
960 rtlphy->txpwr_by_rate_base_5g[path][txnum][1] = value;
961 break;
962 case HT_MCS8_MCS15:
963 rtlphy->txpwr_by_rate_base_5g[path][txnum][2] = value;
964 break;
965 case VHT_1SSMCS0_1SSMCS9:
966 rtlphy->txpwr_by_rate_base_5g[path][txnum][3] = value;
967 break;
968 case VHT_2SSMCS0_2SSMCS9:
969 rtlphy->txpwr_by_rate_base_5g[path][txnum][4] = value;
970 break;
971 default:
972 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
973 "Invalid RateSection %d in Band 5G, Rf Path %d, %dTx in PHY_SetTxPowerByRateBase()\n",
974 rate_section, path, txnum);
975 break;
976 }
977 } else {
978 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
979 "Invalid Band %d in PHY_SetTxPowerByRateBase()\n", band);
980 }
981 }
982
983 static u8 _rtl8821ae_phy_get_txpower_by_rate_base(struct ieee80211_hw *hw,
984 u8 band, u8 path,
985 u8 txnum, u8 rate_section)
986 {
987 struct rtl_priv *rtlpriv = rtl_priv(hw);
988 struct rtl_phy *rtlphy = &rtlpriv->phy;
989 u8 value = 0;
990
991 if (path > RF90_PATH_D) {
992 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
993 "Invalid Rf Path %d in PHY_GetTxPowerByRateBase()\n",
994 path);
995 return 0;
996 }
997
998 if (band == BAND_ON_2_4G) {
999 switch (rate_section) {
1000 case CCK:
1001 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][0];
1002 break;
1003 case OFDM:
1004 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][1];
1005 break;
1006 case HT_MCS0_MCS7:
1007 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][2];
1008 break;
1009 case HT_MCS8_MCS15:
1010 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][3];
1011 break;
1012 case VHT_1SSMCS0_1SSMCS9:
1013 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][4];
1014 break;
1015 case VHT_2SSMCS0_2SSMCS9:
1016 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][5];
1017 break;
1018 default:
1019 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1020 "Invalid RateSection %d in Band 2.4G, Rf Path %d, %dTx in PHY_GetTxPowerByRateBase()\n",
1021 rate_section, path, txnum);
1022 break;
1023 }
1024 } else if (band == BAND_ON_5G) {
1025 switch (rate_section) {
1026 case OFDM:
1027 value = rtlphy->txpwr_by_rate_base_5g[path][txnum][0];
1028 break;
1029 case HT_MCS0_MCS7:
1030 value = rtlphy->txpwr_by_rate_base_5g[path][txnum][1];
1031 break;
1032 case HT_MCS8_MCS15:
1033 value = rtlphy->txpwr_by_rate_base_5g[path][txnum][2];
1034 break;
1035 case VHT_1SSMCS0_1SSMCS9:
1036 value = rtlphy->txpwr_by_rate_base_5g[path][txnum][3];
1037 break;
1038 case VHT_2SSMCS0_2SSMCS9:
1039 value = rtlphy->txpwr_by_rate_base_5g[path][txnum][4];
1040 break;
1041 default:
1042 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1043 "Invalid RateSection %d in Band 5G, Rf Path %d, %dTx in PHY_GetTxPowerByRateBase()\n",
1044 rate_section, path, txnum);
1045 break;
1046 }
1047 } else {
1048 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1049 "Invalid Band %d in PHY_GetTxPowerByRateBase()\n", band);
1050 }
1051
1052 return value;
1053 }
1054
1055 static void _rtl8821ae_phy_store_txpower_by_rate_base(struct ieee80211_hw *hw)
1056 {
1057 struct rtl_priv *rtlpriv = rtl_priv(hw);
1058 struct rtl_phy *rtlphy = &rtlpriv->phy;
1059 u16 rawvalue = 0;
1060 u8 base = 0, path = 0;
1061
1062 for (path = RF90_PATH_A; path <= RF90_PATH_B; ++path) {
1063 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][path][RF_1TX][0] >> 24) & 0xFF;
1064 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1065 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G, path, CCK, RF_1TX, base);
1066
1067 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][path][RF_1TX][2] >> 24) & 0xFF;
1068 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1069 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G, path, OFDM, RF_1TX, base);
1070
1071 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][path][RF_1TX][4] >> 24) & 0xFF;
1072 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1073 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G, path, HT_MCS0_MCS7, RF_1TX, base);
1074
1075 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][path][RF_2TX][6] >> 24) & 0xFF;
1076 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1077 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G, path, HT_MCS8_MCS15, RF_2TX, base);
1078
1079 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][path][RF_1TX][8] >> 24) & 0xFF;
1080 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1081 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G, path, VHT_1SSMCS0_1SSMCS9, RF_1TX, base);
1082
1083 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][path][RF_2TX][11] >> 8) & 0xFF;
1084 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1085 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G, path, VHT_2SSMCS0_2SSMCS9, RF_2TX, base);
1086
1087 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_5G][path][RF_1TX][2] >> 24) & 0xFF;
1088 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1089 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_5G, path, OFDM, RF_1TX, base);
1090
1091 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_5G][path][RF_1TX][4] >> 24) & 0xFF;
1092 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1093 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_5G, path, HT_MCS0_MCS7, RF_1TX, base);
1094
1095 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_5G][path][RF_2TX][6] >> 24) & 0xFF;
1096 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1097 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_5G, path, HT_MCS8_MCS15, RF_2TX, base);
1098
1099 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_5G][path][RF_1TX][8] >> 24) & 0xFF;
1100 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1101 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_5G, path, VHT_1SSMCS0_1SSMCS9, RF_1TX, base);
1102
1103 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset[BAND_ON_5G][path][RF_2TX][11] >> 8) & 0xFF;
1104 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
1105 _rtl8821ae_phy_set_txpower_by_rate_base(hw, BAND_ON_5G, path, VHT_2SSMCS0_2SSMCS9, RF_2TX, base);
1106 }
1107 }
1108
1109 static void _phy_convert_txpower_dbm_to_relative_value(u32 *data, u8 start,
1110 u8 end, u8 base_val)
1111 {
1112 int i;
1113 u8 temp_value = 0;
1114 u32 temp_data = 0;
1115
1116 for (i = 3; i >= 0; --i) {
1117 if (i >= start && i <= end) {
1118 /* Get the exact value */
1119 temp_value = (u8)(*data >> (i * 8)) & 0xF;
1120 temp_value += ((u8)((*data >> (i * 8 + 4)) & 0xF)) * 10;
1121
1122 /* Change the value to a relative value */
1123 temp_value = (temp_value > base_val) ? temp_value -
1124 base_val : base_val - temp_value;
1125 } else {
1126 temp_value = (u8)(*data >> (i * 8)) & 0xFF;
1127 }
1128 temp_data <<= 8;
1129 temp_data |= temp_value;
1130 }
1131 *data = temp_data;
1132 }
1133
1134 static void _rtl8812ae_phy_cross_reference_ht_and_vht_txpower_limit(struct ieee80211_hw *hw)
1135 {
1136 struct rtl_priv *rtlpriv = rtl_priv(hw);
1137 struct rtl_phy *rtlphy = &rtlpriv->phy;
1138 u8 regulation, bw, channel, rate_section;
1139 s8 temp_pwrlmt = 0;
1140
1141 for (regulation = 0; regulation < MAX_REGULATION_NUM; ++regulation) {
1142 for (bw = 0; bw < MAX_5G_BANDWIDTH_NUM; ++bw) {
1143 for (channel = 0; channel < CHANNEL_MAX_NUMBER_5G; ++channel) {
1144 for (rate_section = 0; rate_section < MAX_RATE_SECTION_NUM; ++rate_section) {
1145 temp_pwrlmt = rtlphy->txpwr_limit_5g[regulation]
1146 [bw][rate_section][channel][RF90_PATH_A];
1147 if (temp_pwrlmt == MAX_POWER_INDEX) {
1148 if (bw == 0 || bw == 1) { /*5G 20M 40M VHT and HT can cross reference*/
1149 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1150 "No power limit table of the specified band %d, bandwidth %d, ratesection %d, channel %d, rf path %d\n",
1151 1, bw, rate_section, channel, RF90_PATH_A);
1152 if (rate_section == 2) {
1153 rtlphy->txpwr_limit_5g[regulation][bw][2][channel][RF90_PATH_A] =
1154 rtlphy->txpwr_limit_5g[regulation][bw][4][channel][RF90_PATH_A];
1155 } else if (rate_section == 4) {
1156 rtlphy->txpwr_limit_5g[regulation][bw][4][channel][RF90_PATH_A] =
1157 rtlphy->txpwr_limit_5g[regulation][bw][2][channel][RF90_PATH_A];
1158 } else if (rate_section == 3) {
1159 rtlphy->txpwr_limit_5g[regulation][bw][3][channel][RF90_PATH_A] =
1160 rtlphy->txpwr_limit_5g[regulation][bw][5][channel][RF90_PATH_A];
1161 } else if (rate_section == 5) {
1162 rtlphy->txpwr_limit_5g[regulation][bw][5][channel][RF90_PATH_A] =
1163 rtlphy->txpwr_limit_5g[regulation][bw][3][channel][RF90_PATH_A];
1164 }
1165
1166 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE, "use other value %d\n", temp_pwrlmt);
1167 }
1168 }
1169 }
1170 }
1171 }
1172 }
1173 }
1174
1175 static u8 _rtl8812ae_phy_get_txpower_by_rate_base_index(struct ieee80211_hw *hw,
1176 enum band_type band, u8 rate)
1177 {
1178 struct rtl_priv *rtlpriv = rtl_priv(hw);
1179 u8 index = 0;
1180 if (band == BAND_ON_2_4G) {
1181 switch (rate) {
1182 case MGN_1M:
1183 case MGN_2M:
1184 case MGN_5_5M:
1185 case MGN_11M:
1186 index = 0;
1187 break;
1188
1189 case MGN_6M:
1190 case MGN_9M:
1191 case MGN_12M:
1192 case MGN_18M:
1193 case MGN_24M:
1194 case MGN_36M:
1195 case MGN_48M:
1196 case MGN_54M:
1197 index = 1;
1198 break;
1199
1200 case MGN_MCS0:
1201 case MGN_MCS1:
1202 case MGN_MCS2:
1203 case MGN_MCS3:
1204 case MGN_MCS4:
1205 case MGN_MCS5:
1206 case MGN_MCS6:
1207 case MGN_MCS7:
1208 index = 2;
1209 break;
1210
1211 case MGN_MCS8:
1212 case MGN_MCS9:
1213 case MGN_MCS10:
1214 case MGN_MCS11:
1215 case MGN_MCS12:
1216 case MGN_MCS13:
1217 case MGN_MCS14:
1218 case MGN_MCS15:
1219 index = 3;
1220 break;
1221
1222 default:
1223 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1224 "Wrong rate 0x%x to obtain index in 2.4G in PHY_GetTxPowerByRateBaseIndex()\n",
1225 rate);
1226 break;
1227 }
1228 } else if (band == BAND_ON_5G) {
1229 switch (rate) {
1230 case MGN_6M:
1231 case MGN_9M:
1232 case MGN_12M:
1233 case MGN_18M:
1234 case MGN_24M:
1235 case MGN_36M:
1236 case MGN_48M:
1237 case MGN_54M:
1238 index = 0;
1239 break;
1240
1241 case MGN_MCS0:
1242 case MGN_MCS1:
1243 case MGN_MCS2:
1244 case MGN_MCS3:
1245 case MGN_MCS4:
1246 case MGN_MCS5:
1247 case MGN_MCS6:
1248 case MGN_MCS7:
1249 index = 1;
1250 break;
1251
1252 case MGN_MCS8:
1253 case MGN_MCS9:
1254 case MGN_MCS10:
1255 case MGN_MCS11:
1256 case MGN_MCS12:
1257 case MGN_MCS13:
1258 case MGN_MCS14:
1259 case MGN_MCS15:
1260 index = 2;
1261 break;
1262
1263 case MGN_VHT1SS_MCS0:
1264 case MGN_VHT1SS_MCS1:
1265 case MGN_VHT1SS_MCS2:
1266 case MGN_VHT1SS_MCS3:
1267 case MGN_VHT1SS_MCS4:
1268 case MGN_VHT1SS_MCS5:
1269 case MGN_VHT1SS_MCS6:
1270 case MGN_VHT1SS_MCS7:
1271 case MGN_VHT1SS_MCS8:
1272 case MGN_VHT1SS_MCS9:
1273 index = 3;
1274 break;
1275
1276 case MGN_VHT2SS_MCS0:
1277 case MGN_VHT2SS_MCS1:
1278 case MGN_VHT2SS_MCS2:
1279 case MGN_VHT2SS_MCS3:
1280 case MGN_VHT2SS_MCS4:
1281 case MGN_VHT2SS_MCS5:
1282 case MGN_VHT2SS_MCS6:
1283 case MGN_VHT2SS_MCS7:
1284 case MGN_VHT2SS_MCS8:
1285 case MGN_VHT2SS_MCS9:
1286 index = 4;
1287 break;
1288
1289 default:
1290 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1291 "Wrong rate 0x%x to obtain index in 5G in PHY_GetTxPowerByRateBaseIndex()\n",
1292 rate);
1293 break;
1294 }
1295 }
1296
1297 return index;
1298 }
1299
1300 static void _rtl8812ae_phy_convert_txpower_limit_to_power_index(struct ieee80211_hw *hw)
1301 {
1302 struct rtl_priv *rtlpriv = rtl_priv(hw);
1303 struct rtl_phy *rtlphy = &rtlpriv->phy;
1304 u8 bw40_pwr_base_dbm2_4G, bw40_pwr_base_dbm5G;
1305 u8 regulation, bw, channel, rate_section;
1306 u8 base_index2_4G = 0;
1307 u8 base_index5G = 0;
1308 s8 temp_value = 0, temp_pwrlmt = 0;
1309 u8 rf_path = 0;
1310
1311 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1312 "=====> _rtl8812ae_phy_convert_txpower_limit_to_power_index()\n");
1313
1314 _rtl8812ae_phy_cross_reference_ht_and_vht_txpower_limit(hw);
1315
1316 for (regulation = 0; regulation < MAX_REGULATION_NUM; ++regulation) {
1317 for (bw = 0; bw < MAX_2_4G_BANDWIDTH_NUM; ++bw) {
1318 for (channel = 0; channel < CHANNEL_MAX_NUMBER_2G; ++channel) {
1319 for (rate_section = 0; rate_section < MAX_RATE_SECTION_NUM; ++rate_section) {
1320 /* obtain the base dBm values in 2.4G band
1321 CCK => 11M, OFDM => 54M, HT 1T => MCS7, HT 2T => MCS15*/
1322 if (rate_section == 0) { /*CCK*/
1323 base_index2_4G =
1324 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1325 BAND_ON_2_4G, MGN_11M);
1326 } else if (rate_section == 1) { /*OFDM*/
1327 base_index2_4G =
1328 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1329 BAND_ON_2_4G, MGN_54M);
1330 } else if (rate_section == 2) { /*HT IT*/
1331 base_index2_4G =
1332 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1333 BAND_ON_2_4G, MGN_MCS7);
1334 } else if (rate_section == 3) { /*HT 2T*/
1335 base_index2_4G =
1336 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1337 BAND_ON_2_4G, MGN_MCS15);
1338 }
1339
1340 temp_pwrlmt = rtlphy->txpwr_limit_2_4g[regulation]
1341 [bw][rate_section][channel][RF90_PATH_A];
1342
1343 for (rf_path = RF90_PATH_A;
1344 rf_path < MAX_RF_PATH_NUM;
1345 ++rf_path) {
1346 if (rate_section == 3)
1347 bw40_pwr_base_dbm2_4G =
1348 rtlphy->txpwr_by_rate_base_24g[rf_path][RF_2TX][base_index2_4G];
1349 else
1350 bw40_pwr_base_dbm2_4G =
1351 rtlphy->txpwr_by_rate_base_24g[rf_path][RF_1TX][base_index2_4G];
1352
1353 if (temp_pwrlmt != MAX_POWER_INDEX) {
1354 temp_value = temp_pwrlmt - bw40_pwr_base_dbm2_4G;
1355 rtlphy->txpwr_limit_2_4g[regulation]
1356 [bw][rate_section][channel][rf_path] =
1357 temp_value;
1358 }
1359
1360 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1361 "TxPwrLimit_2_4G[regulation %d][bw %d][rateSection %d][channel %d] = %d\n(TxPwrLimit in dBm %d - BW40PwrLmt2_4G[channel %d][rfpath %d] %d)\n",
1362 regulation, bw, rate_section, channel,
1363 rtlphy->txpwr_limit_2_4g[regulation][bw]
1364 [rate_section][channel][rf_path], (temp_pwrlmt == 63)
1365 ? 0 : temp_pwrlmt/2, channel, rf_path,
1366 bw40_pwr_base_dbm2_4G);
1367 }
1368 }
1369 }
1370 }
1371 }
1372 for (regulation = 0; regulation < MAX_REGULATION_NUM; ++regulation) {
1373 for (bw = 0; bw < MAX_5G_BANDWIDTH_NUM; ++bw) {
1374 for (channel = 0; channel < CHANNEL_MAX_NUMBER_5G; ++channel) {
1375 for (rate_section = 0; rate_section < MAX_RATE_SECTION_NUM; ++rate_section) {
1376 /* obtain the base dBm values in 5G band
1377 OFDM => 54M, HT 1T => MCS7, HT 2T => MCS15,
1378 VHT => 1SSMCS7, VHT 2T => 2SSMCS7*/
1379 if (rate_section == 1) { /*OFDM*/
1380 base_index5G =
1381 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1382 BAND_ON_5G, MGN_54M);
1383 } else if (rate_section == 2) { /*HT 1T*/
1384 base_index5G =
1385 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1386 BAND_ON_5G, MGN_MCS7);
1387 } else if (rate_section == 3) { /*HT 2T*/
1388 base_index5G =
1389 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1390 BAND_ON_5G, MGN_MCS15);
1391 } else if (rate_section == 4) { /*VHT 1T*/
1392 base_index5G =
1393 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1394 BAND_ON_5G, MGN_VHT1SS_MCS7);
1395 } else if (rate_section == 5) { /*VHT 2T*/
1396 base_index5G =
1397 _rtl8812ae_phy_get_txpower_by_rate_base_index(hw,
1398 BAND_ON_5G, MGN_VHT2SS_MCS7);
1399 }
1400
1401 temp_pwrlmt = rtlphy->txpwr_limit_5g[regulation]
1402 [bw][rate_section][channel]
1403 [RF90_PATH_A];
1404
1405 for (rf_path = RF90_PATH_A;
1406 rf_path < MAX_RF_PATH_NUM;
1407 ++rf_path) {
1408 if (rate_section == 3 || rate_section == 5)
1409 bw40_pwr_base_dbm5G =
1410 rtlphy->txpwr_by_rate_base_5g[rf_path]
1411 [RF_2TX][base_index5G];
1412 else
1413 bw40_pwr_base_dbm5G =
1414 rtlphy->txpwr_by_rate_base_5g[rf_path]
1415 [RF_1TX][base_index5G];
1416
1417 if (temp_pwrlmt != MAX_POWER_INDEX) {
1418 temp_value =
1419 temp_pwrlmt - bw40_pwr_base_dbm5G;
1420 rtlphy->txpwr_limit_5g[regulation]
1421 [bw][rate_section][channel]
1422 [rf_path] = temp_value;
1423 }
1424
1425 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1426 "TxPwrLimit_5G[regulation %d][bw %d][rateSection %d][channel %d] =%d\n(TxPwrLimit in dBm %d - BW40PwrLmt5G[chnl group %d][rfpath %d] %d)\n",
1427 regulation, bw, rate_section,
1428 channel, rtlphy->txpwr_limit_5g[regulation]
1429 [bw][rate_section][channel][rf_path],
1430 temp_pwrlmt, channel, rf_path, bw40_pwr_base_dbm5G);
1431 }
1432 }
1433 }
1434 }
1435 }
1436 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1437 "<===== _rtl8812ae_phy_convert_txpower_limit_to_power_index()\n");
1438 }
1439
1440 static void _rtl8821ae_phy_init_txpower_limit(struct ieee80211_hw *hw)
1441 {
1442 struct rtl_priv *rtlpriv = rtl_priv(hw);
1443 struct rtl_phy *rtlphy = &rtlpriv->phy;
1444 u8 i, j, k, l, m;
1445
1446 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1447 "=====> _rtl8821ae_phy_init_txpower_limit()!\n");
1448
1449 for (i = 0; i < MAX_REGULATION_NUM; ++i) {
1450 for (j = 0; j < MAX_2_4G_BANDWIDTH_NUM; ++j)
1451 for (k = 0; k < MAX_RATE_SECTION_NUM; ++k)
1452 for (m = 0; m < CHANNEL_MAX_NUMBER_2G; ++m)
1453 for (l = 0; l < MAX_RF_PATH_NUM; ++l)
1454 rtlphy->txpwr_limit_2_4g
1455 [i][j][k][m][l]
1456 = MAX_POWER_INDEX;
1457 }
1458 for (i = 0; i < MAX_REGULATION_NUM; ++i) {
1459 for (j = 0; j < MAX_5G_BANDWIDTH_NUM; ++j)
1460 for (k = 0; k < MAX_RATE_SECTION_NUM; ++k)
1461 for (m = 0; m < CHANNEL_MAX_NUMBER_5G; ++m)
1462 for (l = 0; l < MAX_RF_PATH_NUM; ++l)
1463 rtlphy->txpwr_limit_5g
1464 [i][j][k][m][l]
1465 = MAX_POWER_INDEX;
1466 }
1467
1468 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1469 "<===== _rtl8821ae_phy_init_txpower_limit()!\n");
1470 }
1471
1472 static void _rtl8821ae_phy_convert_txpower_dbm_to_relative_value(struct ieee80211_hw *hw)
1473 {
1474 struct rtl_priv *rtlpriv = rtl_priv(hw);
1475 struct rtl_phy *rtlphy = &rtlpriv->phy;
1476 u8 base = 0, rfpath = 0;
1477
1478 for (rfpath = RF90_PATH_A; rfpath <= RF90_PATH_B; ++rfpath) {
1479 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath, RF_1TX, CCK);
1480 _phy_convert_txpower_dbm_to_relative_value(
1481 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][0],
1482 0, 3, base);
1483
1484 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath, RF_1TX, OFDM);
1485 _phy_convert_txpower_dbm_to_relative_value(
1486 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][1],
1487 0, 3, base);
1488 _phy_convert_txpower_dbm_to_relative_value(
1489 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][2],
1490 0, 3, base);
1491
1492 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath, RF_1TX, HT_MCS0_MCS7);
1493 _phy_convert_txpower_dbm_to_relative_value(
1494 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][3],
1495 0, 3, base);
1496 _phy_convert_txpower_dbm_to_relative_value(
1497 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][4],
1498 0, 3, base);
1499
1500 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath, RF_2TX, HT_MCS8_MCS15);
1501
1502 _phy_convert_txpower_dbm_to_relative_value(
1503 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][5],
1504 0, 3, base);
1505
1506 _phy_convert_txpower_dbm_to_relative_value(
1507 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][6],
1508 0, 3, base);
1509
1510 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath, RF_1TX, VHT_1SSMCS0_1SSMCS9);
1511 _phy_convert_txpower_dbm_to_relative_value(
1512 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][7],
1513 0, 3, base);
1514 _phy_convert_txpower_dbm_to_relative_value(
1515 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][8],
1516 0, 3, base);
1517 _phy_convert_txpower_dbm_to_relative_value(
1518 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][9],
1519 0, 1, base);
1520
1521 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath, RF_2TX, VHT_2SSMCS0_2SSMCS9);
1522 _phy_convert_txpower_dbm_to_relative_value(
1523 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][9],
1524 2, 3, base);
1525 _phy_convert_txpower_dbm_to_relative_value(
1526 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][10],
1527 0, 3, base);
1528 _phy_convert_txpower_dbm_to_relative_value(
1529 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][11],
1530 0, 3, base);
1531
1532 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_5G, rfpath, RF_1TX, OFDM);
1533 _phy_convert_txpower_dbm_to_relative_value(
1534 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][1],
1535 0, 3, base);
1536 _phy_convert_txpower_dbm_to_relative_value(
1537 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][2],
1538 0, 3, base);
1539
1540 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_5G, rfpath, RF_1TX, HT_MCS0_MCS7);
1541 _phy_convert_txpower_dbm_to_relative_value(
1542 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][3],
1543 0, 3, base);
1544 _phy_convert_txpower_dbm_to_relative_value(
1545 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][4],
1546 0, 3, base);
1547
1548 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_5G, rfpath, RF_2TX, HT_MCS8_MCS15);
1549 _phy_convert_txpower_dbm_to_relative_value(
1550 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_2TX][5],
1551 0, 3, base);
1552 _phy_convert_txpower_dbm_to_relative_value(
1553 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_2TX][6],
1554 0, 3, base);
1555
1556 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_5G, rfpath, RF_1TX, VHT_1SSMCS0_1SSMCS9);
1557 _phy_convert_txpower_dbm_to_relative_value(
1558 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][7],
1559 0, 3, base);
1560 _phy_convert_txpower_dbm_to_relative_value(
1561 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][8],
1562 0, 3, base);
1563 _phy_convert_txpower_dbm_to_relative_value(
1564 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][9],
1565 0, 1, base);
1566
1567 base = _rtl8821ae_phy_get_txpower_by_rate_base(hw, BAND_ON_5G, rfpath, RF_2TX, VHT_2SSMCS0_2SSMCS9);
1568 _phy_convert_txpower_dbm_to_relative_value(
1569 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_1TX][9],
1570 2, 3, base);
1571 _phy_convert_txpower_dbm_to_relative_value(
1572 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_2TX][10],
1573 0, 3, base);
1574 _phy_convert_txpower_dbm_to_relative_value(
1575 &rtlphy->tx_power_by_rate_offset[BAND_ON_5G][rfpath][RF_2TX][11],
1576 0, 3, base);
1577 }
1578
1579 RT_TRACE(rtlpriv, COMP_POWER, DBG_TRACE,
1580 "<===_rtl8821ae_phy_convert_txpower_dbm_to_relative_value()\n");
1581 }
1582
1583 static void _rtl8821ae_phy_txpower_by_rate_configuration(struct ieee80211_hw *hw)
1584 {
1585 _rtl8821ae_phy_store_txpower_by_rate_base(hw);
1586 _rtl8821ae_phy_convert_txpower_dbm_to_relative_value(hw);
1587 }
1588
1589 /* string is in decimal */
1590 static bool _rtl8812ae_get_integer_from_string(char *str, u8 *pint)
1591 {
1592 u16 i = 0;
1593 *pint = 0;
1594
1595 while (str[i] != '\0') {
1596 if (str[i] >= '0' && str[i] <= '9') {
1597 *pint *= 10;
1598 *pint += (str[i] - '0');
1599 } else {
1600 return false;
1601 }
1602 ++i;
1603 }
1604
1605 return true;
1606 }
1607
1608 static bool _rtl8812ae_eq_n_byte(u8 *str1, u8 *str2, u32 num)
1609 {
1610 if (num == 0)
1611 return false;
1612 while (num > 0) {
1613 num--;
1614 if (str1[num] != str2[num])
1615 return false;
1616 }
1617 return true;
1618 }
1619
1620 static s8 _rtl8812ae_phy_get_chnl_idx_of_txpwr_lmt(struct ieee80211_hw *hw,
1621 u8 band, u8 channel)
1622 {
1623 struct rtl_priv *rtlpriv = rtl_priv(hw);
1624 s8 channel_index = -1;
1625 u8 i = 0;
1626
1627 if (band == BAND_ON_2_4G)
1628 channel_index = channel - 1;
1629 else if (band == BAND_ON_5G) {
1630 for (i = 0; i < sizeof(channel5g)/sizeof(u8); ++i) {
1631 if (channel5g[i] == channel)
1632 channel_index = i;
1633 }
1634 } else
1635 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD, "Invalid Band %d in %s\n",
1636 band, __func__);
1637
1638 if (channel_index == -1)
1639 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD,
1640 "Invalid Channel %d of Band %d in %s\n", channel,
1641 band, __func__);
1642
1643 return channel_index;
1644 }
1645
1646 static void _rtl8812ae_phy_set_txpower_limit(struct ieee80211_hw *hw, u8 *pregulation,
1647 u8 *pband, u8 *pbandwidth,
1648 u8 *prate_section, u8 *prf_path,
1649 u8 *pchannel, u8 *ppower_limit)
1650 {
1651 struct rtl_priv *rtlpriv = rtl_priv(hw);
1652 struct rtl_phy *rtlphy = &rtlpriv->phy;
1653 u8 regulation = 0, bandwidth = 0, rate_section = 0, channel;
1654 u8 channel_index;
1655 s8 power_limit = 0, prev_power_limit, ret;
1656
1657 if (!_rtl8812ae_get_integer_from_string((char *)pchannel, &channel) ||
1658 !_rtl8812ae_get_integer_from_string((char *)ppower_limit,
1659 &power_limit)) {
1660 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1661 "Illegal index of pwr_lmt table [chnl %d][val %d]\n",
1662 channel, power_limit);
1663 }
1664
1665 power_limit = power_limit > MAX_POWER_INDEX ?
1666 MAX_POWER_INDEX : power_limit;
1667
1668 if (_rtl8812ae_eq_n_byte(pregulation, (u8 *)("FCC"), 3))
1669 regulation = 0;
1670 else if (_rtl8812ae_eq_n_byte(pregulation, (u8 *)("MKK"), 3))
1671 regulation = 1;
1672 else if (_rtl8812ae_eq_n_byte(pregulation, (u8 *)("ETSI"), 4))
1673 regulation = 2;
1674 else if (_rtl8812ae_eq_n_byte(pregulation, (u8 *)("WW13"), 4))
1675 regulation = 3;
1676
1677 if (_rtl8812ae_eq_n_byte(prate_section, (u8 *)("CCK"), 3))
1678 rate_section = 0;
1679 else if (_rtl8812ae_eq_n_byte(prate_section, (u8 *)("OFDM"), 4))
1680 rate_section = 1;
1681 else if (_rtl8812ae_eq_n_byte(prate_section, (u8 *)("HT"), 2) &&
1682 _rtl8812ae_eq_n_byte(prf_path, (u8 *)("1T"), 2))
1683 rate_section = 2;
1684 else if (_rtl8812ae_eq_n_byte(prate_section, (u8 *)("HT"), 2) &&
1685 _rtl8812ae_eq_n_byte(prf_path, (u8 *)("2T"), 2))
1686 rate_section = 3;
1687 else if (_rtl8812ae_eq_n_byte(prate_section, (u8 *)("VHT"), 3) &&
1688 _rtl8812ae_eq_n_byte(prf_path, (u8 *)("1T"), 2))
1689 rate_section = 4;
1690 else if (_rtl8812ae_eq_n_byte(prate_section, (u8 *)("VHT"), 3) &&
1691 _rtl8812ae_eq_n_byte(prf_path, (u8 *)("2T"), 2))
1692 rate_section = 5;
1693
1694 if (_rtl8812ae_eq_n_byte(pbandwidth, (u8 *)("20M"), 3))
1695 bandwidth = 0;
1696 else if (_rtl8812ae_eq_n_byte(pbandwidth, (u8 *)("40M"), 3))
1697 bandwidth = 1;
1698 else if (_rtl8812ae_eq_n_byte(pbandwidth, (u8 *)("80M"), 3))
1699 bandwidth = 2;
1700 else if (_rtl8812ae_eq_n_byte(pbandwidth, (u8 *)("160M"), 4))
1701 bandwidth = 3;
1702
1703 if (_rtl8812ae_eq_n_byte(pband, (u8 *)("2.4G"), 4)) {
1704 ret = _rtl8812ae_phy_get_chnl_idx_of_txpwr_lmt(hw,
1705 BAND_ON_2_4G,
1706 channel);
1707
1708 if (ret == -1)
1709 return;
1710
1711 channel_index = ret;
1712
1713 prev_power_limit = rtlphy->txpwr_limit_2_4g[regulation]
1714 [bandwidth][rate_section]
1715 [channel_index][RF90_PATH_A];
1716
1717 if (power_limit < prev_power_limit)
1718 rtlphy->txpwr_limit_2_4g[regulation][bandwidth]
1719 [rate_section][channel_index][RF90_PATH_A] =
1720 power_limit;
1721
1722 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1723 "2.4G [regula %d][bw %d][sec %d][chnl %d][val %d]\n",
1724 regulation, bandwidth, rate_section, channel_index,
1725 rtlphy->txpwr_limit_2_4g[regulation][bandwidth]
1726 [rate_section][channel_index][RF90_PATH_A]);
1727 } else if (_rtl8812ae_eq_n_byte(pband, (u8 *)("5G"), 2)) {
1728 ret = _rtl8812ae_phy_get_chnl_idx_of_txpwr_lmt(hw,
1729 BAND_ON_5G,
1730 channel);
1731
1732 if (ret == -1)
1733 return;
1734
1735 channel_index = ret;
1736
1737 prev_power_limit = rtlphy->txpwr_limit_5g[regulation][bandwidth]
1738 [rate_section][channel_index]
1739 [RF90_PATH_A];
1740
1741 if (power_limit < prev_power_limit)
1742 rtlphy->txpwr_limit_5g[regulation][bandwidth]
1743 [rate_section][channel_index][RF90_PATH_A] = power_limit;
1744
1745 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1746 "5G: [regul %d][bw %d][sec %d][chnl %d][val %d]\n",
1747 regulation, bandwidth, rate_section, channel,
1748 rtlphy->txpwr_limit_5g[regulation][bandwidth]
1749 [rate_section][channel_index][RF90_PATH_A]);
1750 } else {
1751 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1752 "Cannot recognize the band info in %s\n", pband);
1753 return;
1754 }
1755 }
1756
1757 static void _rtl8812ae_phy_config_bb_txpwr_lmt(struct ieee80211_hw *hw,
1758 u8 *regulation, u8 *band,
1759 u8 *bandwidth, u8 *rate_section,
1760 u8 *rf_path, u8 *channel,
1761 u8 *power_limit)
1762 {
1763 _rtl8812ae_phy_set_txpower_limit(hw, regulation, band, bandwidth,
1764 rate_section, rf_path, channel,
1765 power_limit);
1766 }
1767
1768 static void _rtl8821ae_phy_read_and_config_txpwr_lmt(struct ieee80211_hw *hw)
1769 {
1770 struct rtl_priv *rtlpriv = rtl_priv(hw);
1771 struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
1772 u32 i = 0;
1773 u32 array_len;
1774 u8 **array;
1775
1776 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
1777 array_len = RTL8812AE_TXPWR_LMT_ARRAY_LEN;
1778 array = RTL8812AE_TXPWR_LMT;
1779 } else {
1780 array_len = RTL8821AE_TXPWR_LMT_ARRAY_LEN;
1781 array = RTL8821AE_TXPWR_LMT;
1782 }
1783
1784 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
1785 "\n");
1786
1787 for (i = 0; i < array_len; i += 7) {
1788 u8 *regulation = array[i];
1789 u8 *band = array[i+1];
1790 u8 *bandwidth = array[i+2];
1791 u8 *rate = array[i+3];
1792 u8 *rf_path = array[i+4];
1793 u8 *chnl = array[i+5];
1794 u8 *val = array[i+6];
1795
1796 _rtl8812ae_phy_config_bb_txpwr_lmt(hw, regulation, band,
1797 bandwidth, rate, rf_path,
1798 chnl, val);
1799 }
1800 }
1801
1802 static bool _rtl8821ae_phy_bb8821a_config_parafile(struct ieee80211_hw *hw)
1803 {
1804 struct rtl_priv *rtlpriv = rtl_priv(hw);
1805 struct rtl_phy *rtlphy = &rtlpriv->phy;
1806 struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
1807 bool rtstatus;
1808
1809 _rtl8821ae_phy_init_txpower_limit(hw);
1810
1811 /* RegEnableTxPowerLimit == 1 for 8812a & 8821a */
1812 if (rtlefuse->eeprom_regulatory != 2)
1813 _rtl8821ae_phy_read_and_config_txpwr_lmt(hw);
1814
1815 rtstatus = _rtl8821ae_phy_config_bb_with_headerfile(hw,
1816 BASEBAND_CONFIG_PHY_REG);
1817 if (rtstatus != true) {
1818 pr_err("Write BB Reg Fail!!\n");
1819 return false;
1820 }
1821 _rtl8821ae_phy_init_tx_power_by_rate(hw);
1822 if (rtlefuse->autoload_failflag == false) {
1823 rtstatus = _rtl8821ae_phy_config_bb_with_pgheaderfile(hw,
1824 BASEBAND_CONFIG_PHY_REG);
1825 }
1826 if (rtstatus != true) {
1827 pr_err("BB_PG Reg Fail!!\n");
1828 return false;
1829 }
1830
1831 _rtl8821ae_phy_txpower_by_rate_configuration(hw);
1832
1833 /* RegEnableTxPowerLimit == 1 for 8812a & 8821a */
1834 if (rtlefuse->eeprom_regulatory != 2)
1835 _rtl8812ae_phy_convert_txpower_limit_to_power_index(hw);
1836
1837 rtstatus = _rtl8821ae_phy_config_bb_with_headerfile(hw,
1838 BASEBAND_CONFIG_AGC_TAB);
1839
1840 if (rtstatus != true) {
1841 pr_err("AGC Table Fail\n");
1842 return false;
1843 }
1844 rtlphy->cck_high_power = (bool)(rtl_get_bbreg(hw,
1845 RFPGA0_XA_HSSIPARAMETER2, 0x200));
1846 return true;
1847 }
1848
1849 static bool
1850 __rtl8821ae_phy_config_with_headerfile(struct ieee80211_hw *hw,
1851 u32 *array_table, u16 arraylen,
1852 void (*set_reg)(struct ieee80211_hw *hw,
1853 u32 regaddr, u32 data))
1854 {
1855 #define COND_ELSE 2
1856 #define COND_ENDIF 3
1857
1858 int i = 0;
1859 u8 cond;
1860 bool matched = true, skipped = false;
1861
1862 while ((i + 1) < arraylen) {
1863 u32 v1 = array_table[i];
1864 u32 v2 = array_table[i + 1];
1865
1866 if (v1 & (BIT(31) | BIT(30))) {/*positive & negative condition*/
1867 if (v1 & BIT(31)) {/* positive condition*/
1868 cond = (u8)((v1 & (BIT(29) | BIT(28))) >> 28);
1869 if (cond == COND_ENDIF) {/*end*/
1870 matched = true;
1871 skipped = false;
1872 } else if (cond == COND_ELSE) /*else*/
1873 matched = skipped ? false : true;
1874 else {/*if , else if*/
1875 if (skipped) {
1876 matched = false;
1877 } else {
1878 if (_rtl8821ae_check_positive(
1879 hw, v1, v2)) {
1880 matched = true;
1881 skipped = true;
1882 } else {
1883 matched = false;
1884 skipped = false;
1885 }
1886 }
1887 }
1888 } else if (v1 & BIT(30)) { /*negative condition*/
1889 /*do nothing*/
1890 }
1891 } else {
1892 if (matched)
1893 set_reg(hw, v1, v2);
1894 }
1895 i = i + 2;
1896 }
1897
1898 return true;
1899 }
1900
1901 static bool _rtl8821ae_phy_config_mac_with_headerfile(struct ieee80211_hw *hw)
1902 {
1903 struct rtl_priv *rtlpriv = rtl_priv(hw);
1904 struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
1905 u32 arraylength;
1906 u32 *ptrarray;
1907
1908 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE, "Read MAC_REG_Array\n");
1909 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
1910 arraylength = RTL8821AE_MAC_1T_ARRAYLEN;
1911 ptrarray = RTL8821AE_MAC_REG_ARRAY;
1912 } else {
1913 arraylength = RTL8812AE_MAC_1T_ARRAYLEN;
1914 ptrarray = RTL8812AE_MAC_REG_ARRAY;
1915 }
1916 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1917 "Img: MAC_REG_ARRAY LEN %d\n", arraylength);
1918
1919 return __rtl8821ae_phy_config_with_headerfile(hw,
1920 ptrarray, arraylength, rtl_write_byte_with_val32);
1921 }
1922
1923 static bool _rtl8821ae_phy_config_bb_with_headerfile(struct ieee80211_hw *hw,
1924 u8 configtype)
1925 {
1926 struct rtl_priv *rtlpriv = rtl_priv(hw);
1927 struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
1928 u32 *array_table;
1929 u16 arraylen;
1930
1931 if (configtype == BASEBAND_CONFIG_PHY_REG) {
1932 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
1933 arraylen = RTL8812AE_PHY_REG_1TARRAYLEN;
1934 array_table = RTL8812AE_PHY_REG_ARRAY;
1935 } else {
1936 arraylen = RTL8821AE_PHY_REG_1TARRAYLEN;
1937 array_table = RTL8821AE_PHY_REG_ARRAY;
1938 }
1939
1940 return __rtl8821ae_phy_config_with_headerfile(hw,
1941 array_table, arraylen,
1942 _rtl8821ae_config_bb_reg);
1943 } else if (configtype == BASEBAND_CONFIG_AGC_TAB) {
1944 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
1945 arraylen = RTL8812AE_AGC_TAB_1TARRAYLEN;
1946 array_table = RTL8812AE_AGC_TAB_ARRAY;
1947 } else {
1948 arraylen = RTL8821AE_AGC_TAB_1TARRAYLEN;
1949 array_table = RTL8821AE_AGC_TAB_ARRAY;
1950 }
1951
1952 return __rtl8821ae_phy_config_with_headerfile(hw,
1953 array_table, arraylen,
1954 rtl_set_bbreg_with_dwmask);
1955 }
1956 return true;
1957 }
1958
1959 static u8 _rtl8821ae_get_rate_section_index(u32 regaddr)
1960 {
1961 u8 index = 0;
1962 regaddr &= 0xFFF;
1963 if (regaddr >= 0xC20 && regaddr <= 0xC4C)
1964 index = (u8)((regaddr - 0xC20) / 4);
1965 else if (regaddr >= 0xE20 && regaddr <= 0xE4C)
1966 index = (u8)((regaddr - 0xE20) / 4);
1967 else
1968 WARN_ONCE(true,
1969 "rtl8821ae: Invalid RegAddr 0x%x\n", regaddr);
1970 return index;
1971 }
1972
1973 static void _rtl8821ae_store_tx_power_by_rate(struct ieee80211_hw *hw,
1974 u32 band, u32 rfpath,
1975 u32 txnum, u32 regaddr,
1976 u32 bitmask, u32 data)
1977 {
1978 struct rtl_priv *rtlpriv = rtl_priv(hw);
1979 struct rtl_phy *rtlphy = &rtlpriv->phy;
1980 u8 rate_section = _rtl8821ae_get_rate_section_index(regaddr);
1981
1982 if (band != BAND_ON_2_4G && band != BAND_ON_5G) {
1983 RT_TRACE(rtlpriv, COMP_INIT, DBG_WARNING, "Invalid Band %d\n", band);
1984 band = BAND_ON_2_4G;
1985 }
1986 if (rfpath >= MAX_RF_PATH) {
1987 RT_TRACE(rtlpriv, COMP_INIT, DBG_WARNING, "Invalid RfPath %d\n", rfpath);
1988 rfpath = MAX_RF_PATH - 1;
1989 }
1990 if (txnum >= MAX_RF_PATH) {
1991 RT_TRACE(rtlpriv, COMP_INIT, DBG_WARNING, "Invalid TxNum %d\n", txnum);
1992 txnum = MAX_RF_PATH - 1;
1993 }
1994 rtlphy->tx_power_by_rate_offset[band][rfpath][txnum][rate_section] = data;
1995 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
1996 "TxPwrByRateOffset[Band %d][RfPath %d][TxNum %d][RateSection %d] = 0x%x\n",
1997 band, rfpath, txnum, rate_section,
1998 rtlphy->tx_power_by_rate_offset[band][rfpath][txnum][rate_section]);
1999 }
2000
2001 static bool _rtl8821ae_phy_config_bb_with_pgheaderfile(struct ieee80211_hw *hw,
2002 u8 configtype)
2003 {
2004 struct rtl_priv *rtlpriv = rtl_priv(hw);
2005 struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
2006 int i;
2007 u32 *array;
2008 u16 arraylen;
2009 u32 v1, v2, v3, v4, v5, v6;
2010
2011 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
2012 arraylen = RTL8812AE_PHY_REG_ARRAY_PGLEN;
2013 array = RTL8812AE_PHY_REG_ARRAY_PG;
2014 } else {
2015 arraylen = RTL8821AE_PHY_REG_ARRAY_PGLEN;
2016 array = RTL8821AE_PHY_REG_ARRAY_PG;
2017 }
2018
2019 if (configtype != BASEBAND_CONFIG_PHY_REG) {
2020 RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
2021 "configtype != BaseBand_Config_PHY_REG\n");
2022 return true;
2023 }
2024 for (i = 0; i < arraylen; i += 6) {
2025 v1 = array[i];
2026 v2 = array[i+1];
2027 v3 = array[i+2];
2028 v4 = array[i+3];
2029 v5 = array[i+4];
2030 v6 = array[i+5];
2031
2032 if (v1 < 0xCDCDCDCD) {
2033 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE &&
2034 (v4 == 0xfe || v4 == 0xffe)) {
2035 msleep(50);
2036 continue;
2037 }
2038
2039 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
2040 if (v4 == 0xfe)
2041 msleep(50);
2042 else if (v4 == 0xfd)
2043 mdelay(5);
2044 else if (v4 == 0xfc)
2045 mdelay(1);
2046 else if (v4 == 0xfb)
2047 udelay(50);
2048 else if (v4 == 0xfa)
2049 udelay(5);
2050 else if (v4 == 0xf9)
2051 udelay(1);
2052 }
2053 _rtl8821ae_store_tx_power_by_rate(hw, v1, v2, v3,
2054 v4, v5, v6);
2055 continue;
2056 } else {
2057 /*don't need the hw_body*/
2058 if (!_rtl8821ae_check_condition(hw, v1)) {
2059 i += 2; /* skip the pair of expression*/
2060 v1 = array[i];
2061 v2 = array[i+1];
2062 v3 = array[i+2];
2063 while (v2 != 0xDEAD) {
2064 i += 3;
2065 v1 = array[i];
2066 v2 = array[i+1];
2067 v3 = array[i+2];
2068 }
2069 }
2070 }
2071 }
2072
2073 return true;
2074 }
2075
2076 bool rtl8812ae_phy_config_rf_with_headerfile(struct ieee80211_hw *hw,
2077 enum radio_path rfpath)
2078 {
2079 bool rtstatus = true;
2080 u32 *radioa_array_table_a, *radioa_array_table_b;
2081 u16 radioa_arraylen_a, radioa_arraylen_b;
2082 struct rtl_priv *rtlpriv = rtl_priv(hw);
2083
2084 radioa_arraylen_a = RTL8812AE_RADIOA_1TARRAYLEN;
2085 radioa_array_table_a = RTL8812AE_RADIOA_ARRAY;
2086 radioa_arraylen_b = RTL8812AE_RADIOB_1TARRAYLEN;
2087 radioa_array_table_b = RTL8812AE_RADIOB_ARRAY;
2088 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2089 "Radio_A:RTL8821AE_RADIOA_ARRAY %d\n", radioa_arraylen_a);
2090 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "Radio No %x\n", rfpath);
2091 rtstatus = true;
2092 switch (rfpath) {
2093 case RF90_PATH_A:
2094 return __rtl8821ae_phy_config_with_headerfile(hw,
2095 radioa_array_table_a, radioa_arraylen_a,
2096 _rtl8821ae_config_rf_radio_a);
2097 break;
2098 case RF90_PATH_B:
2099 return __rtl8821ae_phy_config_with_headerfile(hw,
2100 radioa_array_table_b, radioa_arraylen_b,
2101 _rtl8821ae_config_rf_radio_b);
2102 break;
2103 case RF90_PATH_C:
2104 case RF90_PATH_D:
2105 pr_err("switch case %#x not processed\n", rfpath);
2106 break;
2107 }
2108 return true;
2109 }
2110
2111 bool rtl8821ae_phy_config_rf_with_headerfile(struct ieee80211_hw *hw,
2112 enum radio_path rfpath)
2113 {
2114 bool rtstatus = true;
2115 u32 *radioa_array_table;
2116 u16 radioa_arraylen;
2117 struct rtl_priv *rtlpriv = rtl_priv(hw);
2118
2119 radioa_arraylen = RTL8821AE_RADIOA_1TARRAYLEN;
2120 radioa_array_table = RTL8821AE_RADIOA_ARRAY;
2121 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2122 "Radio_A:RTL8821AE_RADIOA_ARRAY %d\n", radioa_arraylen);
2123 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "Radio No %x\n", rfpath);
2124 rtstatus = true;
2125 switch (rfpath) {
2126 case RF90_PATH_A:
2127 return __rtl8821ae_phy_config_with_headerfile(hw,
2128 radioa_array_table, radioa_arraylen,
2129 _rtl8821ae_config_rf_radio_a);
2130 break;
2131
2132 case RF90_PATH_B:
2133 case RF90_PATH_C:
2134 case RF90_PATH_D:
2135 pr_err("switch case %#x not processed\n", rfpath);
2136 break;
2137 }
2138 return true;
2139 }
2140
2141 void rtl8821ae_phy_get_hw_reg_originalvalue(struct ieee80211_hw *hw)
2142 {
2143 struct rtl_priv *rtlpriv = rtl_priv(hw);
2144 struct rtl_phy *rtlphy = &rtlpriv->phy;
2145
2146 rtlphy->default_initialgain[0] =
2147 (u8)rtl_get_bbreg(hw, ROFDM0_XAAGCCORE1, MASKBYTE0);
2148 rtlphy->default_initialgain[1] =
2149 (u8)rtl_get_bbreg(hw, ROFDM0_XBAGCCORE1, MASKBYTE0);
2150 rtlphy->default_initialgain[2] =
2151 (u8)rtl_get_bbreg(hw, ROFDM0_XCAGCCORE1, MASKBYTE0);
2152 rtlphy->default_initialgain[3] =
2153 (u8)rtl_get_bbreg(hw, ROFDM0_XDAGCCORE1, MASKBYTE0);
2154
2155 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
2156 "Default initial gain (c50=0x%x, c58=0x%x, c60=0x%x, c68=0x%x\n",
2157 rtlphy->default_initialgain[0],
2158 rtlphy->default_initialgain[1],
2159 rtlphy->default_initialgain[2],
2160 rtlphy->default_initialgain[3]);
2161
2162 rtlphy->framesync = (u8)rtl_get_bbreg(hw,
2163 ROFDM0_RXDETECTOR3, MASKBYTE0);
2164 rtlphy->framesync_c34 = rtl_get_bbreg(hw,
2165 ROFDM0_RXDETECTOR2, MASKDWORD);
2166
2167 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
2168 "Default framesync (0x%x) = 0x%x\n",
2169 ROFDM0_RXDETECTOR3, rtlphy->framesync);
2170 }
2171
2172 static void phy_init_bb_rf_register_definition(struct ieee80211_hw *hw)
2173 {
2174 struct rtl_priv *rtlpriv = rtl_priv(hw);
2175 struct rtl_phy *rtlphy = &rtlpriv->phy;
2176
2177 rtlphy->phyreg_def[RF90_PATH_A].rfintfs = RFPGA0_XAB_RFINTERFACESW;
2178 rtlphy->phyreg_def[RF90_PATH_B].rfintfs = RFPGA0_XAB_RFINTERFACESW;
2179
2180 rtlphy->phyreg_def[RF90_PATH_A].rfintfo = RFPGA0_XA_RFINTERFACEOE;
2181 rtlphy->phyreg_def[RF90_PATH_B].rfintfo = RFPGA0_XB_RFINTERFACEOE;
2182
2183 rtlphy->phyreg_def[RF90_PATH_A].rfintfe = RFPGA0_XA_RFINTERFACEOE;
2184 rtlphy->phyreg_def[RF90_PATH_B].rfintfe = RFPGA0_XB_RFINTERFACEOE;
2185
2186 rtlphy->phyreg_def[RF90_PATH_A].rf3wire_offset = RA_LSSIWRITE_8821A;
2187 rtlphy->phyreg_def[RF90_PATH_B].rf3wire_offset = RB_LSSIWRITE_8821A;
2188
2189 rtlphy->phyreg_def[RF90_PATH_A].rfhssi_para2 = RHSSIREAD_8821AE;
2190 rtlphy->phyreg_def[RF90_PATH_B].rfhssi_para2 = RHSSIREAD_8821AE;
2191
2192 rtlphy->phyreg_def[RF90_PATH_A].rf_rb = RA_SIREAD_8821A;
2193 rtlphy->phyreg_def[RF90_PATH_B].rf_rb = RB_SIREAD_8821A;
2194
2195 rtlphy->phyreg_def[RF90_PATH_A].rf_rbpi = RA_PIREAD_8821A;
2196 rtlphy->phyreg_def[RF90_PATH_B].rf_rbpi = RB_PIREAD_8821A;
2197 }
2198
2199 void rtl8821ae_phy_get_txpower_level(struct ieee80211_hw *hw, long *powerlevel)
2200 {
2201 struct rtl_priv *rtlpriv = rtl_priv(hw);
2202 struct rtl_phy *rtlphy = &rtlpriv->phy;
2203 u8 txpwr_level;
2204 long txpwr_dbm;
2205
2206 txpwr_level = rtlphy->cur_cck_txpwridx;
2207 txpwr_dbm = _rtl8821ae_phy_txpwr_idx_to_dbm(hw,
2208 WIRELESS_MODE_B, txpwr_level);
2209 txpwr_level = rtlphy->cur_ofdm24g_txpwridx;
2210 if (_rtl8821ae_phy_txpwr_idx_to_dbm(hw,
2211 WIRELESS_MODE_G,
2212 txpwr_level) > txpwr_dbm)
2213 txpwr_dbm =
2214 _rtl8821ae_phy_txpwr_idx_to_dbm(hw, WIRELESS_MODE_G,
2215 txpwr_level);
2216 txpwr_level = rtlphy->cur_ofdm24g_txpwridx;
2217 if (_rtl8821ae_phy_txpwr_idx_to_dbm(hw,
2218 WIRELESS_MODE_N_24G,
2219 txpwr_level) > txpwr_dbm)
2220 txpwr_dbm =
2221 _rtl8821ae_phy_txpwr_idx_to_dbm(hw, WIRELESS_MODE_N_24G,
2222 txpwr_level);
2223 *powerlevel = txpwr_dbm;
2224 }
2225
2226 static bool _rtl8821ae_phy_get_chnl_index(u8 channel, u8 *chnl_index)
2227 {
2228 u8 i = 0;
2229 bool in_24g = true;
2230
2231 if (channel <= 14) {
2232 in_24g = true;
2233 *chnl_index = channel - 1;
2234 } else {
2235 in_24g = false;
2236
2237 for (i = 0; i < CHANNEL_MAX_NUMBER_5G; ++i) {
2238 if (channel5g[i] == channel) {
2239 *chnl_index = i;
2240 return in_24g;
2241 }
2242 }
2243 }
2244 return in_24g;
2245 }
2246
2247 static s8 _rtl8821ae_phy_get_ratesection_intxpower_byrate(u8 path, u8 rate)
2248 {
2249 s8 rate_section = 0;
2250 switch (rate) {
2251 case DESC_RATE1M:
2252 case DESC_RATE2M:
2253 case DESC_RATE5_5M:
2254 case DESC_RATE11M:
2255 rate_section = 0;
2256 break;
2257 case DESC_RATE6M:
2258 case DESC_RATE9M:
2259 case DESC_RATE12M:
2260 case DESC_RATE18M:
2261 rate_section = 1;
2262 break;
2263 case DESC_RATE24M:
2264 case DESC_RATE36M:
2265 case DESC_RATE48M:
2266 case DESC_RATE54M:
2267 rate_section = 2;
2268 break;
2269 case DESC_RATEMCS0:
2270 case DESC_RATEMCS1:
2271 case DESC_RATEMCS2:
2272 case DESC_RATEMCS3:
2273 rate_section = 3;
2274 break;
2275 case DESC_RATEMCS4:
2276 case DESC_RATEMCS5:
2277 case DESC_RATEMCS6:
2278 case DESC_RATEMCS7:
2279 rate_section = 4;
2280 break;
2281 case DESC_RATEMCS8:
2282 case DESC_RATEMCS9:
2283 case DESC_RATEMCS10:
2284 case DESC_RATEMCS11:
2285 rate_section = 5;
2286 break;
2287 case DESC_RATEMCS12:
2288 case DESC_RATEMCS13:
2289 case DESC_RATEMCS14:
2290 case DESC_RATEMCS15:
2291 rate_section = 6;
2292 break;
2293 case DESC_RATEVHT1SS_MCS0:
2294 case DESC_RATEVHT1SS_MCS1:
2295 case DESC_RATEVHT1SS_MCS2:
2296 case DESC_RATEVHT1SS_MCS3:
2297 rate_section = 7;
2298 break;
2299 case DESC_RATEVHT1SS_MCS4:
2300 case DESC_RATEVHT1SS_MCS5:
2301 case DESC_RATEVHT1SS_MCS6:
2302 case DESC_RATEVHT1SS_MCS7:
2303 rate_section = 8;
2304 break;
2305 case DESC_RATEVHT1SS_MCS8:
2306 case DESC_RATEVHT1SS_MCS9:
2307 case DESC_RATEVHT2SS_MCS0:
2308 case DESC_RATEVHT2SS_MCS1:
2309 rate_section = 9;
2310 break;
2311 case DESC_RATEVHT2SS_MCS2:
2312 case DESC_RATEVHT2SS_MCS3:
2313 case DESC_RATEVHT2SS_MCS4:
2314 case DESC_RATEVHT2SS_MCS5:
2315 rate_section = 10;
2316 break;
2317 case DESC_RATEVHT2SS_MCS6:
2318 case DESC_RATEVHT2SS_MCS7:
2319 case DESC_RATEVHT2SS_MCS8:
2320 case DESC_RATEVHT2SS_MCS9:
2321 rate_section = 11;
2322 break;
2323 default:
2324 WARN_ONCE(true, "rtl8821ae: Rate_Section is Illegal\n");
2325 break;
2326 }
2327
2328 return rate_section;
2329 }
2330
2331 static s8 _rtl8812ae_phy_get_world_wide_limit(s8 *limit_table)
2332 {
2333 s8 min = limit_table[0];
2334 u8 i = 0;
2335
2336 for (i = 0; i < MAX_REGULATION_NUM; ++i) {
2337 if (limit_table[i] < min)
2338 min = limit_table[i];
2339 }
2340 return min;
2341 }
2342
2343 static s8 _rtl8812ae_phy_get_txpower_limit(struct ieee80211_hw *hw,
2344 u8 band,
2345 enum ht_channel_width bandwidth,
2346 enum radio_path rf_path,
2347 u8 rate, u8 channel)
2348 {
2349 struct rtl_priv *rtlpriv = rtl_priv(hw);
2350 struct rtl_efuse *rtlefuse = rtl_efuse(rtlpriv);
2351 struct rtl_phy *rtlphy = &rtlpriv->phy;
2352 short band_temp = -1, regulation = -1, bandwidth_temp = -1,
2353 rate_section = -1, channel_temp = -1;
2354 u16 bd, regu, bdwidth, sec, chnl;
2355 s8 power_limit = MAX_POWER_INDEX;
2356
2357 if (rtlefuse->eeprom_regulatory == 2)
2358 return MAX_POWER_INDEX;
2359
2360 regulation = TXPWR_LMT_WW;
2361
2362 if (band == BAND_ON_2_4G)
2363 band_temp = 0;
2364 else if (band == BAND_ON_5G)
2365 band_temp = 1;
2366
2367 if (bandwidth == HT_CHANNEL_WIDTH_20)
2368 bandwidth_temp = 0;
2369 else if (bandwidth == HT_CHANNEL_WIDTH_20_40)
2370 bandwidth_temp = 1;
2371 else if (bandwidth == HT_CHANNEL_WIDTH_80)
2372 bandwidth_temp = 2;
2373
2374 switch (rate) {
2375 case DESC_RATE1M:
2376 case DESC_RATE2M:
2377 case DESC_RATE5_5M:
2378 case DESC_RATE11M:
2379 rate_section = 0;
2380 break;
2381 case DESC_RATE6M:
2382 case DESC_RATE9M:
2383 case DESC_RATE12M:
2384 case DESC_RATE18M:
2385 case DESC_RATE24M:
2386 case DESC_RATE36M:
2387 case DESC_RATE48M:
2388 case DESC_RATE54M:
2389 rate_section = 1;
2390 break;
2391 case DESC_RATEMCS0:
2392 case DESC_RATEMCS1:
2393 case DESC_RATEMCS2:
2394 case DESC_RATEMCS3:
2395 case DESC_RATEMCS4:
2396 case DESC_RATEMCS5:
2397 case DESC_RATEMCS6:
2398 case DESC_RATEMCS7:
2399 rate_section = 2;
2400 break;
2401 case DESC_RATEMCS8:
2402 case DESC_RATEMCS9:
2403 case DESC_RATEMCS10:
2404 case DESC_RATEMCS11:
2405 case DESC_RATEMCS12:
2406 case DESC_RATEMCS13:
2407 case DESC_RATEMCS14:
2408 case DESC_RATEMCS15:
2409 rate_section = 3;
2410 break;
2411 case DESC_RATEVHT1SS_MCS0:
2412 case DESC_RATEVHT1SS_MCS1:
2413 case DESC_RATEVHT1SS_MCS2:
2414 case DESC_RATEVHT1SS_MCS3:
2415 case DESC_RATEVHT1SS_MCS4:
2416 case DESC_RATEVHT1SS_MCS5:
2417 case DESC_RATEVHT1SS_MCS6:
2418 case DESC_RATEVHT1SS_MCS7:
2419 case DESC_RATEVHT1SS_MCS8:
2420 case DESC_RATEVHT1SS_MCS9:
2421 rate_section = 4;
2422 break;
2423 case DESC_RATEVHT2SS_MCS0:
2424 case DESC_RATEVHT2SS_MCS1:
2425 case DESC_RATEVHT2SS_MCS2:
2426 case DESC_RATEVHT2SS_MCS3:
2427 case DESC_RATEVHT2SS_MCS4:
2428 case DESC_RATEVHT2SS_MCS5:
2429 case DESC_RATEVHT2SS_MCS6:
2430 case DESC_RATEVHT2SS_MCS7:
2431 case DESC_RATEVHT2SS_MCS8:
2432 case DESC_RATEVHT2SS_MCS9:
2433 rate_section = 5;
2434 break;
2435 default:
2436 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD,
2437 "Wrong rate 0x%x\n", rate);
2438 break;
2439 }
2440
2441 if (band_temp == BAND_ON_5G && rate_section == 0)
2442 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD,
2443 "Wrong rate 0x%x: No CCK in 5G Band\n", rate);
2444
2445 /*workaround for wrong index combination to obtain tx power limit,
2446 OFDM only exists in BW 20M*/
2447 if (rate_section == 1)
2448 bandwidth_temp = 0;
2449
2450 /*workaround for wrong index combination to obtain tx power limit,
2451 *HT on 80M will reference to HT on 40M
2452 */
2453 if ((rate_section == 2 || rate_section == 3) && band == BAND_ON_5G &&
2454 bandwidth_temp == 2)
2455 bandwidth_temp = 1;
2456
2457 if (band == BAND_ON_2_4G)
2458 channel_temp = _rtl8812ae_phy_get_chnl_idx_of_txpwr_lmt(hw,
2459 BAND_ON_2_4G, channel);
2460 else if (band == BAND_ON_5G)
2461 channel_temp = _rtl8812ae_phy_get_chnl_idx_of_txpwr_lmt(hw,
2462 BAND_ON_5G, channel);
2463 else if (band == BAND_ON_BOTH)
2464 ;/* BAND_ON_BOTH don't care temporarily */
2465
2466 if (band_temp == -1 || regulation == -1 || bandwidth_temp == -1 ||
2467 rate_section == -1 || channel_temp == -1) {
2468 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD,
2469 "Wrong index value to access power limit table [band %d][regulation %d][bandwidth %d][rf_path %d][rate_section %d][chnl %d]\n",
2470 band_temp, regulation, bandwidth_temp, rf_path,
2471 rate_section, channel_temp);
2472 return MAX_POWER_INDEX;
2473 }
2474
2475 bd = band_temp;
2476 regu = regulation;
2477 bdwidth = bandwidth_temp;
2478 sec = rate_section;
2479 chnl = channel_temp;
2480
2481 if (band == BAND_ON_2_4G) {
2482 s8 limits[10] = {0};
2483 u8 i;
2484
2485 for (i = 0; i < 4; ++i)
2486 limits[i] = rtlphy->txpwr_limit_2_4g[i][bdwidth]
2487 [sec][chnl][rf_path];
2488
2489 power_limit = (regulation == TXPWR_LMT_WW) ?
2490 _rtl8812ae_phy_get_world_wide_limit(limits) :
2491 rtlphy->txpwr_limit_2_4g[regu][bdwidth]
2492 [sec][chnl][rf_path];
2493 } else if (band == BAND_ON_5G) {
2494 s8 limits[10] = {0};
2495 u8 i;
2496
2497 for (i = 0; i < MAX_REGULATION_NUM; ++i)
2498 limits[i] = rtlphy->txpwr_limit_5g[i][bdwidth]
2499 [sec][chnl][rf_path];
2500
2501 power_limit = (regulation == TXPWR_LMT_WW) ?
2502 _rtl8812ae_phy_get_world_wide_limit(limits) :
2503 rtlphy->txpwr_limit_5g[regu][chnl]
2504 [sec][chnl][rf_path];
2505 } else {
2506 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2507 "No power limit table of the specified band\n");
2508 }
2509 return power_limit;
2510 }
2511
2512 static s8 _rtl8821ae_phy_get_txpower_by_rate(struct ieee80211_hw *hw,
2513 u8 band, u8 path, u8 rate)
2514 {
2515 struct rtl_priv *rtlpriv = rtl_priv(hw);
2516 struct rtl_phy *rtlphy = &rtlpriv->phy;
2517 u8 shift = 0, rate_section, tx_num;
2518 s8 tx_pwr_diff = 0;
2519 s8 limit = 0;
2520
2521 rate_section = _rtl8821ae_phy_get_ratesection_intxpower_byrate(path, rate);
2522 tx_num = RF_TX_NUM_NONIMPLEMENT;
2523
2524 if (tx_num == RF_TX_NUM_NONIMPLEMENT) {
2525 if ((rate >= DESC_RATEMCS8 && rate <= DESC_RATEMCS15) ||
2526 (rate >= DESC_RATEVHT2SS_MCS2 && rate <= DESC_RATEVHT2SS_MCS9))
2527 tx_num = RF_2TX;
2528 else
2529 tx_num = RF_1TX;
2530 }
2531
2532 switch (rate) {
2533 case DESC_RATE1M:
2534 case DESC_RATE6M:
2535 case DESC_RATE24M:
2536 case DESC_RATEMCS0:
2537 case DESC_RATEMCS4:
2538 case DESC_RATEMCS8:
2539 case DESC_RATEMCS12:
2540 case DESC_RATEVHT1SS_MCS0:
2541 case DESC_RATEVHT1SS_MCS4:
2542 case DESC_RATEVHT1SS_MCS8:
2543 case DESC_RATEVHT2SS_MCS2:
2544 case DESC_RATEVHT2SS_MCS6:
2545 shift = 0;
2546 break;
2547 case DESC_RATE2M:
2548 case DESC_RATE9M:
2549 case DESC_RATE36M:
2550 case DESC_RATEMCS1:
2551 case DESC_RATEMCS5:
2552 case DESC_RATEMCS9:
2553 case DESC_RATEMCS13:
2554 case DESC_RATEVHT1SS_MCS1:
2555 case DESC_RATEVHT1SS_MCS5:
2556 case DESC_RATEVHT1SS_MCS9:
2557 case DESC_RATEVHT2SS_MCS3:
2558 case DESC_RATEVHT2SS_MCS7:
2559 shift = 8;
2560 break;
2561 case DESC_RATE5_5M:
2562 case DESC_RATE12M:
2563 case DESC_RATE48M:
2564 case DESC_RATEMCS2:
2565 case DESC_RATEMCS6:
2566 case DESC_RATEMCS10:
2567 case DESC_RATEMCS14:
2568 case DESC_RATEVHT1SS_MCS2:
2569 case DESC_RATEVHT1SS_MCS6:
2570 case DESC_RATEVHT2SS_MCS0:
2571 case DESC_RATEVHT2SS_MCS4:
2572 case DESC_RATEVHT2SS_MCS8:
2573 shift = 16;
2574 break;
2575 case DESC_RATE11M:
2576 case DESC_RATE18M:
2577 case DESC_RATE54M:
2578 case DESC_RATEMCS3:
2579 case DESC_RATEMCS7:
2580 case DESC_RATEMCS11:
2581 case DESC_RATEMCS15:
2582 case DESC_RATEVHT1SS_MCS3:
2583 case DESC_RATEVHT1SS_MCS7:
2584 case DESC_RATEVHT2SS_MCS1:
2585 case DESC_RATEVHT2SS_MCS5:
2586 case DESC_RATEVHT2SS_MCS9:
2587 shift = 24;
2588 break;
2589 default:
2590 WARN_ONCE(true, "rtl8821ae: Rate_Section is Illegal\n");
2591 break;
2592 }
2593
2594 tx_pwr_diff = (u8)(rtlphy->tx_power_by_rate_offset[band][path]
2595 [tx_num][rate_section] >> shift) & 0xff;
2596
2597 /* RegEnableTxPowerLimit == 1 for 8812a & 8821a */
2598 if (rtlpriv->efuse.eeprom_regulatory != 2) {
2599 limit = _rtl8812ae_phy_get_txpower_limit(hw, band,
2600 rtlphy->current_chan_bw, path, rate,
2601 rtlphy->current_channel);
2602
2603 if (rate == DESC_RATEVHT1SS_MCS8 || rate == DESC_RATEVHT1SS_MCS9 ||
2604 rate == DESC_RATEVHT2SS_MCS8 || rate == DESC_RATEVHT2SS_MCS9) {
2605 if (limit < 0) {
2606 if (tx_pwr_diff < (-limit))
2607 tx_pwr_diff = -limit;
2608 }
2609 } else {
2610 if (limit < 0)
2611 tx_pwr_diff = limit;
2612 else
2613 tx_pwr_diff = tx_pwr_diff > limit ? limit : tx_pwr_diff;
2614 }
2615 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_LOUD,
2616 "Maximum power by rate %d, final power by rate %d\n",
2617 limit, tx_pwr_diff);
2618 }
2619
2620 return tx_pwr_diff;
2621 }
2622
2623 static u8 _rtl8821ae_get_txpower_index(struct ieee80211_hw *hw, u8 path,
2624 u8 rate, u8 bandwidth, u8 channel)
2625 {
2626 struct rtl_priv *rtlpriv = rtl_priv(hw);
2627 struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
2628 struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
2629 u8 index = (channel - 1);
2630 u8 txpower = 0;
2631 bool in_24g = false;
2632 s8 powerdiff_byrate = 0;
2633
2634 if (((rtlhal->current_bandtype == BAND_ON_2_4G) &&
2635 (channel > 14 || channel < 1)) ||
2636 ((rtlhal->current_bandtype == BAND_ON_5G) && (channel <= 14))) {
2637 index = 0;
2638 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_LOUD,
2639 "Illegal channel!!\n");
2640 }
2641
2642 in_24g = _rtl8821ae_phy_get_chnl_index(channel, &index);
2643 if (in_24g) {
2644 if (RTL8821AE_RX_HAL_IS_CCK_RATE(rate))
2645 txpower = rtlefuse->txpwrlevel_cck[path][index];
2646 else if (DESC_RATE6M <= rate)
2647 txpower = rtlefuse->txpwrlevel_ht40_1s[path][index];
2648 else
2649 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_LOUD, "invalid rate\n");
2650
2651 if (DESC_RATE6M <= rate && rate <= DESC_RATE54M &&
2652 !RTL8821AE_RX_HAL_IS_CCK_RATE(rate))
2653 txpower += rtlefuse->txpwr_legacyhtdiff[path][TX_1S];
2654
2655 if (bandwidth == HT_CHANNEL_WIDTH_20) {
2656 if ((DESC_RATEMCS0 <= rate && rate <= DESC_RATEMCS15) ||
2657 (DESC_RATEVHT1SS_MCS0 <= rate && rate <= DESC_RATEVHT2SS_MCS9))
2658 txpower += rtlefuse->txpwr_ht20diff[path][TX_1S];
2659 if ((DESC_RATEMCS8 <= rate && rate <= DESC_RATEMCS15) ||
2660 (DESC_RATEVHT2SS_MCS0 <= rate && rate <= DESC_RATEVHT2SS_MCS9))
2661 txpower += rtlefuse->txpwr_ht20diff[path][TX_2S];
2662 } else if (bandwidth == HT_CHANNEL_WIDTH_20_40) {
2663 if ((DESC_RATEMCS0 <= rate && rate <= DESC_RATEMCS15) ||
2664 (DESC_RATEVHT1SS_MCS0 <= rate && rate <= DESC_RATEVHT2SS_MCS9))
2665 txpower += rtlefuse->txpwr_ht40diff[path][TX_1S];
2666 if ((DESC_RATEMCS8 <= rate && rate <= DESC_RATEMCS15) ||
2667 (DESC_RATEVHT2SS_MCS0 <= rate && rate <= DESC_RATEVHT2SS_MCS9))
2668 txpower += rtlefuse->txpwr_ht40diff[path][TX_2S];
2669 } else if (bandwidth == HT_CHANNEL_WIDTH_80) {
2670 if ((DESC_RATEMCS0 <= rate && rate <= DESC_RATEMCS15) ||
2671 (DESC_RATEVHT1SS_MCS0 <= rate &&
2672 rate <= DESC_RATEVHT2SS_MCS9))
2673 txpower += rtlefuse->txpwr_ht40diff[path][TX_1S];
2674 if ((DESC_RATEMCS8 <= rate && rate <= DESC_RATEMCS15) ||
2675 (DESC_RATEVHT2SS_MCS0 <= rate &&
2676 rate <= DESC_RATEVHT2SS_MCS9))
2677 txpower += rtlefuse->txpwr_ht40diff[path][TX_2S];
2678 }
2679 } else {
2680 if (DESC_RATE6M <= rate)
2681 txpower = rtlefuse->txpwr_5g_bw40base[path][index];
2682 else
2683 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_WARNING,
2684 "INVALID Rate.\n");
2685
2686 if (DESC_RATE6M <= rate && rate <= DESC_RATE54M &&
2687 !RTL8821AE_RX_HAL_IS_CCK_RATE(rate))
2688 txpower += rtlefuse->txpwr_5g_ofdmdiff[path][TX_1S];
2689
2690 if (bandwidth == HT_CHANNEL_WIDTH_20) {
2691 if ((DESC_RATEMCS0 <= rate && rate <= DESC_RATEMCS15) ||
2692 (DESC_RATEVHT1SS_MCS0 <= rate &&
2693 rate <= DESC_RATEVHT2SS_MCS9))
2694 txpower += rtlefuse->txpwr_5g_bw20diff[path][TX_1S];
2695 if ((DESC_RATEMCS8 <= rate && rate <= DESC_RATEMCS15) ||
2696 (DESC_RATEVHT2SS_MCS0 <= rate &&
2697 rate <= DESC_RATEVHT2SS_MCS9))
2698 txpower += rtlefuse->txpwr_5g_bw20diff[path][TX_2S];
2699 } else if (bandwidth == HT_CHANNEL_WIDTH_20_40) {
2700 if ((DESC_RATEMCS0 <= rate && rate <= DESC_RATEMCS15) ||
2701 (DESC_RATEVHT1SS_MCS0 <= rate &&
2702 rate <= DESC_RATEVHT2SS_MCS9))
2703 txpower += rtlefuse->txpwr_5g_bw40diff[path][TX_1S];
2704 if ((DESC_RATEMCS8 <= rate && rate <= DESC_RATEMCS15) ||
2705 (DESC_RATEVHT2SS_MCS0 <= rate &&
2706 rate <= DESC_RATEVHT2SS_MCS9))
2707 txpower += rtlefuse->txpwr_5g_bw40diff[path][TX_2S];
2708 } else if (bandwidth == HT_CHANNEL_WIDTH_80) {
2709 u8 i;
2710
2711 for (i = 0; i < sizeof(channel5g_80m) / sizeof(u8); ++i)
2712 if (channel5g_80m[i] == channel)
2713 index = i;
2714
2715 if ((DESC_RATEMCS0 <= rate && rate <= DESC_RATEMCS15) ||
2716 (DESC_RATEVHT1SS_MCS0 <= rate &&
2717 rate <= DESC_RATEVHT2SS_MCS9))
2718 txpower = rtlefuse->txpwr_5g_bw80base[path][index]
2719 + rtlefuse->txpwr_5g_bw80diff[path][TX_1S];
2720 if ((DESC_RATEMCS8 <= rate && rate <= DESC_RATEMCS15) ||
2721 (DESC_RATEVHT2SS_MCS0 <= rate &&
2722 rate <= DESC_RATEVHT2SS_MCS9))
2723 txpower = rtlefuse->txpwr_5g_bw80base[path][index]
2724 + rtlefuse->txpwr_5g_bw80diff[path][TX_1S]
2725 + rtlefuse->txpwr_5g_bw80diff[path][TX_2S];
2726 }
2727 }
2728 if (rtlefuse->eeprom_regulatory != 2)
2729 powerdiff_byrate =
2730 _rtl8821ae_phy_get_txpower_by_rate(hw, (u8)(!in_24g),
2731 path, rate);
2732
2733 if (rate == DESC_RATEVHT1SS_MCS8 || rate == DESC_RATEVHT1SS_MCS9 ||
2734 rate == DESC_RATEVHT2SS_MCS8 || rate == DESC_RATEVHT2SS_MCS9)
2735 txpower -= powerdiff_byrate;
2736 else
2737 txpower += powerdiff_byrate;
2738
2739 if (rate > DESC_RATE11M)
2740 txpower += rtlpriv->dm.remnant_ofdm_swing_idx[path];
2741 else
2742 txpower += rtlpriv->dm.remnant_cck_idx;
2743
2744 if (txpower > MAX_POWER_INDEX)
2745 txpower = MAX_POWER_INDEX;
2746
2747 return txpower;
2748 }
2749
2750 static void _rtl8821ae_phy_set_txpower_index(struct ieee80211_hw *hw,
2751 u8 power_index, u8 path, u8 rate)
2752 {
2753 struct rtl_priv *rtlpriv = rtl_priv(hw);
2754
2755 if (path == RF90_PATH_A) {
2756 switch (rate) {
2757 case DESC_RATE1M:
2758 rtl_set_bbreg(hw, RTXAGC_A_CCK11_CCK1,
2759 MASKBYTE0, power_index);
2760 break;
2761 case DESC_RATE2M:
2762 rtl_set_bbreg(hw, RTXAGC_A_CCK11_CCK1,
2763 MASKBYTE1, power_index);
2764 break;
2765 case DESC_RATE5_5M:
2766 rtl_set_bbreg(hw, RTXAGC_A_CCK11_CCK1,
2767 MASKBYTE2, power_index);
2768 break;
2769 case DESC_RATE11M:
2770 rtl_set_bbreg(hw, RTXAGC_A_CCK11_CCK1,
2771 MASKBYTE3, power_index);
2772 break;
2773 case DESC_RATE6M:
2774 rtl_set_bbreg(hw, RTXAGC_A_OFDM18_OFDM6,
2775 MASKBYTE0, power_index);
2776 break;
2777 case DESC_RATE9M:
2778 rtl_set_bbreg(hw, RTXAGC_A_OFDM18_OFDM6,
2779 MASKBYTE1, power_index);
2780 break;
2781 case DESC_RATE12M:
2782 rtl_set_bbreg(hw, RTXAGC_A_OFDM18_OFDM6,
2783 MASKBYTE2, power_index);
2784 break;
2785 case DESC_RATE18M:
2786 rtl_set_bbreg(hw, RTXAGC_A_OFDM18_OFDM6,
2787 MASKBYTE3, power_index);
2788 break;
2789 case DESC_RATE24M:
2790 rtl_set_bbreg(hw, RTXAGC_A_OFDM54_OFDM24,
2791 MASKBYTE0, power_index);
2792 break;
2793 case DESC_RATE36M:
2794 rtl_set_bbreg(hw, RTXAGC_A_OFDM54_OFDM24,
2795 MASKBYTE1, power_index);
2796 break;
2797 case DESC_RATE48M:
2798 rtl_set_bbreg(hw, RTXAGC_A_OFDM54_OFDM24,
2799 MASKBYTE2, power_index);
2800 break;
2801 case DESC_RATE54M:
2802 rtl_set_bbreg(hw, RTXAGC_A_OFDM54_OFDM24,
2803 MASKBYTE3, power_index);
2804 break;
2805 case DESC_RATEMCS0:
2806 rtl_set_bbreg(hw, RTXAGC_A_MCS03_MCS00,
2807 MASKBYTE0, power_index);
2808 break;
2809 case DESC_RATEMCS1:
2810 rtl_set_bbreg(hw, RTXAGC_A_MCS03_MCS00,
2811 MASKBYTE1, power_index);
2812 break;
2813 case DESC_RATEMCS2:
2814 rtl_set_bbreg(hw, RTXAGC_A_MCS03_MCS00,
2815 MASKBYTE2, power_index);
2816 break;
2817 case DESC_RATEMCS3:
2818 rtl_set_bbreg(hw, RTXAGC_A_MCS03_MCS00,
2819 MASKBYTE3, power_index);
2820 break;
2821 case DESC_RATEMCS4:
2822 rtl_set_bbreg(hw, RTXAGC_A_MCS07_MCS04,
2823 MASKBYTE0, power_index);
2824 break;
2825 case DESC_RATEMCS5:
2826 rtl_set_bbreg(hw, RTXAGC_A_MCS07_MCS04,
2827 MASKBYTE1, power_index);
2828 break;
2829 case DESC_RATEMCS6:
2830 rtl_set_bbreg(hw, RTXAGC_A_MCS07_MCS04,
2831 MASKBYTE2, power_index);
2832 break;
2833 case DESC_RATEMCS7:
2834 rtl_set_bbreg(hw, RTXAGC_A_MCS07_MCS04,
2835 MASKBYTE3, power_index);
2836 break;
2837 case DESC_RATEMCS8:
2838 rtl_set_bbreg(hw, RTXAGC_A_MCS11_MCS08,
2839 MASKBYTE0, power_index);
2840 break;
2841 case DESC_RATEMCS9:
2842 rtl_set_bbreg(hw, RTXAGC_A_MCS11_MCS08,
2843 MASKBYTE1, power_index);
2844 break;
2845 case DESC_RATEMCS10:
2846 rtl_set_bbreg(hw, RTXAGC_A_MCS11_MCS08,
2847 MASKBYTE2, power_index);
2848 break;
2849 case DESC_RATEMCS11:
2850 rtl_set_bbreg(hw, RTXAGC_A_MCS11_MCS08,
2851 MASKBYTE3, power_index);
2852 break;
2853 case DESC_RATEMCS12:
2854 rtl_set_bbreg(hw, RTXAGC_A_MCS15_MCS12,
2855 MASKBYTE0, power_index);
2856 break;
2857 case DESC_RATEMCS13:
2858 rtl_set_bbreg(hw, RTXAGC_A_MCS15_MCS12,
2859 MASKBYTE1, power_index);
2860 break;
2861 case DESC_RATEMCS14:
2862 rtl_set_bbreg(hw, RTXAGC_A_MCS15_MCS12,
2863 MASKBYTE2, power_index);
2864 break;
2865 case DESC_RATEMCS15:
2866 rtl_set_bbreg(hw, RTXAGC_A_MCS15_MCS12,
2867 MASKBYTE3, power_index);
2868 break;
2869 case DESC_RATEVHT1SS_MCS0:
2870 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX3_NSS1INDEX0,
2871 MASKBYTE0, power_index);
2872 break;
2873 case DESC_RATEVHT1SS_MCS1:
2874 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX3_NSS1INDEX0,
2875 MASKBYTE1, power_index);
2876 break;
2877 case DESC_RATEVHT1SS_MCS2:
2878 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX3_NSS1INDEX0,
2879 MASKBYTE2, power_index);
2880 break;
2881 case DESC_RATEVHT1SS_MCS3:
2882 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX3_NSS1INDEX0,
2883 MASKBYTE3, power_index);
2884 break;
2885 case DESC_RATEVHT1SS_MCS4:
2886 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX7_NSS1INDEX4,
2887 MASKBYTE0, power_index);
2888 break;
2889 case DESC_RATEVHT1SS_MCS5:
2890 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX7_NSS1INDEX4,
2891 MASKBYTE1, power_index);
2892 break;
2893 case DESC_RATEVHT1SS_MCS6:
2894 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX7_NSS1INDEX4,
2895 MASKBYTE2, power_index);
2896 break;
2897 case DESC_RATEVHT1SS_MCS7:
2898 rtl_set_bbreg(hw, RTXAGC_A_NSS1INDEX7_NSS1INDEX4,
2899 MASKBYTE3, power_index);
2900 break;
2901 case DESC_RATEVHT1SS_MCS8:
2902 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX1_NSS1INDEX8,
2903 MASKBYTE0, power_index);
2904 break;
2905 case DESC_RATEVHT1SS_MCS9:
2906 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX1_NSS1INDEX8,
2907 MASKBYTE1, power_index);
2908 break;
2909 case DESC_RATEVHT2SS_MCS0:
2910 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX1_NSS1INDEX8,
2911 MASKBYTE2, power_index);
2912 break;
2913 case DESC_RATEVHT2SS_MCS1:
2914 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX1_NSS1INDEX8,
2915 MASKBYTE3, power_index);
2916 break;
2917 case DESC_RATEVHT2SS_MCS2:
2918 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX5_NSS2INDEX2,
2919 MASKBYTE0, power_index);
2920 break;
2921 case DESC_RATEVHT2SS_MCS3:
2922 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX5_NSS2INDEX2,
2923 MASKBYTE1, power_index);
2924 break;
2925 case DESC_RATEVHT2SS_MCS4:
2926 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX5_NSS2INDEX2,
2927 MASKBYTE2, power_index);
2928 break;
2929 case DESC_RATEVHT2SS_MCS5:
2930 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX5_NSS2INDEX2,
2931 MASKBYTE3, power_index);
2932 break;
2933 case DESC_RATEVHT2SS_MCS6:
2934 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX9_NSS2INDEX6,
2935 MASKBYTE0, power_index);
2936 break;
2937 case DESC_RATEVHT2SS_MCS7:
2938 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX9_NSS2INDEX6,
2939 MASKBYTE1, power_index);
2940 break;
2941 case DESC_RATEVHT2SS_MCS8:
2942 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX9_NSS2INDEX6,
2943 MASKBYTE2, power_index);
2944 break;
2945 case DESC_RATEVHT2SS_MCS9:
2946 rtl_set_bbreg(hw, RTXAGC_A_NSS2INDEX9_NSS2INDEX6,
2947 MASKBYTE3, power_index);
2948 break;
2949 default:
2950 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD,
2951 "Invalid Rate!!\n");
2952 break;
2953 }
2954 } else if (path == RF90_PATH_B) {
2955 switch (rate) {
2956 case DESC_RATE1M:
2957 rtl_set_bbreg(hw, RTXAGC_B_CCK11_CCK1,
2958 MASKBYTE0, power_index);
2959 break;
2960 case DESC_RATE2M:
2961 rtl_set_bbreg(hw, RTXAGC_B_CCK11_CCK1,
2962 MASKBYTE1, power_index);
2963 break;
2964 case DESC_RATE5_5M:
2965 rtl_set_bbreg(hw, RTXAGC_B_CCK11_CCK1,
2966 MASKBYTE2, power_index);
2967 break;
2968 case DESC_RATE11M:
2969 rtl_set_bbreg(hw, RTXAGC_B_CCK11_CCK1,
2970 MASKBYTE3, power_index);
2971 break;
2972 case DESC_RATE6M:
2973 rtl_set_bbreg(hw, RTXAGC_B_OFDM18_OFDM6,
2974 MASKBYTE0, power_index);
2975 break;
2976 case DESC_RATE9M:
2977 rtl_set_bbreg(hw, RTXAGC_B_OFDM18_OFDM6,
2978 MASKBYTE1, power_index);
2979 break;
2980 case DESC_RATE12M:
2981 rtl_set_bbreg(hw, RTXAGC_B_OFDM18_OFDM6,
2982 MASKBYTE2, power_index);
2983 break;
2984 case DESC_RATE18M:
2985 rtl_set_bbreg(hw, RTXAGC_B_OFDM18_OFDM6,
2986 MASKBYTE3, power_index);
2987 break;
2988 case DESC_RATE24M:
2989 rtl_set_bbreg(hw, RTXAGC_B_OFDM54_OFDM24,
2990 MASKBYTE0, power_index);
2991 break;
2992 case DESC_RATE36M:
2993 rtl_set_bbreg(hw, RTXAGC_B_OFDM54_OFDM24,
2994 MASKBYTE1, power_index);
2995 break;
2996 case DESC_RATE48M:
2997 rtl_set_bbreg(hw, RTXAGC_B_OFDM54_OFDM24,
2998 MASKBYTE2, power_index);
2999 break;
3000 case DESC_RATE54M:
3001 rtl_set_bbreg(hw, RTXAGC_B_OFDM54_OFDM24,
3002 MASKBYTE3, power_index);
3003 break;
3004 case DESC_RATEMCS0:
3005 rtl_set_bbreg(hw, RTXAGC_B_MCS03_MCS00,
3006 MASKBYTE0, power_index);
3007 break;
3008 case DESC_RATEMCS1:
3009 rtl_set_bbreg(hw, RTXAGC_B_MCS03_MCS00,
3010 MASKBYTE1, power_index);
3011 break;
3012 case DESC_RATEMCS2:
3013 rtl_set_bbreg(hw, RTXAGC_B_MCS03_MCS00,
3014 MASKBYTE2, power_index);
3015 break;
3016 case DESC_RATEMCS3:
3017 rtl_set_bbreg(hw, RTXAGC_B_MCS03_MCS00,
3018 MASKBYTE3, power_index);
3019 break;
3020 case DESC_RATEMCS4:
3021 rtl_set_bbreg(hw, RTXAGC_B_MCS07_MCS04,
3022 MASKBYTE0, power_index);
3023 break;
3024 case DESC_RATEMCS5:
3025 rtl_set_bbreg(hw, RTXAGC_B_MCS07_MCS04,
3026 MASKBYTE1, power_index);
3027 break;
3028 case DESC_RATEMCS6:
3029 rtl_set_bbreg(hw, RTXAGC_B_MCS07_MCS04,
3030 MASKBYTE2, power_index);
3031 break;
3032 case DESC_RATEMCS7:
3033 rtl_set_bbreg(hw, RTXAGC_B_MCS07_MCS04,
3034 MASKBYTE3, power_index);
3035 break;
3036 case DESC_RATEMCS8:
3037 rtl_set_bbreg(hw, RTXAGC_B_MCS11_MCS08,
3038 MASKBYTE0, power_index);
3039 break;
3040 case DESC_RATEMCS9:
3041 rtl_set_bbreg(hw, RTXAGC_B_MCS11_MCS08,
3042 MASKBYTE1, power_index);
3043 break;
3044 case DESC_RATEMCS10:
3045 rtl_set_bbreg(hw, RTXAGC_B_MCS11_MCS08,
3046 MASKBYTE2, power_index);
3047 break;
3048 case DESC_RATEMCS11:
3049 rtl_set_bbreg(hw, RTXAGC_B_MCS11_MCS08,
3050 MASKBYTE3, power_index);
3051 break;
3052 case DESC_RATEMCS12:
3053 rtl_set_bbreg(hw, RTXAGC_B_MCS15_MCS12,
3054 MASKBYTE0, power_index);
3055 break;
3056 case DESC_RATEMCS13:
3057 rtl_set_bbreg(hw, RTXAGC_B_MCS15_MCS12,
3058 MASKBYTE1, power_index);
3059 break;
3060 case DESC_RATEMCS14:
3061 rtl_set_bbreg(hw, RTXAGC_B_MCS15_MCS12,
3062 MASKBYTE2, power_index);
3063 break;
3064 case DESC_RATEMCS15:
3065 rtl_set_bbreg(hw, RTXAGC_B_MCS15_MCS12,
3066 MASKBYTE3, power_index);
3067 break;
3068 case DESC_RATEVHT1SS_MCS0:
3069 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX3_NSS1INDEX0,
3070 MASKBYTE0, power_index);
3071 break;
3072 case DESC_RATEVHT1SS_MCS1:
3073 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX3_NSS1INDEX0,
3074 MASKBYTE1, power_index);
3075 break;
3076 case DESC_RATEVHT1SS_MCS2:
3077 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX3_NSS1INDEX0,
3078 MASKBYTE2, power_index);
3079 break;
3080 case DESC_RATEVHT1SS_MCS3:
3081 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX3_NSS1INDEX0,
3082 MASKBYTE3, power_index);
3083 break;
3084 case DESC_RATEVHT1SS_MCS4:
3085 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX7_NSS1INDEX4,
3086 MASKBYTE0, power_index);
3087 break;
3088 case DESC_RATEVHT1SS_MCS5:
3089 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX7_NSS1INDEX4,
3090 MASKBYTE1, power_index);
3091 break;
3092 case DESC_RATEVHT1SS_MCS6:
3093 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX7_NSS1INDEX4,
3094 MASKBYTE2, power_index);
3095 break;
3096 case DESC_RATEVHT1SS_MCS7:
3097 rtl_set_bbreg(hw, RTXAGC_B_NSS1INDEX7_NSS1INDEX4,
3098 MASKBYTE3, power_index);
3099 break;
3100 case DESC_RATEVHT1SS_MCS8:
3101 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX1_NSS1INDEX8,
3102 MASKBYTE0, power_index);
3103 break;
3104 case DESC_RATEVHT1SS_MCS9:
3105 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX1_NSS1INDEX8,
3106 MASKBYTE1, power_index);
3107 break;
3108 case DESC_RATEVHT2SS_MCS0:
3109 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX1_NSS1INDEX8,
3110 MASKBYTE2, power_index);
3111 break;
3112 case DESC_RATEVHT2SS_MCS1:
3113 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX1_NSS1INDEX8,
3114 MASKBYTE3, power_index);
3115 break;
3116 case DESC_RATEVHT2SS_MCS2:
3117 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX5_NSS2INDEX2,
3118 MASKBYTE0, power_index);
3119 break;
3120 case DESC_RATEVHT2SS_MCS3:
3121 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX5_NSS2INDEX2,
3122 MASKBYTE1, power_index);
3123 break;
3124 case DESC_RATEVHT2SS_MCS4:
3125 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX5_NSS2INDEX2,
3126 MASKBYTE2, power_index);
3127 break;
3128 case DESC_RATEVHT2SS_MCS5:
3129 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX5_NSS2INDEX2,
3130 MASKBYTE3, power_index);
3131 break;
3132 case DESC_RATEVHT2SS_MCS6:
3133 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX9_NSS2INDEX6,
3134 MASKBYTE0, power_index);
3135 break;
3136 case DESC_RATEVHT2SS_MCS7:
3137 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX9_NSS2INDEX6,
3138 MASKBYTE1, power_index);
3139 break;
3140 case DESC_RATEVHT2SS_MCS8:
3141 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX9_NSS2INDEX6,
3142 MASKBYTE2, power_index);
3143 break;
3144 case DESC_RATEVHT2SS_MCS9:
3145 rtl_set_bbreg(hw, RTXAGC_B_NSS2INDEX9_NSS2INDEX6,
3146 MASKBYTE3, power_index);
3147 break;
3148 default:
3149 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD,
3150 "Invalid Rate!!\n");
3151 break;
3152 }
3153 } else {
3154 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD,
3155 "Invalid RFPath!!\n");
3156 }
3157 }
3158
3159 static void _rtl8821ae_phy_set_txpower_level_by_path(struct ieee80211_hw *hw,
3160 u8 *array, u8 path,
3161 u8 channel, u8 size)
3162 {
3163 struct rtl_priv *rtlpriv = rtl_priv(hw);
3164 struct rtl_phy *rtlphy = &rtlpriv->phy;
3165 u8 i;
3166 u8 power_index;
3167
3168 for (i = 0; i < size; i++) {
3169 power_index =
3170 _rtl8821ae_get_txpower_index(hw, path, array[i],
3171 rtlphy->current_chan_bw,
3172 channel);
3173 _rtl8821ae_phy_set_txpower_index(hw, power_index, path,
3174 array[i]);
3175 }
3176 }
3177
3178 static void _rtl8821ae_phy_txpower_training_by_path(struct ieee80211_hw *hw,
3179 u8 bw, u8 channel, u8 path)
3180 {
3181 struct rtl_priv *rtlpriv = rtl_priv(hw);
3182 struct rtl_phy *rtlphy = &rtlpriv->phy;
3183
3184 u8 i;
3185 u32 power_level, data, offset;
3186
3187 if (path >= rtlphy->num_total_rfpath)
3188 return;
3189
3190 data = 0;
3191 if (path == RF90_PATH_A) {
3192 power_level =
3193 _rtl8821ae_get_txpower_index(hw, RF90_PATH_A,
3194 DESC_RATEMCS7, bw, channel);
3195 offset = RA_TXPWRTRAING;
3196 } else {
3197 power_level =
3198 _rtl8821ae_get_txpower_index(hw, RF90_PATH_B,
3199 DESC_RATEMCS7, bw, channel);
3200 offset = RB_TXPWRTRAING;
3201 }
3202
3203 for (i = 0; i < 3; i++) {
3204 if (i == 0)
3205 power_level = power_level - 10;
3206 else if (i == 1)
3207 power_level = power_level - 8;
3208 else
3209 power_level = power_level - 6;
3210
3211 data |= (((power_level > 2) ? (power_level) : 2) << (i * 8));
3212 }
3213 rtl_set_bbreg(hw, offset, 0xffffff, data);
3214 }
3215
3216 void rtl8821ae_phy_set_txpower_level_by_path(struct ieee80211_hw *hw,
3217 u8 channel, u8 path)
3218 {
3219 /* struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw)); */
3220 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
3221 struct rtl_priv *rtlpriv = rtl_priv(hw);
3222 struct rtl_phy *rtlphy = &rtlpriv->phy;
3223 u8 cck_rates[] = {DESC_RATE1M, DESC_RATE2M, DESC_RATE5_5M,
3224 DESC_RATE11M};
3225 u8 sizes_of_cck_retes = 4;
3226 u8 ofdm_rates[] = {DESC_RATE6M, DESC_RATE9M, DESC_RATE12M,
3227 DESC_RATE18M, DESC_RATE24M, DESC_RATE36M,
3228 DESC_RATE48M, DESC_RATE54M};
3229 u8 sizes_of_ofdm_retes = 8;
3230 u8 ht_rates_1t[] = {DESC_RATEMCS0, DESC_RATEMCS1, DESC_RATEMCS2,
3231 DESC_RATEMCS3, DESC_RATEMCS4, DESC_RATEMCS5,
3232 DESC_RATEMCS6, DESC_RATEMCS7};
3233 u8 sizes_of_ht_retes_1t = 8;
3234 u8 ht_rates_2t[] = {DESC_RATEMCS8, DESC_RATEMCS9,
3235 DESC_RATEMCS10, DESC_RATEMCS11,
3236 DESC_RATEMCS12, DESC_RATEMCS13,
3237 DESC_RATEMCS14, DESC_RATEMCS15};
3238 u8 sizes_of_ht_retes_2t = 8;
3239 u8 vht_rates_1t[] = {DESC_RATEVHT1SS_MCS0, DESC_RATEVHT1SS_MCS1,
3240 DESC_RATEVHT1SS_MCS2, DESC_RATEVHT1SS_MCS3,
3241 DESC_RATEVHT1SS_MCS4, DESC_RATEVHT1SS_MCS5,
3242 DESC_RATEVHT1SS_MCS6, DESC_RATEVHT1SS_MCS7,
3243 DESC_RATEVHT1SS_MCS8, DESC_RATEVHT1SS_MCS9};
3244 u8 vht_rates_2t[] = {DESC_RATEVHT2SS_MCS0, DESC_RATEVHT2SS_MCS1,
3245 DESC_RATEVHT2SS_MCS2, DESC_RATEVHT2SS_MCS3,
3246 DESC_RATEVHT2SS_MCS4, DESC_RATEVHT2SS_MCS5,
3247 DESC_RATEVHT2SS_MCS6, DESC_RATEVHT2SS_MCS7,
3248 DESC_RATEVHT2SS_MCS8, DESC_RATEVHT2SS_MCS9};
3249 u8 sizes_of_vht_retes = 10;
3250
3251 if (rtlhal->current_bandtype == BAND_ON_2_4G)
3252 _rtl8821ae_phy_set_txpower_level_by_path(hw, cck_rates, path, channel,
3253 sizes_of_cck_retes);
3254
3255 _rtl8821ae_phy_set_txpower_level_by_path(hw, ofdm_rates, path, channel,
3256 sizes_of_ofdm_retes);
3257 _rtl8821ae_phy_set_txpower_level_by_path(hw, ht_rates_1t, path, channel,
3258 sizes_of_ht_retes_1t);
3259 _rtl8821ae_phy_set_txpower_level_by_path(hw, vht_rates_1t, path, channel,
3260 sizes_of_vht_retes);
3261
3262 if (rtlphy->num_total_rfpath >= 2) {
3263 _rtl8821ae_phy_set_txpower_level_by_path(hw, ht_rates_2t, path,
3264 channel,
3265 sizes_of_ht_retes_2t);
3266 _rtl8821ae_phy_set_txpower_level_by_path(hw, vht_rates_2t, path,
3267 channel,
3268 sizes_of_vht_retes);
3269 }
3270
3271 _rtl8821ae_phy_txpower_training_by_path(hw, rtlphy->current_chan_bw,
3272 channel, path);
3273 }
3274
3275 /*just in case, write txpower in DW, to reduce time*/
3276 void rtl8821ae_phy_set_txpower_level(struct ieee80211_hw *hw, u8 channel)
3277 {
3278 struct rtl_priv *rtlpriv = rtl_priv(hw);
3279 struct rtl_phy *rtlphy = &rtlpriv->phy;
3280 u8 path = 0;
3281
3282 for (path = RF90_PATH_A; path < rtlphy->num_total_rfpath; ++path)
3283 rtl8821ae_phy_set_txpower_level_by_path(hw, channel, path);
3284 }
3285
3286 static long _rtl8821ae_phy_txpwr_idx_to_dbm(struct ieee80211_hw *hw,
3287 enum wireless_mode wirelessmode,
3288 u8 txpwridx)
3289 {
3290 long offset;
3291 long pwrout_dbm;
3292
3293 switch (wirelessmode) {
3294 case WIRELESS_MODE_B:
3295 offset = -7;
3296 break;
3297 case WIRELESS_MODE_G:
3298 case WIRELESS_MODE_N_24G:
3299 offset = -8;
3300 break;
3301 default:
3302 offset = -8;
3303 break;
3304 }
3305 pwrout_dbm = txpwridx / 2 + offset;
3306 return pwrout_dbm;
3307 }
3308
3309 void rtl8821ae_phy_scan_operation_backup(struct ieee80211_hw *hw, u8 operation)
3310 {
3311 struct rtl_priv *rtlpriv = rtl_priv(hw);
3312 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
3313 enum io_type iotype = IO_CMD_PAUSE_BAND0_DM_BY_SCAN;
3314
3315 if (!is_hal_stop(rtlhal)) {
3316 switch (operation) {
3317 case SCAN_OPT_BACKUP_BAND0:
3318 iotype = IO_CMD_PAUSE_BAND0_DM_BY_SCAN;
3319 rtlpriv->cfg->ops->set_hw_reg(hw,
3320 HW_VAR_IO_CMD,
3321 (u8 *)&iotype);
3322
3323 break;
3324 case SCAN_OPT_BACKUP_BAND1:
3325 iotype = IO_CMD_PAUSE_BAND1_DM_BY_SCAN;
3326 rtlpriv->cfg->ops->set_hw_reg(hw,
3327 HW_VAR_IO_CMD,
3328 (u8 *)&iotype);
3329
3330 break;
3331 case SCAN_OPT_RESTORE:
3332 iotype = IO_CMD_RESUME_DM_BY_SCAN;
3333 rtlpriv->cfg->ops->set_hw_reg(hw,
3334 HW_VAR_IO_CMD,
3335 (u8 *)&iotype);
3336 break;
3337 default:
3338 pr_err("Unknown Scan Backup operation.\n");
3339 break;
3340 }
3341 }
3342 }
3343
3344 static void _rtl8821ae_phy_set_reg_bw(struct rtl_priv *rtlpriv, u8 bw)
3345 {
3346 u16 reg_rf_mode_bw, tmp = 0;
3347
3348 reg_rf_mode_bw = rtl_read_word(rtlpriv, REG_TRXPTCL_CTL);
3349 switch (bw) {
3350 case HT_CHANNEL_WIDTH_20:
3351 rtl_write_word(rtlpriv, REG_TRXPTCL_CTL, reg_rf_mode_bw & 0xFE7F);
3352 break;
3353 case HT_CHANNEL_WIDTH_20_40:
3354 tmp = reg_rf_mode_bw | BIT(7);
3355 rtl_write_word(rtlpriv, REG_TRXPTCL_CTL, tmp & 0xFEFF);
3356 break;
3357 case HT_CHANNEL_WIDTH_80:
3358 tmp = reg_rf_mode_bw | BIT(8);
3359 rtl_write_word(rtlpriv, REG_TRXPTCL_CTL, tmp & 0xFF7F);
3360 break;
3361 default:
3362 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING, "unknown Bandwidth: 0x%x\n", bw);
3363 break;
3364 }
3365 }
3366
3367 static u8 _rtl8821ae_phy_get_secondary_chnl(struct rtl_priv *rtlpriv)
3368 {
3369 struct rtl_phy *rtlphy = &rtlpriv->phy;
3370 struct rtl_mac *mac = rtl_mac(rtlpriv);
3371 u8 sc_set_40 = 0, sc_set_20 = 0;
3372
3373 if (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_80) {
3374 if (mac->cur_80_prime_sc == PRIME_CHNL_OFFSET_LOWER)
3375 sc_set_40 = VHT_DATA_SC_40_LOWER_OF_80MHZ;
3376 else if (mac->cur_80_prime_sc == PRIME_CHNL_OFFSET_UPPER)
3377 sc_set_40 = VHT_DATA_SC_40_UPPER_OF_80MHZ;
3378 else
3379 pr_err("SCMapping: Not Correct Primary40MHz Setting\n");
3380
3381 if ((mac->cur_40_prime_sc == PRIME_CHNL_OFFSET_LOWER) &&
3382 (mac->cur_80_prime_sc == HAL_PRIME_CHNL_OFFSET_LOWER))
3383 sc_set_20 = VHT_DATA_SC_20_LOWEST_OF_80MHZ;
3384 else if ((mac->cur_40_prime_sc == PRIME_CHNL_OFFSET_UPPER) &&
3385 (mac->cur_80_prime_sc == HAL_PRIME_CHNL_OFFSET_LOWER))
3386 sc_set_20 = VHT_DATA_SC_20_LOWER_OF_80MHZ;
3387 else if ((mac->cur_40_prime_sc == PRIME_CHNL_OFFSET_LOWER) &&
3388 (mac->cur_80_prime_sc == HAL_PRIME_CHNL_OFFSET_UPPER))
3389 sc_set_20 = VHT_DATA_SC_20_UPPER_OF_80MHZ;
3390 else if ((mac->cur_40_prime_sc == PRIME_CHNL_OFFSET_UPPER) &&
3391 (mac->cur_80_prime_sc == HAL_PRIME_CHNL_OFFSET_UPPER))
3392 sc_set_20 = VHT_DATA_SC_20_UPPERST_OF_80MHZ;
3393 else
3394 pr_err("SCMapping: Not Correct Primary40MHz Setting\n");
3395 } else if (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_20_40) {
3396 if (mac->cur_40_prime_sc == PRIME_CHNL_OFFSET_UPPER)
3397 sc_set_20 = VHT_DATA_SC_20_UPPER_OF_80MHZ;
3398 else if (mac->cur_40_prime_sc == PRIME_CHNL_OFFSET_LOWER)
3399 sc_set_20 = VHT_DATA_SC_20_LOWER_OF_80MHZ;
3400 else
3401 pr_err("SCMapping: Not Correct Primary40MHz Setting\n");
3402 }
3403 return (sc_set_40 << 4) | sc_set_20;
3404 }
3405
3406 void rtl8821ae_phy_set_bw_mode_callback(struct ieee80211_hw *hw)
3407 {
3408 struct rtl_priv *rtlpriv = rtl_priv(hw);
3409 struct rtl_phy *rtlphy = &rtlpriv->phy;
3410 u8 sub_chnl = 0;
3411 u8 l1pk_val = 0;
3412
3413 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
3414 "Switch to %s bandwidth\n",
3415 (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_20 ?
3416 "20MHz" :
3417 (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_20_40 ?
3418 "40MHz" : "80MHz")));
3419
3420 _rtl8821ae_phy_set_reg_bw(rtlpriv, rtlphy->current_chan_bw);
3421 sub_chnl = _rtl8821ae_phy_get_secondary_chnl(rtlpriv);
3422 rtl_write_byte(rtlpriv, 0x0483, sub_chnl);
3423
3424 switch (rtlphy->current_chan_bw) {
3425 case HT_CHANNEL_WIDTH_20:
3426 rtl_set_bbreg(hw, RRFMOD, 0x003003C3, 0x00300200);
3427 rtl_set_bbreg(hw, RADC_BUF_CLK, BIT(30), 0);
3428
3429 if (rtlphy->rf_type == RF_2T2R)
3430 rtl_set_bbreg(hw, RL1PEAKTH, 0x03C00000, 7);
3431 else
3432 rtl_set_bbreg(hw, RL1PEAKTH, 0x03C00000, 8);
3433 break;
3434 case HT_CHANNEL_WIDTH_20_40:
3435 rtl_set_bbreg(hw, RRFMOD, 0x003003C3, 0x00300201);
3436 rtl_set_bbreg(hw, RADC_BUF_CLK, BIT(30), 0);
3437 rtl_set_bbreg(hw, RRFMOD, 0x3C, sub_chnl);
3438 rtl_set_bbreg(hw, RCCAONSEC, 0xf0000000, sub_chnl);
3439
3440 if (rtlphy->reg_837 & BIT(2))
3441 l1pk_val = 6;
3442 else {
3443 if (rtlphy->rf_type == RF_2T2R)
3444 l1pk_val = 7;
3445 else
3446 l1pk_val = 8;
3447 }
3448 /* 0x848[25:22] = 0x6 */
3449 rtl_set_bbreg(hw, RL1PEAKTH, 0x03C00000, l1pk_val);
3450
3451 if (sub_chnl == VHT_DATA_SC_20_UPPER_OF_80MHZ)
3452 rtl_set_bbreg(hw, RCCK_SYSTEM, BCCK_SYSTEM, 1);
3453 else
3454 rtl_set_bbreg(hw, RCCK_SYSTEM, BCCK_SYSTEM, 0);
3455 break;
3456
3457 case HT_CHANNEL_WIDTH_80:
3458 /* 0x8ac[21,20,9:6,1,0]=8'b11100010 */
3459 rtl_set_bbreg(hw, RRFMOD, 0x003003C3, 0x00300202);
3460 /* 0x8c4[30] = 1 */
3461 rtl_set_bbreg(hw, RADC_BUF_CLK, BIT(30), 1);
3462 rtl_set_bbreg(hw, RRFMOD, 0x3C, sub_chnl);
3463 rtl_set_bbreg(hw, RCCAONSEC, 0xf0000000, sub_chnl);
3464
3465 if (rtlphy->reg_837 & BIT(2))
3466 l1pk_val = 5;
3467 else {
3468 if (rtlphy->rf_type == RF_2T2R)
3469 l1pk_val = 6;
3470 else
3471 l1pk_val = 7;
3472 }
3473 rtl_set_bbreg(hw, RL1PEAKTH, 0x03C00000, l1pk_val);
3474
3475 break;
3476 default:
3477 pr_err("unknown bandwidth: %#X\n",
3478 rtlphy->current_chan_bw);
3479 break;
3480 }
3481
3482 rtl8812ae_fixspur(hw, rtlphy->current_chan_bw, rtlphy->current_channel);
3483
3484 rtl8821ae_phy_rf6052_set_bandwidth(hw, rtlphy->current_chan_bw);
3485 rtlphy->set_bwmode_inprogress = false;
3486
3487 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD, "\n");
3488 }
3489
3490 void rtl8821ae_phy_set_bw_mode(struct ieee80211_hw *hw,
3491 enum nl80211_channel_type ch_type)
3492 {
3493 struct rtl_priv *rtlpriv = rtl_priv(hw);
3494 struct rtl_phy *rtlphy = &rtlpriv->phy;
3495 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
3496 u8 tmp_bw = rtlphy->current_chan_bw;
3497
3498 if (rtlphy->set_bwmode_inprogress)
3499 return;
3500 rtlphy->set_bwmode_inprogress = true;
3501 if ((!is_hal_stop(rtlhal)) && !(RT_CANNOT_IO(hw)))
3502 rtl8821ae_phy_set_bw_mode_callback(hw);
3503 else {
3504 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
3505 "FALSE driver sleep or unload\n");
3506 rtlphy->set_bwmode_inprogress = false;
3507 rtlphy->current_chan_bw = tmp_bw;
3508 }
3509 }
3510
3511 void rtl8821ae_phy_sw_chnl_callback(struct ieee80211_hw *hw)
3512 {
3513 struct rtl_priv *rtlpriv = rtl_priv(hw);
3514 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
3515 struct rtl_phy *rtlphy = &rtlpriv->phy;
3516 u8 channel = rtlphy->current_channel;
3517 u8 path;
3518 u32 data;
3519
3520 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
3521 "switch to channel%d\n", rtlphy->current_channel);
3522 if (is_hal_stop(rtlhal))
3523 return;
3524
3525 if (36 <= channel && channel <= 48)
3526 data = 0x494;
3527 else if (50 <= channel && channel <= 64)
3528 data = 0x453;
3529 else if (100 <= channel && channel <= 116)
3530 data = 0x452;
3531 else if (118 <= channel)
3532 data = 0x412;
3533 else
3534 data = 0x96a;
3535 rtl_set_bbreg(hw, RFC_AREA, 0x1ffe0000, data);
3536
3537 for (path = RF90_PATH_A; path < rtlphy->num_total_rfpath; path++) {
3538 if (36 <= channel && channel <= 64)
3539 data = 0x101;
3540 else if (100 <= channel && channel <= 140)
3541 data = 0x301;
3542 else if (140 < channel)
3543 data = 0x501;
3544 else
3545 data = 0x000;
3546 rtl8821ae_phy_set_rf_reg(hw, path, RF_CHNLBW,
3547 BIT(18)|BIT(17)|BIT(16)|BIT(9)|BIT(8), data);
3548
3549 rtl8821ae_phy_set_rf_reg(hw, path, RF_CHNLBW,
3550 BMASKBYTE0, channel);
3551
3552 if (channel > 14) {
3553 if (rtlhal->hw_type == HARDWARE_TYPE_RTL8821AE) {
3554 if (36 <= channel && channel <= 64)
3555 data = 0x114E9;
3556 else if (100 <= channel && channel <= 140)
3557 data = 0x110E9;
3558 else
3559 data = 0x110E9;
3560 rtl8821ae_phy_set_rf_reg(hw, path, RF_APK,
3561 BRFREGOFFSETMASK, data);
3562 }
3563 }
3564 }
3565 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE, "\n");
3566 }
3567
3568 u8 rtl8821ae_phy_sw_chnl(struct ieee80211_hw *hw)
3569 {
3570 struct rtl_priv *rtlpriv = rtl_priv(hw);
3571 struct rtl_phy *rtlphy = &rtlpriv->phy;
3572 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
3573 u32 timeout = 1000, timecount = 0;
3574 u8 channel = rtlphy->current_channel;
3575
3576 if (rtlphy->sw_chnl_inprogress)
3577 return 0;
3578 if (rtlphy->set_bwmode_inprogress)
3579 return 0;
3580
3581 if ((is_hal_stop(rtlhal)) || (RT_CANNOT_IO(hw))) {
3582 RT_TRACE(rtlpriv, COMP_CHAN, DBG_LOUD,
3583 "sw_chnl_inprogress false driver sleep or unload\n");
3584 return 0;
3585 }
3586 while (rtlphy->lck_inprogress && timecount < timeout) {
3587 mdelay(50);
3588 timecount += 50;
3589 }
3590
3591 if (rtlphy->current_channel > 14 && rtlhal->current_bandtype != BAND_ON_5G)
3592 rtl8821ae_phy_switch_wirelessband(hw, BAND_ON_5G);
3593 else if (rtlphy->current_channel <= 14 && rtlhal->current_bandtype != BAND_ON_2_4G)
3594 rtl8821ae_phy_switch_wirelessband(hw, BAND_ON_2_4G);
3595
3596 rtlphy->sw_chnl_inprogress = true;
3597 if (channel == 0)
3598 channel = 1;
3599
3600 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
3601 "switch to channel%d, band type is %d\n",
3602 rtlphy->current_channel, rtlhal->current_bandtype);
3603
3604 rtl8821ae_phy_sw_chnl_callback(hw);
3605
3606 rtl8821ae_dm_clear_txpower_tracking_state(hw);
3607 rtl8821ae_phy_set_txpower_level(hw, rtlphy->current_channel);
3608
3609 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE, "\n");
3610 rtlphy->sw_chnl_inprogress = false;
3611 return 1;
3612 }
3613
3614 u8 _rtl8812ae_get_right_chnl_place_for_iqk(u8 chnl)
3615 {
3616 static const u8 channel_all[TARGET_CHNL_NUM_2G_5G_8812] = {
3617 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,
3618 14, 36, 38, 40, 42, 44, 46, 48, 50, 52, 54,
3619 56, 58, 60, 62, 64, 100, 102, 104, 106, 108,
3620 110, 112, 114, 116, 118, 120, 122, 124, 126,
3621 128, 130, 132, 134, 136, 138, 140, 149, 151,
3622 153, 155, 157, 159, 161, 163, 165};
3623 u8 place;
3624
3625 if (chnl > 14) {
3626 for (place = 14; place < sizeof(channel_all); place++)
3627 if (channel_all[place] == chnl)
3628 return place-13;
3629 }
3630
3631 return 0;
3632 }
3633
3634 #define MACBB_REG_NUM 10
3635 #define AFE_REG_NUM 14
3636 #define RF_REG_NUM 3
3637
3638 static void _rtl8821ae_iqk_backup_macbb(struct ieee80211_hw *hw,
3639 u32 *macbb_backup,
3640 u32 *backup_macbb_reg, u32 mac_bb_num)
3641 {
3642 struct rtl_priv *rtlpriv = rtl_priv(hw);
3643 u32 i;
3644
3645 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /*[31] = 0 --> Page C*/
3646 /*save MACBB default value*/
3647 for (i = 0; i < mac_bb_num; i++)
3648 macbb_backup[i] = rtl_read_dword(rtlpriv, backup_macbb_reg[i]);
3649
3650 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "BackupMacBB Success!!!!\n");
3651 }
3652
3653 static void _rtl8821ae_iqk_backup_afe(struct ieee80211_hw *hw, u32 *afe_backup,
3654 u32 *backup_afe_REG, u32 afe_num)
3655 {
3656 struct rtl_priv *rtlpriv = rtl_priv(hw);
3657 u32 i;
3658
3659 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /*[31] = 0 --> Page C*/
3660 /*Save AFE Parameters */
3661 for (i = 0; i < afe_num; i++)
3662 afe_backup[i] = rtl_read_dword(rtlpriv, backup_afe_REG[i]);
3663 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "BackupAFE Success!!!!\n");
3664 }
3665
3666 static void _rtl8821ae_iqk_backup_rf(struct ieee80211_hw *hw, u32 *rfa_backup,
3667 u32 *rfb_backup, u32 *backup_rf_reg,
3668 u32 rf_num)
3669 {
3670 struct rtl_priv *rtlpriv = rtl_priv(hw);
3671 u32 i;
3672
3673 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /*[31] = 0 --> Page C*/
3674 /*Save RF Parameters*/
3675 for (i = 0; i < rf_num; i++) {
3676 rfa_backup[i] = rtl_get_rfreg(hw, RF90_PATH_A, backup_rf_reg[i],
3677 BMASKDWORD);
3678 rfb_backup[i] = rtl_get_rfreg(hw, RF90_PATH_B, backup_rf_reg[i],
3679 BMASKDWORD);
3680 }
3681 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "BackupRF Success!!!!\n");
3682 }
3683
3684 static void _rtl8821ae_iqk_configure_mac(
3685 struct ieee80211_hw *hw
3686 )
3687 {
3688 struct rtl_priv *rtlpriv = rtl_priv(hw);
3689 /* ========MAC register setting========*/
3690 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /*[31] = 0 --> Page C*/
3691 rtl_write_byte(rtlpriv, 0x522, 0x3f);
3692 rtl_set_bbreg(hw, 0x550, BIT(11) | BIT(3), 0x0);
3693 rtl_write_byte(rtlpriv, 0x808, 0x00); /*RX ante off*/
3694 rtl_set_bbreg(hw, 0x838, 0xf, 0xc); /*CCA off*/
3695 }
3696
3697 static void _rtl8821ae_iqk_tx_fill_iqc(struct ieee80211_hw *hw,
3698 enum radio_path path, u32 tx_x, u32 tx_y)
3699 {
3700 struct rtl_priv *rtlpriv = rtl_priv(hw);
3701 switch (path) {
3702 case RF90_PATH_A:
3703 /* [31] = 1 --> Page C1 */
3704 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1);
3705 rtl_write_dword(rtlpriv, 0xc90, 0x00000080);
3706 rtl_write_dword(rtlpriv, 0xcc4, 0x20040000);
3707 rtl_write_dword(rtlpriv, 0xcc8, 0x20000000);
3708 rtl_set_bbreg(hw, 0xccc, 0x000007ff, tx_y);
3709 rtl_set_bbreg(hw, 0xcd4, 0x000007ff, tx_x);
3710 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
3711 "TX_X = %x;;TX_Y = %x =====> fill to IQC\n",
3712 tx_x, tx_y);
3713 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
3714 "0xcd4 = %x;;0xccc = %x ====>fill to IQC\n",
3715 rtl_get_bbreg(hw, 0xcd4, 0x000007ff),
3716 rtl_get_bbreg(hw, 0xccc, 0x000007ff));
3717 break;
3718 default:
3719 break;
3720 }
3721 }
3722
3723 static void _rtl8821ae_iqk_rx_fill_iqc(struct ieee80211_hw *hw,
3724 enum radio_path path, u32 rx_x, u32 rx_y)
3725 {
3726 struct rtl_priv *rtlpriv = rtl_priv(hw);
3727 switch (path) {
3728 case RF90_PATH_A:
3729 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
3730 rtl_set_bbreg(hw, 0xc10, 0x000003ff, rx_x>>1);
3731 rtl_set_bbreg(hw, 0xc10, 0x03ff0000, rx_y>>1);
3732 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
3733 "rx_x = %x;;rx_y = %x ====>fill to IQC\n",
3734 rx_x>>1, rx_y>>1);
3735 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
3736 "0xc10 = %x ====>fill to IQC\n",
3737 rtl_read_dword(rtlpriv, 0xc10));
3738 break;
3739 default:
3740 break;
3741 }
3742 }
3743
3744 #define cal_num 10
3745
3746 static void _rtl8821ae_iqk_tx(struct ieee80211_hw *hw, enum radio_path path)
3747 {
3748 struct rtl_priv *rtlpriv = rtl_priv(hw);
3749 struct rtl_phy *rtlphy = &rtlpriv->phy;
3750 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
3751
3752 u32 tx_fail, rx_fail, delay_count, iqk_ready, cal_retry, cal = 0, temp_reg65;
3753 int tx_x = 0, tx_y = 0, rx_x = 0, rx_y = 0, tx_average = 0, rx_average = 0;
3754 int tx_x0[cal_num], tx_y0[cal_num], tx_x0_rxk[cal_num],
3755 tx_y0_rxk[cal_num], rx_x0[cal_num], rx_y0[cal_num],
3756 tx_dt[cal_num], rx_dt[cal_num];
3757 bool tx0iqkok = false, rx0iqkok = false;
3758 bool vdf_enable = false;
3759 int i, k, vdf_y[3], vdf_x[3],
3760 ii, dx = 0, dy = 0, tx_finish = 0, rx_finish = 0;
3761
3762 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
3763 "BandWidth = %d.\n",
3764 rtlphy->current_chan_bw);
3765 if (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_80)
3766 vdf_enable = true;
3767
3768 while (cal < cal_num) {
3769 switch (path) {
3770 case RF90_PATH_A:
3771 temp_reg65 = rtl_get_rfreg(hw, path, 0x65, 0xffffffff);
3772 /* Path-A LOK */
3773 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /*[31] = 0 --> Page C*/
3774 /*========Path-A AFE all on========*/
3775 /*Port 0 DAC/ADC on*/
3776 rtl_write_dword(rtlpriv, 0xc60, 0x77777777);
3777 rtl_write_dword(rtlpriv, 0xc64, 0x77777777);
3778 rtl_write_dword(rtlpriv, 0xc68, 0x19791979);
3779 rtl_write_dword(rtlpriv, 0xc6c, 0x19791979);
3780 rtl_write_dword(rtlpriv, 0xc70, 0x19791979);
3781 rtl_write_dword(rtlpriv, 0xc74, 0x19791979);
3782 rtl_write_dword(rtlpriv, 0xc78, 0x19791979);
3783 rtl_write_dword(rtlpriv, 0xc7c, 0x19791979);
3784 rtl_write_dword(rtlpriv, 0xc80, 0x19791979);
3785 rtl_write_dword(rtlpriv, 0xc84, 0x19791979);
3786
3787 rtl_set_bbreg(hw, 0xc00, 0xf, 0x4); /*hardware 3-wire off*/
3788
3789 /* LOK Setting */
3790 /* ====== LOK ====== */
3791 /*DAC/ADC sampling rate (160 MHz)*/
3792 rtl_set_bbreg(hw, 0xc5c, BIT(26) | BIT(25) | BIT(24), 0x7);
3793
3794 /* 2. LoK RF Setting (at BW = 20M) */
3795 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x80002);
3796 rtl_set_rfreg(hw, path, 0x18, 0x00c00, 0x3); /* BW 20M */
3797 rtl_set_rfreg(hw, path, 0x30, RFREG_OFFSET_MASK, 0x20000);
3798 rtl_set_rfreg(hw, path, 0x31, RFREG_OFFSET_MASK, 0x0003f);
3799 rtl_set_rfreg(hw, path, 0x32, RFREG_OFFSET_MASK, 0xf3fc3);
3800 rtl_set_rfreg(hw, path, 0x65, RFREG_OFFSET_MASK, 0x931d5);
3801 rtl_set_rfreg(hw, path, 0x8f, RFREG_OFFSET_MASK, 0x8a001);
3802 rtl_set_bbreg(hw, 0xcb8, 0xf, 0xd);
3803 rtl_write_dword(rtlpriv, 0x90c, 0x00008000);
3804 rtl_write_dword(rtlpriv, 0xb00, 0x03000100);
3805 rtl_set_bbreg(hw, 0xc94, BIT(0), 0x1);
3806 rtl_write_dword(rtlpriv, 0x978, 0x29002000);/* TX (X,Y) */
3807 rtl_write_dword(rtlpriv, 0x97c, 0xa9002000);/* RX (X,Y) */
3808 rtl_write_dword(rtlpriv, 0x984, 0x00462910);/* [0]:AGC_en, [15]:idac_K_Mask */
3809
3810 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
3811 rtl_write_dword(rtlpriv, 0xc88, 0x821403f4);
3812
3813 if (rtlhal->current_bandtype)
3814 rtl_write_dword(rtlpriv, 0xc8c, 0x68163e96);
3815 else
3816 rtl_write_dword(rtlpriv, 0xc8c, 0x28163e96);
3817
3818 rtl_write_dword(rtlpriv, 0xc80, 0x18008c10);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
3819 rtl_write_dword(rtlpriv, 0xc84, 0x38008c10);/* RX_TONE_idx[9:0], RxK_Mask[29] */
3820 rtl_write_dword(rtlpriv, 0xcb8, 0x00100000);/* cb8[20] \B1N SI/PI \A8Ï¥\CE\C5v\A4\C1\B5\B9 iqk_dpk module */
3821 rtl_write_dword(rtlpriv, 0x980, 0xfa000000);
3822 rtl_write_dword(rtlpriv, 0x980, 0xf8000000);
3823
3824 mdelay(10); /* Delay 10ms */
3825 rtl_write_dword(rtlpriv, 0xcb8, 0x00000000);
3826
3827 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
3828 rtl_set_rfreg(hw, path, 0x58, 0x7fe00, rtl_get_rfreg(hw, path, 0x8, 0xffc00)); /* Load LOK */
3829
3830 switch (rtlphy->current_chan_bw) {
3831 case 1:
3832 rtl_set_rfreg(hw, path, 0x18, 0x00c00, 0x1);
3833 break;
3834 case 2:
3835 rtl_set_rfreg(hw, path, 0x18, 0x00c00, 0x0);
3836 break;
3837 default:
3838 break;
3839 }
3840
3841 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
3842
3843 /* 3. TX RF Setting */
3844 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
3845 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x80000);
3846 rtl_set_rfreg(hw, path, 0x30, RFREG_OFFSET_MASK, 0x20000);
3847 rtl_set_rfreg(hw, path, 0x31, RFREG_OFFSET_MASK, 0x0003f);
3848 rtl_set_rfreg(hw, path, 0x32, RFREG_OFFSET_MASK, 0xf3fc3);
3849 rtl_set_rfreg(hw, path, 0x65, RFREG_OFFSET_MASK, 0x931d5);
3850 rtl_set_rfreg(hw, path, 0x8f, RFREG_OFFSET_MASK, 0x8a001);
3851 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x00000);
3852 /* ODM_SetBBReg(pDM_Odm, 0xcb8, 0xf, 0xd); */
3853 rtl_write_dword(rtlpriv, 0x90c, 0x00008000);
3854 rtl_write_dword(rtlpriv, 0xb00, 0x03000100);
3855 rtl_set_bbreg(hw, 0xc94, BIT(0), 0x1);
3856 rtl_write_dword(rtlpriv, 0x978, 0x29002000);/* TX (X,Y) */
3857 rtl_write_dword(rtlpriv, 0x97c, 0xa9002000);/* RX (X,Y) */
3858 rtl_write_dword(rtlpriv, 0x984, 0x0046a910);/* [0]:AGC_en, [15]:idac_K_Mask */
3859
3860 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
3861 rtl_write_dword(rtlpriv, 0xc88, 0x821403f1);
3862 if (rtlhal->current_bandtype)
3863 rtl_write_dword(rtlpriv, 0xc8c, 0x40163e96);
3864 else
3865 rtl_write_dword(rtlpriv, 0xc8c, 0x00163e96);
3866
3867 if (vdf_enable == 1) {
3868 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "VDF_enable\n");
3869 for (k = 0; k <= 2; k++) {
3870 switch (k) {
3871 case 0:
3872 rtl_write_dword(rtlpriv, 0xc80, 0x18008c38);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
3873 rtl_write_dword(rtlpriv, 0xc84, 0x38008c38);/* RX_TONE_idx[9:0], RxK_Mask[29] */
3874 rtl_set_bbreg(hw, 0xce8, BIT(31), 0x0);
3875 break;
3876 case 1:
3877 rtl_set_bbreg(hw, 0xc80, BIT(28), 0x0);
3878 rtl_set_bbreg(hw, 0xc84, BIT(28), 0x0);
3879 rtl_set_bbreg(hw, 0xce8, BIT(31), 0x0);
3880 break;
3881 case 2:
3882 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
3883 "vdf_y[1] = %x;;;vdf_y[0] = %x\n", vdf_y[1]>>21 & 0x00007ff, vdf_y[0]>>21 & 0x00007ff);
3884 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
3885 "vdf_x[1] = %x;;;vdf_x[0] = %x\n", vdf_x[1]>>21 & 0x00007ff, vdf_x[0]>>21 & 0x00007ff);
3886 tx_dt[cal] = (vdf_y[1]>>20)-(vdf_y[0]>>20);
3887 tx_dt[cal] = ((16*tx_dt[cal])*10000/15708);
3888 tx_dt[cal] = (tx_dt[cal] >> 1)+(tx_dt[cal] & BIT(0));
3889 rtl_write_dword(rtlpriv, 0xc80, 0x18008c20);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
3890 rtl_write_dword(rtlpriv, 0xc84, 0x38008c20);/* RX_TONE_idx[9:0], RxK_Mask[29] */
3891 rtl_set_bbreg(hw, 0xce8, BIT(31), 0x1);
3892 rtl_set_bbreg(hw, 0xce8, 0x3fff0000, tx_dt[cal] & 0x00003fff);
3893 break;
3894 default:
3895 break;
3896 }
3897 rtl_write_dword(rtlpriv, 0xcb8, 0x00100000);/* cb8[20] \B1N SI/PI \A8Ï¥\CE\C5v\A4\C1\B5\B9 iqk_dpk module */
3898 cal_retry = 0;
3899 while (1) {
3900 /* one shot */
3901 rtl_write_dword(rtlpriv, 0x980, 0xfa000000);
3902 rtl_write_dword(rtlpriv, 0x980, 0xf8000000);
3903
3904 mdelay(10); /* Delay 10ms */
3905 rtl_write_dword(rtlpriv, 0xcb8, 0x00000000);
3906 delay_count = 0;
3907 while (1) {
3908 iqk_ready = rtl_get_bbreg(hw, 0xd00, BIT(10));
3909 if ((~iqk_ready) || (delay_count > 20))
3910 break;
3911 else{
3912 mdelay(1);
3913 delay_count++;
3914 }
3915 }
3916
3917 if (delay_count < 20) { /* If 20ms No Result, then cal_retry++ */
3918 /* ============TXIQK Check============== */
3919 tx_fail = rtl_get_bbreg(hw, 0xd00, BIT(12));
3920
3921 if (~tx_fail) {
3922 rtl_write_dword(rtlpriv, 0xcb8, 0x02000000);
3923 vdf_x[k] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
3924 rtl_write_dword(rtlpriv, 0xcb8, 0x04000000);
3925 vdf_y[k] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
3926 tx0iqkok = true;
3927 break;
3928 } else {
3929 rtl_set_bbreg(hw, 0xccc, 0x000007ff, 0x0);
3930 rtl_set_bbreg(hw, 0xcd4, 0x000007ff, 0x200);
3931 tx0iqkok = false;
3932 cal_retry++;
3933 if (cal_retry == 10)
3934 break;
3935 }
3936 } else {
3937 tx0iqkok = false;
3938 cal_retry++;
3939 if (cal_retry == 10)
3940 break;
3941 }
3942 }
3943 }
3944 if (k == 3) {
3945 tx_x0[cal] = vdf_x[k-1];
3946 tx_y0[cal] = vdf_y[k-1];
3947 }
3948 } else {
3949 rtl_write_dword(rtlpriv, 0xc80, 0x18008c10);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
3950 rtl_write_dword(rtlpriv, 0xc84, 0x38008c10);/* RX_TONE_idx[9:0], RxK_Mask[29] */
3951 rtl_write_dword(rtlpriv, 0xcb8, 0x00100000);/* cb8[20] \B1N SI/PI \A8Ï¥\CE\C5v\A4\C1\B5\B9 iqk_dpk module */
3952 cal_retry = 0;
3953 while (1) {
3954 /* one shot */
3955 rtl_write_dword(rtlpriv, 0x980, 0xfa000000);
3956 rtl_write_dword(rtlpriv, 0x980, 0xf8000000);
3957
3958 mdelay(10); /* Delay 10ms */
3959 rtl_write_dword(rtlpriv, 0xcb8, 0x00000000);
3960 delay_count = 0;
3961 while (1) {
3962 iqk_ready = rtl_get_bbreg(hw, 0xd00, BIT(10));
3963 if ((~iqk_ready) || (delay_count > 20))
3964 break;
3965 else{
3966 mdelay(1);
3967 delay_count++;
3968 }
3969 }
3970
3971 if (delay_count < 20) { /* If 20ms No Result, then cal_retry++ */
3972 /* ============TXIQK Check============== */
3973 tx_fail = rtl_get_bbreg(hw, 0xd00, BIT(12));
3974
3975 if (~tx_fail) {
3976 rtl_write_dword(rtlpriv, 0xcb8, 0x02000000);
3977 tx_x0[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
3978 rtl_write_dword(rtlpriv, 0xcb8, 0x04000000);
3979 tx_y0[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
3980 tx0iqkok = true;
3981 break;
3982 } else {
3983 rtl_set_bbreg(hw, 0xccc, 0x000007ff, 0x0);
3984 rtl_set_bbreg(hw, 0xcd4, 0x000007ff, 0x200);
3985 tx0iqkok = false;
3986 cal_retry++;
3987 if (cal_retry == 10)
3988 break;
3989 }
3990 } else {
3991 tx0iqkok = false;
3992 cal_retry++;
3993 if (cal_retry == 10)
3994 break;
3995 }
3996 }
3997 }
3998
3999 if (tx0iqkok == false)
4000 break; /* TXK fail, Don't do RXK */
4001
4002 if (vdf_enable == 1) {
4003 rtl_set_bbreg(hw, 0xce8, BIT(31), 0x0); /* TX VDF Disable */
4004 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "RXVDF Start\n");
4005 for (k = 0; k <= 2; k++) {
4006 /* ====== RX mode TXK (RXK Step 1) ====== */
4007 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4008 /* 1. TX RF Setting */
4009 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x80000);
4010 rtl_set_rfreg(hw, path, 0x30, RFREG_OFFSET_MASK, 0x30000);
4011 rtl_set_rfreg(hw, path, 0x31, RFREG_OFFSET_MASK, 0x00029);
4012 rtl_set_rfreg(hw, path, 0x32, RFREG_OFFSET_MASK, 0xd7ffb);
4013 rtl_set_rfreg(hw, path, 0x65, RFREG_OFFSET_MASK, temp_reg65);
4014 rtl_set_rfreg(hw, path, 0x8f, RFREG_OFFSET_MASK, 0x8a001);
4015 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x00000);
4016
4017 rtl_set_bbreg(hw, 0xcb8, 0xf, 0xd);
4018 rtl_write_dword(rtlpriv, 0x978, 0x29002000);/* TX (X,Y) */
4019 rtl_write_dword(rtlpriv, 0x97c, 0xa9002000);/* RX (X,Y) */
4020 rtl_write_dword(rtlpriv, 0x984, 0x0046a910);/* [0]:AGC_en, [15]:idac_K_Mask */
4021 rtl_write_dword(rtlpriv, 0x90c, 0x00008000);
4022 rtl_write_dword(rtlpriv, 0xb00, 0x03000100);
4023 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
4024 switch (k) {
4025 case 0:
4026 {
4027 rtl_write_dword(rtlpriv, 0xc80, 0x18008c38);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
4028 rtl_write_dword(rtlpriv, 0xc84, 0x38008c38);/* RX_TONE_idx[9:0], RxK_Mask[29] */
4029 rtl_set_bbreg(hw, 0xce8, BIT(30), 0x0);
4030 }
4031 break;
4032 case 1:
4033 {
4034 rtl_write_dword(rtlpriv, 0xc80, 0x08008c38);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
4035 rtl_write_dword(rtlpriv, 0xc84, 0x28008c38);/* RX_TONE_idx[9:0], RxK_Mask[29] */
4036 rtl_set_bbreg(hw, 0xce8, BIT(30), 0x0);
4037 }
4038 break;
4039 case 2:
4040 {
4041 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4042 "VDF_Y[1] = %x;;;VDF_Y[0] = %x\n",
4043 vdf_y[1]>>21 & 0x00007ff, vdf_y[0]>>21 & 0x00007ff);
4044 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4045 "VDF_X[1] = %x;;;VDF_X[0] = %x\n",
4046 vdf_x[1]>>21 & 0x00007ff, vdf_x[0]>>21 & 0x00007ff);
4047 rx_dt[cal] = (vdf_y[1]>>20)-(vdf_y[0]>>20);
4048 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "Rx_dt = %d\n", rx_dt[cal]);
4049 rx_dt[cal] = ((16*rx_dt[cal])*10000/13823);
4050 rx_dt[cal] = (rx_dt[cal] >> 1)+(rx_dt[cal] & BIT(0));
4051 rtl_write_dword(rtlpriv, 0xc80, 0x18008c20);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
4052 rtl_write_dword(rtlpriv, 0xc84, 0x38008c20);/* RX_TONE_idx[9:0], RxK_Mask[29] */
4053 rtl_set_bbreg(hw, 0xce8, 0x00003fff, rx_dt[cal] & 0x00003fff);
4054 }
4055 break;
4056 default:
4057 break;
4058 }
4059 rtl_write_dword(rtlpriv, 0xc88, 0x821603e0);
4060 rtl_write_dword(rtlpriv, 0xc8c, 0x68163e96);
4061 rtl_write_dword(rtlpriv, 0xcb8, 0x00100000);/* cb8[20] \B1N SI/PI \A8Ï¥\CE\C5v\A4\C1\B5\B9 iqk_dpk module */
4062 cal_retry = 0;
4063 while (1) {
4064 /* one shot */
4065 rtl_write_dword(rtlpriv, 0x980, 0xfa000000);
4066 rtl_write_dword(rtlpriv, 0x980, 0xf8000000);
4067
4068 mdelay(10); /* Delay 10ms */
4069 rtl_write_dword(rtlpriv, 0xcb8, 0x00000000);
4070 delay_count = 0;
4071 while (1) {
4072 iqk_ready = rtl_get_bbreg(hw, 0xd00, BIT(10));
4073 if ((~iqk_ready) || (delay_count > 20))
4074 break;
4075 else{
4076 mdelay(1);
4077 delay_count++;
4078 }
4079 }
4080
4081 if (delay_count < 20) { /* If 20ms No Result, then cal_retry++ */
4082 /* ============TXIQK Check============== */
4083 tx_fail = rtl_get_bbreg(hw, 0xd00, BIT(12));
4084
4085 if (~tx_fail) {
4086 rtl_write_dword(rtlpriv, 0xcb8, 0x02000000);
4087 tx_x0_rxk[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4088 rtl_write_dword(rtlpriv, 0xcb8, 0x04000000);
4089 tx_y0_rxk[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4090 tx0iqkok = true;
4091 break;
4092 } else{
4093 tx0iqkok = false;
4094 cal_retry++;
4095 if (cal_retry == 10)
4096 break;
4097 }
4098 } else {
4099 tx0iqkok = false;
4100 cal_retry++;
4101 if (cal_retry == 10)
4102 break;
4103 }
4104 }
4105
4106 if (tx0iqkok == false) { /* If RX mode TXK fail, then take TXK Result */
4107 tx_x0_rxk[cal] = tx_x0[cal];
4108 tx_y0_rxk[cal] = tx_y0[cal];
4109 tx0iqkok = true;
4110 RT_TRACE(rtlpriv,
4111 COMP_IQK,
4112 DBG_LOUD,
4113 "RXK Step 1 fail\n");
4114 }
4115
4116 /* ====== RX IQK ====== */
4117 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4118 /* 1. RX RF Setting */
4119 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x80000);
4120 rtl_set_rfreg(hw, path, 0x30, RFREG_OFFSET_MASK, 0x30000);
4121 rtl_set_rfreg(hw, path, 0x31, RFREG_OFFSET_MASK, 0x0002f);
4122 rtl_set_rfreg(hw, path, 0x32, RFREG_OFFSET_MASK, 0xfffbb);
4123 rtl_set_rfreg(hw, path, 0x8f, RFREG_OFFSET_MASK, 0x88001);
4124 rtl_set_rfreg(hw, path, 0x65, RFREG_OFFSET_MASK, 0x931d8);
4125 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x00000);
4126
4127 rtl_set_bbreg(hw, 0x978, 0x03FF8000, (tx_x0_rxk[cal])>>21&0x000007ff);
4128 rtl_set_bbreg(hw, 0x978, 0x000007FF, (tx_y0_rxk[cal])>>21&0x000007ff);
4129 rtl_set_bbreg(hw, 0x978, BIT(31), 0x1);
4130 rtl_set_bbreg(hw, 0x97c, BIT(31), 0x0);
4131 rtl_set_bbreg(hw, 0xcb8, 0xF, 0xe);
4132 rtl_write_dword(rtlpriv, 0x90c, 0x00008000);
4133 rtl_write_dword(rtlpriv, 0x984, 0x0046a911);
4134
4135 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
4136 rtl_set_bbreg(hw, 0xc80, BIT(29), 0x1);
4137 rtl_set_bbreg(hw, 0xc84, BIT(29), 0x0);
4138 rtl_write_dword(rtlpriv, 0xc88, 0x02140119);
4139
4140 rtl_write_dword(rtlpriv, 0xc8c, 0x28160d00); /* pDM_Odm->SupportInterface == 1 */
4141
4142 if (k == 2)
4143 rtl_set_bbreg(hw, 0xce8, BIT(30), 0x1); /* RX VDF Enable */
4144 rtl_write_dword(rtlpriv, 0xcb8, 0x00100000);/* cb8[20] \B1N SI/PI \A8Ï¥\CE\C5v\A4\C1\B5\B9 iqk_dpk module */
4145
4146 cal_retry = 0;
4147 while (1) {
4148 /* one shot */
4149 rtl_write_dword(rtlpriv, 0x980, 0xfa000000);
4150 rtl_write_dword(rtlpriv, 0x980, 0xf8000000);
4151
4152 mdelay(10); /* Delay 10ms */
4153 rtl_write_dword(rtlpriv, 0xcb8, 0x00000000);
4154 delay_count = 0;
4155 while (1) {
4156 iqk_ready = rtl_get_bbreg(hw, 0xd00, BIT(10));
4157 if ((~iqk_ready) || (delay_count > 20))
4158 break;
4159 else{
4160 mdelay(1);
4161 delay_count++;
4162 }
4163 }
4164
4165 if (delay_count < 20) { /* If 20ms No Result, then cal_retry++ */
4166 /* ============RXIQK Check============== */
4167 rx_fail = rtl_get_bbreg(hw, 0xd00, BIT(11));
4168 if (rx_fail == 0) {
4169 rtl_write_dword(rtlpriv, 0xcb8, 0x06000000);
4170 vdf_x[k] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4171 rtl_write_dword(rtlpriv, 0xcb8, 0x08000000);
4172 vdf_y[k] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4173 rx0iqkok = true;
4174 break;
4175 } else {
4176 rtl_set_bbreg(hw, 0xc10, 0x000003ff, 0x200>>1);
4177 rtl_set_bbreg(hw, 0xc10, 0x03ff0000, 0x0>>1);
4178 rx0iqkok = false;
4179 cal_retry++;
4180 if (cal_retry == 10)
4181 break;
4182
4183 }
4184 } else{
4185 rx0iqkok = false;
4186 cal_retry++;
4187 if (cal_retry == 10)
4188 break;
4189 }
4190 }
4191
4192 }
4193 if (k == 3) {
4194 rx_x0[cal] = vdf_x[k-1];
4195 rx_y0[cal] = vdf_y[k-1];
4196 }
4197 rtl_set_bbreg(hw, 0xce8, BIT(31), 0x1); /* TX VDF Enable */
4198 }
4199
4200 else{
4201 /* ====== RX mode TXK (RXK Step 1) ====== */
4202 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4203 /* 1. TX RF Setting */
4204 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x80000);
4205 rtl_set_rfreg(hw, path, 0x30, RFREG_OFFSET_MASK, 0x30000);
4206 rtl_set_rfreg(hw, path, 0x31, RFREG_OFFSET_MASK, 0x00029);
4207 rtl_set_rfreg(hw, path, 0x32, RFREG_OFFSET_MASK, 0xd7ffb);
4208 rtl_set_rfreg(hw, path, 0x65, RFREG_OFFSET_MASK, temp_reg65);
4209 rtl_set_rfreg(hw, path, 0x8f, RFREG_OFFSET_MASK, 0x8a001);
4210 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x00000);
4211 rtl_write_dword(rtlpriv, 0x90c, 0x00008000);
4212 rtl_write_dword(rtlpriv, 0xb00, 0x03000100);
4213 rtl_write_dword(rtlpriv, 0x984, 0x0046a910);/* [0]:AGC_en, [15]:idac_K_Mask */
4214
4215 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
4216 rtl_write_dword(rtlpriv, 0xc80, 0x18008c10);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
4217 rtl_write_dword(rtlpriv, 0xc84, 0x38008c10);/* RX_TONE_idx[9:0], RxK_Mask[29] */
4218 rtl_write_dword(rtlpriv, 0xc88, 0x821603e0);
4219 /* ODM_Write4Byte(pDM_Odm, 0xc8c, 0x68163e96); */
4220 rtl_write_dword(rtlpriv, 0xcb8, 0x00100000);/* cb8[20] \B1N SI/PI \A8Ï¥\CE\C5v\A4\C1\B5\B9 iqk_dpk module */
4221 cal_retry = 0;
4222 while (1) {
4223 /* one shot */
4224 rtl_write_dword(rtlpriv, 0x980, 0xfa000000);
4225 rtl_write_dword(rtlpriv, 0x980, 0xf8000000);
4226
4227 mdelay(10); /* Delay 10ms */
4228 rtl_write_dword(rtlpriv, 0xcb8, 0x00000000);
4229 delay_count = 0;
4230 while (1) {
4231 iqk_ready = rtl_get_bbreg(hw, 0xd00, BIT(10));
4232 if ((~iqk_ready) || (delay_count > 20))
4233 break;
4234 else{
4235 mdelay(1);
4236 delay_count++;
4237 }
4238 }
4239
4240 if (delay_count < 20) { /* If 20ms No Result, then cal_retry++ */
4241 /* ============TXIQK Check============== */
4242 tx_fail = rtl_get_bbreg(hw, 0xd00, BIT(12));
4243
4244 if (~tx_fail) {
4245 rtl_write_dword(rtlpriv, 0xcb8, 0x02000000);
4246 tx_x0_rxk[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4247 rtl_write_dword(rtlpriv, 0xcb8, 0x04000000);
4248 tx_y0_rxk[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4249 tx0iqkok = true;
4250 break;
4251 } else {
4252 tx0iqkok = false;
4253 cal_retry++;
4254 if (cal_retry == 10)
4255 break;
4256 }
4257 } else{
4258 tx0iqkok = false;
4259 cal_retry++;
4260 if (cal_retry == 10)
4261 break;
4262 }
4263 }
4264
4265 if (tx0iqkok == false) { /* If RX mode TXK fail, then take TXK Result */
4266 tx_x0_rxk[cal] = tx_x0[cal];
4267 tx_y0_rxk[cal] = tx_y0[cal];
4268 tx0iqkok = true;
4269 RT_TRACE(rtlpriv, COMP_IQK,
4270 DBG_LOUD, "1");
4271 }
4272
4273 /* ====== RX IQK ====== */
4274 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4275 /* 1. RX RF Setting */
4276 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x80000);
4277 rtl_set_rfreg(hw, path, 0x30, RFREG_OFFSET_MASK, 0x30000);
4278 rtl_set_rfreg(hw, path, 0x31, RFREG_OFFSET_MASK, 0x0002f);
4279 rtl_set_rfreg(hw, path, 0x32, RFREG_OFFSET_MASK, 0xfffbb);
4280 rtl_set_rfreg(hw, path, 0x8f, RFREG_OFFSET_MASK, 0x88001);
4281 rtl_set_rfreg(hw, path, 0x65, RFREG_OFFSET_MASK, 0x931d8);
4282 rtl_set_rfreg(hw, path, 0xef, RFREG_OFFSET_MASK, 0x00000);
4283
4284 rtl_set_bbreg(hw, 0x978, 0x03FF8000, (tx_x0_rxk[cal])>>21&0x000007ff);
4285 rtl_set_bbreg(hw, 0x978, 0x000007FF, (tx_y0_rxk[cal])>>21&0x000007ff);
4286 rtl_set_bbreg(hw, 0x978, BIT(31), 0x1);
4287 rtl_set_bbreg(hw, 0x97c, BIT(31), 0x0);
4288 /* ODM_SetBBReg(pDM_Odm, 0xcb8, 0xF, 0xe); */
4289 rtl_write_dword(rtlpriv, 0x90c, 0x00008000);
4290 rtl_write_dword(rtlpriv, 0x984, 0x0046a911);
4291
4292 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
4293 rtl_write_dword(rtlpriv, 0xc80, 0x38008c10);/* TX_TONE_idx[9:0], TxK_Mask[29] TX_Tone = 16 */
4294 rtl_write_dword(rtlpriv, 0xc84, 0x18008c10);/* RX_TONE_idx[9:0], RxK_Mask[29] */
4295 rtl_write_dword(rtlpriv, 0xc88, 0x02140119);
4296
4297 rtl_write_dword(rtlpriv, 0xc8c, 0x28160d00); /*pDM_Odm->SupportInterface == 1*/
4298
4299 rtl_write_dword(rtlpriv, 0xcb8, 0x00100000);/* cb8[20] \B1N SI/PI \A8Ï¥\CE\C5v\A4\C1\B5\B9 iqk_dpk module */
4300
4301 cal_retry = 0;
4302 while (1) {
4303 /* one shot */
4304 rtl_write_dword(rtlpriv, 0x980, 0xfa000000);
4305 rtl_write_dword(rtlpriv, 0x980, 0xf8000000);
4306
4307 mdelay(10); /* Delay 10ms */
4308 rtl_write_dword(rtlpriv, 0xcb8, 0x00000000);
4309 delay_count = 0;
4310 while (1) {
4311 iqk_ready = rtl_get_bbreg(hw, 0xd00, BIT(10));
4312 if ((~iqk_ready) || (delay_count > 20))
4313 break;
4314 else{
4315 mdelay(1);
4316 delay_count++;
4317 }
4318 }
4319
4320 if (delay_count < 20) { /* If 20ms No Result, then cal_retry++ */
4321 /* ============RXIQK Check============== */
4322 rx_fail = rtl_get_bbreg(hw, 0xd00, BIT(11));
4323 if (rx_fail == 0) {
4324 rtl_write_dword(rtlpriv, 0xcb8, 0x06000000);
4325 rx_x0[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4326 rtl_write_dword(rtlpriv, 0xcb8, 0x08000000);
4327 rx_y0[cal] = rtl_get_bbreg(hw, 0xd00, 0x07ff0000)<<21;
4328 rx0iqkok = true;
4329 break;
4330 } else{
4331 rtl_set_bbreg(hw, 0xc10, 0x000003ff, 0x200>>1);
4332 rtl_set_bbreg(hw, 0xc10, 0x03ff0000, 0x0>>1);
4333 rx0iqkok = false;
4334 cal_retry++;
4335 if (cal_retry == 10)
4336 break;
4337
4338 }
4339 } else{
4340 rx0iqkok = false;
4341 cal_retry++;
4342 if (cal_retry == 10)
4343 break;
4344 }
4345 }
4346 }
4347
4348 if (tx0iqkok)
4349 tx_average++;
4350 if (rx0iqkok)
4351 rx_average++;
4352 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4353 rtl_set_rfreg(hw, path, 0x65, RFREG_OFFSET_MASK, temp_reg65);
4354 break;
4355 default:
4356 break;
4357 }
4358 cal++;
4359 }
4360
4361 /* FillIQK Result */
4362 switch (path) {
4363 case RF90_PATH_A:
4364 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4365 "========Path_A =======\n");
4366 if (tx_average == 0)
4367 break;
4368
4369 for (i = 0; i < tx_average; i++) {
4370 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4371 "TX_X0_RXK[%d] = %x ;; TX_Y0_RXK[%d] = %x\n", i,
4372 (tx_x0_rxk[i])>>21&0x000007ff, i,
4373 (tx_y0_rxk[i])>>21&0x000007ff);
4374 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4375 "TX_X0[%d] = %x ;; TX_Y0[%d] = %x\n", i,
4376 (tx_x0[i])>>21&0x000007ff, i,
4377 (tx_y0[i])>>21&0x000007ff);
4378 }
4379 for (i = 0; i < tx_average; i++) {
4380 for (ii = i+1; ii < tx_average; ii++) {
4381 dx = (tx_x0[i]>>21) - (tx_x0[ii]>>21);
4382 if (dx < 3 && dx > -3) {
4383 dy = (tx_y0[i]>>21) - (tx_y0[ii]>>21);
4384 if (dy < 3 && dy > -3) {
4385 tx_x = ((tx_x0[i]>>21) + (tx_x0[ii]>>21))/2;
4386 tx_y = ((tx_y0[i]>>21) + (tx_y0[ii]>>21))/2;
4387 tx_finish = 1;
4388 break;
4389 }
4390 }
4391 }
4392 if (tx_finish == 1)
4393 break;
4394 }
4395
4396 if (tx_finish == 1)
4397 _rtl8821ae_iqk_tx_fill_iqc(hw, path, tx_x, tx_y); /* ? */
4398 else
4399 _rtl8821ae_iqk_tx_fill_iqc(hw, path, 0x200, 0x0);
4400
4401 if (rx_average == 0)
4402 break;
4403
4404 for (i = 0; i < rx_average; i++)
4405 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4406 "RX_X0[%d] = %x ;; RX_Y0[%d] = %x\n", i,
4407 (rx_x0[i])>>21&0x000007ff, i,
4408 (rx_y0[i])>>21&0x000007ff);
4409 for (i = 0; i < rx_average; i++) {
4410 for (ii = i+1; ii < rx_average; ii++) {
4411 dx = (rx_x0[i]>>21) - (rx_x0[ii]>>21);
4412 if (dx < 4 && dx > -4) {
4413 dy = (rx_y0[i]>>21) - (rx_y0[ii]>>21);
4414 if (dy < 4 && dy > -4) {
4415 rx_x = ((rx_x0[i]>>21) + (rx_x0[ii]>>21))/2;
4416 rx_y = ((rx_y0[i]>>21) + (rx_y0[ii]>>21))/2;
4417 rx_finish = 1;
4418 break;
4419 }
4420 }
4421 }
4422 if (rx_finish == 1)
4423 break;
4424 }
4425
4426 if (rx_finish == 1)
4427 _rtl8821ae_iqk_rx_fill_iqc(hw, path, rx_x, rx_y);
4428 else
4429 _rtl8821ae_iqk_rx_fill_iqc(hw, path, 0x200, 0x0);
4430 break;
4431 default:
4432 break;
4433 }
4434 }
4435
4436 static void _rtl8821ae_iqk_restore_rf(struct ieee80211_hw *hw,
4437 enum radio_path path,
4438 u32 *backup_rf_reg,
4439 u32 *rf_backup, u32 rf_reg_num)
4440 {
4441 struct rtl_priv *rtlpriv = rtl_priv(hw);
4442 u32 i;
4443
4444 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4445 for (i = 0; i < RF_REG_NUM; i++)
4446 rtl_set_rfreg(hw, path, backup_rf_reg[i], RFREG_OFFSET_MASK,
4447 rf_backup[i]);
4448
4449 switch (path) {
4450 case RF90_PATH_A:
4451 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4452 "RestoreRF Path A Success!!!!\n");
4453 break;
4454 default:
4455 break;
4456 }
4457 }
4458
4459 static void _rtl8821ae_iqk_restore_afe(struct ieee80211_hw *hw,
4460 u32 *afe_backup, u32 *backup_afe_reg,
4461 u32 afe_num)
4462 {
4463 u32 i;
4464 struct rtl_priv *rtlpriv = rtl_priv(hw);
4465
4466 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4467 /* Reload AFE Parameters */
4468 for (i = 0; i < afe_num; i++)
4469 rtl_write_dword(rtlpriv, backup_afe_reg[i], afe_backup[i]);
4470 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x1); /* [31] = 1 --> Page C1 */
4471 rtl_write_dword(rtlpriv, 0xc80, 0x0);
4472 rtl_write_dword(rtlpriv, 0xc84, 0x0);
4473 rtl_write_dword(rtlpriv, 0xc88, 0x0);
4474 rtl_write_dword(rtlpriv, 0xc8c, 0x3c000000);
4475 rtl_write_dword(rtlpriv, 0xc90, 0x00000080);
4476 rtl_write_dword(rtlpriv, 0xc94, 0x00000000);
4477 rtl_write_dword(rtlpriv, 0xcc4, 0x20040000);
4478 rtl_write_dword(rtlpriv, 0xcc8, 0x20000000);
4479 rtl_write_dword(rtlpriv, 0xcb8, 0x0);
4480 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "RestoreAFE Success!!!!\n");
4481 }
4482
4483 static void _rtl8821ae_iqk_restore_macbb(struct ieee80211_hw *hw,
4484 u32 *macbb_backup,
4485 u32 *backup_macbb_reg,
4486 u32 macbb_num)
4487 {
4488 u32 i;
4489 struct rtl_priv *rtlpriv = rtl_priv(hw);
4490
4491 rtl_set_bbreg(hw, 0x82c, BIT(31), 0x0); /* [31] = 0 --> Page C */
4492 /* Reload MacBB Parameters */
4493 for (i = 0; i < macbb_num; i++)
4494 rtl_write_dword(rtlpriv, backup_macbb_reg[i], macbb_backup[i]);
4495 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD, "RestoreMacBB Success!!!!\n");
4496 }
4497
4498 #undef MACBB_REG_NUM
4499 #undef AFE_REG_NUM
4500 #undef RF_REG_NUM
4501
4502 #define MACBB_REG_NUM 11
4503 #define AFE_REG_NUM 12
4504 #define RF_REG_NUM 3
4505
4506 static void _rtl8821ae_phy_iq_calibrate(struct ieee80211_hw *hw)
4507 {
4508 u32 macbb_backup[MACBB_REG_NUM];
4509 u32 afe_backup[AFE_REG_NUM];
4510 u32 rfa_backup[RF_REG_NUM];
4511 u32 rfb_backup[RF_REG_NUM];
4512 u32 backup_macbb_reg[MACBB_REG_NUM] = {
4513 0xb00, 0x520, 0x550, 0x808, 0x90c, 0xc00, 0xc50,
4514 0xe00, 0xe50, 0x838, 0x82c
4515 };
4516 u32 backup_afe_reg[AFE_REG_NUM] = {
4517 0xc5c, 0xc60, 0xc64, 0xc68, 0xc6c, 0xc70, 0xc74,
4518 0xc78, 0xc7c, 0xc80, 0xc84, 0xcb8
4519 };
4520 u32 backup_rf_reg[RF_REG_NUM] = {0x65, 0x8f, 0x0};
4521
4522 _rtl8821ae_iqk_backup_macbb(hw, macbb_backup, backup_macbb_reg,
4523 MACBB_REG_NUM);
4524 _rtl8821ae_iqk_backup_afe(hw, afe_backup, backup_afe_reg, AFE_REG_NUM);
4525 _rtl8821ae_iqk_backup_rf(hw, rfa_backup, rfb_backup, backup_rf_reg,
4526 RF_REG_NUM);
4527
4528 _rtl8821ae_iqk_configure_mac(hw);
4529 _rtl8821ae_iqk_tx(hw, RF90_PATH_A);
4530 _rtl8821ae_iqk_restore_rf(hw, RF90_PATH_A, backup_rf_reg, rfa_backup,
4531 RF_REG_NUM);
4532
4533 _rtl8821ae_iqk_restore_afe(hw, afe_backup, backup_afe_reg, AFE_REG_NUM);
4534 _rtl8821ae_iqk_restore_macbb(hw, macbb_backup, backup_macbb_reg,
4535 MACBB_REG_NUM);
4536 }
4537
4538 static void _rtl8821ae_phy_set_rfpath_switch(struct ieee80211_hw *hw, bool main)
4539 {
4540 struct rtl_priv *rtlpriv = rtl_priv(hw);
4541 /* struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw)); */
4542 /* struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw)); */
4543 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "\n");
4544
4545 if (main)
4546 rtl_set_bbreg(hw, RA_RFE_PINMUX + 4, BIT(29) | BIT(28), 0x1);
4547 else
4548 rtl_set_bbreg(hw, RA_RFE_PINMUX + 4, BIT(29) | BIT(28), 0x2);
4549 }
4550
4551 #undef IQK_ADDA_REG_NUM
4552 #undef IQK_DELAY_TIME
4553
4554 void rtl8812ae_phy_iq_calibrate(struct ieee80211_hw *hw, bool b_recovery)
4555 {
4556 }
4557
4558 void rtl8812ae_do_iqk(struct ieee80211_hw *hw, u8 delta_thermal_index,
4559 u8 thermal_value, u8 threshold)
4560 {
4561 struct rtl_dm *rtldm = rtl_dm(rtl_priv(hw));
4562
4563 rtldm->thermalvalue_iqk = thermal_value;
4564 rtl8812ae_phy_iq_calibrate(hw, false);
4565 }
4566
4567 void rtl8821ae_phy_iq_calibrate(struct ieee80211_hw *hw, bool b_recovery)
4568 {
4569 struct rtl_priv *rtlpriv = rtl_priv(hw);
4570 struct rtl_phy *rtlphy = &rtlpriv->phy;
4571
4572 if (!rtlphy->lck_inprogress) {
4573 spin_lock(&rtlpriv->locks.iqk_lock);
4574 rtlphy->lck_inprogress = true;
4575 spin_unlock(&rtlpriv->locks.iqk_lock);
4576
4577 _rtl8821ae_phy_iq_calibrate(hw);
4578
4579 spin_lock(&rtlpriv->locks.iqk_lock);
4580 rtlphy->lck_inprogress = false;
4581 spin_unlock(&rtlpriv->locks.iqk_lock);
4582 }
4583 }
4584
4585 void rtl8821ae_reset_iqk_result(struct ieee80211_hw *hw)
4586 {
4587 struct rtl_priv *rtlpriv = rtl_priv(hw);
4588 struct rtl_phy *rtlphy = &rtlpriv->phy;
4589 u8 i;
4590
4591 RT_TRACE(rtlpriv, COMP_IQK, DBG_LOUD,
4592 "rtl8812ae_dm_reset_iqk_result:: settings regs %d default regs %d\n",
4593 (int)(sizeof(rtlphy->iqk_matrix) /
4594 sizeof(struct iqk_matrix_regs)),
4595 IQK_MATRIX_SETTINGS_NUM);
4596
4597 for (i = 0; i < IQK_MATRIX_SETTINGS_NUM; i++) {
4598 rtlphy->iqk_matrix[i].value[0][0] = 0x100;
4599 rtlphy->iqk_matrix[i].value[0][2] = 0x100;
4600 rtlphy->iqk_matrix[i].value[0][4] = 0x100;
4601 rtlphy->iqk_matrix[i].value[0][6] = 0x100;
4602
4603 rtlphy->iqk_matrix[i].value[0][1] = 0x0;
4604 rtlphy->iqk_matrix[i].value[0][3] = 0x0;
4605 rtlphy->iqk_matrix[i].value[0][5] = 0x0;
4606 rtlphy->iqk_matrix[i].value[0][7] = 0x0;
4607
4608 rtlphy->iqk_matrix[i].iqk_done = false;
4609 }
4610 }
4611
4612 void rtl8821ae_do_iqk(struct ieee80211_hw *hw, u8 delta_thermal_index,
4613 u8 thermal_value, u8 threshold)
4614 {
4615 struct rtl_dm *rtldm = rtl_dm(rtl_priv(hw));
4616
4617 rtl8821ae_reset_iqk_result(hw);
4618
4619 rtldm->thermalvalue_iqk = thermal_value;
4620 rtl8821ae_phy_iq_calibrate(hw, false);
4621 }
4622
4623 void rtl8821ae_phy_lc_calibrate(struct ieee80211_hw *hw)
4624 {
4625 }
4626
4627 void rtl8821ae_phy_ap_calibrate(struct ieee80211_hw *hw, s8 delta)
4628 {
4629 }
4630
4631 void rtl8821ae_phy_set_rfpath_switch(struct ieee80211_hw *hw, bool bmain)
4632 {
4633 _rtl8821ae_phy_set_rfpath_switch(hw, bmain);
4634 }
4635
4636 bool rtl8821ae_phy_set_io_cmd(struct ieee80211_hw *hw, enum io_type iotype)
4637 {
4638 struct rtl_priv *rtlpriv = rtl_priv(hw);
4639 struct rtl_phy *rtlphy = &rtlpriv->phy;
4640 bool postprocessing = false;
4641
4642 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
4643 "-->IO Cmd(%#x), set_io_inprogress(%d)\n",
4644 iotype, rtlphy->set_io_inprogress);
4645 do {
4646 switch (iotype) {
4647 case IO_CMD_RESUME_DM_BY_SCAN:
4648 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
4649 "[IO CMD] Resume DM after scan.\n");
4650 postprocessing = true;
4651 break;
4652 case IO_CMD_PAUSE_BAND0_DM_BY_SCAN:
4653 case IO_CMD_PAUSE_BAND1_DM_BY_SCAN:
4654 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
4655 "[IO CMD] Pause DM before scan.\n");
4656 postprocessing = true;
4657 break;
4658 default:
4659 pr_err("switch case %#x not processed\n",
4660 iotype);
4661 break;
4662 }
4663 } while (false);
4664 if (postprocessing && !rtlphy->set_io_inprogress) {
4665 rtlphy->set_io_inprogress = true;
4666 rtlphy->current_io_type = iotype;
4667 } else {
4668 return false;
4669 }
4670 rtl8821ae_phy_set_io(hw);
4671 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE, "IO Type(%#x)\n", iotype);
4672 return true;
4673 }
4674
4675 static void rtl8821ae_phy_set_io(struct ieee80211_hw *hw)
4676 {
4677 struct rtl_priv *rtlpriv = rtl_priv(hw);
4678 struct dig_t *dm_digtable = &rtlpriv->dm_digtable;
4679 struct rtl_phy *rtlphy = &rtlpriv->phy;
4680
4681 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
4682 "--->Cmd(%#x), set_io_inprogress(%d)\n",
4683 rtlphy->current_io_type, rtlphy->set_io_inprogress);
4684 switch (rtlphy->current_io_type) {
4685 case IO_CMD_RESUME_DM_BY_SCAN:
4686 if (rtlpriv->mac80211.opmode == NL80211_IFTYPE_ADHOC)
4687 _rtl8821ae_resume_tx_beacon(hw);
4688 rtl8821ae_dm_write_dig(hw, rtlphy->initgain_backup.xaagccore1);
4689 rtl8821ae_dm_write_cck_cca_thres(hw,
4690 rtlphy->initgain_backup.cca);
4691 break;
4692 case IO_CMD_PAUSE_BAND0_DM_BY_SCAN:
4693 if (rtlpriv->mac80211.opmode == NL80211_IFTYPE_ADHOC)
4694 _rtl8821ae_stop_tx_beacon(hw);
4695 rtlphy->initgain_backup.xaagccore1 = dm_digtable->cur_igvalue;
4696 rtl8821ae_dm_write_dig(hw, 0x17);
4697 rtlphy->initgain_backup.cca = dm_digtable->cur_cck_cca_thres;
4698 rtl8821ae_dm_write_cck_cca_thres(hw, 0x40);
4699 break;
4700 case IO_CMD_PAUSE_BAND1_DM_BY_SCAN:
4701 break;
4702 default:
4703 pr_err("switch case %#x not processed\n",
4704 rtlphy->current_io_type);
4705 break;
4706 }
4707 rtlphy->set_io_inprogress = false;
4708 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
4709 "(%#x)\n", rtlphy->current_io_type);
4710 }
4711
4712 static void rtl8821ae_phy_set_rf_on(struct ieee80211_hw *hw)
4713 {
4714 struct rtl_priv *rtlpriv = rtl_priv(hw);
4715
4716 rtl_write_byte(rtlpriv, REG_SPS0_CTRL, 0x2b);
4717 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE3);
4718 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE2);
4719 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE3);
4720 rtl_write_byte(rtlpriv, REG_TXPAUSE, 0x00);
4721 }
4722
4723 static bool _rtl8821ae_phy_set_rf_power_state(struct ieee80211_hw *hw,
4724 enum rf_pwrstate rfpwr_state)
4725 {
4726 struct rtl_priv *rtlpriv = rtl_priv(hw);
4727 struct rtl_pci_priv *pcipriv = rtl_pcipriv(hw);
4728 struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
4729 struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
4730 bool bresult = true;
4731 u8 i, queue_id;
4732 struct rtl8192_tx_ring *ring = NULL;
4733
4734 switch (rfpwr_state) {
4735 case ERFON:
4736 if ((ppsc->rfpwr_state == ERFOFF) &&
4737 RT_IN_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_HALT_NIC)) {
4738 bool rtstatus = false;
4739 u32 initializecount = 0;
4740
4741 do {
4742 initializecount++;
4743 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
4744 "IPS Set eRf nic enable\n");
4745 rtstatus = rtl_ps_enable_nic(hw);
4746 } while (!rtstatus && (initializecount < 10));
4747 RT_CLEAR_PS_LEVEL(ppsc,
4748 RT_RF_OFF_LEVL_HALT_NIC);
4749 } else {
4750 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
4751 "Set ERFON sleeped:%d ms\n",
4752 jiffies_to_msecs(jiffies -
4753 ppsc->
4754 last_sleep_jiffies));
4755 ppsc->last_awake_jiffies = jiffies;
4756 rtl8821ae_phy_set_rf_on(hw);
4757 }
4758 if (mac->link_state == MAC80211_LINKED) {
4759 rtlpriv->cfg->ops->led_control(hw,
4760 LED_CTL_LINK);
4761 } else {
4762 rtlpriv->cfg->ops->led_control(hw,
4763 LED_CTL_NO_LINK);
4764 }
4765 break;
4766 case ERFOFF:
4767 for (queue_id = 0, i = 0;
4768 queue_id < RTL_PCI_MAX_TX_QUEUE_COUNT;) {
4769 ring = &pcipriv->dev.tx_ring[queue_id];
4770 if (queue_id == BEACON_QUEUE ||
4771 skb_queue_len(&ring->queue) == 0) {
4772 queue_id++;
4773 continue;
4774 } else {
4775 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
4776 "eRf Off/Sleep: %d times TcbBusyQueue[%d] =%d before doze!\n",
4777 (i + 1), queue_id,
4778 skb_queue_len(&ring->queue));
4779
4780 udelay(10);
4781 i++;
4782 }
4783 if (i >= MAX_DOZE_WAITING_TIMES_9x) {
4784 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
4785 "\n ERFSLEEP: %d times TcbBusyQueue[%d] = %d !\n",
4786 MAX_DOZE_WAITING_TIMES_9x,
4787 queue_id,
4788 skb_queue_len(&ring->queue));
4789 break;
4790 }
4791 }
4792
4793 if (ppsc->reg_rfps_level & RT_RF_OFF_LEVL_HALT_NIC) {
4794 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
4795 "IPS Set eRf nic disable\n");
4796 rtl_ps_disable_nic(hw);
4797 RT_SET_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_HALT_NIC);
4798 } else {
4799 if (ppsc->rfoff_reason == RF_CHANGE_BY_IPS) {
4800 rtlpriv->cfg->ops->led_control(hw,
4801 LED_CTL_NO_LINK);
4802 } else {
4803 rtlpriv->cfg->ops->led_control(hw,
4804 LED_CTL_POWER_OFF);
4805 }
4806 }
4807 break;
4808 default:
4809 pr_err("switch case %#x not processed\n",
4810 rfpwr_state);
4811 bresult = false;
4812 break;
4813 }
4814 if (bresult)
4815 ppsc->rfpwr_state = rfpwr_state;
4816 return bresult;
4817 }
4818
4819 bool rtl8821ae_phy_set_rf_power_state(struct ieee80211_hw *hw,
4820 enum rf_pwrstate rfpwr_state)
4821 {
4822 struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
4823
4824 bool bresult = false;
4825
4826 if (rfpwr_state == ppsc->rfpwr_state)
4827 return bresult;
4828 bresult = _rtl8821ae_phy_set_rf_power_state(hw, rfpwr_state);
4829 return bresult;
4830 }