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 }
4831