Merge git://git.infradead.org/users/eparis/audit
[cascardo/linux.git] / drivers / net / wireless / rtlwifi / rtl8723be / phy.c
1 /******************************************************************************
2  *
3  * Copyright(c) 2009-2014  Realtek Corporation.
4  *
5  * This program is free software; you can redistribute it and/or modify it
6  * under the terms of version 2 of the GNU General Public License as
7  * published by the Free Software Foundation.
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
12  * more details.
13  *
14  * The full GNU General Public License is included in this distribution in the
15  * file called LICENSE.
16  *
17  * Contact Information:
18  * wlanfae <wlanfae@realtek.com>
19  * Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
20  * Hsinchu 300, Taiwan.
21  *
22  * Larry Finger <Larry.Finger@lwfinger.net>
23  *
24  *****************************************************************************/
25
26 #include "../wifi.h"
27 #include "../pci.h"
28 #include "../ps.h"
29 #include "reg.h"
30 #include "def.h"
31 #include "phy.h"
32 #include "../rtl8723com/phy_common.h"
33 #include "rf.h"
34 #include "dm.h"
35 #include "../rtl8723com/dm_common.h"
36 #include "table.h"
37 #include "trx.h"
38
39 static bool _rtl8723be_phy_bb8723b_config_parafile(struct ieee80211_hw *hw);
40 static bool _rtl8723be_phy_config_mac_with_headerfile(struct ieee80211_hw *hw);
41 static bool _rtl8723be_phy_config_bb_with_headerfile(struct ieee80211_hw *hw,
42                                                      u8 configtype);
43 static bool _rtl8723be_phy_config_bb_with_pgheaderfile(struct ieee80211_hw *hw,
44                                                        u8 configtype);
45 static bool _rtl8723be_phy_sw_chnl_step_by_step(struct ieee80211_hw *hw,
46                                                 u8 channel, u8 *stage,
47                                                 u8 *step, u32 *delay);
48
49 static void rtl8723be_phy_set_rf_on(struct ieee80211_hw *hw);
50 static void rtl8723be_phy_set_io(struct ieee80211_hw *hw);
51
52 u32 rtl8723be_phy_query_rf_reg(struct ieee80211_hw *hw, enum radio_path rfpath,
53                                u32 regaddr, u32 bitmask)
54 {
55         struct rtl_priv *rtlpriv = rtl_priv(hw);
56         u32 original_value, readback_value, bitshift;
57         unsigned long flags;
58
59         RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
60                  "regaddr(%#x), rfpath(%#x), bitmask(%#x)\n",
61                   regaddr, rfpath, bitmask);
62
63         spin_lock_irqsave(&rtlpriv->locks.rf_lock, flags);
64
65         original_value = rtl8723_phy_rf_serial_read(hw, rfpath, regaddr);
66         bitshift = rtl8723_phy_calculate_bit_shift(bitmask);
67         readback_value = (original_value & bitmask) >> bitshift;
68
69         spin_unlock_irqrestore(&rtlpriv->locks.rf_lock, flags);
70
71         RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
72                  "regaddr(%#x), rfpath(%#x), bitmask(%#x), original_value(%#x)\n",
73                  regaddr, rfpath, bitmask, original_value);
74
75         return readback_value;
76 }
77
78 void rtl8723be_phy_set_rf_reg(struct ieee80211_hw *hw, enum radio_path path,
79                               u32 regaddr, u32 bitmask, u32 data)
80 {
81         struct rtl_priv *rtlpriv = rtl_priv(hw);
82         u32 original_value, bitshift;
83         unsigned long flags;
84
85         RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
86                  "regaddr(%#x), bitmask(%#x), data(%#x), rfpath(%#x)\n",
87                   regaddr, bitmask, data, path);
88
89         spin_lock_irqsave(&rtlpriv->locks.rf_lock, flags);
90
91         if (bitmask != RFREG_OFFSET_MASK) {
92                         original_value = rtl8723_phy_rf_serial_read(hw, path,
93                                                                     regaddr);
94                         bitshift = rtl8723_phy_calculate_bit_shift(bitmask);
95                         data = ((original_value & (~bitmask)) |
96                                 (data << bitshift));
97                 }
98
99         rtl8723_phy_rf_serial_write(hw, path, regaddr, data);
100
101         spin_unlock_irqrestore(&rtlpriv->locks.rf_lock, flags);
102
103         RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
104                  "regaddr(%#x), bitmask(%#x), data(%#x), rfpath(%#x)\n",
105                   regaddr, bitmask, data, path);
106
107 }
108
109 bool rtl8723be_phy_mac_config(struct ieee80211_hw *hw)
110 {
111         struct rtl_priv *rtlpriv = rtl_priv(hw);
112         bool rtstatus = _rtl8723be_phy_config_mac_with_headerfile(hw);
113
114         rtl_write_byte(rtlpriv, 0x04CA, 0x0B);
115         return rtstatus;
116 }
117
118 bool rtl8723be_phy_bb_config(struct ieee80211_hw *hw)
119 {
120         bool rtstatus = true;
121         struct rtl_priv *rtlpriv = rtl_priv(hw);
122         u16 regval;
123         u8 b_reg_hwparafile = 1;
124         u32 tmp;
125         u8 crystalcap = rtlpriv->efuse.crystalcap;
126         rtl8723_phy_init_bb_rf_reg_def(hw);
127         regval = rtl_read_word(rtlpriv, REG_SYS_FUNC_EN);
128         rtl_write_word(rtlpriv, REG_SYS_FUNC_EN,
129                        regval | BIT(13) | BIT(0) | BIT(1));
130
131         rtl_write_byte(rtlpriv, REG_RF_CTRL, RF_EN | RF_RSTB | RF_SDMRSTB);
132         rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN,
133                        FEN_PPLL | FEN_PCIEA | FEN_DIO_PCIE |
134                        FEN_BB_GLB_RSTN | FEN_BBRSTB);
135         tmp = rtl_read_dword(rtlpriv, 0x4c);
136         rtl_write_dword(rtlpriv, 0x4c, tmp | BIT(23));
137
138         rtl_write_byte(rtlpriv, REG_AFE_XTAL_CTRL + 1, 0x80);
139
140         if (b_reg_hwparafile == 1)
141                 rtstatus = _rtl8723be_phy_bb8723b_config_parafile(hw);
142
143         crystalcap = crystalcap & 0x3F;
144         rtl_set_bbreg(hw, REG_MAC_PHY_CTRL, 0xFFF000,
145                       (crystalcap | crystalcap << 6));
146
147         return rtstatus;
148 }
149
150 bool rtl8723be_phy_rf_config(struct ieee80211_hw *hw)
151 {
152         return rtl8723be_phy_rf6052_config(hw);
153 }
154
155 static bool _rtl8723be_check_condition(struct ieee80211_hw *hw,
156                                        const u32  condition)
157 {
158         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
159         struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
160         u32 _board = rtlefuse->board_type; /*need efuse define*/
161         u32 _interface = rtlhal->interface;
162         u32 _platform = 0x08;/*SupportPlatform */
163         u32 cond = condition;
164
165         if (condition == 0xCDCDCDCD)
166                 return true;
167
168         cond = condition & 0xFF;
169         if ((_board & cond) == 0 && cond != 0x1F)
170                 return false;
171
172         cond = condition & 0xFF00;
173         cond = cond >> 8;
174         if ((_interface & cond) == 0 && cond != 0x07)
175                 return false;
176
177         cond = condition & 0xFF0000;
178         cond = cond >> 16;
179         if ((_platform & cond) == 0 && cond != 0x0F)
180                 return false;
181         return true;
182 }
183
184 static void _rtl8723be_config_rf_reg(struct ieee80211_hw *hw, u32 addr,
185                                      u32 data, enum radio_path rfpath,
186                                      u32 regaddr)
187 {
188         if (addr == 0xfe || addr == 0xffe) {
189                 /* In order not to disturb BT music
190                  *      when wifi init.(1ant NIC only)
191                  */
192                 mdelay(50);
193         } else {
194                 rtl_set_rfreg(hw, rfpath, regaddr, RFREG_OFFSET_MASK, data);
195                 udelay(1);
196         }
197 }
198 static void _rtl8723be_config_rf_radio_a(struct ieee80211_hw *hw,
199                                          u32 addr, u32 data)
200 {
201         u32 content = 0x1000; /*RF Content: radio_a_txt*/
202         u32 maskforphyset = (u32)(content & 0xE000);
203
204         _rtl8723be_config_rf_reg(hw, addr, data, RF90_PATH_A,
205                                  addr | maskforphyset);
206
207 }
208
209 static void _rtl8723be_phy_init_tx_power_by_rate(struct ieee80211_hw *hw)
210 {
211         struct rtl_priv *rtlpriv = rtl_priv(hw);
212         struct rtl_phy *rtlphy = &rtlpriv->phy;
213
214         u8 band, path, txnum, section;
215
216         for (band = BAND_ON_2_4G; band <= BAND_ON_5G; ++band)
217                 for (path = 0; path < TX_PWR_BY_RATE_NUM_RF; ++path)
218                         for (txnum = 0; txnum < TX_PWR_BY_RATE_NUM_RF; ++txnum)
219                                 for (section = 0;
220                                      section < TX_PWR_BY_RATE_NUM_SECTION;
221                                      ++section)
222                                         rtlphy->tx_power_by_rate_offset
223                                           [band][path][txnum][section] = 0;
224 }
225
226 static void _rtl8723be_config_bb_reg(struct ieee80211_hw *hw,
227                                      u32 addr, u32 data)
228 {
229         if (addr == 0xfe) {
230                 mdelay(50);
231         } else if (addr == 0xfd) {
232                 mdelay(5);
233         } else if (addr == 0xfc) {
234                 mdelay(1);
235         } else if (addr == 0xfb) {
236                 udelay(50);
237         } else if (addr == 0xfa) {
238                 udelay(5);
239         } else if (addr == 0xf9) {
240                 udelay(1);
241         } else {
242                 rtl_set_bbreg(hw, addr, MASKDWORD, data);
243                 udelay(1);
244         }
245 }
246
247 static void _rtl8723be_phy_set_txpower_by_rate_base(struct ieee80211_hw *hw,
248                                                     u8 band,
249                                                     u8 path, u8 rate_section,
250                                                     u8 txnum, u8 value)
251 {
252         struct rtl_priv *rtlpriv = rtl_priv(hw);
253         struct rtl_phy *rtlphy = &rtlpriv->phy;
254
255         if (path > RF90_PATH_D) {
256                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
257                          "Invalid Rf Path %d in phy_SetTxPowerByRatBase()\n",
258                           path);
259                 return;
260         }
261
262         if (band == BAND_ON_2_4G) {
263                 switch (rate_section) {
264                 case CCK:
265                         rtlphy->txpwr_by_rate_base_24g[path][txnum][0] = value;
266                         break;
267                 case OFDM:
268                         rtlphy->txpwr_by_rate_base_24g[path][txnum][1] = value;
269                         break;
270                 case HT_MCS0_MCS7:
271                         rtlphy->txpwr_by_rate_base_24g[path][txnum][2] = value;
272                         break;
273                 case HT_MCS8_MCS15:
274                         rtlphy->txpwr_by_rate_base_24g[path][txnum][3] = value;
275                         break;
276                 default:
277                         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
278                                  "Invalid RateSection %d in Band 2.4G, Rf Path %d, %dTx in PHY_SetTxPowerByRateBase()\n",
279                                  rate_section, path, txnum);
280                         break;
281                 };
282         } else {
283                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
284                          "Invalid Band %d in PHY_SetTxPowerByRateBase()\n",
285                          band);
286         }
287
288 }
289
290 static u8 _rtl8723be_phy_get_txpower_by_rate_base(struct ieee80211_hw *hw,
291                                                   u8 band, u8 path, u8 txnum,
292                                                   u8 rate_section)
293 {
294         struct rtl_priv *rtlpriv = rtl_priv(hw);
295         struct rtl_phy *rtlphy = &rtlpriv->phy;
296         u8 value = 0;
297         if (path > RF90_PATH_D) {
298                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
299                          "Invalid Rf Path %d in PHY_GetTxPowerByRateBase()\n",
300                           path);
301                 return 0;
302         }
303
304         if (band == BAND_ON_2_4G) {
305                 switch (rate_section) {
306                 case CCK:
307                         value = rtlphy->txpwr_by_rate_base_24g[path][txnum][0];
308                         break;
309                 case OFDM:
310                         value = rtlphy->txpwr_by_rate_base_24g[path][txnum][1];
311                         break;
312                 case HT_MCS0_MCS7:
313                         value = rtlphy->txpwr_by_rate_base_24g[path][txnum][2];
314                         break;
315                 case HT_MCS8_MCS15:
316                         value = rtlphy->txpwr_by_rate_base_24g[path][txnum][3];
317                         break;
318                 default:
319                         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
320                                  "Invalid RateSection %d in Band 2.4G, Rf Path %d, %dTx in PHY_GetTxPowerByRateBase()\n",
321                                  rate_section, path, txnum);
322                         break;
323                 };
324         } else {
325                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
326                          "Invalid Band %d in PHY_GetTxPowerByRateBase()\n",
327                          band);
328         }
329
330         return value;
331 }
332
333 static void _rtl8723be_phy_store_txpower_by_rate_base(struct ieee80211_hw *hw)
334 {
335         struct rtl_priv *rtlpriv = rtl_priv(hw);
336         struct rtl_phy *rtlphy = &rtlpriv->phy;
337         u16 rawvalue = 0;
338         u8 base = 0, path = 0;
339
340         for (path = RF90_PATH_A; path <= RF90_PATH_B; ++path) {
341                 if (path == RF90_PATH_A) {
342                         rawvalue = (u16)(rtlphy->tx_power_by_rate_offset
343                                 [BAND_ON_2_4G][path][RF_1TX][3] >> 24) & 0xFF;
344                         base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
345                         _rtl8723be_phy_set_txpower_by_rate_base(hw,
346                                 BAND_ON_2_4G, path, CCK, RF_1TX, base);
347                 } else if (path == RF90_PATH_B) {
348                         rawvalue = (u16)(rtlphy->tx_power_by_rate_offset
349                                 [BAND_ON_2_4G][path][RF_1TX][3] >> 0) & 0xFF;
350                         base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
351                         _rtl8723be_phy_set_txpower_by_rate_base(hw,
352                                                                 BAND_ON_2_4G,
353                                                                 path, CCK,
354                                                                 RF_1TX, base);
355                 }
356                 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset
357                                 [BAND_ON_2_4G][path][RF_1TX][1] >> 24) & 0xFF;
358                 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
359                 _rtl8723be_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G,
360                                                         path, OFDM, RF_1TX,
361                                                         base);
362
363                 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset
364                                 [BAND_ON_2_4G][path][RF_1TX][5] >> 24) & 0xFF;
365                 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
366                 _rtl8723be_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G,
367                                                         path, HT_MCS0_MCS7,
368                                                         RF_1TX, base);
369
370                 rawvalue = (u16)(rtlphy->tx_power_by_rate_offset
371                                 [BAND_ON_2_4G][path][RF_2TX][7] >> 24) & 0xFF;
372                 base = (rawvalue >> 4) * 10 + (rawvalue & 0xF);
373                 _rtl8723be_phy_set_txpower_by_rate_base(hw, BAND_ON_2_4G,
374                                                         path, HT_MCS8_MCS15,
375                                                         RF_2TX, base);
376         }
377 }
378
379 static void _phy_convert_txpower_dbm_to_relative_value(u32 *data, u8 start,
380                                                 u8 end, u8 base_val)
381 {
382         char i = 0;
383         u8 temp_value = 0;
384         u32 temp_data = 0;
385
386         for (i = 3; i >= 0; --i) {
387                 if (i >= start && i <= end) {
388                         /* Get the exact value */
389                         temp_value = (u8)(*data >> (i * 8)) & 0xF;
390                         temp_value += ((u8)((*data >> (i*8 + 4)) & 0xF)) * 10;
391
392                         /* Change the value to a relative value */
393                         temp_value = (temp_value > base_val) ?
394                                      temp_value - base_val :
395                                      base_val - temp_value;
396                 } else {
397                         temp_value = (u8)(*data >> (i * 8)) & 0xFF;
398                 }
399                 temp_data <<= 8;
400                 temp_data |= temp_value;
401         }
402         *data = temp_data;
403 }
404
405 static void _rtl8723be_phy_convert_txpower_dbm_to_relative_value(
406                                                         struct ieee80211_hw *hw)
407 {
408         struct rtl_priv *rtlpriv = rtl_priv(hw);
409         struct rtl_phy *rtlphy = &rtlpriv->phy;
410         u8 base = 0, rfpath = RF90_PATH_A;
411
412         base = _rtl8723be_phy_get_txpower_by_rate_base(hw,
413                         BAND_ON_2_4G, rfpath, RF_1TX, CCK);
414         _phy_convert_txpower_dbm_to_relative_value(
415             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][2],
416             1, 1, base);
417         _phy_convert_txpower_dbm_to_relative_value(
418             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][3],
419             1, 3, base);
420
421         base = _rtl8723be_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath,
422                                                        RF_1TX, OFDM);
423         _phy_convert_txpower_dbm_to_relative_value(
424             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][0],
425             0, 3, base);
426         _phy_convert_txpower_dbm_to_relative_value(
427             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][1],
428             0, 3, base);
429
430         base = _rtl8723be_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G,
431                                                 rfpath, RF_1TX, HT_MCS0_MCS7);
432         _phy_convert_txpower_dbm_to_relative_value(
433             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][4],
434             0, 3, base);
435         _phy_convert_txpower_dbm_to_relative_value(
436             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][5],
437             0, 3, base);
438
439         base = _rtl8723be_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G,
440                                                        rfpath, RF_2TX,
441                                                        HT_MCS8_MCS15);
442         _phy_convert_txpower_dbm_to_relative_value(
443             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][6],
444             0, 3, base);
445
446         _phy_convert_txpower_dbm_to_relative_value(
447             &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][7],
448             0, 3, base);
449
450         RT_TRACE(rtlpriv, COMP_POWER, DBG_TRACE,
451             "<===_rtl8723be_phy_convert_txpower_dbm_to_relative_value()\n");
452 }
453
454 static void phy_txpower_by_rate_config(struct ieee80211_hw *hw)
455 {
456         _rtl8723be_phy_store_txpower_by_rate_base(hw);
457         _rtl8723be_phy_convert_txpower_dbm_to_relative_value(hw);
458 }
459
460 static bool _rtl8723be_phy_bb8723b_config_parafile(struct ieee80211_hw *hw)
461 {
462         struct rtl_priv *rtlpriv = rtl_priv(hw);
463         struct rtl_phy *rtlphy = &rtlpriv->phy;
464         struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
465         bool rtstatus;
466
467         rtstatus = _rtl8723be_phy_config_bb_with_headerfile(hw,
468                                                 BASEBAND_CONFIG_PHY_REG);
469         if (!rtstatus) {
470                 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG, "Write BB Reg Fail!!");
471                 return false;
472         }
473         _rtl8723be_phy_init_tx_power_by_rate(hw);
474         if (!rtlefuse->autoload_failflag) {
475                 rtlphy->pwrgroup_cnt = 0;
476                 rtstatus = _rtl8723be_phy_config_bb_with_pgheaderfile(hw,
477                                                 BASEBAND_CONFIG_PHY_REG);
478         }
479         phy_txpower_by_rate_config(hw);
480         if (!rtstatus) {
481                 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG, "BB_PG Reg Fail!!");
482                 return false;
483         }
484         rtstatus = _rtl8723be_phy_config_bb_with_headerfile(hw,
485                                                 BASEBAND_CONFIG_AGC_TAB);
486         if (!rtstatus) {
487                 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG, "AGC Table Fail\n");
488                 return false;
489         }
490         rtlphy->cck_high_power = (bool)(rtl_get_bbreg(hw,
491                                                       RFPGA0_XA_HSSIPARAMETER2,
492                                                       0x200));
493         return true;
494 }
495
496 static bool _rtl8723be_phy_config_mac_with_headerfile(struct ieee80211_hw *hw)
497 {
498         struct rtl_priv *rtlpriv = rtl_priv(hw);
499         u32 i;
500         u32 arraylength;
501         u32 *ptrarray;
502
503         RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE, "Read rtl8723beMACPHY_Array\n");
504         arraylength = RTL8723BEMAC_1T_ARRAYLEN;
505         ptrarray = RTL8723BEMAC_1T_ARRAY;
506         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
507                  "Img:RTL8723bEMAC_1T_ARRAY LEN %d\n", arraylength);
508         for (i = 0; i < arraylength; i = i + 2)
509                 rtl_write_byte(rtlpriv, ptrarray[i], (u8)ptrarray[i + 1]);
510         return true;
511 }
512
513 static bool _rtl8723be_phy_config_bb_with_headerfile(struct ieee80211_hw *hw,
514                                                      u8 configtype)
515 {
516         #define READ_NEXT_PAIR(v1, v2, i) \
517                 do { \
518                         i += 2; \
519                         v1 = array_table[i];\
520                         v2 = array_table[i+1]; \
521                 } while (0)
522
523         int i;
524         u32 *array_table;
525         u16 arraylen;
526         struct rtl_priv *rtlpriv = rtl_priv(hw);
527         u32 v1 = 0, v2 = 0;
528
529         if (configtype == BASEBAND_CONFIG_PHY_REG) {
530                 arraylen = RTL8723BEPHY_REG_1TARRAYLEN;
531                 array_table = RTL8723BEPHY_REG_1TARRAY;
532
533                 for (i = 0; i < arraylen; i = i + 2) {
534                         v1 = array_table[i];
535                         v2 = array_table[i+1];
536                         if (v1 < 0xcdcdcdcd) {
537                                 _rtl8723be_config_bb_reg(hw, v1, v2);
538                         } else {/*This line is the start line of branch.*/
539                                 /* to protect READ_NEXT_PAIR not overrun */
540                                 if (i >= arraylen - 2)
541                                         break;
542
543                                 if (!_rtl8723be_check_condition(hw,
544                                                 array_table[i])) {
545                                         /*Discard the following
546                                          *(offset, data) pairs
547                                          */
548                                         READ_NEXT_PAIR(v1, v2, i);
549                                         while (v2 != 0xDEAD &&
550                                                v2 != 0xCDEF &&
551                                                v2 != 0xCDCD &&
552                                                i < arraylen - 2) {
553                                                 READ_NEXT_PAIR(v1, v2, i);
554                                         }
555                                         i -= 2; /* prevent from for-loop += 2*/
556                                 /*Configure matched pairs and
557                                  *skip to end of if-else.
558                                  */
559                                 } else {
560                                         READ_NEXT_PAIR(v1, v2, i);
561                                         while (v2 != 0xDEAD &&
562                                                v2 != 0xCDEF &&
563                                                v2 != 0xCDCD &&
564                                                i < arraylen - 2) {
565                                                 _rtl8723be_config_bb_reg(hw,
566                                                                     v1, v2);
567                                                 READ_NEXT_PAIR(v1, v2, i);
568                                         }
569
570                                         while (v2 != 0xDEAD && i < arraylen - 2)
571                                                 READ_NEXT_PAIR(v1, v2, i);
572                                 }
573                         }
574                 }
575         } else if (configtype == BASEBAND_CONFIG_AGC_TAB) {
576                 arraylen = RTL8723BEAGCTAB_1TARRAYLEN;
577                 array_table = RTL8723BEAGCTAB_1TARRAY;
578
579                 for (i = 0; i < arraylen; i = i + 2) {
580                         v1 = array_table[i];
581                         v2 = array_table[i+1];
582                         if (v1 < 0xCDCDCDCD) {
583                                 rtl_set_bbreg(hw, array_table[i],
584                                               MASKDWORD,
585                                               array_table[i + 1]);
586                                 udelay(1);
587                                 continue;
588                         } else {/*This line is the start line of branch.*/
589                                 /* to protect READ_NEXT_PAIR not overrun */
590                                 if (i >= arraylen - 2)
591                                         break;
592
593                                 if (!_rtl8723be_check_condition(hw,
594                                         array_table[i])) {
595                                         /*Discard the following
596                                          *(offset, data) pairs
597                                          */
598                                         READ_NEXT_PAIR(v1, v2, i);
599                                         while (v2 != 0xDEAD &&
600                                                v2 != 0xCDEF &&
601                                                v2 != 0xCDCD &&
602                                                i < arraylen - 2) {
603                                                 READ_NEXT_PAIR(v1, v2, i);
604                                         }
605                                         i -= 2; /* prevent from for-loop += 2*/
606                                 /*Configure matched pairs and
607                                  *skip to end of if-else.
608                                  */
609                                 } else {
610                                         READ_NEXT_PAIR(v1, v2, i);
611                                         while (v2 != 0xDEAD &&
612                                                v2 != 0xCDEF &&
613                                                v2 != 0xCDCD &&
614                                                i < arraylen - 2) {
615                                                 rtl_set_bbreg(hw, array_table[i],
616                                                               MASKDWORD,
617                                                               array_table[i + 1]);
618                                                 udelay(1);
619                                                 READ_NEXT_PAIR(v1, v2, i);
620                                         }
621
622                                         while (v2 != 0xDEAD && i < arraylen - 2)
623                                                 READ_NEXT_PAIR(v1, v2, i);
624                                 }
625                         }
626                         RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
627                                  "The agctab_array_table[0] is %x Rtl818EEPHY_REGArray[1] is %x\n",
628                                  array_table[i], array_table[i + 1]);
629                 }
630         }
631         return true;
632 }
633
634 static u8 _rtl8723be_get_rate_section_index(u32 regaddr)
635 {
636         u8 index = 0;
637
638         switch (regaddr) {
639         case RTXAGC_A_RATE18_06:
640                 index = 0;
641         break;
642         case RTXAGC_A_RATE54_24:
643                 index = 1;
644         break;
645         case RTXAGC_A_CCK1_MCS32:
646                 index = 2;
647         break;
648         case RTXAGC_B_CCK11_A_CCK2_11:
649                 index = 3;
650         break;
651         case RTXAGC_A_MCS03_MCS00:
652                 index = 4;
653         break;
654         case RTXAGC_A_MCS07_MCS04:
655                 index = 5;
656         break;
657         case RTXAGC_A_MCS11_MCS08:
658                 index = 6;
659         break;
660         case RTXAGC_A_MCS15_MCS12:
661                 index = 7;
662         break;
663         case RTXAGC_B_RATE18_06:
664                 index = 0;
665         break;
666         case RTXAGC_B_RATE54_24:
667                 index = 1;
668         break;
669         case RTXAGC_B_CCK1_55_MCS32:
670                 index = 2;
671         break;
672         case RTXAGC_B_MCS03_MCS00:
673                 index = 4;
674         break;
675         case RTXAGC_B_MCS07_MCS04:
676                 index = 5;
677         break;
678         case RTXAGC_B_MCS11_MCS08:
679                 index = 6;
680         break;
681         case RTXAGC_B_MCS15_MCS12:
682                 index = 7;
683         break;
684         default:
685                 regaddr &= 0xFFF;
686                 if (regaddr >= 0xC20 && regaddr <= 0xC4C)
687                         index = (u8)((regaddr - 0xC20) / 4);
688                 else if (regaddr >= 0xE20 && regaddr <= 0xE4C)
689                         index = (u8)((regaddr - 0xE20) / 4);
690                 break;
691         };
692         return index;
693 }
694
695 static void _rtl8723be_store_tx_power_by_rate(struct ieee80211_hw *hw,
696                                               u32 band, u32 rfpath,
697                                               u32 txnum, u32 regaddr,
698                                               u32 bitmask, u32 data)
699 {
700         struct rtl_priv *rtlpriv = rtl_priv(hw);
701         struct rtl_phy *rtlphy = &rtlpriv->phy;
702         u8 rate_section = _rtl8723be_get_rate_section_index(regaddr);
703
704         if (band != BAND_ON_2_4G && band != BAND_ON_5G) {
705                 RT_TRACE(rtlpriv, FPHY, PHY_TXPWR, "Invalid Band %d\n", band);
706                 return;
707         }
708         if (rfpath > MAX_RF_PATH - 1) {
709                 RT_TRACE(rtlpriv, FPHY, PHY_TXPWR,
710                          "Invalid RfPath %d\n", rfpath);
711                 return;
712         }
713         if (txnum > MAX_RF_PATH - 1) {
714                 RT_TRACE(rtlpriv, FPHY, PHY_TXPWR, "Invalid TxNum %d\n", txnum);
715                 return;
716         }
717
718         rtlphy->tx_power_by_rate_offset[band][rfpath][txnum][rate_section] =
719                                                                         data;
720
721 }
722
723 static bool _rtl8723be_phy_config_bb_with_pgheaderfile(struct ieee80211_hw *hw,
724                                                        u8 configtype)
725 {
726         struct rtl_priv *rtlpriv = rtl_priv(hw);
727         int i;
728         u32 *phy_regarray_table_pg;
729         u16 phy_regarray_pg_len;
730         u32 v1 = 0, v2 = 0, v3 = 0, v4 = 0, v5 = 0, v6 = 0;
731
732         phy_regarray_pg_len = RTL8723BEPHY_REG_ARRAY_PGLEN;
733         phy_regarray_table_pg = RTL8723BEPHY_REG_ARRAY_PG;
734
735         if (configtype == BASEBAND_CONFIG_PHY_REG) {
736                 for (i = 0; i < phy_regarray_pg_len; i = i + 6) {
737                         v1 = phy_regarray_table_pg[i];
738                         v2 = phy_regarray_table_pg[i+1];
739                         v3 = phy_regarray_table_pg[i+2];
740                         v4 = phy_regarray_table_pg[i+3];
741                         v5 = phy_regarray_table_pg[i+4];
742                         v6 = phy_regarray_table_pg[i+5];
743
744                         if (v1 < 0xcdcdcdcd) {
745                                 if (phy_regarray_table_pg[i] == 0xfe ||
746                                     phy_regarray_table_pg[i] == 0xffe)
747                                         mdelay(50);
748                                 else
749                                         _rtl8723be_store_tx_power_by_rate(hw,
750                                                         v1, v2, v3, v4, v5, v6);
751                                 continue;
752                         }
753                 }
754         } else {
755                 RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
756                          "configtype != BaseBand_Config_PHY_REG\n");
757         }
758         return true;
759 }
760
761 bool rtl8723be_phy_config_rf_with_headerfile(struct ieee80211_hw *hw,
762                                              enum radio_path rfpath)
763 {
764         #define READ_NEXT_RF_PAIR(v1, v2, i) \
765                 do { \
766                         i += 2; \
767                         v1 = radioa_array_table[i]; \
768                         v2 = radioa_array_table[i+1]; \
769                 } while (0)
770
771         int i;
772         bool rtstatus = true;
773         u32 *radioa_array_table;
774         u16 radioa_arraylen;
775         struct rtl_priv *rtlpriv = rtl_priv(hw);
776         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
777         u32 v1 = 0, v2 = 0;
778
779         radioa_arraylen = RTL8723BE_RADIOA_1TARRAYLEN;
780         radioa_array_table = RTL8723BE_RADIOA_1TARRAY;
781         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
782                  "Radio_A:RTL8723BE_RADIOA_1TARRAY %d\n", radioa_arraylen);
783         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "Radio No %x\n", rfpath);
784         rtstatus = true;
785         switch (rfpath) {
786         case RF90_PATH_A:
787                 for (i = 0; i < radioa_arraylen; i = i + 2) {
788                         v1 = radioa_array_table[i];
789                         v2 = radioa_array_table[i+1];
790                         if (v1 < 0xcdcdcdcd) {
791                                 _rtl8723be_config_rf_radio_a(hw, v1, v2);
792                         } else {/*This line is the start line of branch.*/
793                                 /* to protect READ_NEXT_PAIR not overrun */
794                                 if (i >= radioa_arraylen - 2)
795                                         break;
796
797                                 if (!_rtl8723be_check_condition(hw,
798                                                 radioa_array_table[i])) {
799                                         /*Discard the following
800                                          *(offset, data) pairs
801                                          */
802                                         READ_NEXT_RF_PAIR(v1, v2, i);
803                                         while (v2 != 0xDEAD &&
804                                                v2 != 0xCDEF &&
805                                                v2 != 0xCDCD &&
806                                                i < radioa_arraylen - 2) {
807                                                 READ_NEXT_RF_PAIR(v1, v2, i);
808                                         }
809                                         i -= 2; /* prevent from for-loop += 2*/
810                                 } else {
811                                         /*Configure matched pairs
812                                          *and skip to end of if-else.
813                                          */
814                                         READ_NEXT_RF_PAIR(v1, v2, i);
815                                         while (v2 != 0xDEAD &&
816                                                v2 != 0xCDEF &&
817                                                v2 != 0xCDCD &&
818                                                i < radioa_arraylen - 2) {
819                                                 _rtl8723be_config_rf_radio_a(hw,
820                                                                         v1, v2);
821                                                 READ_NEXT_RF_PAIR(v1, v2, i);
822                                         }
823
824                                         while (v2 != 0xDEAD &&
825                                                i < radioa_arraylen - 2) {
826                                                 READ_NEXT_RF_PAIR(v1, v2, i);
827                                         }
828                                 }
829                         }
830                 }
831
832                 if (rtlhal->oem_id == RT_CID_819X_HP)
833                         _rtl8723be_config_rf_radio_a(hw, 0x52, 0x7E4BD);
834                 break;
835         case RF90_PATH_B:
836         case RF90_PATH_C:
837                 break;
838         case RF90_PATH_D:
839                 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
840                          "switch case not process\n");
841                 break;
842         }
843         return true;
844 }
845
846 void rtl8723be_phy_get_hw_reg_originalvalue(struct ieee80211_hw *hw)
847 {
848         struct rtl_priv *rtlpriv = rtl_priv(hw);
849         struct rtl_phy *rtlphy = &rtlpriv->phy;
850
851         rtlphy->default_initialgain[0] =
852             (u8)rtl_get_bbreg(hw, ROFDM0_XAAGCCORE1, MASKBYTE0);
853         rtlphy->default_initialgain[1] =
854             (u8)rtl_get_bbreg(hw, ROFDM0_XBAGCCORE1, MASKBYTE0);
855         rtlphy->default_initialgain[2] =
856             (u8)rtl_get_bbreg(hw, ROFDM0_XCAGCCORE1, MASKBYTE0);
857         rtlphy->default_initialgain[3] =
858             (u8)rtl_get_bbreg(hw, ROFDM0_XDAGCCORE1, MASKBYTE0);
859
860         RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
861                  "Default initial gain (c50=0x%x, c58=0x%x, c60=0x%x, c68=0x%x\n",
862                  rtlphy->default_initialgain[0],
863                  rtlphy->default_initialgain[1],
864                  rtlphy->default_initialgain[2],
865                  rtlphy->default_initialgain[3]);
866
867         rtlphy->framesync = (u8)rtl_get_bbreg(hw, ROFDM0_RXDETECTOR3,
868                                                MASKBYTE0);
869         rtlphy->framesync_c34 = rtl_get_bbreg(hw, ROFDM0_RXDETECTOR2,
870                                               MASKDWORD);
871
872         RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
873                  "Default framesync (0x%x) = 0x%x\n",
874                   ROFDM0_RXDETECTOR3, rtlphy->framesync);
875 }
876
877 void rtl8723be_phy_get_txpower_level(struct ieee80211_hw *hw, long *powerlevel)
878 {
879         struct rtl_priv *rtlpriv = rtl_priv(hw);
880         struct rtl_phy *rtlphy = &rtlpriv->phy;
881         u8 txpwr_level;
882         long txpwr_dbm;
883
884         txpwr_level = rtlphy->cur_cck_txpwridx;
885         txpwr_dbm = rtl8723_phy_txpwr_idx_to_dbm(hw, WIRELESS_MODE_B,
886                                                  txpwr_level);
887         txpwr_level = rtlphy->cur_ofdm24g_txpwridx;
888         if (rtl8723_phy_txpwr_idx_to_dbm(hw, WIRELESS_MODE_G, txpwr_level) >
889             txpwr_dbm)
890                 txpwr_dbm =
891                     rtl8723_phy_txpwr_idx_to_dbm(hw, WIRELESS_MODE_G,
892                                                  txpwr_level);
893         txpwr_level = rtlphy->cur_ofdm24g_txpwridx;
894         if (rtl8723_phy_txpwr_idx_to_dbm(hw, WIRELESS_MODE_N_24G,
895                                          txpwr_level) > txpwr_dbm)
896                 txpwr_dbm =
897                     rtl8723_phy_txpwr_idx_to_dbm(hw, WIRELESS_MODE_N_24G,
898                                                  txpwr_level);
899         *powerlevel = txpwr_dbm;
900 }
901
902 static u8 _rtl8723be_phy_get_ratesection_intxpower_byrate(enum radio_path path,
903                                                           u8 rate)
904 {
905         u8 rate_section = 0;
906
907         switch (rate) {
908         case DESC92C_RATE1M:
909                 rate_section = 2;
910                 break;
911
912         case DESC92C_RATE2M:
913         case DESC92C_RATE5_5M:
914                 if (path == RF90_PATH_A)
915                         rate_section = 3;
916                 else if (path == RF90_PATH_B)
917                         rate_section = 2;
918                 break;
919
920         case DESC92C_RATE11M:
921                 rate_section = 3;
922                 break;
923
924         case DESC92C_RATE6M:
925         case DESC92C_RATE9M:
926         case DESC92C_RATE12M:
927         case DESC92C_RATE18M:
928                 rate_section = 0;
929                 break;
930
931         case DESC92C_RATE24M:
932         case DESC92C_RATE36M:
933         case DESC92C_RATE48M:
934         case DESC92C_RATE54M:
935                 rate_section = 1;
936                 break;
937
938         case DESC92C_RATEMCS0:
939         case DESC92C_RATEMCS1:
940         case DESC92C_RATEMCS2:
941         case DESC92C_RATEMCS3:
942                 rate_section = 4;
943                 break;
944
945         case DESC92C_RATEMCS4:
946         case DESC92C_RATEMCS5:
947         case DESC92C_RATEMCS6:
948         case DESC92C_RATEMCS7:
949                 rate_section = 5;
950                 break;
951
952         case DESC92C_RATEMCS8:
953         case DESC92C_RATEMCS9:
954         case DESC92C_RATEMCS10:
955         case DESC92C_RATEMCS11:
956                 rate_section = 6;
957                 break;
958
959         case DESC92C_RATEMCS12:
960         case DESC92C_RATEMCS13:
961         case DESC92C_RATEMCS14:
962         case DESC92C_RATEMCS15:
963                 rate_section = 7;
964                 break;
965
966         default:
967                 RT_ASSERT(true, "Rate_Section is Illegal\n");
968                 break;
969         }
970
971         return rate_section;
972 }
973
974 static u8 _rtl8723be_get_txpower_by_rate(struct ieee80211_hw *hw,
975                                          enum band_type band,
976                                          enum radio_path rfpath, u8 rate)
977 {
978         struct rtl_priv *rtlpriv = rtl_priv(hw);
979         struct rtl_phy *rtlphy = &rtlpriv->phy;
980         u8 shift = 0, rate_section, tx_num;
981         char tx_pwr_diff = 0;
982
983         rate_section = _rtl8723be_phy_get_ratesection_intxpower_byrate(rfpath,
984                                                                        rate);
985         tx_num = RF_TX_NUM_NONIMPLEMENT;
986
987         if (tx_num == RF_TX_NUM_NONIMPLEMENT) {
988                 if (rate >= DESC92C_RATEMCS8 && rate <= DESC92C_RATEMCS15)
989                         tx_num = RF_2TX;
990                 else
991                         tx_num = RF_1TX;
992         }
993
994         switch (rate) {
995         case DESC92C_RATE6M:
996         case DESC92C_RATE24M:
997         case DESC92C_RATEMCS0:
998         case DESC92C_RATEMCS4:
999         case DESC92C_RATEMCS8:
1000         case DESC92C_RATEMCS12:
1001                 shift = 0;
1002                 break;
1003         case DESC92C_RATE1M:
1004         case DESC92C_RATE2M:
1005         case DESC92C_RATE9M:
1006         case DESC92C_RATE36M:
1007         case DESC92C_RATEMCS1:
1008         case DESC92C_RATEMCS5:
1009         case DESC92C_RATEMCS9:
1010         case DESC92C_RATEMCS13:
1011                 shift = 8;
1012                 break;
1013         case DESC92C_RATE5_5M:
1014         case DESC92C_RATE12M:
1015         case DESC92C_RATE48M:
1016         case DESC92C_RATEMCS2:
1017         case DESC92C_RATEMCS6:
1018         case DESC92C_RATEMCS10:
1019         case DESC92C_RATEMCS14:
1020                 shift = 16;
1021                 break;
1022         case DESC92C_RATE11M:
1023         case DESC92C_RATE18M:
1024         case DESC92C_RATE54M:
1025         case DESC92C_RATEMCS3:
1026         case DESC92C_RATEMCS7:
1027         case DESC92C_RATEMCS11:
1028         case DESC92C_RATEMCS15:
1029                 shift = 24;
1030                 break;
1031         default:
1032                 RT_ASSERT(true, "Rate_Section is Illegal\n");
1033                 break;
1034         }
1035         tx_pwr_diff = (u8)(rtlphy->tx_power_by_rate_offset[band][rfpath][tx_num]
1036                                           [rate_section] >> shift) & 0xff;
1037
1038         return  tx_pwr_diff;
1039 }
1040
1041 static u8 _rtl8723be_get_txpower_index(struct ieee80211_hw *hw, u8 path,
1042                                        u8 rate, u8 bandwidth, u8 channel)
1043 {
1044         struct rtl_priv *rtlpriv = rtl_priv(hw);
1045         struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
1046         u8 index = (channel - 1);
1047         u8 txpower;
1048         u8 power_diff_byrate = 0;
1049
1050         if (channel > 14 || channel < 1) {
1051                 index = 0;
1052                 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_LOUD,
1053                          "Illegal channel!\n");
1054         }
1055         if (RX_HAL_IS_CCK_RATE(rate))
1056                 txpower = rtlefuse->txpwrlevel_cck[path][index];
1057         else if (DESC92C_RATE6M <= rate)
1058                 txpower = rtlefuse->txpwrlevel_ht40_1s[path][index];
1059         else
1060                 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_LOUD,
1061                          "invalid rate\n");
1062
1063         if (DESC92C_RATE6M <= rate && rate <= DESC92C_RATE54M &&
1064             !RX_HAL_IS_CCK_RATE(rate))
1065                 txpower += rtlefuse->txpwr_legacyhtdiff[0][TX_1S];
1066
1067         if (bandwidth == HT_CHANNEL_WIDTH_20) {
1068                 if (DESC92C_RATEMCS0 <= rate && rate <= DESC92C_RATEMCS15)
1069                         txpower += rtlefuse->txpwr_ht20diff[0][TX_1S];
1070                 if (DESC92C_RATEMCS8 <= rate && rate <= DESC92C_RATEMCS15)
1071                         txpower += rtlefuse->txpwr_ht20diff[0][TX_2S];
1072         } else if (bandwidth == HT_CHANNEL_WIDTH_20_40) {
1073                 if (DESC92C_RATEMCS0 <= rate && rate <= DESC92C_RATEMCS15)
1074                         txpower += rtlefuse->txpwr_ht40diff[0][TX_1S];
1075                 if (DESC92C_RATEMCS8 <= rate && rate <= DESC92C_RATEMCS15)
1076                         txpower += rtlefuse->txpwr_ht40diff[0][TX_2S];
1077         }
1078
1079         if (rtlefuse->eeprom_regulatory != 2)
1080                 power_diff_byrate = _rtl8723be_get_txpower_by_rate(hw,
1081                                                                    BAND_ON_2_4G,
1082                                                                    path, rate);
1083
1084         txpower += power_diff_byrate;
1085
1086         if (txpower > MAX_POWER_INDEX)
1087                 txpower = MAX_POWER_INDEX;
1088
1089         return txpower;
1090 }
1091
1092 static void _rtl8723be_phy_set_txpower_index(struct ieee80211_hw *hw,
1093                                              u8 power_index, u8 path, u8 rate)
1094 {
1095         struct rtl_priv *rtlpriv = rtl_priv(hw);
1096         if (path == RF90_PATH_A) {
1097                 switch (rate) {
1098                 case DESC92C_RATE1M:
1099                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_CCK1_MCS32,
1100                                                MASKBYTE1, power_index);
1101                         break;
1102                 case DESC92C_RATE2M:
1103                         rtl8723_phy_set_bb_reg(hw, RTXAGC_B_CCK11_A_CCK2_11,
1104                                                MASKBYTE1, power_index);
1105                         break;
1106                 case DESC92C_RATE5_5M:
1107                         rtl8723_phy_set_bb_reg(hw, RTXAGC_B_CCK11_A_CCK2_11,
1108                                                MASKBYTE2, power_index);
1109                         break;
1110                 case DESC92C_RATE11M:
1111                         rtl8723_phy_set_bb_reg(hw, RTXAGC_B_CCK11_A_CCK2_11,
1112                                                MASKBYTE3, power_index);
1113                         break;
1114
1115                 case DESC92C_RATE6M:
1116                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1117                                                MASKBYTE0, power_index);
1118                         break;
1119                 case DESC92C_RATE9M:
1120                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1121                                                MASKBYTE1, power_index);
1122                         break;
1123                 case DESC92C_RATE12M:
1124                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1125                                                MASKBYTE2, power_index);
1126                         break;
1127                 case DESC92C_RATE18M:
1128                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1129                                                MASKBYTE3, power_index);
1130                         break;
1131
1132                 case DESC92C_RATE24M:
1133                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1134                                                MASKBYTE0, power_index);
1135                         break;
1136                 case DESC92C_RATE36M:
1137                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1138                                                MASKBYTE1, power_index);
1139                         break;
1140                 case DESC92C_RATE48M:
1141                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1142                                                MASKBYTE2, power_index);
1143                         break;
1144                 case DESC92C_RATE54M:
1145                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1146                                                MASKBYTE3, power_index);
1147                         break;
1148
1149                 case DESC92C_RATEMCS0:
1150                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1151                                                MASKBYTE0, power_index);
1152                         break;
1153                 case DESC92C_RATEMCS1:
1154                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1155                                                MASKBYTE1, power_index);
1156                         break;
1157                 case DESC92C_RATEMCS2:
1158                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1159                                                MASKBYTE2, power_index);
1160                         break;
1161                 case DESC92C_RATEMCS3:
1162                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1163                                                MASKBYTE3, power_index);
1164                         break;
1165
1166                 case DESC92C_RATEMCS4:
1167                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1168                                                MASKBYTE0, power_index);
1169                         break;
1170                 case DESC92C_RATEMCS5:
1171                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1172                                                MASKBYTE1, power_index);
1173                         break;
1174                 case DESC92C_RATEMCS6:
1175                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1176                                                MASKBYTE2, power_index);
1177                         break;
1178                 case DESC92C_RATEMCS7:
1179                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1180                                                MASKBYTE3, power_index);
1181                         break;
1182
1183                 case DESC92C_RATEMCS8:
1184                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1185                                                MASKBYTE0, power_index);
1186                         break;
1187                 case DESC92C_RATEMCS9:
1188                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1189                                                MASKBYTE1, power_index);
1190                         break;
1191                 case DESC92C_RATEMCS10:
1192                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1193                                                MASKBYTE2, power_index);
1194                         break;
1195                 case DESC92C_RATEMCS11:
1196                         rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1197                                                MASKBYTE3, power_index);
1198                         break;
1199
1200                 default:
1201                         RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD, "Invalid Rate!!\n");
1202                         break;
1203                 }
1204         } else {
1205                 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD, "Invalid RFPath!!\n");
1206         }
1207 }
1208
1209 void rtl8723be_phy_set_txpower_level(struct ieee80211_hw *hw, u8 channel)
1210 {
1211         struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
1212         u8 cck_rates[]  = {DESC92C_RATE1M, DESC92C_RATE2M,
1213                            DESC92C_RATE5_5M, DESC92C_RATE11M};
1214         u8 ofdm_rates[]  = {DESC92C_RATE6M, DESC92C_RATE9M,
1215                             DESC92C_RATE12M, DESC92C_RATE18M,
1216                             DESC92C_RATE24M, DESC92C_RATE36M,
1217                             DESC92C_RATE48M, DESC92C_RATE54M};
1218         u8 ht_rates_1t[]  = {DESC92C_RATEMCS0, DESC92C_RATEMCS1,
1219                              DESC92C_RATEMCS2, DESC92C_RATEMCS3,
1220                              DESC92C_RATEMCS4, DESC92C_RATEMCS5,
1221                              DESC92C_RATEMCS6, DESC92C_RATEMCS7};
1222         u8 i, size;
1223         u8 power_index;
1224
1225         if (!rtlefuse->txpwr_fromeprom)
1226                 return;
1227
1228         size = sizeof(cck_rates) / sizeof(u8);
1229         for (i = 0; i < size; i++) {
1230                 power_index = _rtl8723be_get_txpower_index(hw, RF90_PATH_A,
1231                                         cck_rates[i],
1232                                         rtl_priv(hw)->phy.current_chan_bw,
1233                                         channel);
1234                 _rtl8723be_phy_set_txpower_index(hw, power_index, RF90_PATH_A,
1235                                                  cck_rates[i]);
1236         }
1237         size = sizeof(ofdm_rates) / sizeof(u8);
1238         for (i = 0; i < size; i++) {
1239                 power_index = _rtl8723be_get_txpower_index(hw, RF90_PATH_A,
1240                                         ofdm_rates[i],
1241                                         rtl_priv(hw)->phy.current_chan_bw,
1242                                         channel);
1243                 _rtl8723be_phy_set_txpower_index(hw, power_index, RF90_PATH_A,
1244                                                  ofdm_rates[i]);
1245         }
1246         size = sizeof(ht_rates_1t) / sizeof(u8);
1247         for (i = 0; i < size; i++) {
1248                 power_index = _rtl8723be_get_txpower_index(hw, RF90_PATH_A,
1249                                         ht_rates_1t[i],
1250                                         rtl_priv(hw)->phy.current_chan_bw,
1251                                         channel);
1252                 _rtl8723be_phy_set_txpower_index(hw, power_index, RF90_PATH_A,
1253                                                  ht_rates_1t[i]);
1254         }
1255 }
1256
1257 void rtl8723be_phy_scan_operation_backup(struct ieee80211_hw *hw, u8 operation)
1258 {
1259         struct rtl_priv *rtlpriv = rtl_priv(hw);
1260         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1261         enum io_type iotype;
1262
1263         if (!is_hal_stop(rtlhal)) {
1264                 switch (operation) {
1265                 case SCAN_OPT_BACKUP_BAND0:
1266                         iotype = IO_CMD_PAUSE_BAND0_DM_BY_SCAN;
1267                         rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_IO_CMD,
1268                                                       (u8 *)&iotype);
1269
1270                         break;
1271                 case SCAN_OPT_RESTORE:
1272                         iotype = IO_CMD_RESUME_DM_BY_SCAN;
1273                         rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_IO_CMD,
1274                                                       (u8 *)&iotype);
1275                         break;
1276                 default:
1277                         RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1278                                  "Unknown Scan Backup operation.\n");
1279                         break;
1280                 }
1281         }
1282 }
1283
1284 void rtl8723be_phy_set_bw_mode_callback(struct ieee80211_hw *hw)
1285 {
1286         struct rtl_priv *rtlpriv = rtl_priv(hw);
1287         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1288         struct rtl_phy *rtlphy = &rtlpriv->phy;
1289         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
1290         u8 reg_bw_opmode;
1291         u8 reg_prsr_rsc;
1292
1293         RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
1294                  "Switch to %s bandwidth\n",
1295                   rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_20 ?
1296                   "20MHz" : "40MHz");
1297
1298         if (is_hal_stop(rtlhal)) {
1299                 rtlphy->set_bwmode_inprogress = false;
1300                 return;
1301         }
1302
1303         reg_bw_opmode = rtl_read_byte(rtlpriv, REG_BWOPMODE);
1304         reg_prsr_rsc = rtl_read_byte(rtlpriv, REG_RRSR + 2);
1305
1306         switch (rtlphy->current_chan_bw) {
1307         case HT_CHANNEL_WIDTH_20:
1308                 reg_bw_opmode |= BW_OPMODE_20MHZ;
1309                 rtl_write_byte(rtlpriv, REG_BWOPMODE, reg_bw_opmode);
1310                 break;
1311         case HT_CHANNEL_WIDTH_20_40:
1312                 reg_bw_opmode &= ~BW_OPMODE_20MHZ;
1313                 rtl_write_byte(rtlpriv, REG_BWOPMODE, reg_bw_opmode);
1314                 reg_prsr_rsc = (reg_prsr_rsc & 0x90) |
1315                                (mac->cur_40_prime_sc << 5);
1316                 rtl_write_byte(rtlpriv, REG_RRSR + 2, reg_prsr_rsc);
1317                 break;
1318         default:
1319                 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1320                          "unknown bandwidth: %#X\n", rtlphy->current_chan_bw);
1321                 break;
1322         }
1323
1324         switch (rtlphy->current_chan_bw) {
1325         case HT_CHANNEL_WIDTH_20:
1326                 rtl_set_bbreg(hw, RFPGA0_RFMOD, BRFMOD, 0x0);
1327                 rtl_set_bbreg(hw, RFPGA1_RFMOD, BRFMOD, 0x0);
1328         /*      rtl_set_bbreg(hw, RFPGA0_ANALOGPARAMETER2, BIT(10), 1);*/
1329                 break;
1330         case HT_CHANNEL_WIDTH_20_40:
1331                 rtl_set_bbreg(hw, RFPGA0_RFMOD, BRFMOD, 0x1);
1332                 rtl_set_bbreg(hw, RFPGA1_RFMOD, BRFMOD, 0x1);
1333
1334                 rtl_set_bbreg(hw, RCCK0_SYSTEM, BCCK_SIDEBAND,
1335                               (mac->cur_40_prime_sc >> 1));
1336                 rtl_set_bbreg(hw, ROFDM1_LSTF, 0xC00, mac->cur_40_prime_sc);
1337                 /*rtl_set_bbreg(hw, RFPGA0_ANALOGPARAMETER2, BIT(10), 0);*/
1338
1339                 rtl_set_bbreg(hw, 0x818, (BIT(26) | BIT(27)),
1340                               (mac->cur_40_prime_sc ==
1341                                HAL_PRIME_CHNL_OFFSET_LOWER) ? 2 : 1);
1342                 break;
1343         default:
1344                 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1345                          "unknown bandwidth: %#X\n", rtlphy->current_chan_bw);
1346                 break;
1347         }
1348         rtl8723be_phy_rf6052_set_bandwidth(hw, rtlphy->current_chan_bw);
1349         rtlphy->set_bwmode_inprogress = false;
1350         RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD, "\n");
1351 }
1352
1353 void rtl8723be_phy_set_bw_mode(struct ieee80211_hw *hw,
1354                             enum nl80211_channel_type ch_type)
1355 {
1356         struct rtl_priv *rtlpriv = rtl_priv(hw);
1357         struct rtl_phy *rtlphy = &rtlpriv->phy;
1358         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1359         u8 tmp_bw = rtlphy->current_chan_bw;
1360
1361         if (rtlphy->set_bwmode_inprogress)
1362                 return;
1363         rtlphy->set_bwmode_inprogress = true;
1364         if ((!is_hal_stop(rtlhal)) && !(RT_CANNOT_IO(hw))) {
1365                 rtl8723be_phy_set_bw_mode_callback(hw);
1366         } else {
1367                 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
1368                          "false driver sleep or unload\n");
1369                 rtlphy->set_bwmode_inprogress = false;
1370                 rtlphy->current_chan_bw = tmp_bw;
1371         }
1372 }
1373
1374 void rtl8723be_phy_sw_chnl_callback(struct ieee80211_hw *hw)
1375 {
1376         struct rtl_priv *rtlpriv = rtl_priv(hw);
1377         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1378         struct rtl_phy *rtlphy = &rtlpriv->phy;
1379         u32 delay;
1380
1381         RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
1382                  "switch to channel%d\n", rtlphy->current_channel);
1383         if (is_hal_stop(rtlhal))
1384                 return;
1385         do {
1386                 if (!rtlphy->sw_chnl_inprogress)
1387                         break;
1388                 if (!_rtl8723be_phy_sw_chnl_step_by_step(hw,
1389                                                          rtlphy->current_channel,
1390                                                          &rtlphy->sw_chnl_stage,
1391                                                          &rtlphy->sw_chnl_step,
1392                                                          &delay)) {
1393                         if (delay > 0)
1394                                 mdelay(delay);
1395                         else
1396                                 continue;
1397                 } else {
1398                         rtlphy->sw_chnl_inprogress = false;
1399                 }
1400                 break;
1401         } while (true);
1402         RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE, "\n");
1403 }
1404
1405 u8 rtl8723be_phy_sw_chnl(struct ieee80211_hw *hw)
1406 {
1407         struct rtl_priv *rtlpriv = rtl_priv(hw);
1408         struct rtl_phy *rtlphy = &rtlpriv->phy;
1409         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1410
1411         if (rtlphy->sw_chnl_inprogress)
1412                 return 0;
1413         if (rtlphy->set_bwmode_inprogress)
1414                 return 0;
1415         RT_ASSERT((rtlphy->current_channel <= 14),
1416                   "WIRELESS_MODE_G but channel>14");
1417         rtlphy->sw_chnl_inprogress = true;
1418         rtlphy->sw_chnl_stage = 0;
1419         rtlphy->sw_chnl_step = 0;
1420         if (!(is_hal_stop(rtlhal)) && !(RT_CANNOT_IO(hw))) {
1421                 rtl8723be_phy_sw_chnl_callback(hw);
1422                 RT_TRACE(rtlpriv, COMP_CHAN, DBG_LOUD,
1423                          "sw_chnl_inprogress false schdule workitem current channel %d\n",
1424                          rtlphy->current_channel);
1425                 rtlphy->sw_chnl_inprogress = false;
1426         } else {
1427                 RT_TRACE(rtlpriv, COMP_CHAN, DBG_LOUD,
1428                          "sw_chnl_inprogress false driver sleep or unload\n");
1429                 rtlphy->sw_chnl_inprogress = false;
1430         }
1431         return 1;
1432 }
1433
1434 static bool _rtl8723be_phy_sw_chnl_step_by_step(struct ieee80211_hw *hw,
1435                                                 u8 channel, u8 *stage,
1436                                                 u8 *step, u32 *delay)
1437 {
1438         struct rtl_priv *rtlpriv = rtl_priv(hw);
1439         struct rtl_phy *rtlphy = &rtlpriv->phy;
1440         struct swchnlcmd precommoncmd[MAX_PRECMD_CNT];
1441         u32 precommoncmdcnt;
1442         struct swchnlcmd postcommoncmd[MAX_POSTCMD_CNT];
1443         u32 postcommoncmdcnt;
1444         struct swchnlcmd rfdependcmd[MAX_RFDEPENDCMD_CNT];
1445         u32 rfdependcmdcnt;
1446         struct swchnlcmd *currentcmd = NULL;
1447         u8 rfpath;
1448         u8 num_total_rfpath = rtlphy->num_total_rfpath;
1449
1450         precommoncmdcnt = 0;
1451         rtl8723_phy_set_sw_chnl_cmdarray(precommoncmd, precommoncmdcnt++,
1452                                          MAX_PRECMD_CNT,
1453                                          CMDID_SET_TXPOWEROWER_LEVEL,
1454                                          0, 0, 0);
1455         rtl8723_phy_set_sw_chnl_cmdarray(precommoncmd, precommoncmdcnt++,
1456                                          MAX_PRECMD_CNT, CMDID_END, 0, 0, 0);
1457
1458         postcommoncmdcnt = 0;
1459
1460         rtl8723_phy_set_sw_chnl_cmdarray(postcommoncmd, postcommoncmdcnt++,
1461                                          MAX_POSTCMD_CNT, CMDID_END,
1462                                             0, 0, 0);
1463
1464         rfdependcmdcnt = 0;
1465
1466         RT_ASSERT((channel >= 1 && channel <= 14),
1467                   "illegal channel for Zebra: %d\n", channel);
1468
1469         rtl8723_phy_set_sw_chnl_cmdarray(rfdependcmd, rfdependcmdcnt++,
1470                                          MAX_RFDEPENDCMD_CNT,
1471                                          CMDID_RF_WRITEREG,
1472                                          RF_CHNLBW, channel, 10);
1473
1474         rtl8723_phy_set_sw_chnl_cmdarray(rfdependcmd, rfdependcmdcnt++,
1475                                          MAX_RFDEPENDCMD_CNT,
1476                                             CMDID_END, 0, 0, 0);
1477
1478         do {
1479                 switch (*stage) {
1480                 case 0:
1481                         currentcmd = &precommoncmd[*step];
1482                         break;
1483                 case 1:
1484                         currentcmd = &rfdependcmd[*step];
1485                         break;
1486                 case 2:
1487                         currentcmd = &postcommoncmd[*step];
1488                         break;
1489                 default:
1490                         RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1491                                  "Invalid 'stage' = %d, Check it!\n", *stage);
1492                         return true;
1493                 }
1494
1495                 if (currentcmd->cmdid == CMDID_END) {
1496                         if ((*stage) == 2) {
1497                                 return true;
1498                         } else {
1499                                 (*stage)++;
1500                                 (*step) = 0;
1501                                 continue;
1502                         }
1503                 }
1504
1505                 switch (currentcmd->cmdid) {
1506                 case CMDID_SET_TXPOWEROWER_LEVEL:
1507                         rtl8723be_phy_set_txpower_level(hw, channel);
1508                         break;
1509                 case CMDID_WRITEPORT_ULONG:
1510                         rtl_write_dword(rtlpriv, currentcmd->para1,
1511                                         currentcmd->para2);
1512                         break;
1513                 case CMDID_WRITEPORT_USHORT:
1514                         rtl_write_word(rtlpriv, currentcmd->para1,
1515                                        (u16)currentcmd->para2);
1516                         break;
1517                 case CMDID_WRITEPORT_UCHAR:
1518                         rtl_write_byte(rtlpriv, currentcmd->para1,
1519                                        (u8)currentcmd->para2);
1520                         break;
1521                 case CMDID_RF_WRITEREG:
1522                         for (rfpath = 0; rfpath < num_total_rfpath; rfpath++) {
1523                                 rtlphy->rfreg_chnlval[rfpath] =
1524                                     ((rtlphy->rfreg_chnlval[rfpath] &
1525                                       0xfffffc00) | currentcmd->para2);
1526
1527                                 rtl_set_rfreg(hw, (enum radio_path)rfpath,
1528                                               currentcmd->para1,
1529                                               RFREG_OFFSET_MASK,
1530                                               rtlphy->rfreg_chnlval[rfpath]);
1531                         }
1532                         break;
1533                 default:
1534                         RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
1535                                  "switch case not process\n");
1536                         break;
1537                 }
1538
1539                 break;
1540         } while (true);
1541
1542         (*delay) = currentcmd->msdelay;
1543         (*step)++;
1544         return false;
1545 }
1546
1547 static u8 _rtl8723be_phy_path_a_iqk(struct ieee80211_hw *hw)
1548 {
1549         u32 reg_eac, reg_e94, reg_e9c, tmp;
1550         u8 result = 0x00;
1551
1552         /* leave IQK mode */
1553         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1554         /* switch to path A */
1555         rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000000);
1556         /* enable path A PA in TXIQK mode */
1557         rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, RFREG_OFFSET_MASK, 0x800a0);
1558         rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x20000);
1559         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0003f);
1560         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xc7f87);
1561
1562         /* 1. TX IQK */
1563         /* path-A IQK setting */
1564         /* IQK setting */
1565         rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1566         rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1567         /* path-A IQK setting */
1568         rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1569         rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1570         rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1571         rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1572
1573         rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x821403ea);
1574         rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28160000);
1575         rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1576         rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1577         /* LO calibration setting */
1578         rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x00462911);
1579         /* enter IQK mode */
1580         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1581
1582         /* One shot, path A LOK & IQK */
1583         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1584         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1585
1586         mdelay(IQK_DELAY_TIME);
1587
1588         /* leave IQK mode */
1589         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1590
1591         /* Check failed */
1592         reg_eac = rtl_get_bbreg(hw, 0xeac, MASKDWORD);
1593         reg_e94 = rtl_get_bbreg(hw, 0xe94, MASKDWORD);
1594         reg_e9c = rtl_get_bbreg(hw, 0xe9c, MASKDWORD);
1595
1596         if (!(reg_eac & BIT(28)) &&
1597             (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1598             (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1599                 result |= 0x01;
1600         else /* if Tx not OK, ignore Rx */
1601                 return result;
1602
1603         /* Allen 20131125 */
1604         tmp = (reg_e9c & 0x03FF0000) >> 16;
1605         if ((tmp & 0x200) > 0)
1606                 tmp = 0x400 - tmp;
1607
1608         if (!(reg_eac & BIT(28)) &&
1609             (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1610             (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1611             (tmp < 0xf))
1612                 result |= 0x01;
1613         else /* if Tx not OK, ignore Rx */
1614                 return result;
1615
1616         return result;
1617 }
1618
1619 /* bit0 = 1 => Tx OK, bit1 = 1 => Rx OK */
1620 static u8 _rtl8723be_phy_path_a_rx_iqk(struct ieee80211_hw *hw)
1621 {
1622         u32 reg_eac, reg_e94, reg_e9c, reg_ea4, u32tmp, tmp;
1623         u8 result = 0x00;
1624
1625         /* leave IQK mode */
1626         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1627
1628         /* switch to path A */
1629         rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000000);
1630
1631         /* 1 Get TXIMR setting */
1632         /* modify RXIQK mode table */
1633         rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x1);
1634         rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1635         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1636         /* LNA2 off, PA on for Dcut */
1637         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7fb7);
1638         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1639
1640         /* IQK setting */
1641         rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1642         rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1643
1644         /* path-A IQK setting */
1645         rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1646         rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1647         rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1648         rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1649
1650         rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82160ff0);
1651         rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28110000);
1652         rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1653         rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1654
1655         /* LO calibration setting */
1656         rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a911);
1657
1658         /* enter IQK mode */
1659         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1660
1661         /* One shot, path A LOK & IQK */
1662         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1663         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1664
1665         mdelay(IQK_DELAY_TIME);
1666
1667         /* leave IQK mode */
1668         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1669
1670         /* Check failed */
1671         reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1672         reg_e94 = rtl_get_bbreg(hw, RTX_POWER_BEFORE_IQK_A, MASKDWORD);
1673         reg_e9c = rtl_get_bbreg(hw, RTX_POWER_AFTER_IQK_A, MASKDWORD);
1674
1675         if (!(reg_eac & BIT(28)) &&
1676             (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1677             (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1678                 result |= 0x01;
1679         else /* if Tx not OK, ignore Rx */
1680                 return result;
1681
1682         /* Allen 20131125 */
1683         tmp = (reg_e9c & 0x03FF0000) >> 16;
1684         if ((tmp & 0x200) > 0)
1685                 tmp = 0x400 - tmp;
1686
1687         if (!(reg_eac & BIT(28)) &&
1688             (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1689             (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1690             (tmp < 0xf))
1691                 result |= 0x01;
1692         else /* if Tx not OK, ignore Rx */
1693                 return result;
1694
1695         u32tmp = 0x80007C00 | (reg_e94 & 0x3FF0000) |
1696                  ((reg_e9c & 0x3FF0000) >> 16);
1697         rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, u32tmp);
1698
1699         /* 1 RX IQK */
1700         /* modify RXIQK mode table */
1701         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1702         rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x1);
1703         rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1704         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1705         /* LAN2 on, PA off for Dcut */
1706         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7d77);
1707
1708         /* PA, PAD setting */
1709         rtl_set_rfreg(hw, RF90_PATH_A, 0xdf, RFREG_OFFSET_MASK, 0xf80);
1710         rtl_set_rfreg(hw, RF90_PATH_A, 0x55, RFREG_OFFSET_MASK, 0x4021f);
1711
1712         /* IQK setting */
1713         rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1714
1715         /* path-A IQK setting */
1716         rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1717         rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1718         rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1719         rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1720
1721         rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82110000);
1722         rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x2816001f);
1723         rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1724         rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1725
1726         /* LO calibration setting */
1727         rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a8d1);
1728
1729         /* enter IQK mode */
1730         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1731
1732         /* One shot, path A LOK & IQK */
1733         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1734         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1735
1736         mdelay(IQK_DELAY_TIME);
1737
1738         /* leave IQK mode */
1739         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1740
1741         /* Check failed */
1742         reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1743         reg_ea4 = rtl_get_bbreg(hw, RRX_POWER_BEFORE_IQK_A_2, MASKDWORD);
1744
1745         /* leave IQK mode */
1746         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1747         rtl_set_rfreg(hw, RF90_PATH_A, 0xdf, RFREG_OFFSET_MASK, 0x780);
1748
1749         /* Allen 20131125 */
1750         tmp = (reg_eac & 0x03FF0000) >> 16;
1751                 if ((tmp & 0x200) > 0)
1752                         tmp = 0x400 - tmp;
1753         /* if Tx is OK, check whether Rx is OK */
1754         if (!(reg_eac & BIT(27)) &&
1755             (((reg_ea4 & 0x03FF0000) >> 16) != 0x132) &&
1756             (((reg_eac & 0x03FF0000) >> 16) != 0x36))
1757                 result |= 0x02;
1758         else if (!(reg_eac & BIT(27)) &&
1759                  (((reg_ea4 & 0x03FF0000) >> 16) < 0x110) &&
1760                  (((reg_ea4 & 0x03FF0000) >> 16) > 0xf0) &&
1761                  (tmp < 0xf))
1762                 result |= 0x02;
1763
1764         return result;
1765 }
1766
1767 static u8 _rtl8723be_phy_path_b_iqk(struct ieee80211_hw *hw)
1768 {
1769         u32 reg_eac, reg_e94, reg_e9c, tmp;
1770         u8 result = 0x00;
1771
1772         /* leave IQK mode */
1773         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1774         /* switch to path B */
1775         rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000280);
1776
1777         /* enable path B PA in TXIQK mode */
1778         rtl_set_rfreg(hw, RF90_PATH_A, 0xed, RFREG_OFFSET_MASK, 0x00020);
1779         rtl_set_rfreg(hw, RF90_PATH_A, 0x43, RFREG_OFFSET_MASK, 0x40fc1);
1780
1781         /* 1 Tx IQK */
1782         /* IQK setting */
1783         rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1784         rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1785         /* path-A IQK setting */
1786         rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1787         rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1788         rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1789         rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1790
1791         rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x821403ea);
1792         rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28110000);
1793         rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1794         rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1795
1796         /* LO calibration setting */
1797         rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x00462911);
1798
1799         /* enter IQK mode */
1800         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1801
1802         /* One shot, path B LOK & IQK */
1803         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1804         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1805
1806         mdelay(IQK_DELAY_TIME);
1807
1808         /* leave IQK mode */
1809         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1810
1811         /* Check failed */
1812         reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1813         reg_e94 = rtl_get_bbreg(hw, RTX_POWER_BEFORE_IQK_A, MASKDWORD);
1814         reg_e9c = rtl_get_bbreg(hw, RTX_POWER_AFTER_IQK_A, MASKDWORD);
1815
1816         if (!(reg_eac & BIT(28)) &&
1817             (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1818             (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1819                 result |= 0x01;
1820         else
1821                 return result;
1822
1823         /* Allen 20131125 */
1824         tmp = (reg_e9c & 0x03FF0000) >> 16;
1825         if ((tmp & 0x200) > 0)
1826                 tmp = 0x400 - tmp;
1827
1828         if (!(reg_eac & BIT(28)) &&
1829             (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1830             (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1831             (tmp < 0xf))
1832                 result |= 0x01;
1833         else
1834                 return result;
1835
1836         return result;
1837 }
1838
1839 /* bit0 = 1 => Tx OK, bit1 = 1 => Rx OK */
1840 static u8 _rtl8723be_phy_path_b_rx_iqk(struct ieee80211_hw *hw)
1841 {
1842         u32 reg_e94, reg_e9c, reg_ea4, reg_eac, u32tmp, tmp;
1843         u8 result = 0x00;
1844
1845         /* leave IQK mode */
1846         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1847         /* switch to path B */
1848         rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000280);
1849
1850         /* 1 Get TXIMR setting */
1851         /* modify RXIQK mode table */
1852         rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, RFREG_OFFSET_MASK, 0x800a0);
1853         rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1854         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1855         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7ff7);
1856
1857         /* open PA S1 & SMIXER */
1858         rtl_set_rfreg(hw, RF90_PATH_A, 0xed, RFREG_OFFSET_MASK, 0x00020);
1859         rtl_set_rfreg(hw, RF90_PATH_A, 0x43, RFREG_OFFSET_MASK, 0x60fed);
1860
1861         /* IQK setting */
1862         rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1863         rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1864
1865         /* path-B IQK setting */
1866         rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1867         rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1868         rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1869         rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1870
1871         rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82160ff0);
1872         rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28110000);
1873         rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1874         rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1875
1876         /* LO calibration setting */
1877         rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a911);
1878         /* enter IQK mode */
1879         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1880
1881         /* One shot, path B TXIQK @ RXIQK */
1882         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1883         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1884
1885         mdelay(IQK_DELAY_TIME);
1886
1887         /* leave IQK mode */
1888         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1889         /* Check failed */
1890         reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1891         reg_e94 = rtl_get_bbreg(hw, RTX_POWER_BEFORE_IQK_A, MASKDWORD);
1892         reg_e9c = rtl_get_bbreg(hw, RTX_POWER_AFTER_IQK_A, MASKDWORD);
1893
1894         if (!(reg_eac & BIT(28)) &&
1895             (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1896             (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1897                 result |= 0x01;
1898         else    /* if Tx not OK, ignore Rx */
1899                 return result;
1900
1901         /* Allen 20131125 */
1902         tmp = (reg_e9c & 0x03FF0000) >> 16;
1903         if ((tmp & 0x200) > 0)
1904                 tmp = 0x400 - tmp;
1905
1906         if (!(reg_eac & BIT(28)) &&
1907             (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1908             (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1909             (tmp < 0xf))
1910                 result |= 0x01;
1911         else
1912                 return result;
1913
1914         u32tmp = 0x80007C00 | (reg_e94 & 0x3FF0000)  |
1915                  ((reg_e9c & 0x3FF0000) >> 16);
1916         rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, u32tmp);
1917
1918         /* 1 RX IQK */
1919
1920         /* <20121009, Kordan> RF Mode = 3 */
1921         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1922         rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x1);
1923         rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1924         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1925         rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7d77);
1926         rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x0);
1927
1928         /* open PA S1 & close SMIXER */
1929         rtl_set_rfreg(hw, RF90_PATH_A, 0xed, RFREG_OFFSET_MASK, 0x00020);
1930         rtl_set_rfreg(hw, RF90_PATH_A, 0x43, RFREG_OFFSET_MASK, 0x60fbd);
1931
1932         /* IQK setting */
1933         rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1934
1935         /* path-B IQK setting */
1936         rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1937         rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1938         rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1939         rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1940
1941         rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82110000);
1942         rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x2816001f);
1943         rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1944         rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1945
1946         /* LO calibration setting */
1947         rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a8d1);
1948         /* enter IQK mode */
1949         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1950
1951         /* One shot, path B LOK & IQK */
1952         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1953         rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1954
1955         mdelay(IQK_DELAY_TIME);
1956
1957         /* leave IQK mode */
1958         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1959         /* Check failed */
1960         reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1961         reg_ea4 = rtl_get_bbreg(hw, RRX_POWER_BEFORE_IQK_A_2, MASKDWORD);
1962
1963         /* Allen 20131125 */
1964         tmp = (reg_eac & 0x03FF0000) >> 16;
1965         if ((tmp & 0x200) > 0)
1966                 tmp = 0x400 - tmp;
1967
1968         /* if Tx is OK, check whether Rx is OK */
1969         if (!(reg_eac & BIT(27)) &&
1970             (((reg_ea4 & 0x03FF0000) >> 16) != 0x132) &&
1971             (((reg_eac & 0x03FF0000) >> 16) != 0x36))
1972                 result |= 0x02;
1973         else if (!(reg_eac & BIT(27)) &&
1974                  (((reg_ea4 & 0x03FF0000) >> 16) < 0x110) &&
1975                  (((reg_ea4 & 0x03FF0000) >> 16) > 0xf0) &&
1976                  (tmp < 0xf))
1977                 result |= 0x02;
1978         else
1979                 return result;
1980
1981         return result;
1982 }
1983
1984 static void _rtl8723be_phy_path_b_fill_iqk_matrix(struct ieee80211_hw *hw,
1985                                                   bool b_iqk_ok,
1986                                                   long result[][8],
1987                                                   u8 final_candidate,
1988                                                   bool btxonly)
1989 {
1990         u32 oldval_1, x, tx1_a, reg;
1991         long y, tx1_c;
1992
1993         if (final_candidate == 0xFF) {
1994                 return;
1995         } else if (b_iqk_ok) {
1996                 oldval_1 = (rtl_get_bbreg(hw, ROFDM0_XBTXIQIMBALANCE,
1997                                           MASKDWORD) >> 22) & 0x3FF;
1998                 x = result[final_candidate][4];
1999                 if ((x & 0x00000200) != 0)
2000                         x = x | 0xFFFFFC00;
2001                 tx1_a = (x * oldval_1) >> 8;
2002                 rtl_set_bbreg(hw, ROFDM0_XBTXIQIMBALANCE, 0x3FF, tx1_a);
2003                 rtl_set_bbreg(hw, ROFDM0_ECCATHRESHOLD, BIT(27),
2004                               ((x * oldval_1 >> 7) & 0x1));
2005                 y = result[final_candidate][5];
2006                 if ((y & 0x00000200) != 0)
2007                         y = y | 0xFFFFFC00;
2008                 tx1_c = (y * oldval_1) >> 8;
2009                 rtl_set_bbreg(hw, ROFDM0_XDTXAFE, 0xF0000000,
2010                               ((tx1_c & 0x3C0) >> 6));
2011                 rtl_set_bbreg(hw, ROFDM0_XBTXIQIMBALANCE, 0x003F0000,
2012                               (tx1_c & 0x3F));
2013                 rtl_set_bbreg(hw, ROFDM0_ECCATHRESHOLD, BIT(25),
2014                               ((y * oldval_1 >> 7) & 0x1));
2015                 if (btxonly)
2016                         return;
2017                 reg = result[final_candidate][6];
2018                 rtl_set_bbreg(hw, ROFDM0_XBRXIQIMBALANCE, 0x3FF, reg);
2019                 reg = result[final_candidate][7] & 0x3F;
2020                 rtl_set_bbreg(hw, ROFDM0_XBRXIQIMBALANCE, 0xFC00, reg);
2021                 reg = (result[final_candidate][7] >> 6) & 0xF;
2022                 /* rtl_set_bbreg(hw, 0xca0, 0xF0000000, reg); */
2023         }
2024 }
2025
2026 static bool _rtl8723be_phy_simularity_compare(struct ieee80211_hw *hw,
2027                                               long result[][8], u8 c1, u8 c2)
2028 {
2029         u32 i, j, diff, simularity_bitmap, bound = 0;
2030
2031         u8 final_candidate[2] = {0xFF, 0xFF}; /* for path A and path B */
2032         bool bresult = true; /* is2t = true*/
2033         s32 tmp1 = 0, tmp2 = 0;
2034
2035         bound = 8;
2036
2037         simularity_bitmap = 0;
2038
2039         for (i = 0; i < bound; i++) {
2040                 if ((i == 1) || (i == 3) || (i == 5) || (i == 7)) {
2041                         if ((result[c1][i] & 0x00000200) != 0)
2042                                 tmp1 = result[c1][i] | 0xFFFFFC00;
2043                         else
2044                                 tmp1 = result[c1][i];
2045
2046                         if ((result[c2][i] & 0x00000200) != 0)
2047                                 tmp2 = result[c2][i] | 0xFFFFFC00;
2048                         else
2049                                 tmp2 = result[c2][i];
2050                 } else {
2051                         tmp1 = result[c1][i];
2052                         tmp2 = result[c2][i];
2053                 }
2054
2055                 diff = (tmp1 > tmp2) ? (tmp1 - tmp2) : (tmp2 - tmp1);
2056
2057                 if (diff > MAX_TOLERANCE) {
2058                         if ((i == 2 || i == 6) && !simularity_bitmap) {
2059                                 if (result[c1][i] + result[c1][i + 1] == 0)
2060                                         final_candidate[(i / 4)] = c2;
2061                                 else if (result[c2][i] + result[c2][i + 1] == 0)
2062                                         final_candidate[(i / 4)] = c1;
2063                                 else
2064                                         simularity_bitmap |= (1 << i);
2065                         } else
2066                                 simularity_bitmap |= (1 << i);
2067                 }
2068         }
2069
2070         if (simularity_bitmap == 0) {
2071                 for (i = 0; i < (bound / 4); i++) {
2072                         if (final_candidate[i] != 0xFF) {
2073                                 for (j = i * 4; j < (i + 1) * 4 - 2; j++)
2074                                         result[3][j] =
2075                                                 result[final_candidate[i]][j];
2076                                 bresult = false;
2077                         }
2078                 }
2079                 return bresult;
2080         } else {
2081                 if (!(simularity_bitmap & 0x03)) { /* path A TX OK */
2082                         for (i = 0; i < 2; i++)
2083                                 result[3][i] = result[c1][i];
2084                 }
2085                 if (!(simularity_bitmap & 0x0c)) { /* path A RX OK */
2086                         for (i = 2; i < 4; i++)
2087                                 result[3][i] = result[c1][i];
2088                 }
2089                 if (!(simularity_bitmap & 0x30)) { /* path B TX OK */
2090                         for (i = 4; i < 6; i++)
2091                                 result[3][i] = result[c1][i];
2092                 }
2093                 if (!(simularity_bitmap & 0xc0)) { /* path B RX OK */
2094                         for (i = 6; i < 8; i++)
2095                                 result[3][i] = result[c1][i];
2096                 }
2097                 return false;
2098         }
2099 }
2100
2101 static void _rtl8723be_phy_iq_calibrate(struct ieee80211_hw *hw,
2102                                         long result[][8], u8 t, bool is2t)
2103 {
2104         struct rtl_priv *rtlpriv = rtl_priv(hw);
2105         struct rtl_phy *rtlphy = &rtlpriv->phy;
2106         u32 i;
2107         u8 patha_ok, pathb_ok;
2108         u32 adda_reg[IQK_ADDA_REG_NUM] = {
2109                 0x85c, 0xe6c, 0xe70, 0xe74,
2110                 0xe78, 0xe7c, 0xe80, 0xe84,
2111                 0xe88, 0xe8c, 0xed0, 0xed4,
2112                 0xed8, 0xedc, 0xee0, 0xeec
2113         };
2114
2115         u32 iqk_mac_reg[IQK_MAC_REG_NUM] = {
2116                 0x522, 0x550, 0x551, 0x040
2117         };
2118         u32 iqk_bb_reg[IQK_BB_REG_NUM] = {
2119                 ROFDM0_TRXPATHENABLE, ROFDM0_TRMUXPAR,
2120                 RFPGA0_XCD_RFINTERFACESW, 0xb68, 0xb6c,
2121                 0x870, 0x860,
2122                 0x864, 0xa04
2123         };
2124         const u32 retrycount = 2;
2125
2126         u32 path_sel_bb;/* path_sel_rf */
2127
2128         u8 tmp_reg_c50, tmp_reg_c58;
2129
2130         tmp_reg_c50 = rtl_get_bbreg(hw, 0xc50, MASKBYTE0);
2131         tmp_reg_c58 = rtl_get_bbreg(hw, 0xc58, MASKBYTE0);
2132
2133         if (t == 0) {
2134                 rtl8723_save_adda_registers(hw, adda_reg,
2135                                             rtlphy->adda_backup, 16);
2136                 rtl8723_phy_save_mac_registers(hw, iqk_mac_reg,
2137                                                rtlphy->iqk_mac_backup);
2138                 rtl8723_save_adda_registers(hw, iqk_bb_reg,
2139                                             rtlphy->iqk_bb_backup,
2140                                             IQK_BB_REG_NUM);
2141         }
2142         rtl8723_phy_path_adda_on(hw, adda_reg, true, is2t);
2143         if (t == 0) {
2144                 rtlphy->rfpi_enable = (u8)rtl_get_bbreg(hw,
2145                                                 RFPGA0_XA_HSSIPARAMETER1,
2146                                                 BIT(8));
2147         }
2148
2149         path_sel_bb = rtl_get_bbreg(hw, 0x948, MASKDWORD);
2150
2151         rtl8723_phy_mac_setting_calibration(hw, iqk_mac_reg,
2152                                             rtlphy->iqk_mac_backup);
2153         /*BB Setting*/
2154         rtl_set_bbreg(hw, 0xa04, 0x0f000000, 0xf);
2155         rtl_set_bbreg(hw, 0xc04, MASKDWORD, 0x03a05600);
2156         rtl_set_bbreg(hw, 0xc08, MASKDWORD, 0x000800e4);
2157         rtl_set_bbreg(hw, 0x874, MASKDWORD, 0x22204000);
2158
2159         /* path A TX IQK */
2160         for (i = 0; i < retrycount; i++) {
2161                 patha_ok = _rtl8723be_phy_path_a_iqk(hw);
2162                 if (patha_ok == 0x01) {
2163                         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2164                                 "Path A Tx IQK Success!!\n");
2165                         result[t][0] = (rtl_get_bbreg(hw, 0xe94, MASKDWORD) &
2166                                         0x3FF0000) >> 16;
2167                         result[t][1] = (rtl_get_bbreg(hw, 0xe9c, MASKDWORD) &
2168                                         0x3FF0000) >> 16;
2169                         break;
2170                 } else {
2171                         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2172                                  "Path A Tx IQK Fail!!\n");
2173                 }
2174         }
2175         /* path A RX IQK */
2176         for (i = 0; i < retrycount; i++) {
2177                 patha_ok = _rtl8723be_phy_path_a_rx_iqk(hw);
2178                 if (patha_ok == 0x03) {
2179                         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2180                                  "Path A Rx IQK Success!!\n");
2181                         result[t][2] = (rtl_get_bbreg(hw, 0xea4, MASKDWORD) &
2182                                         0x3FF0000) >> 16;
2183                         result[t][3] = (rtl_get_bbreg(hw, 0xeac, MASKDWORD) &
2184                                         0x3FF0000) >> 16;
2185                         break;
2186                 }
2187                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2188                          "Path A Rx IQK Fail!!\n");
2189         }
2190
2191         if (0x00 == patha_ok)
2192                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "Path A IQK Fail!!\n");
2193
2194         if (is2t) {
2195                 /* path B TX IQK */
2196                 for (i = 0; i < retrycount; i++) {
2197                         pathb_ok = _rtl8723be_phy_path_b_iqk(hw);
2198                         if (pathb_ok == 0x01) {
2199                                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2200                                          "Path B Tx IQK Success!!\n");
2201                                 result[t][4] = (rtl_get_bbreg(hw, 0xe94,
2202                                                               MASKDWORD) &
2203                                                               0x3FF0000) >> 16;
2204                                 result[t][5] = (rtl_get_bbreg(hw, 0xe9c,
2205                                                               MASKDWORD) &
2206                                                               0x3FF0000) >> 16;
2207                                 break;
2208                         }
2209                         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2210                                  "Path B Tx IQK Fail!!\n");
2211                 }
2212                 /* path B RX IQK */
2213                 for (i = 0; i < retrycount; i++) {
2214                         pathb_ok = _rtl8723be_phy_path_b_rx_iqk(hw);
2215                         if (pathb_ok == 0x03) {
2216                                 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2217                                          "Path B Rx IQK Success!!\n");
2218                                 result[t][6] = (rtl_get_bbreg(hw, 0xea4,
2219                                                               MASKDWORD) &
2220                                                               0x3FF0000) >> 16;
2221                                 result[t][7] = (rtl_get_bbreg(hw, 0xeac,
2222                                                               MASKDWORD) &
2223                                                               0x3FF0000) >> 16;
2224                                 break;
2225                         }
2226                         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2227                                  "Path B Rx IQK Fail!!\n");
2228                 }
2229         }
2230
2231         /* Back to BB mode, load original value */
2232         rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0);
2233
2234         if (t != 0) {
2235                 rtl8723_phy_reload_adda_registers(hw, adda_reg,
2236                                                   rtlphy->adda_backup, 16);
2237                 rtl8723_phy_reload_mac_registers(hw, iqk_mac_reg,
2238                                                  rtlphy->iqk_mac_backup);
2239                 rtl8723_phy_reload_adda_registers(hw, iqk_bb_reg,
2240                                                   rtlphy->iqk_bb_backup,
2241                                                   IQK_BB_REG_NUM);
2242
2243                 rtl_set_bbreg(hw, 0x948, MASKDWORD, path_sel_bb);
2244                 /*rtl_set_rfreg(hw, RF90_PATH_B, 0xb0, 0xfffff, path_sel_rf);*/
2245
2246                 rtl_set_bbreg(hw, 0xc50, MASKBYTE0, 0x50);
2247                 rtl_set_bbreg(hw, 0xc50, MASKBYTE0, tmp_reg_c50);
2248                 if (is2t) {
2249                         rtl_set_bbreg(hw, 0xc58, MASKBYTE0, 0x50);
2250                         rtl_set_bbreg(hw, 0xc58, MASKBYTE0, tmp_reg_c58);
2251                 }
2252                 rtl_set_bbreg(hw, 0xe30, MASKDWORD, 0x01008c00);
2253                 rtl_set_bbreg(hw, 0xe34, MASKDWORD, 0x01008c00);
2254         }
2255         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "8723be IQK Finish!!\n");
2256 }
2257
2258 static u8 _get_right_chnl_place_for_iqk(u8 chnl)
2259 {
2260         u8 channel_all[TARGET_CHNL_NUM_2G_5G] = {
2261                         1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12,
2262                         13, 14, 36, 38, 40, 42, 44, 46,
2263                         48, 50, 52, 54, 56, 58, 60, 62, 64,
2264                         100, 102, 104, 106, 108, 110,
2265                         112, 114, 116, 118, 120, 122,
2266                         124, 126, 128, 130, 132, 134, 136,
2267                         138, 140, 149, 151, 153, 155, 157,
2268                         159, 161, 163, 165};
2269         u8 place = chnl;
2270
2271         if (chnl > 14) {
2272                 for (place = 14; place < sizeof(channel_all); place++) {
2273                         if (channel_all[place] == chnl)
2274                                 return place - 13;
2275                 }
2276         }
2277         return 0;
2278 }
2279
2280 static void _rtl8723be_phy_lc_calibrate(struct ieee80211_hw *hw, bool is2t)
2281 {
2282         u8 tmpreg;
2283         u32 rf_a_mode = 0, rf_b_mode = 0, lc_cal;
2284         struct rtl_priv *rtlpriv = rtl_priv(hw);
2285
2286         tmpreg = rtl_read_byte(rtlpriv, 0xd03);
2287
2288         if ((tmpreg & 0x70) != 0)
2289                 rtl_write_byte(rtlpriv, 0xd03, tmpreg & 0x8F);
2290         else
2291                 rtl_write_byte(rtlpriv, REG_TXPAUSE, 0xFF);
2292
2293         if ((tmpreg & 0x70) != 0) {
2294                 rf_a_mode = rtl_get_rfreg(hw, RF90_PATH_A, 0x00, MASK12BITS);
2295
2296                 if (is2t)
2297                         rf_b_mode = rtl_get_rfreg(hw, RF90_PATH_B, 0x00,
2298                                                   MASK12BITS);
2299
2300                 rtl_set_rfreg(hw, RF90_PATH_A, 0x00, MASK12BITS,
2301                               (rf_a_mode & 0x8FFFF) | 0x10000);
2302
2303                 if (is2t)
2304                         rtl_set_rfreg(hw, RF90_PATH_B, 0x00, MASK12BITS,
2305                                       (rf_b_mode & 0x8FFFF) | 0x10000);
2306         }
2307         lc_cal = rtl_get_rfreg(hw, RF90_PATH_A, 0x18, MASK12BITS);
2308
2309         rtl_set_rfreg(hw, RF90_PATH_A, 0xb0, RFREG_OFFSET_MASK, 0xdfbe0);
2310         rtl_set_rfreg(hw, RF90_PATH_A, 0x18, MASK12BITS, 0x8c0a);
2311
2312         /* In order not to disturb BT music when wifi init.(1ant NIC only) */
2313         /*mdelay(100);*/
2314         /* In order not to disturb BT music when wifi init.(1ant NIC only) */
2315         mdelay(50);
2316
2317         rtl_set_rfreg(hw, RF90_PATH_A, 0xb0, RFREG_OFFSET_MASK, 0xdffe0);
2318
2319         if ((tmpreg & 0x70) != 0) {
2320                 rtl_write_byte(rtlpriv, 0xd03, tmpreg);
2321                 rtl_set_rfreg(hw, RF90_PATH_A, 0x00, MASK12BITS, rf_a_mode);
2322
2323                 if (is2t)
2324                         rtl_set_rfreg(hw, RF90_PATH_B, 0x00,
2325                                       MASK12BITS, rf_b_mode);
2326         } else {
2327                 rtl_write_byte(rtlpriv, REG_TXPAUSE, 0x00);
2328         }
2329 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "\n");
2330
2331 }
2332
2333 static void _rtl8723be_phy_set_rfpath_switch(struct ieee80211_hw *hw,
2334                                              bool bmain, bool is2t)
2335 {
2336         struct rtl_priv *rtlpriv = rtl_priv(hw);
2337         RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "\n");
2338
2339         if (bmain) /* left antenna */
2340                 rtl_set_bbreg(hw, 0x92C, MASKDWORD, 0x1);
2341         else
2342                 rtl_set_bbreg(hw, 0x92C, MASKDWORD, 0x2);
2343 }
2344
2345 #undef IQK_ADDA_REG_NUM
2346 #undef IQK_DELAY_TIME
2347 /* IQK is merge from Merge Temp */
2348 void rtl8723be_phy_iq_calibrate(struct ieee80211_hw *hw, bool b_recovery)
2349 {
2350         struct rtl_priv *rtlpriv = rtl_priv(hw);
2351         struct rtl_phy *rtlphy = &rtlpriv->phy;
2352         long result[4][8];
2353         u8 i, final_candidate, idx;
2354         bool b_patha_ok, b_pathb_ok;
2355         long reg_e94, reg_e9c, reg_ea4, reg_eac, reg_eb4, reg_ebc, reg_ec4;
2356         long reg_ecc, reg_tmp = 0;
2357         bool is12simular, is13simular, is23simular;
2358         u32 iqk_bb_reg[9] = {
2359                 ROFDM0_XARXIQIMBALANCE,
2360                 ROFDM0_XBRXIQIMBALANCE,
2361                 ROFDM0_ECCATHRESHOLD,
2362                 ROFDM0_AGCRSSITABLE,
2363                 ROFDM0_XATXIQIMBALANCE,
2364                 ROFDM0_XBTXIQIMBALANCE,
2365                 ROFDM0_XCTXAFE,
2366                 ROFDM0_XDTXAFE,
2367                 ROFDM0_RXIQEXTANTA
2368         };
2369         u32 path_sel_bb = 0; /* path_sel_rf = 0 */
2370
2371         if (rtlphy->lck_inprogress)
2372                 return;
2373
2374         spin_lock(&rtlpriv->locks.iqk_lock);
2375         rtlphy->lck_inprogress = true;
2376         spin_unlock(&rtlpriv->locks.iqk_lock);
2377
2378         if (b_recovery) {
2379                 rtl8723_phy_reload_adda_registers(hw, iqk_bb_reg,
2380                                                   rtlphy->iqk_bb_backup, 9);
2381                 return;
2382         }
2383         /* Save RF Path */
2384         path_sel_bb = rtl_get_bbreg(hw, 0x948, MASKDWORD);
2385         /* path_sel_rf = rtl_get_rfreg(hw, RF90_PATH_A, 0xb0, 0xfffff); */
2386
2387         for (i = 0; i < 8; i++) {
2388                 result[0][i] = 0;
2389                 result[1][i] = 0;
2390                 result[2][i] = 0;
2391                 result[3][i] = 0;
2392         }
2393         final_candidate = 0xff;
2394         b_patha_ok = false;
2395         b_pathb_ok = false;
2396         is12simular = false;
2397         is23simular = false;
2398         is13simular = false;
2399         for (i = 0; i < 3; i++) {
2400                 _rtl8723be_phy_iq_calibrate(hw, result, i, true);
2401                 if (i == 1) {
2402                         is12simular = _rtl8723be_phy_simularity_compare(hw,
2403                                                                         result,
2404                                                                         0, 1);
2405                         if (is12simular) {
2406                                 final_candidate = 0;
2407                                 break;
2408                         }
2409                 }
2410                 if (i == 2) {
2411                         is13simular = _rtl8723be_phy_simularity_compare(hw,
2412                                                                         result,
2413                                                                         0, 2);
2414                         if (is13simular) {
2415                                 final_candidate = 0;
2416                                 break;
2417                         }
2418                         is23simular = _rtl8723be_phy_simularity_compare(hw,
2419                                                                         result,
2420                                                                         1, 2);
2421                         if (is23simular) {
2422                                 final_candidate = 1;
2423                         } else {
2424                                 for (i = 0; i < 8; i++)
2425                                         reg_tmp += result[3][i];
2426
2427                                 if (reg_tmp != 0)
2428                                         final_candidate = 3;
2429                                 else
2430                                         final_candidate = 0xFF;
2431                         }
2432                 }
2433         }
2434         for (i = 0; i < 4; i++) {
2435                 reg_e94 = result[i][0];
2436                 reg_e9c = result[i][1];
2437                 reg_ea4 = result[i][2];
2438                 reg_eac = result[i][3];
2439                 reg_eb4 = result[i][4];
2440                 reg_ebc = result[i][5];
2441                 reg_ec4 = result[i][6];
2442                 reg_ecc = result[i][7];
2443         }
2444         if (final_candidate != 0xff) {
2445                 reg_e94 = result[final_candidate][0];
2446                 rtlphy->reg_e94 = reg_e94;
2447                 reg_e9c = result[final_candidate][1];
2448                 rtlphy->reg_e9c = reg_e9c;
2449                 reg_ea4 = result[final_candidate][2];
2450                 reg_eac = result[final_candidate][3];
2451                 reg_eb4 = result[final_candidate][4];
2452                 rtlphy->reg_eb4 = reg_eb4;
2453                 reg_ebc = result[final_candidate][5];
2454                 rtlphy->reg_ebc = reg_ebc;
2455                 reg_ec4 = result[final_candidate][6];
2456                 reg_ecc = result[final_candidate][7];
2457                 b_patha_ok = true;
2458                 b_pathb_ok = true;
2459         } else {
2460                 rtlphy->reg_e94 = 0x100;
2461                 rtlphy->reg_eb4 = 0x100;
2462                 rtlphy->reg_e9c = 0x0;
2463                 rtlphy->reg_ebc = 0x0;
2464         }
2465         if (reg_e94 != 0)
2466                 rtl8723_phy_path_a_fill_iqk_matrix(hw, b_patha_ok, result,
2467                                                    final_candidate,
2468                                                    (reg_ea4 == 0));
2469         if (reg_eb4 != 0)
2470                 _rtl8723be_phy_path_b_fill_iqk_matrix(hw, b_pathb_ok, result,
2471                                                       final_candidate,
2472                                                       (reg_ec4 == 0));
2473
2474         idx = _get_right_chnl_place_for_iqk(rtlphy->current_channel);
2475
2476         if (final_candidate < 4) {
2477                 for (i = 0; i < IQK_MATRIX_REG_NUM; i++)
2478                         rtlphy->iqk_matrix[idx].value[0][i] =
2479                                                 result[final_candidate][i];
2480                 rtlphy->iqk_matrix[idx].iqk_done = true;
2481
2482         }
2483         rtl8723_save_adda_registers(hw, iqk_bb_reg,
2484                                     rtlphy->iqk_bb_backup, 9);
2485
2486         rtl_set_bbreg(hw, 0x948, MASKDWORD, path_sel_bb);
2487         /* rtl_set_rfreg(hw, RF90_PATH_A, 0xb0, 0xfffff, path_sel_rf); */
2488
2489         spin_lock(&rtlpriv->locks.iqk_lock);
2490         rtlphy->lck_inprogress = false;
2491         spin_unlock(&rtlpriv->locks.iqk_lock);
2492 }
2493
2494 void rtl8723be_phy_lc_calibrate(struct ieee80211_hw *hw)
2495 {
2496         struct rtl_priv *rtlpriv = rtl_priv(hw);
2497         struct rtl_phy *rtlphy = &rtlpriv->phy;
2498         struct rtl_hal *rtlhal = &rtlpriv->rtlhal;
2499         u32 timeout = 2000, timecount = 0;
2500
2501         while (rtlpriv->mac80211.act_scanning && timecount < timeout) {
2502                 udelay(50);
2503                 timecount += 50;
2504         }
2505
2506         rtlphy->lck_inprogress = true;
2507         RTPRINT(rtlpriv, FINIT, INIT_IQK,
2508                 "LCK:Start!!! currentband %x delay %d ms\n",
2509                  rtlhal->current_bandtype, timecount);
2510
2511         _rtl8723be_phy_lc_calibrate(hw, false);
2512
2513         rtlphy->lck_inprogress = false;
2514 }
2515
2516 void rtl8723be_phy_set_rfpath_switch(struct ieee80211_hw *hw, bool bmain)
2517 {
2518         _rtl8723be_phy_set_rfpath_switch(hw, bmain, true);
2519 }
2520
2521 bool rtl8723be_phy_set_io_cmd(struct ieee80211_hw *hw, enum io_type iotype)
2522 {
2523         struct rtl_priv *rtlpriv = rtl_priv(hw);
2524         struct rtl_phy *rtlphy = &rtlpriv->phy;
2525         bool b_postprocessing = false;
2526
2527         RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2528                  "-->IO Cmd(%#x), set_io_inprogress(%d)\n",
2529                   iotype, rtlphy->set_io_inprogress);
2530         do {
2531                 switch (iotype) {
2532                 case IO_CMD_RESUME_DM_BY_SCAN:
2533                         RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2534                                  "[IO CMD] Resume DM after scan.\n");
2535                         b_postprocessing = true;
2536                         break;
2537                 case IO_CMD_PAUSE_BAND0_DM_BY_SCAN:
2538                         RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2539                                  "[IO CMD] Pause DM before scan.\n");
2540                         b_postprocessing = true;
2541                         break;
2542                 default:
2543                         RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
2544                                  "switch case not process\n");
2545                         break;
2546                 }
2547         } while (false);
2548         if (b_postprocessing && !rtlphy->set_io_inprogress) {
2549                 rtlphy->set_io_inprogress = true;
2550                 rtlphy->current_io_type = iotype;
2551         } else {
2552                 return false;
2553         }
2554         rtl8723be_phy_set_io(hw);
2555         RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE, "IO Type(%#x)\n", iotype);
2556         return true;
2557 }
2558
2559 static void rtl8723be_phy_set_io(struct ieee80211_hw *hw)
2560 {
2561         struct rtl_priv *rtlpriv = rtl_priv(hw);
2562         struct dig_t *dm_digtable = &rtlpriv->dm_digtable;
2563         struct rtl_phy *rtlphy = &rtlpriv->phy;
2564
2565         RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2566                  "--->Cmd(%#x), set_io_inprogress(%d)\n",
2567                   rtlphy->current_io_type, rtlphy->set_io_inprogress);
2568         switch (rtlphy->current_io_type) {
2569         case IO_CMD_RESUME_DM_BY_SCAN:
2570                 dm_digtable->cur_igvalue = rtlphy->initgain_backup.xaagccore1;
2571                 /*rtl92c_dm_write_dig(hw);*/
2572                 rtl8723be_phy_set_txpower_level(hw, rtlphy->current_channel);
2573                 rtl_set_bbreg(hw, RCCK0_CCA, 0xff0000, 0x83);
2574                 break;
2575         case IO_CMD_PAUSE_BAND0_DM_BY_SCAN:
2576                 rtlphy->initgain_backup.xaagccore1 = dm_digtable->cur_igvalue;
2577                 dm_digtable->cur_igvalue = 0x17;
2578                 rtl_set_bbreg(hw, RCCK0_CCA, 0xff0000, 0x40);
2579                 break;
2580         default:
2581                 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
2582                          "switch case not process\n");
2583                 break;
2584         }
2585         rtlphy->set_io_inprogress = false;
2586         RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2587                  "(%#x)\n", rtlphy->current_io_type);
2588 }
2589
2590 static void rtl8723be_phy_set_rf_on(struct ieee80211_hw *hw)
2591 {
2592         struct rtl_priv *rtlpriv = rtl_priv(hw);
2593
2594         rtl_write_byte(rtlpriv, REG_SPS0_CTRL, 0x2b);
2595         rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE3);
2596         rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE2);
2597         rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE3);
2598         rtl_write_byte(rtlpriv, REG_TXPAUSE, 0x00);
2599 }
2600
2601 static void _rtl8723be_phy_set_rf_sleep(struct ieee80211_hw *hw)
2602 {
2603         struct rtl_priv *rtlpriv = rtl_priv(hw);
2604
2605         rtl_write_byte(rtlpriv, REG_TXPAUSE, 0xFF);
2606         rtl_set_rfreg(hw, RF90_PATH_A, 0x00, RFREG_OFFSET_MASK, 0x00);
2607         rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE2);
2608         rtl_write_byte(rtlpriv, REG_SPS0_CTRL, 0x22);
2609 }
2610
2611 static bool _rtl8723be_phy_set_rf_power_state(struct ieee80211_hw *hw,
2612                                               enum rf_pwrstate rfpwr_state)
2613 {
2614         struct rtl_priv *rtlpriv = rtl_priv(hw);
2615         struct rtl_pci_priv *pcipriv = rtl_pcipriv(hw);
2616         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
2617         struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
2618         bool bresult = true;
2619         u8 i, queue_id;
2620         struct rtl8192_tx_ring *ring = NULL;
2621
2622         switch (rfpwr_state) {
2623         case ERFON:
2624                 if ((ppsc->rfpwr_state == ERFOFF) &&
2625                      RT_IN_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_HALT_NIC)) {
2626                         bool rtstatus;
2627                         u32 initializecount = 0;
2628                         do {
2629                                 initializecount++;
2630                                 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2631                                          "IPS Set eRf nic enable\n");
2632                                 rtstatus = rtl_ps_enable_nic(hw);
2633                         } while (!rtstatus && (initializecount < 10));
2634                                 RT_CLEAR_PS_LEVEL(ppsc,
2635                                                   RT_RF_OFF_LEVL_HALT_NIC);
2636                 } else {
2637                         RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2638                                  "Set ERFON sleeped:%d ms\n",
2639                                   jiffies_to_msecs(jiffies -
2640                                                    ppsc->last_sleep_jiffies));
2641                         ppsc->last_awake_jiffies = jiffies;
2642                         rtl8723be_phy_set_rf_on(hw);
2643                 }
2644                 if (mac->link_state == MAC80211_LINKED)
2645                         rtlpriv->cfg->ops->led_control(hw, LED_CTL_LINK);
2646                 else
2647                         rtlpriv->cfg->ops->led_control(hw, LED_CTL_NO_LINK);
2648
2649                 break;
2650
2651         case ERFOFF:
2652                 for (queue_id = 0, i = 0;
2653                      queue_id < RTL_PCI_MAX_TX_QUEUE_COUNT;) {
2654                         ring = &pcipriv->dev.tx_ring[queue_id];
2655                         /* Don't check BEACON Q.
2656                          * BEACON Q is always not empty,
2657                          * because '_rtl8723be_cmd_send_packet'
2658                          */
2659                         if (queue_id == BEACON_QUEUE ||
2660                             skb_queue_len(&ring->queue) == 0) {
2661                                 queue_id++;
2662                                 continue;
2663                         } else {
2664                                 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2665                                          "eRf Off/Sleep: %d times TcbBusyQueue[%d] =%d before doze!\n",
2666                                          (i + 1), queue_id,
2667                                          skb_queue_len(&ring->queue));
2668
2669                                 udelay(10);
2670                                 i++;
2671                         }
2672                         if (i >= MAX_DOZE_WAITING_TIMES_9x) {
2673                                 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2674                                          "ERFSLEEP: %d times TcbBusyQueue[%d] = %d !\n",
2675                                           MAX_DOZE_WAITING_TIMES_9x,
2676                                           queue_id,
2677                                           skb_queue_len(&ring->queue));
2678                                 break;
2679                         }
2680                 }
2681
2682                 if (ppsc->reg_rfps_level & RT_RF_OFF_LEVL_HALT_NIC) {
2683                         RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2684                                  "IPS Set eRf nic disable\n");
2685                         rtl_ps_disable_nic(hw);
2686                         RT_SET_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_HALT_NIC);
2687                 } else {
2688                         if (ppsc->rfoff_reason == RF_CHANGE_BY_IPS) {
2689                                 rtlpriv->cfg->ops->led_control(hw,
2690                                                                LED_CTL_NO_LINK);
2691                         } else {
2692                                 rtlpriv->cfg->ops->led_control(hw,
2693                                                              LED_CTL_POWER_OFF);
2694                         }
2695                 }
2696                 break;
2697
2698         case ERFSLEEP:
2699                 if (ppsc->rfpwr_state == ERFOFF)
2700                         break;
2701                 for (queue_id = 0, i = 0;
2702                      queue_id < RTL_PCI_MAX_TX_QUEUE_COUNT;) {
2703                         ring = &pcipriv->dev.tx_ring[queue_id];
2704                         if (skb_queue_len(&ring->queue) == 0) {
2705                                 queue_id++;
2706                                 continue;
2707                         } else {
2708                                 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2709                                          "eRf Off/Sleep: %d times TcbBusyQueue[%d] =%d before doze!\n",
2710                                          (i + 1), queue_id,
2711                                          skb_queue_len(&ring->queue));
2712
2713                                 udelay(10);
2714                                 i++;
2715                         }
2716                         if (i >= MAX_DOZE_WAITING_TIMES_9x) {
2717                                 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2718                                          "ERFSLEEP: %d times TcbBusyQueue[%d] = %d !\n",
2719                                          MAX_DOZE_WAITING_TIMES_9x,
2720                                          queue_id,
2721                                          skb_queue_len(&ring->queue));
2722                                 break;
2723                         }
2724                 }
2725                 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2726                          "Set ERFSLEEP awaked:%d ms\n",
2727                           jiffies_to_msecs(jiffies -
2728                                            ppsc->last_awake_jiffies));
2729                 ppsc->last_sleep_jiffies = jiffies;
2730                 _rtl8723be_phy_set_rf_sleep(hw);
2731                 break;
2732
2733         default:
2734                 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
2735                          "switch case not process\n");
2736                 bresult = false;
2737                 break;
2738         }
2739         if (bresult)
2740                 ppsc->rfpwr_state = rfpwr_state;
2741         return bresult;
2742 }
2743
2744 bool rtl8723be_phy_set_rf_power_state(struct ieee80211_hw *hw,
2745                                       enum rf_pwrstate rfpwr_state)
2746 {
2747         struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
2748
2749         bool bresult = false;
2750
2751         if (rfpwr_state == ppsc->rfpwr_state)
2752                 return bresult;
2753         bresult = _rtl8723be_phy_set_rf_power_state(hw, rfpwr_state);
2754         return bresult;
2755 }