1 /******************************************************************************
3 * Copyright(c) 2009-2014 Realtek Corporation.
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.
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
14 * The full GNU General Public License is included in this distribution in the
15 * file called LICENSE.
17 * Contact Information:
18 * wlanfae <wlanfae@realtek.com>
19 * Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
20 * Hsinchu 300, Taiwan.
22 * Larry Finger <Larry.Finger@lwfinger.net>
24 *****************************************************************************/
32 #include "../rtl8723com/phy_common.h"
35 #include "../rtl8723com/dm_common.h"
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,
43 static bool _rtl8723be_phy_config_bb_with_pgheaderfile(struct ieee80211_hw *hw,
45 static bool _rtl8723be_phy_sw_chnl_step_by_step(struct ieee80211_hw *hw,
46 u8 channel, u8 *stage,
47 u8 *step, u32 *delay);
49 static void rtl8723be_phy_set_rf_on(struct ieee80211_hw *hw);
50 static void rtl8723be_phy_set_io(struct ieee80211_hw *hw);
52 u32 rtl8723be_phy_query_rf_reg(struct ieee80211_hw *hw, enum radio_path rfpath,
53 u32 regaddr, u32 bitmask)
55 struct rtl_priv *rtlpriv = rtl_priv(hw);
56 u32 original_value, readback_value, bitshift;
59 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
60 "regaddr(%#x), rfpath(%#x), bitmask(%#x)\n",
61 regaddr, rfpath, bitmask);
63 spin_lock_irqsave(&rtlpriv->locks.rf_lock, flags);
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;
69 spin_unlock_irqrestore(&rtlpriv->locks.rf_lock, flags);
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);
75 return readback_value;
78 void rtl8723be_phy_set_rf_reg(struct ieee80211_hw *hw, enum radio_path path,
79 u32 regaddr, u32 bitmask, u32 data)
81 struct rtl_priv *rtlpriv = rtl_priv(hw);
82 u32 original_value, bitshift;
85 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
86 "regaddr(%#x), bitmask(%#x), data(%#x), rfpath(%#x)\n",
87 regaddr, bitmask, data, path);
89 spin_lock_irqsave(&rtlpriv->locks.rf_lock, flags);
91 if (bitmask != RFREG_OFFSET_MASK) {
92 original_value = rtl8723_phy_rf_serial_read(hw, path,
94 bitshift = rtl8723_phy_calculate_bit_shift(bitmask);
95 data = ((original_value & (~bitmask)) |
99 rtl8723_phy_rf_serial_write(hw, path, regaddr, data);
101 spin_unlock_irqrestore(&rtlpriv->locks.rf_lock, flags);
103 RT_TRACE(rtlpriv, COMP_RF, DBG_TRACE,
104 "regaddr(%#x), bitmask(%#x), data(%#x), rfpath(%#x)\n",
105 regaddr, bitmask, data, path);
109 bool rtl8723be_phy_mac_config(struct ieee80211_hw *hw)
111 struct rtl_priv *rtlpriv = rtl_priv(hw);
112 bool rtstatus = _rtl8723be_phy_config_mac_with_headerfile(hw);
114 rtl_write_byte(rtlpriv, 0x04CA, 0x0B);
118 bool rtl8723be_phy_bb_config(struct ieee80211_hw *hw)
120 bool rtstatus = true;
121 struct rtl_priv *rtlpriv = rtl_priv(hw);
123 u8 b_reg_hwparafile = 1;
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));
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));
138 rtl_write_byte(rtlpriv, REG_AFE_XTAL_CTRL + 1, 0x80);
140 if (b_reg_hwparafile == 1)
141 rtstatus = _rtl8723be_phy_bb8723b_config_parafile(hw);
143 crystalcap = crystalcap & 0x3F;
144 rtl_set_bbreg(hw, REG_MAC_PHY_CTRL, 0xFFF000,
145 (crystalcap | crystalcap << 6));
150 bool rtl8723be_phy_rf_config(struct ieee80211_hw *hw)
152 return rtl8723be_phy_rf6052_config(hw);
155 static bool _rtl8723be_check_condition(struct ieee80211_hw *hw,
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;
165 if (condition == 0xCDCDCDCD)
168 cond = condition & 0xFF;
169 if ((_board & cond) == 0 && cond != 0x1F)
172 cond = condition & 0xFF00;
174 if ((_interface & cond) == 0 && cond != 0x07)
177 cond = condition & 0xFF0000;
179 if ((_platform & cond) == 0 && cond != 0x0F)
184 static void _rtl8723be_config_rf_reg(struct ieee80211_hw *hw, u32 addr,
185 u32 data, enum radio_path rfpath,
188 if (addr == 0xfe || addr == 0xffe) {
189 /* In order not to disturb BT music
190 * when wifi init.(1ant NIC only)
194 rtl_set_rfreg(hw, rfpath, regaddr, RFREG_OFFSET_MASK, data);
198 static void _rtl8723be_config_rf_radio_a(struct ieee80211_hw *hw,
201 u32 content = 0x1000; /*RF Content: radio_a_txt*/
202 u32 maskforphyset = (u32)(content & 0xE000);
204 _rtl8723be_config_rf_reg(hw, addr, data, RF90_PATH_A,
205 addr | maskforphyset);
209 static void _rtl8723be_phy_init_tx_power_by_rate(struct ieee80211_hw *hw)
211 struct rtl_priv *rtlpriv = rtl_priv(hw);
212 struct rtl_phy *rtlphy = &rtlpriv->phy;
214 u8 band, path, txnum, section;
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)
220 section < TX_PWR_BY_RATE_NUM_SECTION;
222 rtlphy->tx_power_by_rate_offset
223 [band][path][txnum][section] = 0;
226 static void _rtl8723be_config_bb_reg(struct ieee80211_hw *hw,
231 } else if (addr == 0xfd) {
233 } else if (addr == 0xfc) {
235 } else if (addr == 0xfb) {
237 } else if (addr == 0xfa) {
239 } else if (addr == 0xf9) {
242 rtl_set_bbreg(hw, addr, MASKDWORD, data);
247 static void _rtl8723be_phy_set_txpower_by_rate_base(struct ieee80211_hw *hw,
249 u8 path, u8 rate_section,
252 struct rtl_priv *rtlpriv = rtl_priv(hw);
253 struct rtl_phy *rtlphy = &rtlpriv->phy;
255 if (path > RF90_PATH_D) {
256 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
257 "Invalid Rf Path %d in phy_SetTxPowerByRatBase()\n",
262 if (band == BAND_ON_2_4G) {
263 switch (rate_section) {
265 rtlphy->txpwr_by_rate_base_24g[path][txnum][0] = value;
268 rtlphy->txpwr_by_rate_base_24g[path][txnum][1] = value;
271 rtlphy->txpwr_by_rate_base_24g[path][txnum][2] = value;
274 rtlphy->txpwr_by_rate_base_24g[path][txnum][3] = value;
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);
283 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
284 "Invalid Band %d in PHY_SetTxPowerByRateBase()\n",
290 static u8 _rtl8723be_phy_get_txpower_by_rate_base(struct ieee80211_hw *hw,
291 u8 band, u8 path, u8 txnum,
294 struct rtl_priv *rtlpriv = rtl_priv(hw);
295 struct rtl_phy *rtlphy = &rtlpriv->phy;
297 if (path > RF90_PATH_D) {
298 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
299 "Invalid Rf Path %d in PHY_GetTxPowerByRateBase()\n",
304 if (band == BAND_ON_2_4G) {
305 switch (rate_section) {
307 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][0];
310 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][1];
313 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][2];
316 value = rtlphy->txpwr_by_rate_base_24g[path][txnum][3];
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);
325 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
326 "Invalid Band %d in PHY_GetTxPowerByRateBase()\n",
333 static void _rtl8723be_phy_store_txpower_by_rate_base(struct ieee80211_hw *hw)
335 struct rtl_priv *rtlpriv = rtl_priv(hw);
336 struct rtl_phy *rtlphy = &rtlpriv->phy;
338 u8 base = 0, path = 0;
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,
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,
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,
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,
379 static void _phy_convert_txpower_dbm_to_relative_value(u32 *data, u8 start,
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;
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;
397 temp_value = (u8)(*data >> (i * 8)) & 0xFF;
400 temp_data |= temp_value;
405 static void _rtl8723be_phy_convert_txpower_dbm_to_relative_value(
406 struct ieee80211_hw *hw)
408 struct rtl_priv *rtlpriv = rtl_priv(hw);
409 struct rtl_phy *rtlphy = &rtlpriv->phy;
410 u8 base = 0, rfpath = RF90_PATH_A;
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],
417 _phy_convert_txpower_dbm_to_relative_value(
418 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][3],
421 base = _rtl8723be_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G, rfpath,
423 _phy_convert_txpower_dbm_to_relative_value(
424 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][0],
426 _phy_convert_txpower_dbm_to_relative_value(
427 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][1],
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],
435 _phy_convert_txpower_dbm_to_relative_value(
436 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_1TX][5],
439 base = _rtl8723be_phy_get_txpower_by_rate_base(hw, BAND_ON_2_4G,
442 _phy_convert_txpower_dbm_to_relative_value(
443 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][6],
446 _phy_convert_txpower_dbm_to_relative_value(
447 &rtlphy->tx_power_by_rate_offset[BAND_ON_2_4G][rfpath][RF_2TX][7],
450 RT_TRACE(rtlpriv, COMP_POWER, DBG_TRACE,
451 "<===_rtl8723be_phy_convert_txpower_dbm_to_relative_value()\n");
454 static void phy_txpower_by_rate_config(struct ieee80211_hw *hw)
456 _rtl8723be_phy_store_txpower_by_rate_base(hw);
457 _rtl8723be_phy_convert_txpower_dbm_to_relative_value(hw);
460 static bool _rtl8723be_phy_bb8723b_config_parafile(struct ieee80211_hw *hw)
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));
467 rtstatus = _rtl8723be_phy_config_bb_with_headerfile(hw,
468 BASEBAND_CONFIG_PHY_REG);
470 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG, "Write BB Reg Fail!!\n");
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);
479 phy_txpower_by_rate_config(hw);
481 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG, "BB_PG Reg Fail!!\n");
484 rtstatus = _rtl8723be_phy_config_bb_with_headerfile(hw,
485 BASEBAND_CONFIG_AGC_TAB);
487 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG, "AGC Table Fail\n");
490 rtlphy->cck_high_power = (bool)(rtl_get_bbreg(hw,
491 RFPGA0_XA_HSSIPARAMETER2,
496 static bool _rtl8723be_phy_config_mac_with_headerfile(struct ieee80211_hw *hw)
498 struct rtl_priv *rtlpriv = rtl_priv(hw);
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]);
513 static bool _rtl8723be_phy_config_bb_with_headerfile(struct ieee80211_hw *hw,
516 #define READ_NEXT_PAIR(v1, v2, i) \
519 v1 = array_table[i];\
520 v2 = array_table[i+1]; \
526 struct rtl_priv *rtlpriv = rtl_priv(hw);
529 if (configtype == BASEBAND_CONFIG_PHY_REG) {
530 arraylen = RTL8723BEPHY_REG_1TARRAYLEN;
531 array_table = RTL8723BEPHY_REG_1TARRAY;
533 for (i = 0; i < arraylen; i = i + 2) {
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)
543 if (!_rtl8723be_check_condition(hw,
545 /*Discard the following
546 *(offset, data) pairs
548 READ_NEXT_PAIR(v1, v2, i);
549 while (v2 != 0xDEAD &&
553 READ_NEXT_PAIR(v1, v2, i);
555 i -= 2; /* prevent from for-loop += 2*/
556 /*Configure matched pairs and
557 *skip to end of if-else.
560 READ_NEXT_PAIR(v1, v2, i);
561 while (v2 != 0xDEAD &&
565 _rtl8723be_config_bb_reg(hw,
567 READ_NEXT_PAIR(v1, v2, i);
570 while (v2 != 0xDEAD && i < arraylen - 2)
571 READ_NEXT_PAIR(v1, v2, i);
575 } else if (configtype == BASEBAND_CONFIG_AGC_TAB) {
576 arraylen = RTL8723BEAGCTAB_1TARRAYLEN;
577 array_table = RTL8723BEAGCTAB_1TARRAY;
579 for (i = 0; i < arraylen; i = i + 2) {
581 v2 = array_table[i+1];
582 if (v1 < 0xCDCDCDCD) {
583 rtl_set_bbreg(hw, array_table[i],
588 } else {/*This line is the start line of branch.*/
589 /* to protect READ_NEXT_PAIR not overrun */
590 if (i >= arraylen - 2)
593 if (!_rtl8723be_check_condition(hw,
595 /*Discard the following
596 *(offset, data) pairs
598 READ_NEXT_PAIR(v1, v2, i);
599 while (v2 != 0xDEAD &&
603 READ_NEXT_PAIR(v1, v2, i);
605 i -= 2; /* prevent from for-loop += 2*/
606 /*Configure matched pairs and
607 *skip to end of if-else.
610 READ_NEXT_PAIR(v1, v2, i);
611 while (v2 != 0xDEAD &&
615 rtl_set_bbreg(hw, array_table[i],
619 READ_NEXT_PAIR(v1, v2, i);
622 while (v2 != 0xDEAD && i < arraylen - 2)
623 READ_NEXT_PAIR(v1, v2, i);
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]);
634 static u8 _rtl8723be_get_rate_section_index(u32 regaddr)
639 case RTXAGC_A_RATE18_06:
642 case RTXAGC_A_RATE54_24:
645 case RTXAGC_A_CCK1_MCS32:
648 case RTXAGC_B_CCK11_A_CCK2_11:
651 case RTXAGC_A_MCS03_MCS00:
654 case RTXAGC_A_MCS07_MCS04:
657 case RTXAGC_A_MCS11_MCS08:
660 case RTXAGC_A_MCS15_MCS12:
663 case RTXAGC_B_RATE18_06:
666 case RTXAGC_B_RATE54_24:
669 case RTXAGC_B_CCK1_55_MCS32:
672 case RTXAGC_B_MCS03_MCS00:
675 case RTXAGC_B_MCS07_MCS04:
678 case RTXAGC_B_MCS11_MCS08:
681 case RTXAGC_B_MCS15_MCS12:
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);
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)
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);
704 if (band != BAND_ON_2_4G && band != BAND_ON_5G) {
705 RT_TRACE(rtlpriv, FPHY, PHY_TXPWR, "Invalid Band %d\n", band);
708 if (rfpath > MAX_RF_PATH - 1) {
709 RT_TRACE(rtlpriv, FPHY, PHY_TXPWR,
710 "Invalid RfPath %d\n", rfpath);
713 if (txnum > MAX_RF_PATH - 1) {
714 RT_TRACE(rtlpriv, FPHY, PHY_TXPWR, "Invalid TxNum %d\n", txnum);
718 rtlphy->tx_power_by_rate_offset[band][rfpath][txnum][rate_section] =
723 static bool _rtl8723be_phy_config_bb_with_pgheaderfile(struct ieee80211_hw *hw,
726 struct rtl_priv *rtlpriv = rtl_priv(hw);
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;
732 phy_regarray_pg_len = RTL8723BEPHY_REG_ARRAY_PGLEN;
733 phy_regarray_table_pg = RTL8723BEPHY_REG_ARRAY_PG;
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];
744 if (v1 < 0xcdcdcdcd) {
745 if (phy_regarray_table_pg[i] == 0xfe ||
746 phy_regarray_table_pg[i] == 0xffe)
749 _rtl8723be_store_tx_power_by_rate(hw,
750 v1, v2, v3, v4, v5, v6);
755 RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
756 "configtype != BaseBand_Config_PHY_REG\n");
761 bool rtl8723be_phy_config_rf_with_headerfile(struct ieee80211_hw *hw,
762 enum radio_path rfpath)
764 #define READ_NEXT_RF_PAIR(v1, v2, i) \
767 v1 = radioa_array_table[i]; \
768 v2 = radioa_array_table[i+1]; \
772 bool rtstatus = true;
773 u32 *radioa_array_table;
775 struct rtl_priv *rtlpriv = rtl_priv(hw);
776 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
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);
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)
797 if (!_rtl8723be_check_condition(hw,
798 radioa_array_table[i])) {
799 /*Discard the following
800 *(offset, data) pairs
802 READ_NEXT_RF_PAIR(v1, v2, i);
803 while (v2 != 0xDEAD &&
806 i < radioa_arraylen - 2) {
807 READ_NEXT_RF_PAIR(v1, v2, i);
809 i -= 2; /* prevent from for-loop += 2*/
811 /*Configure matched pairs
812 *and skip to end of if-else.
814 READ_NEXT_RF_PAIR(v1, v2, i);
815 while (v2 != 0xDEAD &&
818 i < radioa_arraylen - 2) {
819 _rtl8723be_config_rf_radio_a(hw,
821 READ_NEXT_RF_PAIR(v1, v2, i);
824 while (v2 != 0xDEAD &&
825 i < radioa_arraylen - 2) {
826 READ_NEXT_RF_PAIR(v1, v2, i);
832 if (rtlhal->oem_id == RT_CID_819X_HP)
833 _rtl8723be_config_rf_radio_a(hw, 0x52, 0x7E4BD);
839 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
840 "switch case %#x not processed\n", rfpath);
846 void rtl8723be_phy_get_hw_reg_originalvalue(struct ieee80211_hw *hw)
848 struct rtl_priv *rtlpriv = rtl_priv(hw);
849 struct rtl_phy *rtlphy = &rtlpriv->phy;
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);
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]);
867 rtlphy->framesync = (u8)rtl_get_bbreg(hw, ROFDM0_RXDETECTOR3,
869 rtlphy->framesync_c34 = rtl_get_bbreg(hw, ROFDM0_RXDETECTOR2,
872 RT_TRACE(rtlpriv, COMP_INIT, DBG_TRACE,
873 "Default framesync (0x%x) = 0x%x\n",
874 ROFDM0_RXDETECTOR3, rtlphy->framesync);
877 static u8 _rtl8723be_phy_get_ratesection_intxpower_byrate(enum radio_path path,
888 case DESC92C_RATE5_5M:
889 if (path == RF90_PATH_A)
891 else if (path == RF90_PATH_B)
895 case DESC92C_RATE11M:
901 case DESC92C_RATE12M:
902 case DESC92C_RATE18M:
906 case DESC92C_RATE24M:
907 case DESC92C_RATE36M:
908 case DESC92C_RATE48M:
909 case DESC92C_RATE54M:
913 case DESC92C_RATEMCS0:
914 case DESC92C_RATEMCS1:
915 case DESC92C_RATEMCS2:
916 case DESC92C_RATEMCS3:
920 case DESC92C_RATEMCS4:
921 case DESC92C_RATEMCS5:
922 case DESC92C_RATEMCS6:
923 case DESC92C_RATEMCS7:
927 case DESC92C_RATEMCS8:
928 case DESC92C_RATEMCS9:
929 case DESC92C_RATEMCS10:
930 case DESC92C_RATEMCS11:
934 case DESC92C_RATEMCS12:
935 case DESC92C_RATEMCS13:
936 case DESC92C_RATEMCS14:
937 case DESC92C_RATEMCS15:
942 RT_ASSERT(true, "Rate_Section is Illegal\n");
949 static u8 _rtl8723be_get_txpower_by_rate(struct ieee80211_hw *hw,
951 enum radio_path rfpath, u8 rate)
953 struct rtl_priv *rtlpriv = rtl_priv(hw);
954 struct rtl_phy *rtlphy = &rtlpriv->phy;
955 u8 shift = 0, rate_section, tx_num;
958 rate_section = _rtl8723be_phy_get_ratesection_intxpower_byrate(rfpath,
960 tx_num = RF_TX_NUM_NONIMPLEMENT;
962 if (tx_num == RF_TX_NUM_NONIMPLEMENT) {
963 if (rate >= DESC92C_RATEMCS8 && rate <= DESC92C_RATEMCS15)
971 case DESC92C_RATE24M:
972 case DESC92C_RATEMCS0:
973 case DESC92C_RATEMCS4:
974 case DESC92C_RATEMCS8:
975 case DESC92C_RATEMCS12:
981 case DESC92C_RATE36M:
982 case DESC92C_RATEMCS1:
983 case DESC92C_RATEMCS5:
984 case DESC92C_RATEMCS9:
985 case DESC92C_RATEMCS13:
988 case DESC92C_RATE5_5M:
989 case DESC92C_RATE12M:
990 case DESC92C_RATE48M:
991 case DESC92C_RATEMCS2:
992 case DESC92C_RATEMCS6:
993 case DESC92C_RATEMCS10:
994 case DESC92C_RATEMCS14:
997 case DESC92C_RATE11M:
998 case DESC92C_RATE18M:
999 case DESC92C_RATE54M:
1000 case DESC92C_RATEMCS3:
1001 case DESC92C_RATEMCS7:
1002 case DESC92C_RATEMCS11:
1003 case DESC92C_RATEMCS15:
1007 RT_ASSERT(true, "Rate_Section is Illegal\n");
1010 tx_pwr_diff = (u8)(rtlphy->tx_power_by_rate_offset[band][rfpath][tx_num]
1011 [rate_section] >> shift) & 0xff;
1016 static u8 _rtl8723be_get_txpower_index(struct ieee80211_hw *hw, u8 path,
1017 u8 rate, u8 bandwidth, u8 channel)
1019 struct rtl_priv *rtlpriv = rtl_priv(hw);
1020 struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
1021 u8 index = (channel - 1);
1023 u8 power_diff_byrate = 0;
1025 if (channel > 14 || channel < 1) {
1027 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_LOUD,
1028 "Illegal channel!\n");
1030 if (RX_HAL_IS_CCK_RATE(rate))
1031 txpower = rtlefuse->txpwrlevel_cck[path][index];
1032 else if (DESC92C_RATE6M <= rate)
1033 txpower = rtlefuse->txpwrlevel_ht40_1s[path][index];
1035 RT_TRACE(rtlpriv, COMP_POWER_TRACKING, DBG_LOUD,
1038 if (DESC92C_RATE6M <= rate && rate <= DESC92C_RATE54M &&
1039 !RX_HAL_IS_CCK_RATE(rate))
1040 txpower += rtlefuse->txpwr_legacyhtdiff[0][TX_1S];
1042 if (bandwidth == HT_CHANNEL_WIDTH_20) {
1043 if (DESC92C_RATEMCS0 <= rate && rate <= DESC92C_RATEMCS15)
1044 txpower += rtlefuse->txpwr_ht20diff[0][TX_1S];
1045 if (DESC92C_RATEMCS8 <= rate && rate <= DESC92C_RATEMCS15)
1046 txpower += rtlefuse->txpwr_ht20diff[0][TX_2S];
1047 } else if (bandwidth == HT_CHANNEL_WIDTH_20_40) {
1048 if (DESC92C_RATEMCS0 <= rate && rate <= DESC92C_RATEMCS15)
1049 txpower += rtlefuse->txpwr_ht40diff[0][TX_1S];
1050 if (DESC92C_RATEMCS8 <= rate && rate <= DESC92C_RATEMCS15)
1051 txpower += rtlefuse->txpwr_ht40diff[0][TX_2S];
1054 if (rtlefuse->eeprom_regulatory != 2)
1055 power_diff_byrate = _rtl8723be_get_txpower_by_rate(hw,
1059 txpower += power_diff_byrate;
1061 if (txpower > MAX_POWER_INDEX)
1062 txpower = MAX_POWER_INDEX;
1067 static void _rtl8723be_phy_set_txpower_index(struct ieee80211_hw *hw,
1068 u8 power_index, u8 path, u8 rate)
1070 struct rtl_priv *rtlpriv = rtl_priv(hw);
1071 if (path == RF90_PATH_A) {
1073 case DESC92C_RATE1M:
1074 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_CCK1_MCS32,
1075 MASKBYTE1, power_index);
1077 case DESC92C_RATE2M:
1078 rtl8723_phy_set_bb_reg(hw, RTXAGC_B_CCK11_A_CCK2_11,
1079 MASKBYTE1, power_index);
1081 case DESC92C_RATE5_5M:
1082 rtl8723_phy_set_bb_reg(hw, RTXAGC_B_CCK11_A_CCK2_11,
1083 MASKBYTE2, power_index);
1085 case DESC92C_RATE11M:
1086 rtl8723_phy_set_bb_reg(hw, RTXAGC_B_CCK11_A_CCK2_11,
1087 MASKBYTE3, power_index);
1090 case DESC92C_RATE6M:
1091 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1092 MASKBYTE0, power_index);
1094 case DESC92C_RATE9M:
1095 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1096 MASKBYTE1, power_index);
1098 case DESC92C_RATE12M:
1099 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1100 MASKBYTE2, power_index);
1102 case DESC92C_RATE18M:
1103 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE18_06,
1104 MASKBYTE3, power_index);
1107 case DESC92C_RATE24M:
1108 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1109 MASKBYTE0, power_index);
1111 case DESC92C_RATE36M:
1112 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1113 MASKBYTE1, power_index);
1115 case DESC92C_RATE48M:
1116 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1117 MASKBYTE2, power_index);
1119 case DESC92C_RATE54M:
1120 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_RATE54_24,
1121 MASKBYTE3, power_index);
1124 case DESC92C_RATEMCS0:
1125 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1126 MASKBYTE0, power_index);
1128 case DESC92C_RATEMCS1:
1129 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1130 MASKBYTE1, power_index);
1132 case DESC92C_RATEMCS2:
1133 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1134 MASKBYTE2, power_index);
1136 case DESC92C_RATEMCS3:
1137 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS03_MCS00,
1138 MASKBYTE3, power_index);
1141 case DESC92C_RATEMCS4:
1142 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1143 MASKBYTE0, power_index);
1145 case DESC92C_RATEMCS5:
1146 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1147 MASKBYTE1, power_index);
1149 case DESC92C_RATEMCS6:
1150 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1151 MASKBYTE2, power_index);
1153 case DESC92C_RATEMCS7:
1154 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS07_MCS04,
1155 MASKBYTE3, power_index);
1158 case DESC92C_RATEMCS8:
1159 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1160 MASKBYTE0, power_index);
1162 case DESC92C_RATEMCS9:
1163 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1164 MASKBYTE1, power_index);
1166 case DESC92C_RATEMCS10:
1167 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1168 MASKBYTE2, power_index);
1170 case DESC92C_RATEMCS11:
1171 rtl8723_phy_set_bb_reg(hw, RTXAGC_A_MCS11_MCS08,
1172 MASKBYTE3, power_index);
1176 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD, "Invalid Rate!!\n");
1180 RT_TRACE(rtlpriv, COMP_POWER, DBG_LOUD, "Invalid RFPath!!\n");
1184 void rtl8723be_phy_set_txpower_level(struct ieee80211_hw *hw, u8 channel)
1186 struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
1187 u8 cck_rates[] = {DESC92C_RATE1M, DESC92C_RATE2M,
1188 DESC92C_RATE5_5M, DESC92C_RATE11M};
1189 u8 ofdm_rates[] = {DESC92C_RATE6M, DESC92C_RATE9M,
1190 DESC92C_RATE12M, DESC92C_RATE18M,
1191 DESC92C_RATE24M, DESC92C_RATE36M,
1192 DESC92C_RATE48M, DESC92C_RATE54M};
1193 u8 ht_rates_1t[] = {DESC92C_RATEMCS0, DESC92C_RATEMCS1,
1194 DESC92C_RATEMCS2, DESC92C_RATEMCS3,
1195 DESC92C_RATEMCS4, DESC92C_RATEMCS5,
1196 DESC92C_RATEMCS6, DESC92C_RATEMCS7};
1200 if (!rtlefuse->txpwr_fromeprom)
1203 size = sizeof(cck_rates) / sizeof(u8);
1204 for (i = 0; i < size; i++) {
1205 power_index = _rtl8723be_get_txpower_index(hw, RF90_PATH_A,
1207 rtl_priv(hw)->phy.current_chan_bw,
1209 _rtl8723be_phy_set_txpower_index(hw, power_index, RF90_PATH_A,
1212 size = sizeof(ofdm_rates) / sizeof(u8);
1213 for (i = 0; i < size; i++) {
1214 power_index = _rtl8723be_get_txpower_index(hw, RF90_PATH_A,
1216 rtl_priv(hw)->phy.current_chan_bw,
1218 _rtl8723be_phy_set_txpower_index(hw, power_index, RF90_PATH_A,
1221 size = sizeof(ht_rates_1t) / sizeof(u8);
1222 for (i = 0; i < size; i++) {
1223 power_index = _rtl8723be_get_txpower_index(hw, RF90_PATH_A,
1225 rtl_priv(hw)->phy.current_chan_bw,
1227 _rtl8723be_phy_set_txpower_index(hw, power_index, RF90_PATH_A,
1232 void rtl8723be_phy_scan_operation_backup(struct ieee80211_hw *hw, u8 operation)
1234 struct rtl_priv *rtlpriv = rtl_priv(hw);
1235 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1236 enum io_type iotype;
1238 if (!is_hal_stop(rtlhal)) {
1239 switch (operation) {
1240 case SCAN_OPT_BACKUP_BAND0:
1241 iotype = IO_CMD_PAUSE_BAND0_DM_BY_SCAN;
1242 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_IO_CMD,
1246 case SCAN_OPT_RESTORE:
1247 iotype = IO_CMD_RESUME_DM_BY_SCAN;
1248 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_IO_CMD,
1252 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1253 "Unknown Scan Backup operation.\n");
1259 void rtl8723be_phy_set_bw_mode_callback(struct ieee80211_hw *hw)
1261 struct rtl_priv *rtlpriv = rtl_priv(hw);
1262 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1263 struct rtl_phy *rtlphy = &rtlpriv->phy;
1264 struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
1268 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
1269 "Switch to %s bandwidth\n",
1270 rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_20 ?
1273 if (is_hal_stop(rtlhal)) {
1274 rtlphy->set_bwmode_inprogress = false;
1278 reg_bw_opmode = rtl_read_byte(rtlpriv, REG_BWOPMODE);
1279 reg_prsr_rsc = rtl_read_byte(rtlpriv, REG_RRSR + 2);
1281 switch (rtlphy->current_chan_bw) {
1282 case HT_CHANNEL_WIDTH_20:
1283 reg_bw_opmode |= BW_OPMODE_20MHZ;
1284 rtl_write_byte(rtlpriv, REG_BWOPMODE, reg_bw_opmode);
1286 case HT_CHANNEL_WIDTH_20_40:
1287 reg_bw_opmode &= ~BW_OPMODE_20MHZ;
1288 rtl_write_byte(rtlpriv, REG_BWOPMODE, reg_bw_opmode);
1289 reg_prsr_rsc = (reg_prsr_rsc & 0x90) |
1290 (mac->cur_40_prime_sc << 5);
1291 rtl_write_byte(rtlpriv, REG_RRSR + 2, reg_prsr_rsc);
1294 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1295 "unknown bandwidth: %#X\n", rtlphy->current_chan_bw);
1299 switch (rtlphy->current_chan_bw) {
1300 case HT_CHANNEL_WIDTH_20:
1301 rtl_set_bbreg(hw, RFPGA0_RFMOD, BRFMOD, 0x0);
1302 rtl_set_bbreg(hw, RFPGA1_RFMOD, BRFMOD, 0x0);
1303 /* rtl_set_bbreg(hw, RFPGA0_ANALOGPARAMETER2, BIT(10), 1);*/
1305 case HT_CHANNEL_WIDTH_20_40:
1306 rtl_set_bbreg(hw, RFPGA0_RFMOD, BRFMOD, 0x1);
1307 rtl_set_bbreg(hw, RFPGA1_RFMOD, BRFMOD, 0x1);
1309 rtl_set_bbreg(hw, RCCK0_SYSTEM, BCCK_SIDEBAND,
1310 (mac->cur_40_prime_sc >> 1));
1311 rtl_set_bbreg(hw, ROFDM1_LSTF, 0xC00, mac->cur_40_prime_sc);
1312 /*rtl_set_bbreg(hw, RFPGA0_ANALOGPARAMETER2, BIT(10), 0);*/
1314 rtl_set_bbreg(hw, 0x818, (BIT(26) | BIT(27)),
1315 (mac->cur_40_prime_sc ==
1316 HAL_PRIME_CHNL_OFFSET_LOWER) ? 2 : 1);
1319 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1320 "unknown bandwidth: %#X\n", rtlphy->current_chan_bw);
1323 rtl8723be_phy_rf6052_set_bandwidth(hw, rtlphy->current_chan_bw);
1324 rtlphy->set_bwmode_inprogress = false;
1325 RT_TRACE(rtlpriv, COMP_SCAN, DBG_LOUD, "\n");
1328 void rtl8723be_phy_set_bw_mode(struct ieee80211_hw *hw,
1329 enum nl80211_channel_type ch_type)
1331 struct rtl_priv *rtlpriv = rtl_priv(hw);
1332 struct rtl_phy *rtlphy = &rtlpriv->phy;
1333 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1334 u8 tmp_bw = rtlphy->current_chan_bw;
1336 if (rtlphy->set_bwmode_inprogress)
1338 rtlphy->set_bwmode_inprogress = true;
1339 if ((!is_hal_stop(rtlhal)) && !(RT_CANNOT_IO(hw))) {
1340 rtl8723be_phy_set_bw_mode_callback(hw);
1342 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
1343 "false driver sleep or unload\n");
1344 rtlphy->set_bwmode_inprogress = false;
1345 rtlphy->current_chan_bw = tmp_bw;
1349 void rtl8723be_phy_sw_chnl_callback(struct ieee80211_hw *hw)
1351 struct rtl_priv *rtlpriv = rtl_priv(hw);
1352 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1353 struct rtl_phy *rtlphy = &rtlpriv->phy;
1356 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE,
1357 "switch to channel%d\n", rtlphy->current_channel);
1358 if (is_hal_stop(rtlhal))
1361 if (!rtlphy->sw_chnl_inprogress)
1363 if (!_rtl8723be_phy_sw_chnl_step_by_step(hw,
1364 rtlphy->current_channel,
1365 &rtlphy->sw_chnl_stage,
1366 &rtlphy->sw_chnl_step,
1373 rtlphy->sw_chnl_inprogress = false;
1377 RT_TRACE(rtlpriv, COMP_SCAN, DBG_TRACE, "\n");
1380 u8 rtl8723be_phy_sw_chnl(struct ieee80211_hw *hw)
1382 struct rtl_priv *rtlpriv = rtl_priv(hw);
1383 struct rtl_phy *rtlphy = &rtlpriv->phy;
1384 struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1386 if (rtlphy->sw_chnl_inprogress)
1388 if (rtlphy->set_bwmode_inprogress)
1390 RT_ASSERT((rtlphy->current_channel <= 14),
1391 "WIRELESS_MODE_G but channel>14");
1392 rtlphy->sw_chnl_inprogress = true;
1393 rtlphy->sw_chnl_stage = 0;
1394 rtlphy->sw_chnl_step = 0;
1395 if (!(is_hal_stop(rtlhal)) && !(RT_CANNOT_IO(hw))) {
1396 rtl8723be_phy_sw_chnl_callback(hw);
1397 RT_TRACE(rtlpriv, COMP_CHAN, DBG_LOUD,
1398 "sw_chnl_inprogress false schedule workitem current channel %d\n",
1399 rtlphy->current_channel);
1400 rtlphy->sw_chnl_inprogress = false;
1402 RT_TRACE(rtlpriv, COMP_CHAN, DBG_LOUD,
1403 "sw_chnl_inprogress false driver sleep or unload\n");
1404 rtlphy->sw_chnl_inprogress = false;
1409 static bool _rtl8723be_phy_sw_chnl_step_by_step(struct ieee80211_hw *hw,
1410 u8 channel, u8 *stage,
1411 u8 *step, u32 *delay)
1413 struct rtl_priv *rtlpriv = rtl_priv(hw);
1414 struct rtl_phy *rtlphy = &rtlpriv->phy;
1415 struct swchnlcmd precommoncmd[MAX_PRECMD_CNT];
1416 u32 precommoncmdcnt;
1417 struct swchnlcmd postcommoncmd[MAX_POSTCMD_CNT];
1418 u32 postcommoncmdcnt;
1419 struct swchnlcmd rfdependcmd[MAX_RFDEPENDCMD_CNT];
1421 struct swchnlcmd *currentcmd = NULL;
1423 u8 num_total_rfpath = rtlphy->num_total_rfpath;
1425 precommoncmdcnt = 0;
1426 rtl8723_phy_set_sw_chnl_cmdarray(precommoncmd, precommoncmdcnt++,
1428 CMDID_SET_TXPOWEROWER_LEVEL,
1430 rtl8723_phy_set_sw_chnl_cmdarray(precommoncmd, precommoncmdcnt++,
1431 MAX_PRECMD_CNT, CMDID_END, 0, 0, 0);
1433 postcommoncmdcnt = 0;
1435 rtl8723_phy_set_sw_chnl_cmdarray(postcommoncmd, postcommoncmdcnt++,
1436 MAX_POSTCMD_CNT, CMDID_END,
1441 RT_ASSERT((channel >= 1 && channel <= 14),
1442 "illegal channel for Zebra: %d\n", channel);
1444 rtl8723_phy_set_sw_chnl_cmdarray(rfdependcmd, rfdependcmdcnt++,
1445 MAX_RFDEPENDCMD_CNT,
1447 RF_CHNLBW, channel, 10);
1449 rtl8723_phy_set_sw_chnl_cmdarray(rfdependcmd, rfdependcmdcnt++,
1450 MAX_RFDEPENDCMD_CNT,
1451 CMDID_END, 0, 0, 0);
1456 currentcmd = &precommoncmd[*step];
1459 currentcmd = &rfdependcmd[*step];
1462 currentcmd = &postcommoncmd[*step];
1465 RT_TRACE(rtlpriv, COMP_ERR, DBG_EMERG,
1466 "Invalid 'stage' = %d, Check it!\n", *stage);
1470 if (currentcmd->cmdid == CMDID_END) {
1471 if ((*stage) == 2) {
1480 switch (currentcmd->cmdid) {
1481 case CMDID_SET_TXPOWEROWER_LEVEL:
1482 rtl8723be_phy_set_txpower_level(hw, channel);
1484 case CMDID_WRITEPORT_ULONG:
1485 rtl_write_dword(rtlpriv, currentcmd->para1,
1488 case CMDID_WRITEPORT_USHORT:
1489 rtl_write_word(rtlpriv, currentcmd->para1,
1490 (u16)currentcmd->para2);
1492 case CMDID_WRITEPORT_UCHAR:
1493 rtl_write_byte(rtlpriv, currentcmd->para1,
1494 (u8)currentcmd->para2);
1496 case CMDID_RF_WRITEREG:
1497 for (rfpath = 0; rfpath < num_total_rfpath; rfpath++) {
1498 rtlphy->rfreg_chnlval[rfpath] =
1499 ((rtlphy->rfreg_chnlval[rfpath] &
1500 0xfffffc00) | currentcmd->para2);
1502 rtl_set_rfreg(hw, (enum radio_path)rfpath,
1505 rtlphy->rfreg_chnlval[rfpath]);
1509 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
1510 "switch case %#x not processed\n",
1518 (*delay) = currentcmd->msdelay;
1523 static u8 _rtl8723be_phy_path_a_iqk(struct ieee80211_hw *hw)
1525 u32 reg_eac, reg_e94, reg_e9c, tmp;
1528 /* leave IQK mode */
1529 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1530 /* switch to path A */
1531 rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000000);
1532 /* enable path A PA in TXIQK mode */
1533 rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, RFREG_OFFSET_MASK, 0x800a0);
1534 rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x20000);
1535 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0003f);
1536 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xc7f87);
1539 /* path-A IQK setting */
1541 rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1542 rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1543 /* path-A IQK setting */
1544 rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1545 rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1546 rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1547 rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1549 rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x821403ea);
1550 rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28160000);
1551 rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1552 rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1553 /* LO calibration setting */
1554 rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x00462911);
1555 /* enter IQK mode */
1556 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1558 /* One shot, path A LOK & IQK */
1559 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1560 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1562 mdelay(IQK_DELAY_TIME);
1564 /* leave IQK mode */
1565 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1568 reg_eac = rtl_get_bbreg(hw, 0xeac, MASKDWORD);
1569 reg_e94 = rtl_get_bbreg(hw, 0xe94, MASKDWORD);
1570 reg_e9c = rtl_get_bbreg(hw, 0xe9c, MASKDWORD);
1572 if (!(reg_eac & BIT(28)) &&
1573 (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1574 (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1576 else /* if Tx not OK, ignore Rx */
1579 /* Allen 20131125 */
1580 tmp = (reg_e9c & 0x03FF0000) >> 16;
1581 if ((tmp & 0x200) > 0)
1584 if (!(reg_eac & BIT(28)) &&
1585 (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1586 (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1589 else /* if Tx not OK, ignore Rx */
1595 /* bit0 = 1 => Tx OK, bit1 = 1 => Rx OK */
1596 static u8 _rtl8723be_phy_path_a_rx_iqk(struct ieee80211_hw *hw)
1598 u32 reg_eac, reg_e94, reg_e9c, reg_ea4, u32tmp, tmp;
1601 /* leave IQK mode */
1602 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1604 /* switch to path A */
1605 rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000000);
1607 /* 1 Get TXIMR setting */
1608 /* modify RXIQK mode table */
1609 rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x1);
1610 rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1611 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1612 /* LNA2 off, PA on for Dcut */
1613 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7fb7);
1614 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1617 rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1618 rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1620 /* path-A IQK setting */
1621 rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1622 rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1623 rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1624 rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1626 rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82160ff0);
1627 rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28110000);
1628 rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1629 rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1631 /* LO calibration setting */
1632 rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a911);
1634 /* enter IQK mode */
1635 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1637 /* One shot, path A LOK & IQK */
1638 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1639 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1641 mdelay(IQK_DELAY_TIME);
1643 /* leave IQK mode */
1644 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1647 reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1648 reg_e94 = rtl_get_bbreg(hw, RTX_POWER_BEFORE_IQK_A, MASKDWORD);
1649 reg_e9c = rtl_get_bbreg(hw, RTX_POWER_AFTER_IQK_A, MASKDWORD);
1651 if (!(reg_eac & BIT(28)) &&
1652 (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1653 (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1655 else /* if Tx not OK, ignore Rx */
1658 /* Allen 20131125 */
1659 tmp = (reg_e9c & 0x03FF0000) >> 16;
1660 if ((tmp & 0x200) > 0)
1663 if (!(reg_eac & BIT(28)) &&
1664 (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1665 (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1668 else /* if Tx not OK, ignore Rx */
1671 u32tmp = 0x80007C00 | (reg_e94 & 0x3FF0000) |
1672 ((reg_e9c & 0x3FF0000) >> 16);
1673 rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, u32tmp);
1676 /* modify RXIQK mode table */
1677 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1678 rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x1);
1679 rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1680 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1681 /* LAN2 on, PA off for Dcut */
1682 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7d77);
1684 /* PA, PAD setting */
1685 rtl_set_rfreg(hw, RF90_PATH_A, 0xdf, RFREG_OFFSET_MASK, 0xf80);
1686 rtl_set_rfreg(hw, RF90_PATH_A, 0x55, RFREG_OFFSET_MASK, 0x4021f);
1689 rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1691 /* path-A IQK setting */
1692 rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1693 rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1694 rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1695 rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1697 rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82110000);
1698 rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x2816001f);
1699 rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1700 rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1702 /* LO calibration setting */
1703 rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a8d1);
1705 /* enter IQK mode */
1706 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1708 /* One shot, path A LOK & IQK */
1709 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1710 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1712 mdelay(IQK_DELAY_TIME);
1714 /* leave IQK mode */
1715 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1718 reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1719 reg_ea4 = rtl_get_bbreg(hw, RRX_POWER_BEFORE_IQK_A_2, MASKDWORD);
1721 /* leave IQK mode */
1722 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1723 rtl_set_rfreg(hw, RF90_PATH_A, 0xdf, RFREG_OFFSET_MASK, 0x780);
1725 /* Allen 20131125 */
1726 tmp = (reg_eac & 0x03FF0000) >> 16;
1727 if ((tmp & 0x200) > 0)
1729 /* if Tx is OK, check whether Rx is OK */
1730 if (!(reg_eac & BIT(27)) &&
1731 (((reg_ea4 & 0x03FF0000) >> 16) != 0x132) &&
1732 (((reg_eac & 0x03FF0000) >> 16) != 0x36))
1734 else if (!(reg_eac & BIT(27)) &&
1735 (((reg_ea4 & 0x03FF0000) >> 16) < 0x110) &&
1736 (((reg_ea4 & 0x03FF0000) >> 16) > 0xf0) &&
1743 static u8 _rtl8723be_phy_path_b_iqk(struct ieee80211_hw *hw)
1745 u32 reg_eac, reg_e94, reg_e9c, tmp;
1748 /* leave IQK mode */
1749 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1750 /* switch to path B */
1751 rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000280);
1753 /* enable path B PA in TXIQK mode */
1754 rtl_set_rfreg(hw, RF90_PATH_A, 0xed, RFREG_OFFSET_MASK, 0x00020);
1755 rtl_set_rfreg(hw, RF90_PATH_A, 0x43, RFREG_OFFSET_MASK, 0x40fc1);
1759 rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1760 rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1761 /* path-A IQK setting */
1762 rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1763 rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1764 rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1765 rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1767 rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x821403ea);
1768 rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28110000);
1769 rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1770 rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1772 /* LO calibration setting */
1773 rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x00462911);
1775 /* enter IQK mode */
1776 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1778 /* One shot, path B LOK & IQK */
1779 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1780 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1782 mdelay(IQK_DELAY_TIME);
1784 /* leave IQK mode */
1785 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1788 reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1789 reg_e94 = rtl_get_bbreg(hw, RTX_POWER_BEFORE_IQK_A, MASKDWORD);
1790 reg_e9c = rtl_get_bbreg(hw, RTX_POWER_AFTER_IQK_A, MASKDWORD);
1792 if (!(reg_eac & BIT(28)) &&
1793 (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1794 (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1799 /* Allen 20131125 */
1800 tmp = (reg_e9c & 0x03FF0000) >> 16;
1801 if ((tmp & 0x200) > 0)
1804 if (!(reg_eac & BIT(28)) &&
1805 (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1806 (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1815 /* bit0 = 1 => Tx OK, bit1 = 1 => Rx OK */
1816 static u8 _rtl8723be_phy_path_b_rx_iqk(struct ieee80211_hw *hw)
1818 u32 reg_e94, reg_e9c, reg_ea4, reg_eac, u32tmp, tmp;
1821 /* leave IQK mode */
1822 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1823 /* switch to path B */
1824 rtl_set_bbreg(hw, 0x948, MASKDWORD, 0x00000280);
1826 /* 1 Get TXIMR setting */
1827 /* modify RXIQK mode table */
1828 rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, RFREG_OFFSET_MASK, 0x800a0);
1829 rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1830 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1831 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7ff7);
1833 /* open PA S1 & SMIXER */
1834 rtl_set_rfreg(hw, RF90_PATH_A, 0xed, RFREG_OFFSET_MASK, 0x00020);
1835 rtl_set_rfreg(hw, RF90_PATH_A, 0x43, RFREG_OFFSET_MASK, 0x60fed);
1838 rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, 0x01007c00);
1839 rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1841 /* path-B IQK setting */
1842 rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1843 rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1844 rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1845 rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1847 rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82160ff0);
1848 rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x28110000);
1849 rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1850 rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1852 /* LO calibration setting */
1853 rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a911);
1854 /* enter IQK mode */
1855 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1857 /* One shot, path B TXIQK @ RXIQK */
1858 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1859 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1861 mdelay(IQK_DELAY_TIME);
1863 /* leave IQK mode */
1864 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1866 reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1867 reg_e94 = rtl_get_bbreg(hw, RTX_POWER_BEFORE_IQK_A, MASKDWORD);
1868 reg_e9c = rtl_get_bbreg(hw, RTX_POWER_AFTER_IQK_A, MASKDWORD);
1870 if (!(reg_eac & BIT(28)) &&
1871 (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1872 (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1874 else /* if Tx not OK, ignore Rx */
1877 /* Allen 20131125 */
1878 tmp = (reg_e9c & 0x03FF0000) >> 16;
1879 if ((tmp & 0x200) > 0)
1882 if (!(reg_eac & BIT(28)) &&
1883 (((reg_e94 & 0x03FF0000) >> 16) < 0x110) &&
1884 (((reg_e94 & 0x03FF0000) >> 16) > 0xf0) &&
1890 u32tmp = 0x80007C00 | (reg_e94 & 0x3FF0000) |
1891 ((reg_e9c & 0x3FF0000) >> 16);
1892 rtl_set_bbreg(hw, RTX_IQK, MASKDWORD, u32tmp);
1896 /* <20121009, Kordan> RF Mode = 3 */
1897 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1898 rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x1);
1899 rtl_set_rfreg(hw, RF90_PATH_A, RF_RCK_OS, RFREG_OFFSET_MASK, 0x30000);
1900 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G1, RFREG_OFFSET_MASK, 0x0001f);
1901 rtl_set_rfreg(hw, RF90_PATH_A, RF_TXPA_G2, RFREG_OFFSET_MASK, 0xf7d77);
1902 rtl_set_rfreg(hw, RF90_PATH_A, RF_WE_LUT, 0x80000, 0x0);
1904 /* open PA S1 & close SMIXER */
1905 rtl_set_rfreg(hw, RF90_PATH_A, 0xed, RFREG_OFFSET_MASK, 0x00020);
1906 rtl_set_rfreg(hw, RF90_PATH_A, 0x43, RFREG_OFFSET_MASK, 0x60fbd);
1909 rtl_set_bbreg(hw, RRX_IQK, MASKDWORD, 0x01004800);
1911 /* path-B IQK setting */
1912 rtl_set_bbreg(hw, RTX_IQK_TONE_A, MASKDWORD, 0x38008c1c);
1913 rtl_set_bbreg(hw, RRX_IQK_TONE_A, MASKDWORD, 0x18008c1c);
1914 rtl_set_bbreg(hw, RTX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1915 rtl_set_bbreg(hw, RRX_IQK_TONE_B, MASKDWORD, 0x38008c1c);
1917 rtl_set_bbreg(hw, RTX_IQK_PI_A, MASKDWORD, 0x82110000);
1918 rtl_set_bbreg(hw, RRX_IQK_PI_A, MASKDWORD, 0x2816001f);
1919 rtl_set_bbreg(hw, RTX_IQK_PI_B, MASKDWORD, 0x82110000);
1920 rtl_set_bbreg(hw, RRX_IQK_PI_B, MASKDWORD, 0x28110000);
1922 /* LO calibration setting */
1923 rtl_set_bbreg(hw, RIQK_AGC_RSP, MASKDWORD, 0x0046a8d1);
1924 /* enter IQK mode */
1925 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x80800000);
1927 /* One shot, path B LOK & IQK */
1928 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf9000000);
1929 rtl_set_bbreg(hw, RIQK_AGC_PTS, MASKDWORD, 0xf8000000);
1931 mdelay(IQK_DELAY_TIME);
1933 /* leave IQK mode */
1934 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0x00000000);
1936 reg_eac = rtl_get_bbreg(hw, RRX_POWER_AFTER_IQK_A_2, MASKDWORD);
1937 reg_ea4 = rtl_get_bbreg(hw, RRX_POWER_BEFORE_IQK_A_2, MASKDWORD);
1939 /* Allen 20131125 */
1940 tmp = (reg_eac & 0x03FF0000) >> 16;
1941 if ((tmp & 0x200) > 0)
1944 /* if Tx is OK, check whether Rx is OK */
1945 if (!(reg_eac & BIT(27)) &&
1946 (((reg_ea4 & 0x03FF0000) >> 16) != 0x132) &&
1947 (((reg_eac & 0x03FF0000) >> 16) != 0x36))
1949 else if (!(reg_eac & BIT(27)) &&
1950 (((reg_ea4 & 0x03FF0000) >> 16) < 0x110) &&
1951 (((reg_ea4 & 0x03FF0000) >> 16) > 0xf0) &&
1960 static void _rtl8723be_phy_path_b_fill_iqk_matrix(struct ieee80211_hw *hw,
1966 u32 oldval_1, x, tx1_a, reg;
1969 if (final_candidate == 0xFF) {
1971 } else if (b_iqk_ok) {
1972 oldval_1 = (rtl_get_bbreg(hw, ROFDM0_XBTXIQIMBALANCE,
1973 MASKDWORD) >> 22) & 0x3FF;
1974 x = result[final_candidate][4];
1975 if ((x & 0x00000200) != 0)
1977 tx1_a = (x * oldval_1) >> 8;
1978 rtl_set_bbreg(hw, ROFDM0_XBTXIQIMBALANCE, 0x3FF, tx1_a);
1979 rtl_set_bbreg(hw, ROFDM0_ECCATHRESHOLD, BIT(27),
1980 ((x * oldval_1 >> 7) & 0x1));
1981 y = result[final_candidate][5];
1982 if ((y & 0x00000200) != 0)
1984 tx1_c = (y * oldval_1) >> 8;
1985 rtl_set_bbreg(hw, ROFDM0_XDTXAFE, 0xF0000000,
1986 ((tx1_c & 0x3C0) >> 6));
1987 rtl_set_bbreg(hw, ROFDM0_XBTXIQIMBALANCE, 0x003F0000,
1989 rtl_set_bbreg(hw, ROFDM0_ECCATHRESHOLD, BIT(25),
1990 ((y * oldval_1 >> 7) & 0x1));
1993 reg = result[final_candidate][6];
1994 rtl_set_bbreg(hw, ROFDM0_XBRXIQIMBALANCE, 0x3FF, reg);
1995 reg = result[final_candidate][7] & 0x3F;
1996 rtl_set_bbreg(hw, ROFDM0_XBRXIQIMBALANCE, 0xFC00, reg);
1997 reg = (result[final_candidate][7] >> 6) & 0xF;
1998 /* rtl_set_bbreg(hw, 0xca0, 0xF0000000, reg); */
2002 static bool _rtl8723be_phy_simularity_compare(struct ieee80211_hw *hw,
2003 long result[][8], u8 c1, u8 c2)
2005 u32 i, j, diff, simularity_bitmap, bound = 0;
2007 u8 final_candidate[2] = {0xFF, 0xFF}; /* for path A and path B */
2008 bool bresult = true; /* is2t = true*/
2009 s32 tmp1 = 0, tmp2 = 0;
2013 simularity_bitmap = 0;
2015 for (i = 0; i < bound; i++) {
2016 if ((i == 1) || (i == 3) || (i == 5) || (i == 7)) {
2017 if ((result[c1][i] & 0x00000200) != 0)
2018 tmp1 = result[c1][i] | 0xFFFFFC00;
2020 tmp1 = result[c1][i];
2022 if ((result[c2][i] & 0x00000200) != 0)
2023 tmp2 = result[c2][i] | 0xFFFFFC00;
2025 tmp2 = result[c2][i];
2027 tmp1 = result[c1][i];
2028 tmp2 = result[c2][i];
2031 diff = (tmp1 > tmp2) ? (tmp1 - tmp2) : (tmp2 - tmp1);
2033 if (diff > MAX_TOLERANCE) {
2034 if ((i == 2 || i == 6) && !simularity_bitmap) {
2035 if (result[c1][i] + result[c1][i + 1] == 0)
2036 final_candidate[(i / 4)] = c2;
2037 else if (result[c2][i] + result[c2][i + 1] == 0)
2038 final_candidate[(i / 4)] = c1;
2040 simularity_bitmap |= (1 << i);
2042 simularity_bitmap |= (1 << i);
2046 if (simularity_bitmap == 0) {
2047 for (i = 0; i < (bound / 4); i++) {
2048 if (final_candidate[i] != 0xFF) {
2049 for (j = i * 4; j < (i + 1) * 4 - 2; j++)
2051 result[final_candidate[i]][j];
2057 if (!(simularity_bitmap & 0x03)) { /* path A TX OK */
2058 for (i = 0; i < 2; i++)
2059 result[3][i] = result[c1][i];
2061 if (!(simularity_bitmap & 0x0c)) { /* path A RX OK */
2062 for (i = 2; i < 4; i++)
2063 result[3][i] = result[c1][i];
2065 if (!(simularity_bitmap & 0x30)) { /* path B TX OK */
2066 for (i = 4; i < 6; i++)
2067 result[3][i] = result[c1][i];
2069 if (!(simularity_bitmap & 0xc0)) { /* path B RX OK */
2070 for (i = 6; i < 8; i++)
2071 result[3][i] = result[c1][i];
2077 static void _rtl8723be_phy_iq_calibrate(struct ieee80211_hw *hw,
2078 long result[][8], u8 t, bool is2t)
2080 struct rtl_priv *rtlpriv = rtl_priv(hw);
2081 struct rtl_phy *rtlphy = &rtlpriv->phy;
2083 u8 patha_ok, pathb_ok;
2084 u32 adda_reg[IQK_ADDA_REG_NUM] = {
2085 0x85c, 0xe6c, 0xe70, 0xe74,
2086 0xe78, 0xe7c, 0xe80, 0xe84,
2087 0xe88, 0xe8c, 0xed0, 0xed4,
2088 0xed8, 0xedc, 0xee0, 0xeec
2091 u32 iqk_mac_reg[IQK_MAC_REG_NUM] = {
2092 0x522, 0x550, 0x551, 0x040
2094 u32 iqk_bb_reg[IQK_BB_REG_NUM] = {
2095 ROFDM0_TRXPATHENABLE, ROFDM0_TRMUXPAR,
2096 RFPGA0_XCD_RFINTERFACESW, 0xb68, 0xb6c,
2100 const u32 retrycount = 2;
2102 u32 path_sel_bb;/* path_sel_rf */
2104 u8 tmp_reg_c50, tmp_reg_c58;
2106 tmp_reg_c50 = rtl_get_bbreg(hw, 0xc50, MASKBYTE0);
2107 tmp_reg_c58 = rtl_get_bbreg(hw, 0xc58, MASKBYTE0);
2110 rtl8723_save_adda_registers(hw, adda_reg,
2111 rtlphy->adda_backup, 16);
2112 rtl8723_phy_save_mac_registers(hw, iqk_mac_reg,
2113 rtlphy->iqk_mac_backup);
2114 rtl8723_save_adda_registers(hw, iqk_bb_reg,
2115 rtlphy->iqk_bb_backup,
2118 rtl8723_phy_path_adda_on(hw, adda_reg, true, is2t);
2120 rtlphy->rfpi_enable = (u8)rtl_get_bbreg(hw,
2121 RFPGA0_XA_HSSIPARAMETER1,
2125 path_sel_bb = rtl_get_bbreg(hw, 0x948, MASKDWORD);
2127 rtl8723_phy_mac_setting_calibration(hw, iqk_mac_reg,
2128 rtlphy->iqk_mac_backup);
2130 rtl_set_bbreg(hw, 0xa04, 0x0f000000, 0xf);
2131 rtl_set_bbreg(hw, 0xc04, MASKDWORD, 0x03a05600);
2132 rtl_set_bbreg(hw, 0xc08, MASKDWORD, 0x000800e4);
2133 rtl_set_bbreg(hw, 0x874, MASKDWORD, 0x22204000);
2136 for (i = 0; i < retrycount; i++) {
2137 patha_ok = _rtl8723be_phy_path_a_iqk(hw);
2138 if (patha_ok == 0x01) {
2139 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2140 "Path A Tx IQK Success!!\n");
2141 result[t][0] = (rtl_get_bbreg(hw, 0xe94, MASKDWORD) &
2143 result[t][1] = (rtl_get_bbreg(hw, 0xe9c, MASKDWORD) &
2147 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2148 "Path A Tx IQK Fail!!\n");
2152 for (i = 0; i < retrycount; i++) {
2153 patha_ok = _rtl8723be_phy_path_a_rx_iqk(hw);
2154 if (patha_ok == 0x03) {
2155 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2156 "Path A Rx IQK Success!!\n");
2157 result[t][2] = (rtl_get_bbreg(hw, 0xea4, MASKDWORD) &
2159 result[t][3] = (rtl_get_bbreg(hw, 0xeac, MASKDWORD) &
2163 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2164 "Path A Rx IQK Fail!!\n");
2167 if (0x00 == patha_ok)
2168 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "Path A IQK Fail!!\n");
2172 for (i = 0; i < retrycount; i++) {
2173 pathb_ok = _rtl8723be_phy_path_b_iqk(hw);
2174 if (pathb_ok == 0x01) {
2175 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2176 "Path B Tx IQK Success!!\n");
2177 result[t][4] = (rtl_get_bbreg(hw, 0xe94,
2180 result[t][5] = (rtl_get_bbreg(hw, 0xe9c,
2185 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2186 "Path B Tx IQK Fail!!\n");
2189 for (i = 0; i < retrycount; i++) {
2190 pathb_ok = _rtl8723be_phy_path_b_rx_iqk(hw);
2191 if (pathb_ok == 0x03) {
2192 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2193 "Path B Rx IQK Success!!\n");
2194 result[t][6] = (rtl_get_bbreg(hw, 0xea4,
2197 result[t][7] = (rtl_get_bbreg(hw, 0xeac,
2202 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
2203 "Path B Rx IQK Fail!!\n");
2207 /* Back to BB mode, load original value */
2208 rtl_set_bbreg(hw, RFPGA0_IQK, MASKDWORD, 0);
2211 rtl8723_phy_reload_adda_registers(hw, adda_reg,
2212 rtlphy->adda_backup, 16);
2213 rtl8723_phy_reload_mac_registers(hw, iqk_mac_reg,
2214 rtlphy->iqk_mac_backup);
2215 rtl8723_phy_reload_adda_registers(hw, iqk_bb_reg,
2216 rtlphy->iqk_bb_backup,
2219 rtl_set_bbreg(hw, 0x948, MASKDWORD, path_sel_bb);
2220 /*rtl_set_rfreg(hw, RF90_PATH_B, 0xb0, 0xfffff, path_sel_rf);*/
2222 rtl_set_bbreg(hw, 0xc50, MASKBYTE0, 0x50);
2223 rtl_set_bbreg(hw, 0xc50, MASKBYTE0, tmp_reg_c50);
2225 rtl_set_bbreg(hw, 0xc58, MASKBYTE0, 0x50);
2226 rtl_set_bbreg(hw, 0xc58, MASKBYTE0, tmp_reg_c58);
2228 rtl_set_bbreg(hw, 0xe30, MASKDWORD, 0x01008c00);
2229 rtl_set_bbreg(hw, 0xe34, MASKDWORD, 0x01008c00);
2231 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "8723be IQK Finish!!\n");
2234 static u8 _get_right_chnl_place_for_iqk(u8 chnl)
2236 u8 channel_all[TARGET_CHNL_NUM_2G_5G] = {
2237 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12,
2238 13, 14, 36, 38, 40, 42, 44, 46,
2239 48, 50, 52, 54, 56, 58, 60, 62, 64,
2240 100, 102, 104, 106, 108, 110,
2241 112, 114, 116, 118, 120, 122,
2242 124, 126, 128, 130, 132, 134, 136,
2243 138, 140, 149, 151, 153, 155, 157,
2244 159, 161, 163, 165};
2248 for (place = 14; place < sizeof(channel_all); place++) {
2249 if (channel_all[place] == chnl)
2256 static void _rtl8723be_phy_lc_calibrate(struct ieee80211_hw *hw, bool is2t)
2259 u32 rf_a_mode = 0, rf_b_mode = 0, lc_cal;
2260 struct rtl_priv *rtlpriv = rtl_priv(hw);
2262 tmpreg = rtl_read_byte(rtlpriv, 0xd03);
2264 if ((tmpreg & 0x70) != 0)
2265 rtl_write_byte(rtlpriv, 0xd03, tmpreg & 0x8F);
2267 rtl_write_byte(rtlpriv, REG_TXPAUSE, 0xFF);
2269 if ((tmpreg & 0x70) != 0) {
2270 rf_a_mode = rtl_get_rfreg(hw, RF90_PATH_A, 0x00, MASK12BITS);
2273 rf_b_mode = rtl_get_rfreg(hw, RF90_PATH_B, 0x00,
2276 rtl_set_rfreg(hw, RF90_PATH_A, 0x00, MASK12BITS,
2277 (rf_a_mode & 0x8FFFF) | 0x10000);
2280 rtl_set_rfreg(hw, RF90_PATH_B, 0x00, MASK12BITS,
2281 (rf_b_mode & 0x8FFFF) | 0x10000);
2283 lc_cal = rtl_get_rfreg(hw, RF90_PATH_A, 0x18, MASK12BITS);
2285 rtl_set_rfreg(hw, RF90_PATH_A, 0xb0, RFREG_OFFSET_MASK, 0xdfbe0);
2286 rtl_set_rfreg(hw, RF90_PATH_A, 0x18, MASK12BITS, 0x8c0a);
2288 /* In order not to disturb BT music when wifi init.(1ant NIC only) */
2290 /* In order not to disturb BT music when wifi init.(1ant NIC only) */
2293 rtl_set_rfreg(hw, RF90_PATH_A, 0xb0, RFREG_OFFSET_MASK, 0xdffe0);
2295 if ((tmpreg & 0x70) != 0) {
2296 rtl_write_byte(rtlpriv, 0xd03, tmpreg);
2297 rtl_set_rfreg(hw, RF90_PATH_A, 0x00, MASK12BITS, rf_a_mode);
2300 rtl_set_rfreg(hw, RF90_PATH_B, 0x00,
2301 MASK12BITS, rf_b_mode);
2303 rtl_write_byte(rtlpriv, REG_TXPAUSE, 0x00);
2305 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "\n");
2308 static void _rtl8723be_phy_set_rfpath_switch(struct ieee80211_hw *hw,
2309 bool bmain, bool is2t)
2311 struct rtl_priv *rtlpriv = rtl_priv(hw);
2312 RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD, "\n");
2314 if (bmain) /* left antenna */
2315 rtl_set_bbreg(hw, 0x92C, MASKDWORD, 0x1);
2317 rtl_set_bbreg(hw, 0x92C, MASKDWORD, 0x2);
2320 #undef IQK_ADDA_REG_NUM
2321 #undef IQK_DELAY_TIME
2322 /* IQK is merge from Merge Temp */
2323 void rtl8723be_phy_iq_calibrate(struct ieee80211_hw *hw, bool b_recovery)
2325 struct rtl_priv *rtlpriv = rtl_priv(hw);
2326 struct rtl_phy *rtlphy = &rtlpriv->phy;
2328 u8 i, final_candidate, idx;
2329 bool b_patha_ok, b_pathb_ok;
2330 long reg_e94, reg_e9c, reg_ea4, reg_eac, reg_eb4, reg_ebc, reg_ec4;
2331 long reg_ecc, reg_tmp = 0;
2332 bool is12simular, is13simular, is23simular;
2333 u32 iqk_bb_reg[9] = {
2334 ROFDM0_XARXIQIMBALANCE,
2335 ROFDM0_XBRXIQIMBALANCE,
2336 ROFDM0_ECCATHRESHOLD,
2337 ROFDM0_AGCRSSITABLE,
2338 ROFDM0_XATXIQIMBALANCE,
2339 ROFDM0_XBTXIQIMBALANCE,
2344 u32 path_sel_bb = 0; /* path_sel_rf = 0 */
2346 if (rtlphy->lck_inprogress)
2349 spin_lock(&rtlpriv->locks.iqk_lock);
2350 rtlphy->lck_inprogress = true;
2351 spin_unlock(&rtlpriv->locks.iqk_lock);
2354 rtl8723_phy_reload_adda_registers(hw, iqk_bb_reg,
2355 rtlphy->iqk_bb_backup, 9);
2359 path_sel_bb = rtl_get_bbreg(hw, 0x948, MASKDWORD);
2360 /* path_sel_rf = rtl_get_rfreg(hw, RF90_PATH_A, 0xb0, 0xfffff); */
2362 for (i = 0; i < 8; i++) {
2368 final_candidate = 0xff;
2371 is12simular = false;
2372 is23simular = false;
2373 is13simular = false;
2374 for (i = 0; i < 3; i++) {
2375 _rtl8723be_phy_iq_calibrate(hw, result, i, true);
2377 is12simular = _rtl8723be_phy_simularity_compare(hw,
2381 final_candidate = 0;
2386 is13simular = _rtl8723be_phy_simularity_compare(hw,
2390 final_candidate = 0;
2393 is23simular = _rtl8723be_phy_simularity_compare(hw,
2397 final_candidate = 1;
2399 for (i = 0; i < 8; i++)
2400 reg_tmp += result[3][i];
2403 final_candidate = 3;
2405 final_candidate = 0xFF;
2409 for (i = 0; i < 4; i++) {
2410 reg_e94 = result[i][0];
2411 reg_e9c = result[i][1];
2412 reg_ea4 = result[i][2];
2413 reg_eac = result[i][3];
2414 reg_eb4 = result[i][4];
2415 reg_ebc = result[i][5];
2416 reg_ec4 = result[i][6];
2417 reg_ecc = result[i][7];
2419 if (final_candidate != 0xff) {
2420 reg_e94 = result[final_candidate][0];
2421 rtlphy->reg_e94 = reg_e94;
2422 reg_e9c = result[final_candidate][1];
2423 rtlphy->reg_e9c = reg_e9c;
2424 reg_ea4 = result[final_candidate][2];
2425 reg_eac = result[final_candidate][3];
2426 reg_eb4 = result[final_candidate][4];
2427 rtlphy->reg_eb4 = reg_eb4;
2428 reg_ebc = result[final_candidate][5];
2429 rtlphy->reg_ebc = reg_ebc;
2430 reg_ec4 = result[final_candidate][6];
2431 reg_ecc = result[final_candidate][7];
2435 rtlphy->reg_e94 = 0x100;
2436 rtlphy->reg_eb4 = 0x100;
2437 rtlphy->reg_e9c = 0x0;
2438 rtlphy->reg_ebc = 0x0;
2441 rtl8723_phy_path_a_fill_iqk_matrix(hw, b_patha_ok, result,
2445 _rtl8723be_phy_path_b_fill_iqk_matrix(hw, b_pathb_ok, result,
2449 idx = _get_right_chnl_place_for_iqk(rtlphy->current_channel);
2451 if (final_candidate < 4) {
2452 for (i = 0; i < IQK_MATRIX_REG_NUM; i++)
2453 rtlphy->iqk_matrix[idx].value[0][i] =
2454 result[final_candidate][i];
2455 rtlphy->iqk_matrix[idx].iqk_done = true;
2458 rtl8723_save_adda_registers(hw, iqk_bb_reg,
2459 rtlphy->iqk_bb_backup, 9);
2461 rtl_set_bbreg(hw, 0x948, MASKDWORD, path_sel_bb);
2462 /* rtl_set_rfreg(hw, RF90_PATH_A, 0xb0, 0xfffff, path_sel_rf); */
2464 spin_lock(&rtlpriv->locks.iqk_lock);
2465 rtlphy->lck_inprogress = false;
2466 spin_unlock(&rtlpriv->locks.iqk_lock);
2469 void rtl8723be_phy_lc_calibrate(struct ieee80211_hw *hw)
2471 struct rtl_priv *rtlpriv = rtl_priv(hw);
2472 struct rtl_phy *rtlphy = &rtlpriv->phy;
2473 struct rtl_hal *rtlhal = &rtlpriv->rtlhal;
2474 u32 timeout = 2000, timecount = 0;
2476 while (rtlpriv->mac80211.act_scanning && timecount < timeout) {
2481 rtlphy->lck_inprogress = true;
2482 RTPRINT(rtlpriv, FINIT, INIT_IQK,
2483 "LCK:Start!!! currentband %x delay %d ms\n",
2484 rtlhal->current_bandtype, timecount);
2486 _rtl8723be_phy_lc_calibrate(hw, false);
2488 rtlphy->lck_inprogress = false;
2491 void rtl8723be_phy_set_rfpath_switch(struct ieee80211_hw *hw, bool bmain)
2493 _rtl8723be_phy_set_rfpath_switch(hw, bmain, true);
2496 bool rtl8723be_phy_set_io_cmd(struct ieee80211_hw *hw, enum io_type iotype)
2498 struct rtl_priv *rtlpriv = rtl_priv(hw);
2499 struct rtl_phy *rtlphy = &rtlpriv->phy;
2500 bool b_postprocessing = false;
2502 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2503 "-->IO Cmd(%#x), set_io_inprogress(%d)\n",
2504 iotype, rtlphy->set_io_inprogress);
2507 case IO_CMD_RESUME_DM_BY_SCAN:
2508 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2509 "[IO CMD] Resume DM after scan.\n");
2510 b_postprocessing = true;
2512 case IO_CMD_PAUSE_BAND0_DM_BY_SCAN:
2513 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2514 "[IO CMD] Pause DM before scan.\n");
2515 b_postprocessing = true;
2518 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
2519 "switch case %#x not processed\n", iotype);
2523 if (b_postprocessing && !rtlphy->set_io_inprogress) {
2524 rtlphy->set_io_inprogress = true;
2525 rtlphy->current_io_type = iotype;
2529 rtl8723be_phy_set_io(hw);
2530 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE, "IO Type(%#x)\n", iotype);
2534 static void rtl8723be_phy_set_io(struct ieee80211_hw *hw)
2536 struct rtl_priv *rtlpriv = rtl_priv(hw);
2537 struct dig_t *dm_digtable = &rtlpriv->dm_digtable;
2538 struct rtl_phy *rtlphy = &rtlpriv->phy;
2540 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2541 "--->Cmd(%#x), set_io_inprogress(%d)\n",
2542 rtlphy->current_io_type, rtlphy->set_io_inprogress);
2543 switch (rtlphy->current_io_type) {
2544 case IO_CMD_RESUME_DM_BY_SCAN:
2545 dm_digtable->cur_igvalue = rtlphy->initgain_backup.xaagccore1;
2546 /*rtl92c_dm_write_dig(hw);*/
2547 rtl8723be_phy_set_txpower_level(hw, rtlphy->current_channel);
2548 rtl_set_bbreg(hw, RCCK0_CCA, 0xff0000, 0x83);
2550 case IO_CMD_PAUSE_BAND0_DM_BY_SCAN:
2551 rtlphy->initgain_backup.xaagccore1 = dm_digtable->cur_igvalue;
2552 dm_digtable->cur_igvalue = 0x17;
2553 rtl_set_bbreg(hw, RCCK0_CCA, 0xff0000, 0x40);
2556 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
2557 "switch case %#x not processed\n",
2558 rtlphy->current_io_type);
2561 rtlphy->set_io_inprogress = false;
2562 RT_TRACE(rtlpriv, COMP_CMD, DBG_TRACE,
2563 "(%#x)\n", rtlphy->current_io_type);
2566 static void rtl8723be_phy_set_rf_on(struct ieee80211_hw *hw)
2568 struct rtl_priv *rtlpriv = rtl_priv(hw);
2570 rtl_write_byte(rtlpriv, REG_SPS0_CTRL, 0x2b);
2571 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE3);
2572 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE2);
2573 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE3);
2574 rtl_write_byte(rtlpriv, REG_TXPAUSE, 0x00);
2577 static void _rtl8723be_phy_set_rf_sleep(struct ieee80211_hw *hw)
2579 struct rtl_priv *rtlpriv = rtl_priv(hw);
2581 rtl_write_byte(rtlpriv, REG_TXPAUSE, 0xFF);
2582 rtl_set_rfreg(hw, RF90_PATH_A, 0x00, RFREG_OFFSET_MASK, 0x00);
2583 rtl_write_byte(rtlpriv, REG_SYS_FUNC_EN, 0xE2);
2584 rtl_write_byte(rtlpriv, REG_SPS0_CTRL, 0x22);
2587 static bool _rtl8723be_phy_set_rf_power_state(struct ieee80211_hw *hw,
2588 enum rf_pwrstate rfpwr_state)
2590 struct rtl_priv *rtlpriv = rtl_priv(hw);
2591 struct rtl_pci_priv *pcipriv = rtl_pcipriv(hw);
2592 struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
2593 struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
2594 bool bresult = true;
2596 struct rtl8192_tx_ring *ring = NULL;
2598 switch (rfpwr_state) {
2600 if ((ppsc->rfpwr_state == ERFOFF) &&
2601 RT_IN_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_HALT_NIC)) {
2603 u32 initializecount = 0;
2606 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2607 "IPS Set eRf nic enable\n");
2608 rtstatus = rtl_ps_enable_nic(hw);
2609 } while (!rtstatus && (initializecount < 10));
2610 RT_CLEAR_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_HALT_NIC);
2612 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2613 "Set ERFON sleeped:%d ms\n",
2614 jiffies_to_msecs(jiffies -
2615 ppsc->last_sleep_jiffies));
2616 ppsc->last_awake_jiffies = jiffies;
2617 rtl8723be_phy_set_rf_on(hw);
2619 if (mac->link_state == MAC80211_LINKED)
2620 rtlpriv->cfg->ops->led_control(hw, LED_CTL_LINK);
2622 rtlpriv->cfg->ops->led_control(hw, LED_CTL_NO_LINK);
2627 for (queue_id = 0, i = 0;
2628 queue_id < RTL_PCI_MAX_TX_QUEUE_COUNT;) {
2629 ring = &pcipriv->dev.tx_ring[queue_id];
2630 /* Don't check BEACON Q.
2631 * BEACON Q is always not empty,
2632 * because '_rtl8723be_cmd_send_packet'
2634 if (queue_id == BEACON_QUEUE ||
2635 skb_queue_len(&ring->queue) == 0) {
2639 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2640 "eRf Off/Sleep: %d times TcbBusyQueue[%d] =%d before doze!\n",
2642 skb_queue_len(&ring->queue));
2647 if (i >= MAX_DOZE_WAITING_TIMES_9x) {
2648 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2649 "ERFSLEEP: %d times TcbBusyQueue[%d] = %d !\n",
2650 MAX_DOZE_WAITING_TIMES_9x,
2652 skb_queue_len(&ring->queue));
2657 if (ppsc->reg_rfps_level & RT_RF_OFF_LEVL_HALT_NIC) {
2658 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2659 "IPS Set eRf nic disable\n");
2660 rtl_ps_disable_nic(hw);
2661 RT_SET_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_HALT_NIC);
2663 if (ppsc->rfoff_reason == RF_CHANGE_BY_IPS) {
2664 rtlpriv->cfg->ops->led_control(hw,
2667 rtlpriv->cfg->ops->led_control(hw,
2674 if (ppsc->rfpwr_state == ERFOFF)
2676 for (queue_id = 0, i = 0;
2677 queue_id < RTL_PCI_MAX_TX_QUEUE_COUNT;) {
2678 ring = &pcipriv->dev.tx_ring[queue_id];
2679 if (skb_queue_len(&ring->queue) == 0) {
2683 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2684 "eRf Off/Sleep: %d times TcbBusyQueue[%d] =%d before doze!\n",
2686 skb_queue_len(&ring->queue));
2691 if (i >= MAX_DOZE_WAITING_TIMES_9x) {
2692 RT_TRACE(rtlpriv, COMP_ERR, DBG_WARNING,
2693 "ERFSLEEP: %d times TcbBusyQueue[%d] = %d !\n",
2694 MAX_DOZE_WAITING_TIMES_9x,
2696 skb_queue_len(&ring->queue));
2700 RT_TRACE(rtlpriv, COMP_RF, DBG_DMESG,
2701 "Set ERFSLEEP awaked:%d ms\n",
2702 jiffies_to_msecs(jiffies -
2703 ppsc->last_awake_jiffies));
2704 ppsc->last_sleep_jiffies = jiffies;
2705 _rtl8723be_phy_set_rf_sleep(hw);
2709 RT_TRACE(rtlpriv, COMP_ERR, DBG_LOUD,
2710 "switch case %#x not processed\n", rfpwr_state);
2715 ppsc->rfpwr_state = rfpwr_state;
2719 bool rtl8723be_phy_set_rf_power_state(struct ieee80211_hw *hw,
2720 enum rf_pwrstate rfpwr_state)
2722 struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
2724 bool bresult = false;
2726 if (rfpwr_state == ppsc->rfpwr_state)
2728 bresult = _rtl8723be_phy_set_rf_power_state(hw, rfpwr_state);