1 /******************************************************************************
3 * Copyright(c) 2007 - 2011 Realtek Corporation. All rights reserved.
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 * You should have received a copy of the GNU General Public License along with
15 * this program; if not, write to the Free Software Foundation, Inc.,
16 * 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
19 ******************************************************************************/
21 #include "mp_precomp.h"
22 #include "phydm_precomp.h"
24 #ifndef index_mapping_NUM_88E
25 #define index_mapping_NUM_88E 15
28 /* #if(DM_ODM_SUPPORT_TYPE & ODM_WIN) */
30 #define CALCULATE_SWINGTALBE_OFFSET(_offset, _direction, _size, _delta_thermal) \
32 for (_offset = 0; _offset < _size; _offset++) { \
34 if (_delta_thermal < thermal_threshold[_direction][_offset]) { \
41 if (_offset >= _size)\
46 void configure_txpower_track(
48 struct _TXPWRTRACK_CFG *p_config
51 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
53 #if (DM_ODM_SUPPORT_TYPE == ODM_WIN)
54 /* if (IS_HARDWARE_TYPE_8812(p_dm_odm->adapter)) */
55 if (p_dm_odm->support_ic_type == ODM_RTL8812)
56 configure_txpower_track_8812a(p_config);
62 if (p_dm_odm->support_ic_type == ODM_RTL8814A)
63 configure_txpower_track_8814a(p_config);
68 if (p_dm_odm->support_ic_type == ODM_RTL8188E)
69 configure_txpower_track_8188e(p_config);
73 if (p_dm_odm->support_ic_type == ODM_RTL8197F)
74 configure_txpower_track_8197f(p_config);
78 if (p_dm_odm->support_ic_type == ODM_RTL8822B)
79 configure_txpower_track_8822b(p_config);
85 #if (RTL8192E_SUPPORT == 1)
87 odm_txpowertracking_callback_thermal_meter_92e(
88 #if (DM_ODM_SUPPORT_TYPE & ODM_AP)
91 struct _ADAPTER *adapter
95 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
96 u8 thermal_value = 0, delta, delta_IQK, delta_LCK, channel, is_decrease, rf_mimo_mode;
97 u8 thermal_value_avg_count = 0;
98 u8 OFDM_min_index = 10; /* OFDM BB Swing should be less than +2.5dB, which is required by Arthur */
99 s8 OFDM_index[2], index ;
100 u32 thermal_value_avg = 0, reg0x18;
101 u32 i = 0, j = 0, rf;
102 s32 value32, CCK_index = 0, ele_A, ele_D, ele_C, X, Y;
103 struct rtl8192cd_priv *priv = p_dm_odm->priv;
105 rf_mimo_mode = p_dm_odm->rf_type;
106 /* ODM_RT_TRACE(p_dm_odm,ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,("%s:%d rf_mimo_mode:%d\n", __FUNCTION__, __LINE__, rf_mimo_mode)); */
109 if ((OPMODE & WIFI_MP_STATE) || priv->pshare->rf_ft_var.mp_specific) {
110 channel = priv->pshare->working_channel;
111 if (priv->pshare->mp_txpwr_tracking == false)
116 channel = (priv->pmib->dot11RFEntry.dot11channel);
119 thermal_value = (unsigned char)odm_get_rf_reg(p_dm_odm, RF_PATH_A, ODM_RF_T_METER_92E, 0xfc00); /* 0x42: RF Reg[15:10] 88E */
120 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\nReadback Thermal Meter = 0x%x pre thermal meter 0x%x EEPROMthermalmeter 0x%x\n", thermal_value, priv->pshare->thermal_value, priv->pmib->dot11RFEntry.ther));
123 switch (rf_mimo_mode) {
135 /* Query OFDM path A default setting Bit[31:21] */
136 ele_D = phy_query_bb_reg(priv, REG_OFDM_0_XA_TX_IQ_IMBALANCE, MASKOFDM_D);
137 for (i = 0; i < OFDM_TABLE_SIZE_92E; i++) {
138 if (ele_D == (ofdm_swing_table_92e[i] >> 22)) {
139 OFDM_index[0] = (unsigned char)i;
140 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("PathA 0xC80[31:22] = 0x%x, OFDM_index=%d\n", ele_D, OFDM_index[0]));
145 /* Query OFDM path B default setting */
146 if (rf_mimo_mode == MIMO_2T2R) {
147 ele_D = phy_query_bb_reg(priv, REG_OFDM_0_XB_TX_IQ_IMBALANCE, MASKOFDM_D);
148 for (i = 0; i < OFDM_TABLE_SIZE_92E; i++) {
149 if (ele_D == (ofdm_swing_table_92e[i] >> 22)) {
150 OFDM_index[1] = (unsigned char)i;
151 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("PathB 0xC88[31:22] = 0x%x, OFDM_index=%d\n", ele_D, OFDM_index[1]));
157 /* calculate average thermal meter */
159 priv->pshare->thermal_value_avg_88xx[priv->pshare->thermal_value_avg_index_88xx] = thermal_value;
160 priv->pshare->thermal_value_avg_index_88xx++;
161 if (priv->pshare->thermal_value_avg_index_88xx == AVG_THERMAL_NUM_88XX)
162 priv->pshare->thermal_value_avg_index_88xx = 0;
164 for (i = 0; i < AVG_THERMAL_NUM_88XX; i++) {
165 if (priv->pshare->thermal_value_avg_88xx[i]) {
166 thermal_value_avg += priv->pshare->thermal_value_avg_88xx[i];
167 thermal_value_avg_count++;
171 if (thermal_value_avg_count) {
172 thermal_value = (unsigned char)(thermal_value_avg / thermal_value_avg_count);
173 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("AVG Thermal Meter = 0x%x\n", thermal_value));
178 if (!priv->pshare->thermal_value) {
179 priv->pshare->thermal_value = priv->pmib->dot11RFEntry.ther;
180 priv->pshare->thermal_value_iqk = thermal_value;
181 priv->pshare->thermal_value_lck = thermal_value;
184 if (thermal_value != priv->pshare->thermal_value) {
185 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\n******** START POWER TRACKING ********\n"));
186 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\nReadback Thermal Meter = 0x%x pre thermal meter 0x%x EEPROMthermalmeter 0x%x\n", thermal_value, priv->pshare->thermal_value, priv->pmib->dot11RFEntry.ther));
188 delta = RTL_ABS(thermal_value, priv->pmib->dot11RFEntry.ther);
189 delta_IQK = RTL_ABS(thermal_value, priv->pshare->thermal_value_iqk);
190 delta_LCK = RTL_ABS(thermal_value, priv->pshare->thermal_value_lck);
191 is_decrease = ((thermal_value < priv->pmib->dot11RFEntry.ther) ? 1 : 0);
193 #ifdef _TRACKING_TABLE_FILE
194 if (priv->pshare->rf_ft_var.pwr_track_file) {
195 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("diff: (%s)%d ==> get index from table : %d)\n", (is_decrease ? "-" : "+"), delta, get_tx_tracking_index(priv, channel, i, delta, is_decrease, 0)));
198 for (i = 0; i < rf; i++) {
199 OFDM_index[i] = priv->pshare->OFDM_index0[i] + get_tx_tracking_index(priv, channel, i, delta, is_decrease, 0);
200 OFDM_index[i] = ((OFDM_index[i] > (OFDM_TABLE_SIZE_92E- 1)) ? (OFDM_TABLE_SIZE_92E - 1) : OFDM_index[i]);
201 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> decrese power ---> new OFDM_INDEX:%d (%d + %d)\n", OFDM_index[i], priv->pshare->OFDM_index0[i], get_tx_tracking_index(priv, channel, i, delta, is_decrease, 0)));
202 CCK_index = priv->pshare->CCK_index0 + get_tx_tracking_index(priv, channel, i, delta, is_decrease, 1);
203 CCK_index = ((CCK_index > (CCK_TABLE_SIZE_92E - 1)) ? (CCK_TABLE_SIZE_92E - 1) : CCK_index);
204 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> Decrese power ---> new CCK_INDEX:%d (%d + %d)\n", CCK_index, priv->pshare->CCK_index0, get_tx_tracking_index(priv, channel, i, delta, is_decrease, 1)));
207 for (i = 0; i < rf; i++) {
208 OFDM_index[i] = priv->pshare->OFDM_index0[i] - get_tx_tracking_index(priv, channel, i, delta, is_decrease, 0);
209 OFDM_index[i] = ((OFDM_index[i] < OFDM_min_index) ? OFDM_min_index : OFDM_index[i]);
210 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> Increse power ---> new OFDM_INDEX:%d (%d - %d)\n", OFDM_index[i], priv->pshare->OFDM_index0[i], get_tx_tracking_index(priv, channel, i, delta, is_decrease, 0)));
211 CCK_index = priv->pshare->CCK_index0 - get_tx_tracking_index(priv, channel, i, delta, is_decrease, 1);
212 CCK_index = ((CCK_index < 0) ? 0 : CCK_index);
213 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> Increse power ---> new CCK_INDEX:%d (%d - %d)\n", CCK_index, priv->pshare->CCK_index0, get_tx_tracking_index(priv, channel, i, delta, is_decrease, 1)));
217 #endif /* CFG_TRACKING_TABLE_FILE */
219 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("ofdm_swing_table_92e[(unsigned int)OFDM_index[0]] = %x\n", ofdm_swing_table_92e[(unsigned int)OFDM_index[0]]));
220 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("ofdm_swing_table_92e[(unsigned int)OFDM_index[1]] = %x\n", ofdm_swing_table_92e[(unsigned int)OFDM_index[1]]));
222 /* Adujst OFDM Ant_A according to IQK result */
223 ele_D = (ofdm_swing_table_92e[(unsigned int)OFDM_index[0]] & 0xFFC00000) >> 22;
224 X = priv->pshare->rege94;
225 Y = priv->pshare->rege9c;
228 if ((X & 0x00000200) != 0)
230 ele_A = ((X * ele_D) >> 8) & 0x000003FF;
232 /* new element C = element D x Y */
233 if ((Y & 0x00000200) != 0)
235 ele_C = ((Y * ele_D) >> 8) & 0x000003FF;
237 /* wirte new elements A, C, D to regC80 and regC94, element B is always 0 */
238 value32 = (ele_D << 22) | ((ele_C & 0x3F) << 16) | ele_A;
239 phy_set_bb_reg(priv, REG_OFDM_0_XA_TX_IQ_IMBALANCE, MASKDWORD, value32);
241 value32 = (ele_C & 0x000003C0) >> 6;
242 phy_set_bb_reg(priv, REG_OFDM_0_XC_TX_AFE, MASKH4BITS, value32);
244 value32 = ((X * ele_D) >> 7) & 0x01;
245 phy_set_bb_reg(priv, REG_OFDM_0_ECCA_THRESHOLD, BIT(24), value32);
247 phy_set_bb_reg(priv, REG_OFDM_0_XA_TX_IQ_IMBALANCE, MASKDWORD, ofdm_swing_table_92e[(unsigned int)OFDM_index[0]]);
248 phy_set_bb_reg(priv, REG_OFDM_0_XC_TX_AFE, MASKH4BITS, 0x00);
249 phy_set_bb_reg(priv, REG_OFDM_0_ECCA_THRESHOLD, BIT(24), 0x00);
252 set_CCK_swing_index(priv, CCK_index);
255 ele_D = (ofdm_swing_table_92e[(unsigned int)OFDM_index[1]] & 0xFFC00000) >> 22;
256 X = priv->pshare->regeb4;
257 Y = priv->pshare->regebc;
260 if ((X & 0x00000200) != 0) /* consider minus */
262 ele_A = ((X * ele_D) >> 8) & 0x000003FF;
264 /* new element C = element D x Y */
265 if ((Y & 0x00000200) != 0)
267 ele_C = ((Y * ele_D) >> 8) & 0x00003FF;
269 /* wirte new elements A, C, D to regC88 and regC9C, element B is always 0 */
270 value32 = (ele_D << 22) | ((ele_C & 0x3F) << 16) | ele_A;
271 phy_set_bb_reg(priv, REG_OFDM_0_XB_TX_IQ_IMBALANCE, MASKDWORD, value32);
273 value32 = (ele_C & 0x000003C0) >> 6;
274 phy_set_bb_reg(priv, REG_OFDM_0_XD_TX_AFE, MASKH4BITS, value32);
276 value32 = ((X * ele_D) >> 7) & 0x01;
277 phy_set_bb_reg(priv, REG_OFDM_0_ECCA_THRESHOLD, BIT(28), value32);
279 phy_set_bb_reg(priv, REG_OFDM_0_XB_TX_IQ_IMBALANCE, MASKDWORD, ofdm_swing_table_92e[(unsigned int)OFDM_index[1]]);
280 phy_set_bb_reg(priv, REG_OFDM_0_XD_TX_AFE, MASKH4BITS, 0x00);
281 phy_set_bb_reg(priv, REG_OFDM_0_ECCA_THRESHOLD, BIT(28), 0x00);
286 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("0xc80 = 0x%x\n", phy_query_bb_reg(priv, REG_OFDM_0_XA_TX_IQ_IMBALANCE, MASKDWORD)));
287 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("0xc88 = 0x%x\n", phy_query_bb_reg(priv, REG_OFDM_0_XB_TX_IQ_IMBALANCE, MASKDWORD)));
290 priv->pshare->thermal_value_iqk = thermal_value;
292 if (!(priv->pshare->rf_ft_var.mp_specific && (OPMODE & (WIFI_MP_CTX_BACKGROUND | WIFI_MP_CTX_PACKET))))
294 phy_iq_calibrate_8192e(p_dm_odm, false);
299 reg0x18 = phy_query_rf_reg(priv, RF_PATH_A, 0x18, MASK20BITS, 1);
300 phy_set_rf_reg(priv, RF_PATH_A, 0xB4, BIT(14), 1);
301 phy_set_rf_reg(priv, RF_PATH_A, 0x18, BIT(15), 1);
303 phy_set_rf_reg(priv, RF_PATH_A, 0xB4, BIT(14), 0);
304 phy_set_rf_reg(priv, RF_PATH_A, 0x18, MASK20BITS, reg0x18);
306 priv->pshare->thermal_value_lck = thermal_value;
310 /* update thermal meter value */
311 priv->pshare->thermal_value = thermal_value;
312 for (i = 0 ; i < rf ; i++)
313 priv->pshare->OFDM_index[i] = OFDM_index[i];
314 priv->pshare->CCK_index = CCK_index;
316 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\n******** END:%s() ********\n", __FUNCTION__));
322 #if (RTL8197F_SUPPORT == 1 || RTL8822B_SUPPORT == 1)
324 odm_txpowertracking_callback_thermal_meter_jaguar_series3(
325 #if (DM_ODM_SUPPORT_TYPE & ODM_AP)
328 struct _ADAPTER *adapter
333 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
334 u8 thermal_value = 0, delta, delta_LCK, delta_IQK, channel, is_increase;
335 u8 thermal_value_avg_count = 0, p = 0, i = 0;
336 u32 thermal_value_avg = 0;
337 struct rtl8192cd_priv *priv = p_dm_odm->priv;
338 struct _TXPWRTRACK_CFG c;
339 struct odm_rf_calibration_structure *p_rf_calibrate_info = &(p_dm_odm->rf_calibrate_info);
341 /*4 1. The following TWO tables decide the final index of OFDM/CCK swing table.*/
342 u8 *delta_swing_table_idx_tup_a = NULL, *delta_swing_table_idx_tdown_a = NULL;
343 u8 *delta_swing_table_idx_tup_b = NULL, *delta_swing_table_idx_tdown_b = NULL;
344 u8 *delta_swing_table_idx_tup_cck_a = NULL, *delta_swing_table_idx_tdown_cck_a = NULL;
345 u8 *delta_swing_table_idx_tup_cck_b = NULL, *delta_swing_table_idx_tdown_cck_b = NULL;
346 /*for 8814 add by Yu Chen*/
347 u8 *delta_swing_table_idx_tup_c = NULL, *delta_swing_table_idx_tdown_c = NULL;
348 u8 *delta_swing_table_idx_tup_d = NULL, *delta_swing_table_idx_tdown_d = NULL;
349 u8 *delta_swing_table_idx_tup_cck_c = NULL, *delta_swing_table_idx_tdown_cck_c = NULL;
350 u8 *delta_swing_table_idx_tup_cck_d = NULL, *delta_swing_table_idx_tdown_cck_d = NULL;
353 if ((OPMODE & WIFI_MP_STATE) || priv->pshare->rf_ft_var.mp_specific) {
354 channel = priv->pshare->working_channel;
355 if (priv->pshare->mp_txpwr_tracking == false)
360 channel = (priv->pmib->dot11RFEntry.dot11channel);
363 configure_txpower_track(p_dm_odm, &c);
365 (*c.get_delta_all_swing_table)(p_dm_odm, (u8 **)&delta_swing_table_idx_tup_a, (u8 **)&delta_swing_table_idx_tdown_a,
366 (u8 **)&delta_swing_table_idx_tup_b, (u8 **)&delta_swing_table_idx_tdown_b,
367 (u8 **)&delta_swing_table_idx_tup_cck_a, (u8 **)&delta_swing_table_idx_tdown_cck_a,
368 (u8 **)&delta_swing_table_idx_tup_cck_b, (u8 **)&delta_swing_table_idx_tdown_cck_b);
370 thermal_value = (u8)odm_get_rf_reg(p_dm_odm, ODM_RF_PATH_A, c.thermal_reg_addr, 0xfc00); /*0x42: RF Reg[15:10] 88E*/
372 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
373 ("Readback Thermal Meter = 0x%x(%d) EEPROMthermalmeter 0x%x(%d)\n"
374 , thermal_value, thermal_value, priv->pmib->dot11RFEntry.ther, priv->pmib->dot11RFEntry.ther));
377 if (!p_dm_odm->rf_calibrate_info.thermal_value)
378 p_dm_odm->rf_calibrate_info.thermal_value = priv->pmib->dot11RFEntry.ther;
380 if (!p_dm_odm->rf_calibrate_info.thermal_value_lck)
381 p_dm_odm->rf_calibrate_info.thermal_value_lck = priv->pmib->dot11RFEntry.ther;
383 if (!p_dm_odm->rf_calibrate_info.thermal_value_iqk)
384 p_dm_odm->rf_calibrate_info.thermal_value_iqk = priv->pmib->dot11RFEntry.ther;
386 /* calculate average thermal meter */
387 p_dm_odm->rf_calibrate_info.thermal_value_avg[p_dm_odm->rf_calibrate_info.thermal_value_avg_index] = thermal_value;
388 p_dm_odm->rf_calibrate_info.thermal_value_avg_index++;
390 if (p_dm_odm->rf_calibrate_info.thermal_value_avg_index == c.average_thermal_num) /*Average times = c.average_thermal_num*/
391 p_dm_odm->rf_calibrate_info.thermal_value_avg_index = 0;
393 for (i = 0; i < c.average_thermal_num; i++) {
394 if (p_dm_odm->rf_calibrate_info.thermal_value_avg[i]) {
395 thermal_value_avg += p_dm_odm->rf_calibrate_info.thermal_value_avg[i];
396 thermal_value_avg_count++;
400 if (thermal_value_avg_count) {/*Calculate Average thermal_value after average enough times*/
401 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
402 ("thermal_value_avg=0x%x(%d) thermal_value_avg_count = %d\n"
403 , thermal_value_avg, thermal_value_avg, thermal_value_avg_count));
405 thermal_value = (u8)(thermal_value_avg / thermal_value_avg_count);
407 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
408 ("AVG Thermal Meter = 0x%X(%d), EEPROMthermalmeter = 0x%X(%d)\n", thermal_value, thermal_value, priv->pmib->dot11RFEntry.ther, priv->pmib->dot11RFEntry.ther));
411 /*4 Calculate delta, delta_LCK, delta_IQK.*/
412 delta = RTL_ABS(thermal_value, priv->pmib->dot11RFEntry.ther);
413 delta_LCK = RTL_ABS(thermal_value, p_dm_odm->rf_calibrate_info.thermal_value_lck);
414 delta_IQK = RTL_ABS(thermal_value, p_dm_odm->rf_calibrate_info.thermal_value_iqk);
415 is_increase = ((thermal_value < priv->pmib->dot11RFEntry.ther) ? 0 : 1);
417 if (delta > 29) { /* power track table index(thermal diff.) upper bound*/
418 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("delta(%d) > 29, set delta to 29\n", delta));
423 /*4 if necessary, do LCK.*/
425 if (delta_LCK > c.threshold_iqk) {
426 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("delta_LCK(%d) >= threshold_iqk(%d)\n", delta_LCK, c.threshold_iqk));
427 p_dm_odm->rf_calibrate_info.thermal_value_lck = thermal_value;
428 if (c.phy_lc_calibrate)
429 (*c.phy_lc_calibrate)(p_dm_odm);
432 if (delta_IQK > c.threshold_iqk) {
433 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("delta_IQK(%d) >= threshold_iqk(%d)\n", delta_IQK, c.threshold_iqk));
434 p_dm_odm->rf_calibrate_info.thermal_value_iqk = thermal_value;
436 (*c.do_iqk)(p_dm_odm, true, 0, 0);
439 if (!priv->pmib->dot11RFEntry.ther) /*Don't do power tracking since no calibrated thermal value*/
442 /*4 Do Power Tracking*/
444 if (thermal_value != p_dm_odm->rf_calibrate_info.thermal_value) {
445 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
446 ("\n\n******** START POWER TRACKING ********\n"));
447 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
448 ("Readback Thermal Meter = 0x%x pre thermal meter 0x%x EEPROMthermalmeter 0x%x\n",
449 thermal_value, p_dm_odm->rf_calibrate_info.thermal_value, priv->pmib->dot11RFEntry.ther));
451 #ifdef _TRACKING_TABLE_FILE
452 if (priv->pshare->rf_ft_var.pwr_track_file) {
453 if (is_increase) { /*thermal is higher than base*/
454 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++) {
457 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
458 ("delta_swing_table_idx_tup_b[%d] = %d delta_swing_table_idx_tup_cck_b[%d] = %d\n", delta, delta_swing_table_idx_tup_b[delta], delta, delta_swing_table_idx_tup_cck_b[delta]));
459 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_b[delta];
460 p_rf_calibrate_info->absolute_cck_swing_idx[p] = delta_swing_table_idx_tup_cck_b[delta];
461 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
462 ("******Temp is higher and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_B] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_B] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
466 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
467 ("delta_swing_table_idx_tup_c[%d] = %d delta_swing_table_idx_tup_cck_c[%d] = %d\n", delta, delta_swing_table_idx_tup_c[delta], delta, delta_swing_table_idx_tup_cck_c[delta]));
468 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_c[delta];
469 p_rf_calibrate_info->absolute_cck_swing_idx[p] = delta_swing_table_idx_tup_cck_c[delta];
470 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
471 ("******Temp is higher and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_C] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_C] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
475 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
476 ("delta_swing_table_idx_tup_d[%d] = %d delta_swing_table_idx_tup_cck_d[%d] = %d\n", delta, delta_swing_table_idx_tup_d[delta], delta, delta_swing_table_idx_tup_cck_d[delta]));
477 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_d[delta];
478 p_rf_calibrate_info->absolute_cck_swing_idx[p] = delta_swing_table_idx_tup_cck_d[delta];
479 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
480 ("******Temp is higher and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_D] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_D] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
483 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
484 ("delta_swing_table_idx_tup_a[%d] = %d delta_swing_table_idx_tup_cck_a[%d] = %d\n", delta, delta_swing_table_idx_tup_a[delta], delta, delta_swing_table_idx_tup_cck_a[delta]));
485 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_a[delta];
486 p_rf_calibrate_info->absolute_cck_swing_idx[p] = delta_swing_table_idx_tup_cck_a[delta];
487 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
488 ("******Temp is higher and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_A] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_A] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
492 } else { /* thermal is lower than base*/
493 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++) {
496 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
497 ("delta_swing_table_idx_tdown_b[%d] = %d delta_swing_table_idx_tdown_cck_b[%d] = %d\n", delta, delta_swing_table_idx_tdown_b[delta], delta, delta_swing_table_idx_tdown_cck_b[delta]));
498 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_b[delta];
499 p_rf_calibrate_info->absolute_cck_swing_idx[p] = -1 * delta_swing_table_idx_tdown_cck_b[delta];
500 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
501 ("******Temp is lower and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_B] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_B] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
505 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
506 ("delta_swing_table_idx_tdown_c[%d] = %d delta_swing_table_idx_tdown_cck_c[%d] = %d\n", delta, delta_swing_table_idx_tdown_c[delta], delta, delta_swing_table_idx_tdown_cck_c[delta]));
507 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_c[delta];
508 p_rf_calibrate_info->absolute_cck_swing_idx[p] = -1 * delta_swing_table_idx_tdown_cck_c[delta];
509 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
510 ("******Temp is lower and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_C] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_C] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
514 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
515 ("delta_swing_table_idx_tdown_d[%d] = %d delta_swing_table_idx_tdown_cck_d[%d] = %d\n", delta, delta_swing_table_idx_tdown_d[delta], delta, delta_swing_table_idx_tdown_cck_d[delta]));
516 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_d[delta];
517 p_rf_calibrate_info->absolute_cck_swing_idx[p] = -1 * delta_swing_table_idx_tdown_cck_d[delta];
518 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
519 ("******Temp is lower and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_D] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_D] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
523 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
524 ("delta_swing_table_idx_tdown_a[%d] = %d delta_swing_table_idx_tdown_cck_a[%d] = %d\n", delta, delta_swing_table_idx_tdown_a[delta], delta, delta_swing_table_idx_tdown_cck_a[delta]));
525 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_a[delta];
526 p_rf_calibrate_info->absolute_cck_swing_idx[p] = -1 * delta_swing_table_idx_tdown_cck_a[delta];
527 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
528 ("******Temp is lower and pRF->absolute_ofdm_swing_idx[ODM_RF_PATH_A] = %d pRF->absolute_cck_swing_idx[ODM_RF_PATH_A] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p], p_rf_calibrate_info->absolute_cck_swing_idx[p]));
535 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> increse power --->\n"));
536 if (GET_CHIP_VER(priv) == VERSION_8197F) {
537 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
538 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, BBSWING, p, 0);
539 } else if (GET_CHIP_VER(priv) == VERSION_8822B) {
540 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
541 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, MIX_MODE, p, 0);
544 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> decrese power --->\n"));
545 if (GET_CHIP_VER(priv) == VERSION_8197F) {
546 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
547 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, BBSWING, p, 0);
548 } else if (GET_CHIP_VER(priv) == VERSION_8822B) {
549 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
550 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, MIX_MODE, p, 0);
556 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\n******** END:%s() ********\n\n", __func__));
557 /*update thermal meter value*/
558 p_dm_odm->rf_calibrate_info.thermal_value = thermal_value;
566 /*#if (RTL8814A_SUPPORT == 1)*/
567 #if (RTL8814A_SUPPORT == 1)
570 odm_txpowertracking_callback_thermal_meter_jaguar_series2(
571 #if (DM_ODM_SUPPORT_TYPE & ODM_AP)
574 struct _ADAPTER *adapter
578 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
579 u8 thermal_value = 0, delta, delta_LCK, delta_IQK, channel, is_increase;
580 u8 thermal_value_avg_count = 0, p = 0, i = 0;
581 u32 thermal_value_avg = 0, reg0x18;
582 u32 bb_swing_reg[4] = {REG_A_TX_SCALE_JAGUAR, REG_B_TX_SCALE_JAGUAR, REG_C_TX_SCALE_JAGUAR2, REG_D_TX_SCALE_JAGUAR2};
585 struct rtl8192cd_priv *priv = p_dm_odm->priv;
586 struct _TXPWRTRACK_CFG c;
587 boolean is_tssi_enable = false;
588 struct odm_rf_calibration_structure *p_rf_calibrate_info = &(p_dm_odm->rf_calibrate_info);
590 /* 4 1. The following TWO tables decide the final index of OFDM/CCK swing table. */
591 u8 *delta_swing_table_idx_tup_a = NULL, *delta_swing_table_idx_tdown_a = NULL;
592 u8 *delta_swing_table_idx_tup_b = NULL, *delta_swing_table_idx_tdown_b = NULL;
593 /* for 8814 add by Yu Chen */
594 u8 *delta_swing_table_idx_tup_c = NULL, *delta_swing_table_idx_tdown_c = NULL;
595 u8 *delta_swing_table_idx_tup_d = NULL, *delta_swing_table_idx_tdown_d = NULL;
598 if ((OPMODE & WIFI_MP_STATE) || priv->pshare->rf_ft_var.mp_specific) {
599 channel = priv->pshare->working_channel;
600 if (priv->pshare->mp_txpwr_tracking == false)
605 channel = (priv->pmib->dot11RFEntry.dot11channel);
608 configure_txpower_track(p_dm_odm, &c);
609 p_rf_calibrate_info->default_ofdm_index = priv->pshare->OFDM_index0[ODM_RF_PATH_A];
611 (*c.get_delta_swing_table)(p_dm_odm, (u8 **)&delta_swing_table_idx_tup_a, (u8 **)&delta_swing_table_idx_tdown_a,
612 (u8 **)&delta_swing_table_idx_tup_b, (u8 **)&delta_swing_table_idx_tdown_b);
614 if (p_dm_odm->support_ic_type & ODM_RTL8814A) /* for 8814 path C & D */
615 (*c.get_delta_swing_table8814only)(p_dm_odm, (u8 **)&delta_swing_table_idx_tup_c, (u8 **)&delta_swing_table_idx_tdown_c,
616 (u8 **)&delta_swing_table_idx_tup_d, (u8 **)&delta_swing_table_idx_tdown_d);
618 thermal_value = (u8)odm_get_rf_reg(p_dm_odm, ODM_RF_PATH_A, c.thermal_reg_addr, 0xfc00); /* 0x42: RF Reg[15:10] 88E */
619 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
620 ("\nReadback Thermal Meter = 0x%x, pre thermal meter 0x%x, EEPROMthermalmeter 0x%x\n", thermal_value, p_dm_odm->rf_calibrate_info.thermal_value, priv->pmib->dot11RFEntry.ther));
623 if (!p_dm_odm->rf_calibrate_info.thermal_value)
624 p_dm_odm->rf_calibrate_info.thermal_value = priv->pmib->dot11RFEntry.ther;
626 if (!p_dm_odm->rf_calibrate_info.thermal_value_lck)
627 p_dm_odm->rf_calibrate_info.thermal_value_lck = priv->pmib->dot11RFEntry.ther;
629 if (!p_dm_odm->rf_calibrate_info.thermal_value_iqk)
630 p_dm_odm->rf_calibrate_info.thermal_value_iqk = priv->pmib->dot11RFEntry.ther;
632 is_tssi_enable = (boolean)odm_get_rf_reg(p_dm_odm, ODM_RF_PATH_A, REG_RF_TX_GAIN_OFFSET, BIT(7)); /* check TSSI enable */
634 /* 4 Query OFDM BB swing default setting Bit[31:21] */
635 for (p = ODM_RF_PATH_A ; p < c.rf_path_count ; p++) {
636 ele_D = odm_get_bb_reg(p_dm_odm, bb_swing_reg[p], 0xffe00000);
637 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
638 ("0x%x:0x%x ([31:21] = 0x%x)\n", bb_swing_reg[p], odm_get_bb_reg(p_dm_odm, bb_swing_reg[p], MASKDWORD), ele_D));
640 for (bb_swing_idx = 0; bb_swing_idx < TXSCALE_TABLE_SIZE; bb_swing_idx++) {/* 4 */
641 if (ele_D == tx_scaling_table_jaguar[bb_swing_idx]) {
642 p_dm_odm->rf_calibrate_info.OFDM_index[p] = (u8)bb_swing_idx;
643 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
644 ("OFDM_index[%d]=%d\n", p, p_dm_odm->rf_calibrate_info.OFDM_index[p]));
648 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("kfree_offset[%d]=%d\n", p, p_rf_calibrate_info->kfree_offset[p]));
652 /* calculate average thermal meter */
653 p_dm_odm->rf_calibrate_info.thermal_value_avg[p_dm_odm->rf_calibrate_info.thermal_value_avg_index] = thermal_value;
654 p_dm_odm->rf_calibrate_info.thermal_value_avg_index++;
655 if (p_dm_odm->rf_calibrate_info.thermal_value_avg_index == c.average_thermal_num) /* Average times = c.average_thermal_num */
656 p_dm_odm->rf_calibrate_info.thermal_value_avg_index = 0;
658 for (i = 0; i < c.average_thermal_num; i++) {
659 if (p_dm_odm->rf_calibrate_info.thermal_value_avg[i]) {
660 thermal_value_avg += p_dm_odm->rf_calibrate_info.thermal_value_avg[i];
661 thermal_value_avg_count++;
665 if (thermal_value_avg_count) { /* Calculate Average thermal_value after average enough times */
666 thermal_value = (u8)(thermal_value_avg / thermal_value_avg_count);
667 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
668 ("AVG Thermal Meter = 0x%X, EEPROMthermalmeter = 0x%X\n", thermal_value, priv->pmib->dot11RFEntry.ther));
671 /* 4 Calculate delta, delta_LCK, delta_IQK. */
672 delta = RTL_ABS(thermal_value, priv->pmib->dot11RFEntry.ther);
673 delta_LCK = RTL_ABS(thermal_value, p_dm_odm->rf_calibrate_info.thermal_value_lck);
674 delta_IQK = RTL_ABS(thermal_value, p_dm_odm->rf_calibrate_info.thermal_value_iqk);
675 is_increase = ((thermal_value < priv->pmib->dot11RFEntry.ther) ? 0 : 1);
677 /* 4 if necessary, do LCK. */
678 if (!(p_dm_odm->support_ic_type & ODM_RTL8821)) {
679 if (delta_LCK > c.threshold_iqk) {
680 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("delta_LCK(%d) >= threshold_iqk(%d)\n", delta_LCK, c.threshold_iqk));
681 p_dm_odm->rf_calibrate_info.thermal_value_lck = thermal_value;
683 /*Use RTLCK, so close power tracking driver LCK*/
684 #if (RTL8814A_SUPPORT != 1)
685 if (!(p_dm_odm->support_ic_type & ODM_RTL8814A)) {
686 if (c.phy_lc_calibrate)
687 (*c.phy_lc_calibrate)(p_dm_odm);
693 if (delta_IQK > c.threshold_iqk) {
694 panic_printk("%s(%d)\n", __FUNCTION__, __LINE__);
695 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("delta_IQK(%d) >= threshold_iqk(%d)\n", delta_IQK, c.threshold_iqk));
696 p_dm_odm->rf_calibrate_info.thermal_value_iqk = thermal_value;
698 (*c.do_iqk)(p_dm_odm, true, 0, 0);
701 if (!priv->pmib->dot11RFEntry.ther) /*Don't do power tracking since no calibrated thermal value*/
704 /* 4 Do Power Tracking */
706 if (is_tssi_enable == true) {
707 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("**********Enter PURE TSSI MODE**********\n"));
708 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
709 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, TSSI_MODE, p, 0);
710 } else if (thermal_value != p_dm_odm->rf_calibrate_info.thermal_value) {
711 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
712 ("\n******** START POWER TRACKING ********\n"));
713 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
714 ("\nReadback Thermal Meter = 0x%x pre thermal meter 0x%x EEPROMthermalmeter 0x%x\n", thermal_value, p_dm_odm->rf_calibrate_info.thermal_value, priv->pmib->dot11RFEntry.ther));
716 #ifdef _TRACKING_TABLE_FILE
717 if (priv->pshare->rf_ft_var.pwr_track_file) {
718 if (is_increase) { /* thermal is higher than base */
719 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++) {
722 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
723 ("delta_swing_table_idx_tup_b[%d] = %d\n", delta, delta_swing_table_idx_tup_b[delta]));
724 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_b[delta]; /* Record delta swing for mix mode power tracking */
725 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
726 ("******Temp is higher and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_B] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
730 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
731 ("delta_swing_table_idx_tup_c[%d] = %d\n", delta, delta_swing_table_idx_tup_c[delta]));
732 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_c[delta]; /* Record delta swing for mix mode power tracking */
733 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
734 ("******Temp is higher and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_C] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
738 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
739 ("delta_swing_table_idx_tup_d[%d] = %d\n", delta, delta_swing_table_idx_tup_d[delta]));
740 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_d[delta]; /* Record delta swing for mix mode power tracking */
741 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
742 ("******Temp is higher and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_D] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
746 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
747 ("delta_swing_table_idx_tup_a[%d] = %d\n", delta, delta_swing_table_idx_tup_a[delta]));
748 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = delta_swing_table_idx_tup_a[delta]; /* Record delta swing for mix mode power tracking */
749 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
750 ("******Temp is higher and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_A] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
754 } else { /* thermal is lower than base */
755 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++) {
758 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
759 ("delta_swing_table_idx_tdown_b[%d] = %d\n", delta, delta_swing_table_idx_tdown_b[delta]));
760 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_b[delta]; /* Record delta swing for mix mode power tracking */
761 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
762 ("******Temp is lower and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_B] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
766 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
767 ("delta_swing_table_idx_tdown_c[%d] = %d\n", delta, delta_swing_table_idx_tdown_c[delta]));
768 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_c[delta]; /* Record delta swing for mix mode power tracking */
769 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
770 ("******Temp is lower and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_C] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
774 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
775 ("delta_swing_table_idx_tdown_d[%d] = %d\n", delta, delta_swing_table_idx_tdown_d[delta]));
776 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_d[delta]; /* Record delta swing for mix mode power tracking */
777 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
778 ("******Temp is lower and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_D] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
782 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
783 ("delta_swing_table_idx_tdown_a[%d] = %d\n", delta, delta_swing_table_idx_tdown_a[delta]));
784 p_rf_calibrate_info->absolute_ofdm_swing_idx[p] = -1 * delta_swing_table_idx_tdown_a[delta]; /* Record delta swing for mix mode power tracking */
785 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
786 ("******Temp is lower and p_dm_odm->absolute_ofdm_swing_idx[ODM_RF_PATH_A] = %d\n", p_rf_calibrate_info->absolute_ofdm_swing_idx[p]));
793 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> increse power --->\n"));
794 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
795 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, MIX_MODE, p, 0);
797 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> decrese power --->\n"));
798 for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
799 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, MIX_MODE, p, 0);
804 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\n******** END:%s() ********\n", __FUNCTION__));
805 /* update thermal meter value */
806 p_dm_odm->rf_calibrate_info.thermal_value = thermal_value;
812 #if (RTL8812A_SUPPORT == 1 || RTL8881A_SUPPORT == 1)
814 odm_txpowertracking_callback_thermal_meter_jaguar_series(
815 #if (DM_ODM_SUPPORT_TYPE & ODM_AP)
818 struct _ADAPTER *adapter
822 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
823 unsigned char thermal_value = 0, delta, delta_LCK, channel, is_decrease;
824 unsigned char thermal_value_avg_count = 0;
825 unsigned int thermal_value_avg = 0, reg0x18;
826 unsigned int bb_swing_reg[4] = {0xc1c, 0xe1c, 0x181c, 0x1a1c};
828 char OFDM_index[2], index;
829 unsigned int i = 0, j = 0, rf_path, max_rf_path = 2, rf;
830 struct rtl8192cd_priv *priv = p_dm_odm->priv;
831 unsigned char OFDM_min_index = 7; /* OFDM BB Swing should be less than +2.5dB, which is required by Arthur and Mimic */
836 if ((OPMODE & WIFI_MP_STATE) || priv->pshare->rf_ft_var.mp_specific) {
837 channel = priv->pshare->working_channel;
838 if (priv->pshare->mp_txpwr_tracking == false)
843 channel = (priv->pmib->dot11RFEntry.dot11channel);
847 if (p_dm_odm->support_ic_type == ODM_RTL8881A) {
849 if ((get_bonding_type_8881A() == BOND_8881AM || get_bonding_type_8881A() == BOND_8881AN)
850 && priv->pshare->rf_ft_var.use_intpa8881A && (*p_dm_odm->p_band_type == ODM_BAND_2_4G))
851 OFDM_min_index = 6; /* intPA - upper bond set to +3 dB (base: -2 dB)ot11RFEntry.phy_band_select == PHY_BAND_2G)) */
853 OFDM_min_index = 10; /* OFDM BB Swing should be less than +1dB, which is required by Arthur and Mimic */
858 thermal_value = (unsigned char)phy_query_rf_reg(priv, RF_PATH_A, 0x42, 0xfc00, 1); /* 0x42: RF Reg[15:10] 88E */
859 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\nReadback Thermal Meter = 0x%x pre thermal meter 0x%x EEPROMthermalmeter 0x%x\n", thermal_value, priv->pshare->thermal_value, priv->pmib->dot11RFEntry.ther));
862 /* 4 Query OFDM BB swing default setting Bit[31:21] */
863 for (rf_path = 0 ; rf_path < max_rf_path ; rf_path++) {
864 ele_D = phy_query_bb_reg(priv, bb_swing_reg[rf_path], 0xffe00000);
865 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("0x%x:0x%x ([31:21] = 0x%x)\n", bb_swing_reg[rf_path], phy_query_bb_reg(priv, bb_swing_reg[rf_path], MASKDWORD), ele_D));
866 for (i = 0; i < OFDM_TABLE_SIZE_8812; i++) {/* 4 */
867 if (ele_D == ofdm_swing_table_8812[i]) {
868 OFDM_index[rf_path] = (unsigned char)i;
869 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("OFDM_index[%d]=%d\n", rf_path, OFDM_index[rf_path]));
875 /* Query OFDM path A default setting Bit[31:21] */
876 ele_D = phy_query_bb_reg(priv, 0xc1c, 0xffe00000);
877 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("0xc1c:0x%x ([31:21] = 0x%x)\n", phy_query_bb_reg(priv, 0xc1c, MASKDWORD), ele_D));
878 for (i = 0; i < OFDM_TABLE_SIZE_8812; i++) {/* 4 */
879 if (ele_D == ofdm_swing_table_8812[i]) {
880 OFDM_index[0] = (unsigned char)i;
881 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("OFDM_index[0]=%d\n", OFDM_index[0]));
885 /* Query OFDM path B default setting */
887 ele_D = phy_query_bb_reg(priv, 0xe1c, 0xffe00000);
888 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("0xe1c:0x%x ([32:21] = 0x%x)\n", phy_query_bb_reg(priv, 0xe1c, MASKDWORD), ele_D));
889 for (i = 0; i < OFDM_TABLE_SIZE_8812; i++) {
890 if (ele_D == ofdm_swing_table_8812[i]) {
891 OFDM_index[1] = (unsigned char)i;
892 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("OFDM_index[1]=%d\n", OFDM_index[1]));
899 if (!priv->pshare->thermal_value) {
900 priv->pshare->thermal_value = priv->pmib->dot11RFEntry.ther;
901 priv->pshare->thermal_value_lck = thermal_value;
904 /* calculate average thermal meter */
906 priv->pshare->thermal_value_avg_8812[priv->pshare->thermal_value_avg_index_8812] = thermal_value;
907 priv->pshare->thermal_value_avg_index_8812++;
908 if (priv->pshare->thermal_value_avg_index_8812 == AVG_THERMAL_NUM_8812)
909 priv->pshare->thermal_value_avg_index_8812 = 0;
911 for (i = 0; i < AVG_THERMAL_NUM_8812; i++) {
912 if (priv->pshare->thermal_value_avg_8812[i]) {
913 thermal_value_avg += priv->pshare->thermal_value_avg_8812[i];
914 thermal_value_avg_count++;
918 if (thermal_value_avg_count) {
919 thermal_value = (unsigned char)(thermal_value_avg / thermal_value_avg_count);
920 /* printk("AVG Thermal Meter = 0x%x\n", thermal_value); */
925 /* 4 If necessary, do power tracking */
927 if (!priv->pmib->dot11RFEntry.ther) /*Don't do power tracking since no calibrated thermal value*/
930 if (thermal_value != priv->pshare->thermal_value) {
931 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\n******** START POWER TRACKING ********\n"));
932 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\nReadback Thermal Meter = 0x%x pre thermal meter 0x%x EEPROMthermalmeter 0x%x\n", thermal_value, priv->pshare->thermal_value, priv->pmib->dot11RFEntry.ther));
933 delta = RTL_ABS(thermal_value, priv->pmib->dot11RFEntry.ther);
934 delta_LCK = RTL_ABS(thermal_value, priv->pshare->thermal_value_lck);
935 is_decrease = ((thermal_value < priv->pmib->dot11RFEntry.ther) ? 1 : 0);
936 /* if (*p_dm_odm->p_band_type == ODM_BAND_5G) */
938 #ifdef _TRACKING_TABLE_FILE
939 if (priv->pshare->rf_ft_var.pwr_track_file) {
940 for (rf_path = 0; rf_path < max_rf_path; rf_path++) {
941 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("diff: (%s)%d ==> get index from table : %d)\n", (is_decrease ? "-" : "+"), delta, get_tx_tracking_index(priv, channel, rf_path, delta, is_decrease, 0)));
943 OFDM_index[rf_path] = priv->pshare->OFDM_index0[rf_path] + get_tx_tracking_index(priv, channel, rf_path, delta, is_decrease, 0);
944 OFDM_index[rf_path] = ((OFDM_index[rf_path] > (OFDM_TABLE_SIZE_8812 - 1)) ? (OFDM_TABLE_SIZE_8812 - 1) : OFDM_index[rf_path]);
945 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> decrese power ---> new OFDM_INDEX:%d (%d + %d)\n", OFDM_index[rf_path], priv->pshare->OFDM_index0[rf_path], get_tx_tracking_index(priv, channel, rf_path, delta, is_decrease, 0)));
946 #if 0/* RTL8881A_SUPPORT */
947 if (p_dm_odm->support_ic_type == ODM_RTL8881A) {
948 if (priv->pshare->rf_ft_var.pwrtrk_tx_agc_enable) {
949 if (priv->pshare->add_tx_agc) { /* tx_agc has been added */
950 add_tx_power88xx_ac(priv, 0);
951 priv->pshare->add_tx_agc = 0;
952 priv->pshare->add_tx_agc_index = 0;
959 OFDM_index[rf_path] = priv->pshare->OFDM_index0[rf_path] - get_tx_tracking_index(priv, channel, rf_path, delta, is_decrease, 0);
960 #if 0/* RTL8881A_SUPPORT */
961 if (p_dm_odm->support_ic_type == ODM_RTL8881A) {
962 if (priv->pshare->rf_ft_var.pwrtrk_tx_agc_enable) {
963 if (OFDM_index[i] < OFDM_min_index) {
964 priv->pshare->add_tx_agc_index = (OFDM_min_index - OFDM_index[i]) / 2; /* Calculate Remnant tx_agc value, 2 index for 1 tx_agc */
965 add_tx_power88xx_ac(priv, priv->pshare->add_tx_agc_index);
966 priv->pshare->add_tx_agc = 1; /* add_tx_agc Flag = 1 */
967 OFDM_index[i] = OFDM_min_index;
969 if (priv->pshare->add_tx_agc) { /* tx_agc been added */
970 priv->pshare->add_tx_agc = 0;
971 priv->pshare->add_tx_agc_index = 0;
972 add_tx_power88xx_ac(priv, 0); /* minus the added TPI */
978 OFDM_index[rf_path] = ((OFDM_index[rf_path] < OFDM_min_index) ? OFDM_min_index : OFDM_index[rf_path]);
980 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, (">>> increse power ---> new OFDM_INDEX:%d (%d - %d)\n", OFDM_index[rf_path], priv->pshare->OFDM_index0[rf_path], get_tx_tracking_index(priv, channel, rf_path, delta, is_decrease, 0)));
985 /* 4 Set new BB swing index */
986 for (rf_path = 0; rf_path < max_rf_path; rf_path++) {
987 phy_set_bb_reg(priv, bb_swing_reg[rf_path], 0xffe00000, ofdm_swing_table_8812[(unsigned int)OFDM_index[rf_path]]);
988 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("Readback 0x%x[31:21] = 0x%x, OFDM_index:%d\n", bb_swing_reg[rf_path], phy_query_bb_reg(priv, bb_swing_reg[rf_path], 0xffe00000), OFDM_index[rf_path]));
994 reg0x18 = phy_query_rf_reg(priv, RF_PATH_A, 0x18, MASK20BITS, 1);
995 phy_set_rf_reg(priv, RF_PATH_A, 0xB4, BIT(14), 1);
996 phy_set_rf_reg(priv, RF_PATH_A, 0x18, BIT(15), 1);
997 delay_ms(200); /* frequency deviation */
998 phy_set_rf_reg(priv, RF_PATH_A, 0xB4, BIT(14), 0);
999 phy_set_rf_reg(priv, RF_PATH_A, 0x18, MASK20BITS, reg0x18);
1000 #ifdef CONFIG_RTL_8812_SUPPORT
1001 if (GET_CHIP_VER(priv) == VERSION_8812E)
1002 update_bbrf_val8812(priv, priv->pmib->dot11RFEntry.dot11channel);
1005 priv->pshare->thermal_value_lck = thermal_value;
1007 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("\n******** END:%s() ********\n", __FUNCTION__));
1009 /* update thermal meter value */
1010 priv->pshare->thermal_value = thermal_value;
1011 for (rf_path = 0; rf_path < max_rf_path; rf_path++)
1012 priv->pshare->OFDM_index[rf_path] = OFDM_index[rf_path];
1020 odm_txpowertracking_callback_thermal_meter(
1021 #if (DM_ODM_SUPPORT_TYPE & ODM_AP)
1024 struct _ADAPTER *adapter
1028 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
1029 struct odm_rf_calibration_structure *p_rf_calibrate_info = &(p_dm_odm->rf_calibrate_info);
1032 #if (RTL8197F_SUPPORT == 1 || RTL8822B_SUPPORT == 1)
1033 if (p_dm_odm->support_ic_type == ODM_RTL8197F || p_dm_odm->support_ic_type == ODM_RTL8822B) {
1034 odm_txpowertracking_callback_thermal_meter_jaguar_series3(p_dm_odm);
1038 #if (RTL8814A_SUPPORT == 1) /*use this function to do power tracking after 8814 by YuChen*/
1039 if (p_dm_odm->support_ic_type & ODM_RTL8814A) {
1040 odm_txpowertracking_callback_thermal_meter_jaguar_series2(p_dm_odm);
1044 #if (RTL8881A_SUPPORT || RTL8812A_SUPPORT == 1)
1045 if (p_dm_odm->support_ic_type & ODM_RTL8812 || p_dm_odm->support_ic_type & ODM_RTL8881A) {
1046 odm_txpowertracking_callback_thermal_meter_jaguar_series(p_dm_odm);
1051 #if (RTL8192E_SUPPORT == 1)
1052 if (p_dm_odm->support_ic_type == ODM_RTL8192E) {
1053 odm_txpowertracking_callback_thermal_meter_92e(p_dm_odm);
1058 #if !(DM_ODM_SUPPORT_TYPE & ODM_AP)
1059 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(adapter);
1060 /* PMGNT_INFO p_mgnt_info = &adapter->mgnt_info; */
1064 u8 thermal_value = 0, delta, delta_LCK, delta_IQK, offset;
1065 u8 thermal_value_avg_count = 0;
1066 u32 thermal_value_avg = 0;
1067 /* s32 ele_A=0, ele_D, TempCCk, X, value32;
1069 * s8 OFDM_index[2], CCK_index=0, OFDM_index_old[2]={0,0}, CCK_index_old=0, index;
1070 * s8 deltaPowerIndex = 0; */
1071 u32 i = 0;/* , j = 0; */
1072 boolean is2T = false;
1073 /* bool bInteralPA = false; */
1075 u8 OFDM_max_index = 34, rf = (is2T) ? 2 : 1; /* OFDM BB Swing should be less than +3.0dB, which is required by Arthur */
1076 u8 indexforchannel = 0;/*get_right_chnl_place_for_iqk(p_hal_data->current_channel)*/
1077 enum _POWER_DEC_INC { POWER_DEC, POWER_INC };
1078 #if (DM_ODM_SUPPORT_TYPE == ODM_CE)
1079 struct PHY_DM_STRUCT *p_dm_odm = &p_hal_data->odmpriv;
1081 #if (DM_ODM_SUPPORT_TYPE == ODM_WIN)
1082 struct PHY_DM_STRUCT *p_dm_odm = &p_hal_data->DM_OutSrc;
1085 struct _TXPWRTRACK_CFG c;
1088 /* 4 1. The following TWO tables decide the final index of OFDM/CCK swing table. */
1089 s8 delta_swing_table_idx[2][index_mapping_NUM_88E] = {
1090 /* {{Power decreasing(lower temperature)}, {Power increasing(higher temperature)}} */
1091 {0, 0, 2, 3, 4, 4, 5, 6, 7, 7, 8, 9, 10, 10, 11}, {0, 0, 1, 2, 3, 4, 4, 4, 4, 5, 7, 8, 9, 9, 10}
1093 u8 thermal_threshold[2][index_mapping_NUM_88E] = {
1094 /* {{Power decreasing(lower temperature)}, {Power increasing(higher temperature)}} */
1095 {0, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 26, 27}, {0, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 22, 25, 25, 25}
1098 #if (DM_ODM_SUPPORT_TYPE & ODM_AP)
1099 struct rtl8192cd_priv *priv = p_dm_odm->priv;
1102 /* 4 2. Initilization ( 7 steps in total ) */
1104 configure_txpower_track(p_dm_odm, &c);
1106 p_dm_odm->rf_calibrate_info.txpowertracking_callback_cnt++; /* cosa add for debug */
1107 p_dm_odm->rf_calibrate_info.is_txpowertracking_init = true;
1109 #if (MP_DRIVER == 1)
1110 p_dm_odm->rf_calibrate_info.txpowertrack_control = p_hal_data->txpowertrack_control; /* <Kordan> We should keep updating the control variable according to HalData.
1111 * <Kordan> rf_calibrate_info.rega24 will be initialized when ODM HW configuring, but MP configures with para files. */
1112 p_dm_odm->rf_calibrate_info.rega24 = 0x090e1317;
1115 #if (DM_ODM_SUPPORT_TYPE == ODM_AP) && defined(MP_TEST)
1116 if ((OPMODE & WIFI_MP_STATE) || p_dm_odm->priv->pshare->rf_ft_var.mp_specific) {
1117 if (p_dm_odm->priv->pshare->mp_txpwr_tracking == false)
1121 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("===>odm_txpowertracking_callback_thermal_meter_8188e, p_dm_odm->bb_swing_idx_cck_base: %d, p_dm_odm->bb_swing_idx_ofdm_base: %d\n", p_rf_calibrate_info->bb_swing_idx_cck_base, p_rf_calibrate_info->bb_swing_idx_ofdm_base));
1123 if (!p_dm_odm->rf_calibrate_info.tm_trigger) {
1124 odm_set_rf_reg(p_dm_odm, RF_PATH_A, c.thermal_reg_addr, BIT(17) | BIT(16), 0x3);
1125 p_dm_odm->rf_calibrate_info.tm_trigger = 1;
1129 thermal_value = (u8)odm_get_rf_reg(p_dm_odm, RF_PATH_A, c.thermal_reg_addr, 0xfc00); /* 0x42: RF Reg[15:10] 88E */
1130 #if !(DM_ODM_SUPPORT_TYPE & ODM_AP)
1131 if (!thermal_value || !p_dm_odm->rf_calibrate_info.txpowertrack_control)
1133 if (!p_dm_odm->rf_calibrate_info.txpowertrack_control)
1137 /* 4 3. Initialize ThermalValues of rf_calibrate_info */
1139 if (!p_dm_odm->rf_calibrate_info.thermal_value) {
1140 p_dm_odm->rf_calibrate_info.thermal_value_lck = thermal_value;
1141 p_dm_odm->rf_calibrate_info.thermal_value_iqk = thermal_value;
1144 if (p_dm_odm->rf_calibrate_info.is_reloadtxpowerindex)
1145 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("reload ofdm index for band switch\n"));
1147 /* 4 4. Calculate average thermal meter */
1149 p_dm_odm->rf_calibrate_info.thermal_value_avg[p_dm_odm->rf_calibrate_info.thermal_value_avg_index] = thermal_value;
1150 p_dm_odm->rf_calibrate_info.thermal_value_avg_index++;
1151 if (p_dm_odm->rf_calibrate_info.thermal_value_avg_index == c.average_thermal_num)
1152 p_dm_odm->rf_calibrate_info.thermal_value_avg_index = 0;
1154 for (i = 0; i < c.average_thermal_num; i++) {
1155 if (p_dm_odm->rf_calibrate_info.thermal_value_avg[i]) {
1156 thermal_value_avg += p_dm_odm->rf_calibrate_info.thermal_value_avg[i];
1157 thermal_value_avg_count++;
1161 if (thermal_value_avg_count) {
1162 /* Give the new thermo value a weighting */
1163 thermal_value_avg += (thermal_value * 4);
1165 thermal_value = (u8)(thermal_value_avg / (thermal_value_avg_count + 4));
1166 p_rf_calibrate_info->thermal_value_delta = thermal_value - priv->pmib->dot11RFEntry.ther;
1167 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("AVG Thermal Meter = 0x%x\n", thermal_value));
1170 /* 4 5. Calculate delta, delta_LCK, delta_IQK. */
1172 delta = (thermal_value > p_dm_odm->rf_calibrate_info.thermal_value) ? (thermal_value - p_dm_odm->rf_calibrate_info.thermal_value) : (p_dm_odm->rf_calibrate_info.thermal_value - thermal_value);
1173 delta_LCK = (thermal_value > p_dm_odm->rf_calibrate_info.thermal_value_lck) ? (thermal_value - p_dm_odm->rf_calibrate_info.thermal_value_lck) : (p_dm_odm->rf_calibrate_info.thermal_value_lck - thermal_value);
1174 delta_IQK = (thermal_value > p_dm_odm->rf_calibrate_info.thermal_value_iqk) ? (thermal_value - p_dm_odm->rf_calibrate_info.thermal_value_iqk) : (p_dm_odm->rf_calibrate_info.thermal_value_iqk - thermal_value);
1176 /* 4 6. If necessary, do LCK. */
1177 if (!(p_dm_odm->support_ic_type & ODM_RTL8821)) {
1178 /*if((delta_LCK > p_hal_data->delta_lck) && (p_hal_data->delta_lck != 0))*/
1179 if (delta_LCK >= c.threshold_iqk) {
1180 /*Delta temperature is equal to or larger than 20 centigrade.*/
1181 p_dm_odm->rf_calibrate_info.thermal_value_lck = thermal_value;
1182 (*c.phy_lc_calibrate)(p_dm_odm);
1186 /* 3 7. If necessary, move the index of swing table to adjust Tx power. */
1188 if (delta > 0 && p_dm_odm->rf_calibrate_info.txpowertrack_control) {
1189 #if (DM_ODM_SUPPORT_TYPE & (ODM_WIN | ODM_CE))
1190 delta = thermal_value > p_hal_data->eeprom_thermal_meter ? (thermal_value - p_hal_data->eeprom_thermal_meter) : (p_hal_data->eeprom_thermal_meter - thermal_value);
1192 delta = (thermal_value > p_dm_odm->priv->pmib->dot11RFEntry.ther) ? (thermal_value - p_dm_odm->priv->pmib->dot11RFEntry.ther) : (p_dm_odm->priv->pmib->dot11RFEntry.ther - thermal_value);
1196 /* 4 7.1 The Final Power index = BaseIndex + power_index_offset */
1198 #if (DM_ODM_SUPPORT_TYPE & (ODM_WIN | ODM_CE))
1199 if (thermal_value > p_hal_data->eeprom_thermal_meter) {
1201 if (thermal_value > p_dm_odm->priv->pmib->dot11RFEntry.ther) {
1203 CALCULATE_SWINGTALBE_OFFSET(offset, POWER_INC, index_mapping_NUM_88E, delta);
1204 p_dm_odm->rf_calibrate_info.delta_power_index_last = p_dm_odm->rf_calibrate_info.delta_power_index;
1205 p_dm_odm->rf_calibrate_info.delta_power_index = delta_swing_table_idx[POWER_INC][offset];
1209 CALCULATE_SWINGTALBE_OFFSET(offset, POWER_DEC, index_mapping_NUM_88E, delta);
1210 p_dm_odm->rf_calibrate_info.delta_power_index_last = p_dm_odm->rf_calibrate_info.delta_power_index;
1211 p_dm_odm->rf_calibrate_info.delta_power_index = (-1) * delta_swing_table_idx[POWER_DEC][offset];
1214 if (p_dm_odm->rf_calibrate_info.delta_power_index == p_dm_odm->rf_calibrate_info.delta_power_index_last)
1215 p_dm_odm->rf_calibrate_info.power_index_offset = 0;
1217 p_dm_odm->rf_calibrate_info.power_index_offset = p_dm_odm->rf_calibrate_info.delta_power_index - p_dm_odm->rf_calibrate_info.delta_power_index_last;
1219 for (i = 0; i < rf; i++)
1220 p_dm_odm->rf_calibrate_info.OFDM_index[i] = p_rf_calibrate_info->bb_swing_idx_ofdm_base + p_dm_odm->rf_calibrate_info.power_index_offset;
1221 p_dm_odm->rf_calibrate_info.CCK_index = p_rf_calibrate_info->bb_swing_idx_cck_base + p_dm_odm->rf_calibrate_info.power_index_offset;
1223 p_rf_calibrate_info->bb_swing_idx_cck = p_dm_odm->rf_calibrate_info.CCK_index;
1224 p_rf_calibrate_info->bb_swing_idx_ofdm[RF_PATH_A] = p_dm_odm->rf_calibrate_info.OFDM_index[RF_PATH_A];
1226 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("The 'CCK' final index(%d) = BaseIndex(%d) + power_index_offset(%d)\n", p_rf_calibrate_info->bb_swing_idx_cck, p_rf_calibrate_info->bb_swing_idx_cck_base, p_dm_odm->rf_calibrate_info.power_index_offset));
1227 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("The 'OFDM' final index(%d) = BaseIndex(%d) + power_index_offset(%d)\n", p_rf_calibrate_info->bb_swing_idx_ofdm[RF_PATH_A], p_rf_calibrate_info->bb_swing_idx_ofdm_base, p_dm_odm->rf_calibrate_info.power_index_offset));
1229 /* 4 7.1 Handle boundary conditions of index. */
1232 for (i = 0; i < rf; i++) {
1233 if (p_dm_odm->rf_calibrate_info.OFDM_index[i] > OFDM_max_index)
1234 p_dm_odm->rf_calibrate_info.OFDM_index[i] = OFDM_max_index;
1235 else if (p_dm_odm->rf_calibrate_info.OFDM_index[i] < 0)
1236 p_dm_odm->rf_calibrate_info.OFDM_index[i] = 0;
1239 if (p_dm_odm->rf_calibrate_info.CCK_index > c.swing_table_size_cck - 1)
1240 p_dm_odm->rf_calibrate_info.CCK_index = c.swing_table_size_cck - 1;
1241 else if (p_dm_odm->rf_calibrate_info.CCK_index < 0)
1242 p_dm_odm->rf_calibrate_info.CCK_index = 0;
1244 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
1245 ("The thermal meter is unchanged or TxPowerTracking OFF: thermal_value: %d, p_dm_odm->rf_calibrate_info.thermal_value: %d)\n", thermal_value, p_dm_odm->rf_calibrate_info.thermal_value));
1246 p_dm_odm->rf_calibrate_info.power_index_offset = 0;
1248 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
1249 ("TxPowerTracking: [CCK] Swing Current index: %d, Swing base index: %d\n", p_dm_odm->rf_calibrate_info.CCK_index, p_rf_calibrate_info->bb_swing_idx_cck_base));
1251 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,
1252 ("TxPowerTracking: [OFDM] Swing Current index: %d, Swing base index: %d\n", p_dm_odm->rf_calibrate_info.OFDM_index[RF_PATH_A], p_rf_calibrate_info->bb_swing_idx_ofdm_base));
1254 if (p_dm_odm->rf_calibrate_info.power_index_offset != 0 && p_dm_odm->rf_calibrate_info.txpowertrack_control) {
1255 /* 4 7.2 Configure the Swing Table to adjust Tx Power. */
1257 p_dm_odm->rf_calibrate_info.is_tx_power_changed = true; /* Always true after Tx Power is adjusted by power tracking. */
1259 /* 2012/04/23 MH According to Luke's suggestion, we can not write BB digital */
1260 /* to increase TX power. Otherwise, EVM will be bad. */
1262 /* 2012/04/25 MH Add for tx power tracking to set tx power in tx agc for 88E. */
1263 if (thermal_value > p_dm_odm->rf_calibrate_info.thermal_value) {
1264 /* ODM_RT_TRACE(p_dm_odm,ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, */
1265 /* ("Temperature Increasing: delta_pi: %d, delta_t: %d, Now_t: %d, EFUSE_t: %d, Last_t: %d\n", */
1266 /* p_dm_odm->rf_calibrate_info.power_index_offset, delta, thermal_value, p_hal_data->eeprom_thermal_meter, p_dm_odm->rf_calibrate_info.thermal_value)); */
1267 } else if (thermal_value < p_dm_odm->rf_calibrate_info.thermal_value) { /* Low temperature */
1268 /* ODM_RT_TRACE(p_dm_odm,ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, */
1269 /* ("Temperature Decreasing: delta_pi: %d, delta_t: %d, Now_t: %d, EFUSE_t: %d, Last_t: %d\n", */
1270 /* p_dm_odm->rf_calibrate_info.power_index_offset, delta, thermal_value, p_hal_data->eeprom_thermal_meter, p_dm_odm->rf_calibrate_info.thermal_value)); */
1272 #if !(DM_ODM_SUPPORT_TYPE & ODM_AP)
1273 if (thermal_value > p_hal_data->eeprom_thermal_meter)
1275 if (thermal_value > p_dm_odm->priv->pmib->dot11RFEntry.ther)
1278 /* ODM_RT_TRACE(p_dm_odm,ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,("Temperature(%d) hugher than PG value(%d), increases the power by tx_agc\n", thermal_value, p_hal_data->eeprom_thermal_meter)); */
1279 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, TXAGC, 0, 0);
1281 /* ODM_RT_TRACE(p_dm_odm,ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD,("Temperature(%d) lower than PG value(%d), increases the power by tx_agc\n", thermal_value, p_hal_data->eeprom_thermal_meter)); */
1282 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, BBSWING, RF_PATH_A, indexforchannel);
1284 (*c.odm_tx_pwr_track_set_pwr)(p_dm_odm, BBSWING, RF_PATH_B, indexforchannel);
1287 p_rf_calibrate_info->bb_swing_idx_cck_base = p_rf_calibrate_info->bb_swing_idx_cck;
1288 p_rf_calibrate_info->bb_swing_idx_ofdm_base = p_rf_calibrate_info->bb_swing_idx_ofdm[RF_PATH_A];
1289 p_dm_odm->rf_calibrate_info.thermal_value = thermal_value;
1293 #if !(DM_ODM_SUPPORT_TYPE & ODM_AP)
1294 /* if((delta_IQK > p_hal_data->delta_iqk) && (p_hal_data->delta_iqk != 0)) */
1295 if ((delta_IQK >= 8)) /* Delta temperature is equal to or larger than 20 centigrade. */
1296 (*c.do_iqk)(p_dm_odm, delta_IQK, thermal_value, 8);
1299 ODM_RT_TRACE(p_dm_odm, ODM_COMP_TX_PWR_TRACK, ODM_DBG_LOUD, ("<===dm_TXPowerTrackingCallback_ThermalMeter_8188E\n"));
1301 p_dm_odm->rf_calibrate_info.tx_powercount = 0;
1304 #if (DM_ODM_SUPPORT_TYPE & ODM_WIN)
1308 phy_path_a_stand_by(
1309 struct _ADAPTER *p_adapter
1312 RTPRINT(FINIT, INIT_IQK, ("path-A standby mode!\n"));
1314 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0x0);
1315 phy_set_bb_reg(p_adapter, 0x840, MASKDWORD, 0x00010000);
1316 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0x808000);
1320 * #define MAX_TOLERANCE 5
1321 * #define IQK_DELAY_TIME 1 */ /* ms */
1323 u8 /* bit0 = 1 => Tx OK, bit1 = 1 => Rx OK */
1324 phy_path_a_iqk_8192c(
1325 struct _ADAPTER *p_adapter,
1326 boolean config_path_b
1330 u32 reg_eac, reg_e94, reg_e9c, reg_ea4;
1332 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
1334 RTPRINT(FINIT, INIT_IQK, ("path A IQK!\n"));
1336 /* path-A IQK setting */
1337 RTPRINT(FINIT, INIT_IQK, ("path-A IQK setting!\n"));
1338 if (p_adapter->interface_index == 0) {
1339 phy_set_bb_reg(p_adapter, REG_TX_IQK_TONE_A, MASKDWORD, 0x10008c1f);
1340 phy_set_bb_reg(p_adapter, REG_RX_IQK_TONE_A, MASKDWORD, 0x10008c1f);
1342 phy_set_bb_reg(p_adapter, REG_TX_IQK_TONE_A, MASKDWORD, 0x10008c22);
1343 phy_set_bb_reg(p_adapter, REG_RX_IQK_TONE_A, MASKDWORD, 0x10008c22);
1346 phy_set_bb_reg(p_adapter, REG_TX_IQK_PI_A, MASKDWORD, 0x82140102);
1348 phy_set_bb_reg(p_adapter, REG_RX_IQK_PI_A, MASKDWORD, config_path_b ? 0x28160202 :
1349 IS_81xxC_VENDOR_UMC_B_CUT(p_hal_data->version_id) ? 0x28160202 : 0x28160502);
1351 /* path-B IQK setting */
1352 if (config_path_b) {
1353 phy_set_bb_reg(p_adapter, REG_TX_IQK_TONE_B, MASKDWORD, 0x10008c22);
1354 phy_set_bb_reg(p_adapter, REG_RX_IQK_TONE_B, MASKDWORD, 0x10008c22);
1355 phy_set_bb_reg(p_adapter, REG_TX_IQK_PI_B, MASKDWORD, 0x82140102);
1356 phy_set_bb_reg(p_adapter, REG_RX_IQK_PI_B, MASKDWORD, 0x28160202);
1359 /* LO calibration setting */
1360 RTPRINT(FINIT, INIT_IQK, ("LO calibration setting!\n"));
1361 phy_set_bb_reg(p_adapter, REG_IQK_AGC_RSP, MASKDWORD, 0x001028d1);
1363 /* One shot, path A LOK & IQK */
1364 RTPRINT(FINIT, INIT_IQK, ("One shot, path A LOK & IQK!\n"));
1365 phy_set_bb_reg(p_adapter, REG_IQK_AGC_PTS, MASKDWORD, 0xf9000000);
1366 phy_set_bb_reg(p_adapter, REG_IQK_AGC_PTS, MASKDWORD, 0xf8000000);
1369 RTPRINT(FINIT, INIT_IQK, ("delay %d ms for One shot, path A LOK & IQK.\n", IQK_DELAY_TIME));
1370 platform_stall_execution(IQK_DELAY_TIME * 1000);
1373 reg_eac = phy_query_bb_reg(p_adapter, REG_RX_POWER_AFTER_IQK_A_2, MASKDWORD);
1374 RTPRINT(FINIT, INIT_IQK, ("0xeac = 0x%x\n", reg_eac));
1375 reg_e94 = phy_query_bb_reg(p_adapter, REG_TX_POWER_BEFORE_IQK_A, MASKDWORD);
1376 RTPRINT(FINIT, INIT_IQK, ("0xe94 = 0x%x\n", reg_e94));
1377 reg_e9c = phy_query_bb_reg(p_adapter, REG_TX_POWER_AFTER_IQK_A, MASKDWORD);
1378 RTPRINT(FINIT, INIT_IQK, ("0xe9c = 0x%x\n", reg_e9c));
1379 reg_ea4 = phy_query_bb_reg(p_adapter, REG_RX_POWER_BEFORE_IQK_A_2, MASKDWORD);
1380 RTPRINT(FINIT, INIT_IQK, ("0xea4 = 0x%x\n", reg_ea4));
1382 if (!(reg_eac & BIT(28)) &&
1383 (((reg_e94 & 0x03FF0000) >> 16) != 0x142) &&
1384 (((reg_e9c & 0x03FF0000) >> 16) != 0x42))
1386 else /* if Tx not OK, ignore Rx */
1389 if (!(reg_eac & BIT(27)) && /* if Tx is OK, check whether Rx is OK */
1390 (((reg_ea4 & 0x03FF0000) >> 16) != 0x132) &&
1391 (((reg_eac & 0x03FF0000) >> 16) != 0x36))
1394 RTPRINT(FINIT, INIT_IQK, ("path A Rx IQK fail!!\n"));
1401 u8 /* bit0 = 1 => Tx OK, bit1 = 1 => Rx OK */
1402 phy_path_b_iqk_8192c(
1403 struct _ADAPTER *p_adapter
1406 u32 reg_eac, reg_eb4, reg_ebc, reg_ec4, reg_ecc;
1408 RTPRINT(FINIT, INIT_IQK, ("path B IQK!\n"));
1410 /* One shot, path B LOK & IQK */
1411 RTPRINT(FINIT, INIT_IQK, ("One shot, path A LOK & IQK!\n"));
1412 phy_set_bb_reg(p_adapter, REG_IQK_AGC_CONT, MASKDWORD, 0x00000002);
1413 phy_set_bb_reg(p_adapter, REG_IQK_AGC_CONT, MASKDWORD, 0x00000000);
1416 RTPRINT(FINIT, INIT_IQK, ("delay %d ms for One shot, path B LOK & IQK.\n", IQK_DELAY_TIME));
1417 platform_stall_execution(IQK_DELAY_TIME * 1000);
1420 reg_eac = phy_query_bb_reg(p_adapter, REG_RX_POWER_AFTER_IQK_A_2, MASKDWORD);
1421 RTPRINT(FINIT, INIT_IQK, ("0xeac = 0x%x\n", reg_eac));
1422 reg_eb4 = phy_query_bb_reg(p_adapter, REG_TX_POWER_BEFORE_IQK_B, MASKDWORD);
1423 RTPRINT(FINIT, INIT_IQK, ("0xeb4 = 0x%x\n", reg_eb4));
1424 reg_ebc = phy_query_bb_reg(p_adapter, REG_TX_POWER_AFTER_IQK_B, MASKDWORD);
1425 RTPRINT(FINIT, INIT_IQK, ("0xebc = 0x%x\n", reg_ebc));
1426 reg_ec4 = phy_query_bb_reg(p_adapter, REG_RX_POWER_BEFORE_IQK_B_2, MASKDWORD);
1427 RTPRINT(FINIT, INIT_IQK, ("0xec4 = 0x%x\n", reg_ec4));
1428 reg_ecc = phy_query_bb_reg(p_adapter, REG_RX_POWER_AFTER_IQK_B_2, MASKDWORD);
1429 RTPRINT(FINIT, INIT_IQK, ("0xecc = 0x%x\n", reg_ecc));
1431 if (!(reg_eac & BIT(31)) &&
1432 (((reg_eb4 & 0x03FF0000) >> 16) != 0x142) &&
1433 (((reg_ebc & 0x03FF0000) >> 16) != 0x42))
1438 if (!(reg_eac & BIT(30)) &&
1439 (((reg_ec4 & 0x03FF0000) >> 16) != 0x132) &&
1440 (((reg_ecc & 0x03FF0000) >> 16) != 0x36))
1443 RTPRINT(FINIT, INIT_IQK, ("path B Rx IQK fail!!\n"));
1451 phy_path_a_fill_iqk_matrix(
1452 struct _ADAPTER *p_adapter,
1459 u32 oldval_0, X, TX0_A, reg;
1461 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
1463 RTPRINT(FINIT, INIT_IQK, ("path A IQ Calibration %s !\n", (is_iqk_ok) ? "Success" : "Failed"));
1465 if (final_candidate == 0xFF)
1468 else if (is_iqk_ok) {
1469 oldval_0 = (phy_query_bb_reg(p_adapter, REG_OFDM_0_XA_TX_IQ_IMBALANCE, MASKDWORD) >> 22) & 0x3FF;
1471 X = result[final_candidate][0];
1472 if ((X & 0x00000200) != 0)
1474 TX0_A = (X * oldval_0) >> 8;
1475 RTPRINT(FINIT, INIT_IQK, ("X = 0x%x, TX0_A = 0x%x, oldval_0 0x%x\n", X, TX0_A, oldval_0));
1476 phy_set_bb_reg(p_adapter, REG_OFDM_0_XA_TX_IQ_IMBALANCE, 0x3FF, TX0_A);
1477 phy_set_bb_reg(p_adapter, REG_OFDM_0_ECCA_THRESHOLD, BIT(31), ((X * oldval_0 >> 7) & 0x1));
1479 Y = result[final_candidate][1];
1480 if ((Y & 0x00000200) != 0)
1483 /* path B IQK result + 3 */
1484 if (p_adapter->interface_index == 1 && p_hal_data->current_band_type == BAND_ON_5G)
1487 TX0_C = (Y * oldval_0) >> 8;
1488 RTPRINT(FINIT, INIT_IQK, ("Y = 0x%x, TX = 0x%x\n", Y, TX0_C));
1489 phy_set_bb_reg(p_adapter, REG_OFDM_0_XC_TX_AFE, 0xF0000000, ((TX0_C & 0x3C0) >> 6));
1490 phy_set_bb_reg(p_adapter, REG_OFDM_0_XA_TX_IQ_IMBALANCE, 0x003F0000, (TX0_C & 0x3F));
1491 phy_set_bb_reg(p_adapter, REG_OFDM_0_ECCA_THRESHOLD, BIT(29), ((Y * oldval_0 >> 7) & 0x1));
1494 RTPRINT(FINIT, INIT_IQK, ("phy_path_a_fill_iqk_matrix only Tx OK\n"));
1498 reg = result[final_candidate][2];
1499 phy_set_bb_reg(p_adapter, REG_OFDM_0_XA_RX_IQ_IMBALANCE, 0x3FF, reg);
1501 reg = result[final_candidate][3] & 0x3F;
1502 phy_set_bb_reg(p_adapter, REG_OFDM_0_XA_RX_IQ_IMBALANCE, 0xFC00, reg);
1504 reg = (result[final_candidate][3] >> 6) & 0xF;
1505 phy_set_bb_reg(p_adapter, REG_OFDM_0_RX_IQ_EXT_ANTA, 0xF0000000, reg);
1510 phy_path_b_fill_iqk_matrix(
1511 struct _ADAPTER *p_adapter,
1515 boolean is_tx_only /* do Tx only */
1518 u32 oldval_1, X, TX1_A, reg;
1520 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
1522 RTPRINT(FINIT, INIT_IQK, ("path B IQ Calibration %s !\n", (is_iqk_ok) ? "Success" : "Failed"));
1524 if (final_candidate == 0xFF)
1527 else if (is_iqk_ok) {
1528 oldval_1 = (phy_query_bb_reg(p_adapter, REG_OFDM_0_XB_TX_IQ_IMBALANCE, MASKDWORD) >> 22) & 0x3FF;
1530 X = result[final_candidate][4];
1531 if ((X & 0x00000200) != 0)
1533 TX1_A = (X * oldval_1) >> 8;
1534 RTPRINT(FINIT, INIT_IQK, ("X = 0x%x, TX1_A = 0x%x\n", X, TX1_A));
1535 phy_set_bb_reg(p_adapter, REG_OFDM_0_XB_TX_IQ_IMBALANCE, 0x3FF, TX1_A);
1536 phy_set_bb_reg(p_adapter, REG_OFDM_0_ECCA_THRESHOLD, BIT(27), ((X * oldval_1 >> 7) & 0x1));
1538 Y = result[final_candidate][5];
1539 if ((Y & 0x00000200) != 0)
1541 if (p_hal_data->current_band_type == BAND_ON_5G)
1542 Y += 3; /* temp modify for preformance */
1543 TX1_C = (Y * oldval_1) >> 8;
1544 RTPRINT(FINIT, INIT_IQK, ("Y = 0x%x, TX1_C = 0x%x\n", Y, TX1_C));
1545 phy_set_bb_reg(p_adapter, REG_OFDM_0_XD_TX_AFE, 0xF0000000, ((TX1_C & 0x3C0) >> 6));
1546 phy_set_bb_reg(p_adapter, REG_OFDM_0_XB_TX_IQ_IMBALANCE, 0x003F0000, (TX1_C & 0x3F));
1547 phy_set_bb_reg(p_adapter, REG_OFDM_0_ECCA_THRESHOLD, BIT(25), ((Y * oldval_1 >> 7) & 0x1));
1552 reg = result[final_candidate][6];
1553 phy_set_bb_reg(p_adapter, REG_OFDM_0_XB_RX_IQ_IMBALANCE, 0x3FF, reg);
1555 reg = result[final_candidate][7] & 0x3F;
1556 phy_set_bb_reg(p_adapter, REG_OFDM_0_XB_RX_IQ_IMBALANCE, 0xFC00, reg);
1558 reg = (result[final_candidate][7] >> 6) & 0xF;
1559 phy_set_bb_reg(p_adapter, REG_OFDM_0_AGC_RSSI_TABLE, 0x0000F000, reg);
1565 phy_simularity_compare_92c(
1566 struct _ADAPTER *p_adapter,
1572 u32 i, j, diff, simularity_bit_map, bound = 0;
1573 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
1574 u8 final_candidate[2] = {0xFF, 0xFF}; /* for path A and path B */
1575 boolean is_result = true, is2T = IS_92C_SERIAL(p_hal_data->version_id);
1582 simularity_bit_map = 0;
1584 for (i = 0; i < bound; i++) {
1585 diff = (result[c1][i] > result[c2][i]) ? (result[c1][i] - result[c2][i]) : (result[c2][i] - result[c1][i]);
1586 if (diff > MAX_TOLERANCE) {
1587 if ((i == 2 || i == 6) && !simularity_bit_map) {
1588 if (result[c1][i] + result[c1][i + 1] == 0)
1589 final_candidate[(i / 4)] = c2;
1590 else if (result[c2][i] + result[c2][i + 1] == 0)
1591 final_candidate[(i / 4)] = c1;
1593 simularity_bit_map = simularity_bit_map | (1 << i);
1595 simularity_bit_map = simularity_bit_map | (1 << i);
1599 if (simularity_bit_map == 0) {
1600 for (i = 0; i < (bound / 4); i++) {
1601 if (final_candidate[i] != 0xFF) {
1602 for (j = i * 4; j < (i + 1) * 4 - 2; j++)
1603 result[3][j] = result[final_candidate[i]][j];
1608 } else if (!(simularity_bit_map & 0x0F)) { /* path A OK */
1609 for (i = 0; i < 4; i++)
1610 result[3][i] = result[c1][i];
1612 } else if (!(simularity_bit_map & 0xF0) && is2T) { /* path B OK */
1613 for (i = 4; i < 8; i++)
1614 result[3][i] = result[c1][i];
1622 return false => do IQK again
1625 phy_simularity_compare(
1626 struct _ADAPTER *p_adapter,
1632 return phy_simularity_compare_92c(p_adapter, result, c1, c2);
1637 _phy_iq_calibrate_8192c(
1638 struct _ADAPTER *p_adapter,
1644 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
1646 u8 path_aok, path_bok;
1647 u32 ADDA_REG[IQK_ADDA_REG_NUM] = {
1648 REG_FPGA0_XCD_SWITCH_CONTROL, REG_BLUE_TOOTH,
1649 REG_RX_WAIT_CCA, REG_TX_CCK_RFON,
1650 REG_TX_CCK_BBON, REG_TX_OFDM_RFON,
1651 REG_TX_OFDM_BBON, REG_TX_TO_RX,
1652 REG_TX_TO_TX, REG_RX_CCK,
1653 REG_RX_OFDM, REG_RX_WAIT_RIFS,
1654 REG_RX_TO_RX, REG_STANDBY,
1655 REG_SLEEP, REG_PMPD_ANAEN
1657 u32 IQK_MAC_REG[IQK_MAC_REG_NUM] = {
1658 REG_TXPAUSE, REG_BCN_CTRL,
1659 REG_BCN_CTRL_1, REG_GPIO_MUXCFG
1662 /* since 92C & 92D have the different define in IQK_BB_REG */
1663 u32 IQK_BB_REG_92C[IQK_BB_REG_NUM] = {
1664 REG_OFDM_0_TRX_PATH_ENABLE, REG_OFDM_0_TR_MUX_PAR,
1665 REG_FPGA0_XCD_RF_INTERFACE_SW, REG_CONFIG_ANT_A, REG_CONFIG_ANT_B,
1666 REG_FPGA0_XAB_RF_INTERFACE_SW, REG_FPGA0_XA_RF_INTERFACE_OE,
1667 REG_FPGA0_XB_RF_INTERFACE_OE, /*REG_FPGA0_RFMOD*/ REG_CCK_0_AFE_SETTING
1670 u32 IQK_BB_REG_92D[IQK_BB_REG_NUM_92D] = { /* for normal */
1671 REG_FPGA0_XAB_RF_INTERFACE_SW, REG_FPGA0_XA_RF_INTERFACE_OE,
1672 REG_FPGA0_XB_RF_INTERFACE_OE, REG_OFDM_0_TR_MUX_PAR,
1673 REG_FPGA0_XCD_RF_INTERFACE_SW, REG_OFDM_0_TRX_PATH_ENABLE,
1674 /*REG_FPGA0_RFMOD*/ REG_CCK_0_AFE_SETTING, REG_FPGA0_ANALOG_PARAMETER4,
1675 REG_OFDM_0_XA_AGC_CORE1, REG_OFDM_0_XB_AGC_CORE1
1678 const u32 retry_count = 9;
1680 const u32 retry_count = 2;
1682 /* Neil Chen--2011--05--19--
1684 u8 rf_path_switch = 0x0;
1686 /* Note: IQ calibration must be performed after loading */
1687 /* PHY_REG.txt , and radio_a, radio_b.txt */
1692 /* bbvalue = phy_query_bb_reg(p_adapter, REG_FPGA0_RFMOD, MASKDWORD); */
1693 /* RTPRINT(FINIT, INIT_IQK, ("_phy_iq_calibrate_8192c()==>0x%08x\n",bbvalue)); */
1695 RTPRINT(FINIT, INIT_IQK, ("IQ Calibration for %s\n", (is2T ? "2T2R" : "1T1R")));
1697 /* Save ADDA parameters, turn path A ADDA on */
1698 phy_save_adda_registers(p_adapter, ADDA_REG, p_hal_data->ADDA_backup, IQK_ADDA_REG_NUM);
1699 phy_save_mac_registers(p_adapter, IQK_MAC_REG, p_hal_data->IQK_MAC_backup);
1700 phy_save_adda_registers(p_adapter, IQK_BB_REG_92C, p_hal_data->IQK_BB_backup, IQK_BB_REG_NUM);
1703 phy_path_adda_on(p_adapter, ADDA_REG, true, is2T);
1706 p_hal_data->is_rf_pi_enable = (u8)phy_query_bb_reg(p_adapter, REG_FPGA0_XA_HSSI_PARAMETER1, BIT(8));
1708 if (!p_hal_data->is_rf_pi_enable) {
1709 /* Switch BB to PI mode to do IQ Calibration. */
1710 phy_pi_mode_switch(p_adapter, true);
1714 phy_mac_setting_calibration(p_adapter, IQK_MAC_REG, p_hal_data->IQK_MAC_backup);
1716 /* phy_set_bb_reg(p_adapter, REG_FPGA0_RFMOD, BIT24, 0x00); */
1717 phy_set_bb_reg(p_adapter, REG_CCK_0_AFE_SETTING, MASKDWORD, (0x0f000000 | (phy_query_bb_reg(p_adapter, REG_CCK_0_AFE_SETTING, MASKDWORD))));
1718 phy_set_bb_reg(p_adapter, REG_OFDM_0_TRX_PATH_ENABLE, MASKDWORD, 0x03a05600);
1719 phy_set_bb_reg(p_adapter, REG_OFDM_0_TR_MUX_PAR, MASKDWORD, 0x000800e4);
1720 phy_set_bb_reg(p_adapter, REG_FPGA0_XCD_RF_INTERFACE_SW, MASKDWORD, 0x22204000);
1722 phy_set_bb_reg(p_adapter, REG_FPGA0_XAB_RF_INTERFACE_SW, BIT(10), 0x01);
1723 phy_set_bb_reg(p_adapter, REG_FPGA0_XAB_RF_INTERFACE_SW, BIT(26), 0x01);
1724 phy_set_bb_reg(p_adapter, REG_FPGA0_XA_RF_INTERFACE_OE, BIT(10), 0x00);
1725 phy_set_bb_reg(p_adapter, REG_FPGA0_XB_RF_INTERFACE_OE, BIT(10), 0x00);
1729 phy_set_bb_reg(p_adapter, REG_FPGA0_XA_LSSI_PARAMETER, MASKDWORD, 0x00010000);
1730 phy_set_bb_reg(p_adapter, REG_FPGA0_XB_LSSI_PARAMETER, MASKDWORD, 0x00010000);
1735 phy_set_bb_reg(p_adapter, REG_CONFIG_ANT_A, MASKDWORD, 0x00080000);
1738 phy_set_bb_reg(p_adapter, REG_CONFIG_ANT_B, MASKDWORD, 0x00080000);
1740 /* IQ calibration setting */
1741 RTPRINT(FINIT, INIT_IQK, ("IQK setting!\n"));
1742 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0x808000);
1743 phy_set_bb_reg(p_adapter, REG_TX_IQK, MASKDWORD, 0x01007c00);
1744 phy_set_bb_reg(p_adapter, REG_RX_IQK, MASKDWORD, 0x01004800);
1746 for (i = 0 ; i < retry_count ; i++) {
1747 path_aok = phy_path_a_iqk_8192c(p_adapter, is2T);
1748 if (path_aok == 0x03) {
1749 RTPRINT(FINIT, INIT_IQK, ("path A IQK Success!!\n"));
1750 result[t][0] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_BEFORE_IQK_A, MASKDWORD) & 0x3FF0000) >> 16;
1751 result[t][1] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_AFTER_IQK_A, MASKDWORD) & 0x3FF0000) >> 16;
1752 result[t][2] = (phy_query_bb_reg(p_adapter, REG_RX_POWER_BEFORE_IQK_A_2, MASKDWORD) & 0x3FF0000) >> 16;
1753 result[t][3] = (phy_query_bb_reg(p_adapter, REG_RX_POWER_AFTER_IQK_A_2, MASKDWORD) & 0x3FF0000) >> 16;
1755 } else if (i == (retry_count - 1) && path_aok == 0x01) { /* Tx IQK OK */
1756 RTPRINT(FINIT, INIT_IQK, ("path A IQK Only Tx Success!!\n"));
1758 result[t][0] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_BEFORE_IQK_A, MASKDWORD) & 0x3FF0000) >> 16;
1759 result[t][1] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_AFTER_IQK_A, MASKDWORD) & 0x3FF0000) >> 16;
1763 if (0x00 == path_aok)
1764 RTPRINT(FINIT, INIT_IQK, ("path A IQK failed!!\n"));
1767 phy_path_a_stand_by(p_adapter);
1769 /* Turn path B ADDA on */
1770 phy_path_adda_on(p_adapter, ADDA_REG, false, is2T);
1772 for (i = 0 ; i < retry_count ; i++) {
1773 path_bok = phy_path_b_iqk_8192c(p_adapter);
1774 if (path_bok == 0x03) {
1775 RTPRINT(FINIT, INIT_IQK, ("path B IQK Success!!\n"));
1776 result[t][4] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_BEFORE_IQK_B, MASKDWORD) & 0x3FF0000) >> 16;
1777 result[t][5] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_AFTER_IQK_B, MASKDWORD) & 0x3FF0000) >> 16;
1778 result[t][6] = (phy_query_bb_reg(p_adapter, REG_RX_POWER_BEFORE_IQK_B_2, MASKDWORD) & 0x3FF0000) >> 16;
1779 result[t][7] = (phy_query_bb_reg(p_adapter, REG_RX_POWER_AFTER_IQK_B_2, MASKDWORD) & 0x3FF0000) >> 16;
1781 } else if (i == (retry_count - 1) && path_bok == 0x01) { /* Tx IQK OK */
1782 RTPRINT(FINIT, INIT_IQK, ("path B Only Tx IQK Success!!\n"));
1783 result[t][4] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_BEFORE_IQK_B, MASKDWORD) & 0x3FF0000) >> 16;
1784 result[t][5] = (phy_query_bb_reg(p_adapter, REG_TX_POWER_AFTER_IQK_B, MASKDWORD) & 0x3FF0000) >> 16;
1788 if (0x00 == path_bok)
1789 RTPRINT(FINIT, INIT_IQK, ("path B IQK failed!!\n"));
1792 /* Back to BB mode, load original value */
1793 RTPRINT(FINIT, INIT_IQK, ("IQK:Back to BB mode, load original value!\n"));
1794 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0);
1797 if (!p_hal_data->is_rf_pi_enable) {
1798 /* Switch back BB to SI mode after finish IQ Calibration. */
1799 phy_pi_mode_switch(p_adapter, false);
1802 /* Reload ADDA power saving parameters */
1803 phy_reload_adda_registers(p_adapter, ADDA_REG, p_hal_data->ADDA_backup, IQK_ADDA_REG_NUM);
1805 /* Reload MAC parameters */
1806 phy_reload_mac_registers(p_adapter, IQK_MAC_REG, p_hal_data->IQK_MAC_backup);
1808 /* Reload BB parameters */
1809 phy_reload_adda_registers(p_adapter, IQK_BB_REG_92C, p_hal_data->IQK_BB_backup, IQK_BB_REG_NUM);
1811 /*Restore RX initial gain*/
1812 phy_set_bb_reg(p_adapter, REG_FPGA0_XA_LSSI_PARAMETER, MASKDWORD, 0x00032ed3);
1814 phy_set_bb_reg(p_adapter, REG_FPGA0_XB_LSSI_PARAMETER, MASKDWORD, 0x00032ed3);
1815 /* load 0xe30 IQC default value */
1816 phy_set_bb_reg(p_adapter, REG_TX_IQK_TONE_A, MASKDWORD, 0x01008c00);
1817 phy_set_bb_reg(p_adapter, REG_RX_IQK_TONE_A, MASKDWORD, 0x01008c00);
1820 RTPRINT(FINIT, INIT_IQK, ("_phy_iq_calibrate_8192c() <==\n"));
1826 _phy_lccalibrate92c(
1827 struct _ADAPTER *p_adapter,
1832 u32 rf_amode = 0, rf_bmode = 0, lc_cal;
1833 /* HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter); */
1835 /* Check continuous TX and Packet TX */
1836 tmp_reg = platform_efio_read_1byte(p_adapter, 0xd03);
1838 if ((tmp_reg & 0x70) != 0) /* Deal with contisuous TX case */
1839 platform_efio_write_1byte(p_adapter, 0xd03, tmp_reg & 0x8F); /* disable all continuous TX */
1840 else /* Deal with Packet TX case */
1841 platform_efio_write_1byte(p_adapter, REG_TXPAUSE, 0xFF); /* block all queues */
1843 if ((tmp_reg & 0x70) != 0) {
1844 /* 1. Read original RF mode */
1846 rf_amode = phy_query_rf_reg(p_adapter, RF_PATH_A, RF_AC, MASK12BITS);
1850 rf_bmode = phy_query_rf_reg(p_adapter, RF_PATH_B, RF_AC, MASK12BITS);
1852 /* 2. Set RF mode = standby mode */
1854 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_AC, MASK12BITS, (rf_amode & 0x8FFFF) | 0x10000);
1858 phy_set_rf_reg(p_adapter, RF_PATH_B, RF_AC, MASK12BITS, (rf_bmode & 0x8FFFF) | 0x10000);
1861 /* 3. Read RF reg18 */
1862 lc_cal = phy_query_rf_reg(p_adapter, RF_PATH_A, RF_CHNLBW, MASK12BITS);
1864 /* 4. Set LC calibration begin bit15 */
1865 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_CHNLBW, MASK12BITS, lc_cal | 0x08000);
1870 /* Restore original situation */
1871 if ((tmp_reg & 0x70) != 0) { /* Deal with contisuous TX case */
1873 platform_efio_write_1byte(p_adapter, 0xd03, tmp_reg);
1874 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_AC, MASK12BITS, rf_amode);
1878 phy_set_rf_reg(p_adapter, RF_PATH_B, RF_AC, MASK12BITS, rf_bmode);
1879 } else /* Deal with Packet TX case */
1880 platform_efio_write_1byte(p_adapter, REG_TXPAUSE, 0x00);
1886 struct _ADAPTER *p_adapter,
1890 _phy_lccalibrate92c(p_adapter, is2T);
1895 /* Analog Pre-distortion calibration */
1896 #define APK_BB_REG_NUM 8
1897 #define APK_CURVE_REG_NUM 4
1901 _phy_ap_calibrate_8192c(
1902 struct _ADAPTER *p_adapter,
1907 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
1909 u32 reg_d[PATH_NUM];
1910 u32 tmp_reg, index, offset, i, apkbound;
1911 u8 path, pathbound = PATH_NUM;
1912 u32 BB_backup[APK_BB_REG_NUM];
1913 u32 BB_REG[APK_BB_REG_NUM] = {
1914 REG_FPGA1_TX_BLOCK, REG_OFDM_0_TRX_PATH_ENABLE,
1915 REG_FPGA0_RFMOD, REG_OFDM_0_TR_MUX_PAR,
1916 REG_FPGA0_XCD_RF_INTERFACE_SW, REG_FPGA0_XAB_RF_INTERFACE_SW,
1917 REG_FPGA0_XA_RF_INTERFACE_OE, REG_FPGA0_XB_RF_INTERFACE_OE
1919 u32 BB_AP_MODE[APK_BB_REG_NUM] = {
1920 0x00000020, 0x00a05430, 0x02040000,
1921 0x000800e4, 0x00204000
1923 u32 BB_normal_AP_MODE[APK_BB_REG_NUM] = {
1924 0x00000020, 0x00a05430, 0x02040000,
1925 0x000800e4, 0x22204000
1928 u32 AFE_backup[IQK_ADDA_REG_NUM];
1929 u32 AFE_REG[IQK_ADDA_REG_NUM] = {
1930 REG_FPGA0_XCD_SWITCH_CONTROL, REG_BLUE_TOOTH,
1931 REG_RX_WAIT_CCA, REG_TX_CCK_RFON,
1932 REG_TX_CCK_BBON, REG_TX_OFDM_RFON,
1933 REG_TX_OFDM_BBON, REG_TX_TO_RX,
1934 REG_TX_TO_TX, REG_RX_CCK,
1935 REG_RX_OFDM, REG_RX_WAIT_RIFS,
1936 REG_RX_TO_RX, REG_STANDBY,
1937 REG_SLEEP, REG_PMPD_ANAEN
1940 u32 MAC_backup[IQK_MAC_REG_NUM];
1941 u32 MAC_REG[IQK_MAC_REG_NUM] = {
1942 REG_TXPAUSE, REG_BCN_CTRL,
1943 REG_BCN_CTRL_1, REG_GPIO_MUXCFG
1946 u32 APK_RF_init_value[PATH_NUM][APK_BB_REG_NUM] = {
1947 {0x0852c, 0x1852c, 0x5852c, 0x1852c, 0x5852c},
1948 {0x2852e, 0x0852e, 0x3852e, 0x0852e, 0x0852e}
1951 u32 APK_normal_RF_init_value[PATH_NUM][APK_BB_REG_NUM] = {
1952 {0x0852c, 0x0a52c, 0x3a52c, 0x5a52c, 0x5a52c}, /* path settings equal to path b settings */
1953 {0x0852c, 0x0a52c, 0x5a52c, 0x5a52c, 0x5a52c}
1956 u32 APK_RF_value_0[PATH_NUM][APK_BB_REG_NUM] = {
1957 {0x52019, 0x52014, 0x52013, 0x5200f, 0x5208d},
1958 {0x5201a, 0x52019, 0x52016, 0x52033, 0x52050}
1961 u32 APK_normal_RF_value_0[PATH_NUM][APK_BB_REG_NUM] = {
1962 {0x52019, 0x52017, 0x52010, 0x5200d, 0x5206a}, /* path settings equal to path b settings */
1963 {0x52019, 0x52017, 0x52010, 0x5200d, 0x5206a}
1966 u32 APK_RF_value_A[PATH_NUM][APK_BB_REG_NUM] = {
1967 {0x1adb0, 0x1adb0, 0x1ada0, 0x1ad90, 0x1ad80},
1968 {0x00fb0, 0x00fb0, 0x00fa0, 0x00f90, 0x00f80}
1971 u32 AFE_on_off[PATH_NUM] = {
1972 0x04db25a4, 0x0b1b25a4
1973 }; /* path A on path B off / path A off path B on */
1975 u32 APK_offset[PATH_NUM] = {
1976 REG_CONFIG_ANT_A, REG_CONFIG_ANT_B
1979 u32 APK_normal_offset[PATH_NUM] = {
1980 REG_CONFIG_PMPD_ANT_A, REG_CONFIG_PMPD_ANT_B
1983 u32 APK_value[PATH_NUM] = {
1984 0x92fc0000, 0x12fc0000
1987 u32 APK_normal_value[PATH_NUM] = {
1988 0x92680000, 0x12680000
1991 s8 APK_delta_mapping[APK_BB_REG_NUM][13] = {
1992 {-4, -3, -2, -2, -1, -1, 0, 1, 2, 3, 4, 5, 6},
1993 {-4, -3, -2, -2, -1, -1, 0, 1, 2, 3, 4, 5, 6},
1994 {-6, -4, -2, -2, -1, -1, 0, 1, 2, 3, 4, 5, 6},
1995 {-1, -1, -1, -1, -1, -1, 0, 1, 2, 3, 4, 5, 6},
1996 {-11, -9, -7, -5, -3, -1, 0, 0, 0, 0, 0, 0, 0}
1999 u32 APK_normal_setting_value_1[13] = {
2000 0x01017018, 0xf7ed8f84, 0x1b1a1816, 0x2522201e, 0x322e2b28,
2001 0x433f3a36, 0x5b544e49, 0x7b726a62, 0xa69a8f84, 0xdfcfc0b3,
2002 0x12680000, 0x00880000, 0x00880000
2005 u32 APK_normal_setting_value_2[16] = {
2006 0x01c7021d, 0x01670183, 0x01000123, 0x00bf00e2, 0x008d00a3,
2007 0x0068007b, 0x004d0059, 0x003a0042, 0x002b0031, 0x001f0025,
2008 0x0017001b, 0x00110014, 0x000c000f, 0x0009000b, 0x00070008,
2012 u32 APK_result[PATH_NUM][APK_BB_REG_NUM]; /* val_1_1a, val_1_2a, val_2a, val_3a, val_4a
2013 * u32 AP_curve[PATH_NUM][APK_CURVE_REG_NUM]; */
2015 s32 BB_offset, delta_V, delta_offset;
2018 PMPT_CONTEXT p_mpt_ctx = &(p_adapter->mpt_ctx);
2020 p_mpt_ctx->APK_bound[0] = 45;
2021 p_mpt_ctx->APK_bound[1] = 52;
2024 RTPRINT(FINIT, INIT_IQK, ("==>_phy_ap_calibrate_8192c() delta %d\n", delta));
2025 RTPRINT(FINIT, INIT_IQK, ("AP Calibration for %s\n", (is2T ? "2T2R" : "1T1R")));
2029 /* 2 FOR NORMAL CHIP SETTINGS */
2031 /* Temporarily do not allow normal driver to do the following settings because these offset
2032 * and value will cause RF internal PA to be unpredictably disabled by HW, such that RF Tx signal
2033 * will disappear after disable/enable card many times on 88CU. RF SD and DD have not find the
2034 * root cause, so we remove these actions temporarily. Added by tynli and SD3 Allen. 2010.05.31. */
2038 /* settings adjust for normal chip */
2039 for (index = 0; index < PATH_NUM; index++) {
2040 APK_offset[index] = APK_normal_offset[index];
2041 APK_value[index] = APK_normal_value[index];
2042 AFE_on_off[index] = 0x6fdb25a4;
2045 for (index = 0; index < APK_BB_REG_NUM; index++) {
2046 for (path = 0; path < pathbound; path++) {
2047 APK_RF_init_value[path][index] = APK_normal_RF_init_value[path][index];
2048 APK_RF_value_0[path][index] = APK_normal_RF_value_0[path][index];
2050 BB_AP_MODE[index] = BB_normal_AP_MODE[index];
2055 /* save BB default value */
2056 for (index = 0; index < APK_BB_REG_NUM ; index++) {
2057 if (index == 0) /* skip */
2059 BB_backup[index] = phy_query_bb_reg(p_adapter, BB_REG[index], MASKDWORD);
2062 /* save MAC default value */
2063 phy_save_mac_registers(p_adapter, MAC_REG, MAC_backup);
2065 /* save AFE default value */
2066 phy_save_adda_registers(p_adapter, AFE_REG, AFE_backup, IQK_ADDA_REG_NUM);
2068 for (path = 0; path < pathbound; path++) {
2071 if (path == RF_PATH_A) {
2073 /* load APK setting */
2075 offset = REG_PDP_ANT_A;
2076 for (index = 0; index < 11; index++) {
2077 phy_set_bb_reg(p_adapter, offset, MASKDWORD, APK_normal_setting_value_1[index]);
2078 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", offset, phy_query_bb_reg(p_adapter, offset, MASKDWORD)));
2083 phy_set_bb_reg(p_adapter, REG_CONFIG_PMPD_ANT_B, MASKDWORD, 0x12680000);
2085 offset = REG_CONFIG_ANT_A;
2086 for (; index < 13; index++) {
2087 phy_set_bb_reg(p_adapter, offset, MASKDWORD, APK_normal_setting_value_1[index]);
2088 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", offset, phy_query_bb_reg(p_adapter, offset, MASKDWORD)));
2094 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0x400000);
2097 offset = REG_PDP_ANT_A;
2098 for (index = 0; index < 16; index++) {
2099 phy_set_bb_reg(p_adapter, offset, MASKDWORD, APK_normal_setting_value_2[index]);
2100 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", offset, phy_query_bb_reg(p_adapter, offset, MASKDWORD)));
2104 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0);
2105 } else if (path == RF_PATH_B) {
2107 /* load APK setting */
2109 offset = REG_PDP_ANT_B;
2110 for (index = 0; index < 10; index++) {
2111 phy_set_bb_reg(p_adapter, offset, MASKDWORD, APK_normal_setting_value_1[index]);
2112 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", offset, phy_query_bb_reg(p_adapter, offset, MASKDWORD)));
2116 phy_set_bb_reg(p_adapter, REG_CONFIG_PMPD_ANT_A, MASKDWORD, 0x12680000);
2118 phy_set_bb_reg(p_adapter, REG_CONFIG_PMPD_ANT_B, MASKDWORD, 0x12680000);
2120 offset = REG_CONFIG_ANT_A;
2122 for (; index < 13; index++) { /* offset 0xb68, 0xb6c */
2123 phy_set_bb_reg(p_adapter, offset, MASKDWORD, APK_normal_setting_value_1[index]);
2124 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", offset, phy_query_bb_reg(p_adapter, offset, MASKDWORD)));
2130 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0x400000);
2134 for (index = 0; index < 16; index++) {
2135 phy_set_bb_reg(p_adapter, offset, MASKDWORD, APK_normal_setting_value_2[index]);
2136 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", offset, phy_query_bb_reg(p_adapter, offset, MASKDWORD)));
2140 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0);
2143 /* save RF default value */
2144 reg_d[path] = phy_query_rf_reg(p_adapter, path, RF_TXBIAS_A, RFREGOFFSETMASK);
2146 /* path A AFE all on, path B AFE All off or vise versa */
2147 for (index = 0; index < IQK_ADDA_REG_NUM ; index++)
2148 phy_set_bb_reg(p_adapter, AFE_REG[index], MASKDWORD, AFE_on_off[path]);
2149 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0xe70 %x\n", phy_query_bb_reg(p_adapter, REG_RX_WAIT_CCA, MASKDWORD)));
2153 for (index = 0; index < APK_BB_REG_NUM ; index++) {
2155 if (index == 0) /* skip */
2158 phy_set_bb_reg(p_adapter, BB_REG[index], MASKDWORD, BB_AP_MODE[index]);
2159 else if (BB_REG[index] == 0x870)
2160 phy_set_bb_reg(p_adapter, BB_REG[index], MASKDWORD, BB_backup[index] | BIT(10) | BIT(26));
2162 phy_set_bb_reg(p_adapter, BB_REG[index], BIT(10), 0x0);
2165 phy_set_bb_reg(p_adapter, REG_TX_IQK_TONE_A, MASKDWORD, 0x01008c00);
2166 phy_set_bb_reg(p_adapter, REG_RX_IQK_TONE_A, MASKDWORD, 0x01008c00);
2167 } else { /* path B */
2168 phy_set_bb_reg(p_adapter, REG_TX_IQK_TONE_B, MASKDWORD, 0x01008c00);
2169 phy_set_bb_reg(p_adapter, REG_RX_IQK_TONE_B, MASKDWORD, 0x01008c00);
2173 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x800 %x\n", phy_query_bb_reg(p_adapter, 0x800, MASKDWORD)));
2176 phy_mac_setting_calibration(p_adapter, MAC_REG, MAC_backup);
2178 if (path == RF_PATH_A) /* path B to standby mode */
2179 phy_set_rf_reg(p_adapter, RF_PATH_B, RF_AC, RFREGOFFSETMASK, 0x10000);
2180 else { /* path A to standby mode */
2181 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_AC, RFREGOFFSETMASK, 0x10000);
2182 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_MODE1, RFREGOFFSETMASK, 0x1000f);
2183 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_MODE2, RFREGOFFSETMASK, 0x20103);
2186 delta_offset = ((delta + 14) / 2);
2187 if (delta_offset < 0)
2189 else if (delta_offset > 12)
2192 /* AP calibration */
2193 for (index = 0; index < APK_BB_REG_NUM; index++) {
2194 if (index != 1) /* only DO PA11+PAD01001, AP RF setting */
2197 tmp_reg = APK_RF_init_value[path][index];
2199 if (!p_hal_data->is_apk_thermal_meter_ignore) {
2200 BB_offset = (tmp_reg & 0xF0000) >> 16;
2202 if (!(tmp_reg & BIT(15))) /* sign bit 0 */
2203 BB_offset = -BB_offset;
2205 delta_V = APK_delta_mapping[index][delta_offset];
2207 BB_offset += delta_V;
2209 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() APK index %d tmp_reg 0x%x delta_V %d delta_offset %d\n", index, tmp_reg, delta_V, delta_offset));
2211 if (BB_offset < 0) {
2212 tmp_reg = tmp_reg & (~BIT(15));
2213 BB_offset = -BB_offset;
2215 tmp_reg = tmp_reg | BIT(15);
2216 tmp_reg = (tmp_reg & 0xFFF0FFFF) | (BB_offset << 16);
2220 #if DEV_BUS_TYPE == RT_PCI_INTERFACE
2221 if (IS_81xxC_VENDOR_UMC_B_CUT(p_hal_data->version_id))
2222 phy_set_rf_reg(p_adapter, path, RF_IPA_A, RFREGOFFSETMASK, 0x894ae);
2225 phy_set_rf_reg(p_adapter, path, RF_IPA_A, RFREGOFFSETMASK, 0x8992e);
2226 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0xc %x\n", phy_query_rf_reg(p_adapter, path, RF_IPA_A, RFREGOFFSETMASK)));
2227 phy_set_rf_reg(p_adapter, path, RF_AC, RFREGOFFSETMASK, APK_RF_value_0[path][index]);
2228 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x0 %x\n", phy_query_rf_reg(p_adapter, path, RF_AC, RFREGOFFSETMASK)));
2229 phy_set_rf_reg(p_adapter, path, RF_TXBIAS_A, RFREGOFFSETMASK, tmp_reg);
2230 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0xd %x\n", phy_query_rf_reg(p_adapter, path, RF_TXBIAS_A, RFREGOFFSETMASK)));
2232 /* PA11+PAD01111, one shot */
2235 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0x800000);
2237 phy_set_bb_reg(p_adapter, APK_offset[path], MASKDWORD, APK_value[0]);
2238 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", APK_offset[path], phy_query_bb_reg(p_adapter, APK_offset[path], MASKDWORD)));
2240 phy_set_bb_reg(p_adapter, APK_offset[path], MASKDWORD, APK_value[1]);
2241 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0x%x value 0x%x\n", APK_offset[path], phy_query_bb_reg(p_adapter, APK_offset[path], MASKDWORD)));
2245 phy_set_bb_reg(p_adapter, REG_FPGA0_IQK, 0xffffff00, 0);
2247 if (path == RF_PATH_A)
2248 tmp_reg = phy_query_bb_reg(p_adapter, REG_APK, 0x03E00000);
2250 tmp_reg = phy_query_bb_reg(p_adapter, REG_APK, 0xF8000000);
2251 RTPRINT(FINIT, INIT_IQK, ("_phy_ap_calibrate_8192c() offset 0xbd8[25:21] %x\n", tmp_reg));
2255 } while (tmp_reg > apkbound && i < 4);
2257 APK_result[path][index] = tmp_reg;
2261 /* reload MAC default value */
2262 phy_reload_mac_registers(p_adapter, MAC_REG, MAC_backup);
2264 /* reload BB default value */
2265 for (index = 0; index < APK_BB_REG_NUM ; index++) {
2267 if (index == 0) /* skip */
2269 phy_set_bb_reg(p_adapter, BB_REG[index], MASKDWORD, BB_backup[index]);
2272 /* reload AFE default value */
2273 phy_reload_adda_registers(p_adapter, AFE_REG, AFE_backup, IQK_ADDA_REG_NUM);
2275 /* reload RF path default value */
2276 for (path = 0; path < pathbound; path++) {
2277 phy_set_rf_reg(p_adapter, path, RF_TXBIAS_A, RFREGOFFSETMASK, reg_d[path]);
2278 if (path == RF_PATH_B) {
2279 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_MODE1, RFREGOFFSETMASK, 0x1000f);
2280 phy_set_rf_reg(p_adapter, RF_PATH_A, RF_MODE2, RFREGOFFSETMASK, 0x20101);
2283 /* note no index == 0 */
2284 if (APK_result[path][1] > 6)
2285 APK_result[path][1] = 6;
2286 RTPRINT(FINIT, INIT_IQK, ("apk path %d result %d 0x%x \t", path, 1, APK_result[path][1]));
2289 RTPRINT(FINIT, INIT_IQK, ("\n"));
2292 for (path = 0; path < pathbound; path++) {
2293 phy_set_rf_reg(p_adapter, path, RF_BS_PA_APSET_G1_G4, RFREGOFFSETMASK,
2294 ((APK_result[path][1] << 15) | (APK_result[path][1] << 10) | (APK_result[path][1] << 5) | APK_result[path][1]));
2295 if (path == RF_PATH_A)
2296 phy_set_rf_reg(p_adapter, path, RF_BS_PA_APSET_G5_G8, RFREGOFFSETMASK,
2297 ((APK_result[path][1] << 15) | (APK_result[path][1] << 10) | (0x00 << 5) | 0x05));
2299 phy_set_rf_reg(p_adapter, path, RF_BS_PA_APSET_G5_G8, RFREGOFFSETMASK,
2300 ((APK_result[path][1] << 15) | (APK_result[path][1] << 10) | (0x02 << 5) | 0x05));
2302 phy_set_rf_reg(p_adapter, path, RF_BS_PA_APSET_G9_G11, RFREGOFFSETMASK, ((0x08 << 15) | (0x08 << 10) | (0x08 << 5) | 0x08));
2305 p_hal_data->is_ap_kdone = true;
2307 RTPRINT(FINIT, INIT_IQK, ("<==_phy_ap_calibrate_8192c()\n"));
2312 phy_iq_calibrate_8192c(
2313 struct _ADAPTER *p_adapter,
2317 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
2318 s32 result[4][8]; /* last is final result */
2319 u8 i, final_candidate, indexforchannel;
2320 boolean is_patha_ok, is_pathb_ok;
2321 s32 rege94, rege9c, regea4, regeac, regeb4, regebc, regec4, regecc, reg_tmp = 0;
2322 boolean is12simular, is13simular, is23simular;
2323 boolean is_start_cont_tx = false, is_single_tone = false, is_carrier_suppression = false;
2324 u32 IQK_BB_REG_92C[IQK_BB_REG_NUM] = {
2325 REG_OFDM_0_XA_RX_IQ_IMBALANCE, REG_OFDM_0_XB_RX_IQ_IMBALANCE,
2326 REG_OFDM_0_ECCA_THRESHOLD, REG_OFDM_0_AGC_RSSI_TABLE,
2327 REG_OFDM_0_XA_TX_IQ_IMBALANCE, REG_OFDM_0_XB_TX_IQ_IMBALANCE,
2328 REG_OFDM_0_XC_TX_AFE, REG_OFDM_0_XD_TX_AFE,
2329 REG_OFDM_0_RX_IQ_EXT_ANTA
2332 if (odm_check_power_status(p_adapter) == false)
2336 is_start_cont_tx = p_adapter->mpt_ctx.is_start_cont_tx;
2337 is_single_tone = p_adapter->mpt_ctx.is_single_tone;
2338 is_carrier_suppression = p_adapter->mpt_ctx.is_carrier_suppression;
2341 /* ignore IQK when continuous Tx */
2342 if (is_start_cont_tx || is_single_tone || is_carrier_suppression)
2345 #ifdef DISABLE_BB_RF
2348 if (p_adapter->is_slave_of_dmsp)
2352 phy_reload_adda_registers(p_adapter, IQK_BB_REG_92C, p_hal_data->IQK_BB_backup_recover, 9);
2357 RTPRINT(FINIT, INIT_IQK, ("IQK:Start!!!\n"));
2359 for (i = 0; i < 8; i++) {
2365 final_candidate = 0xff;
2366 is_patha_ok = false;
2367 is_pathb_ok = false;
2368 is12simular = false;
2369 is23simular = false;
2370 is13simular = false;
2372 acquire_cck_and_rw_page_a_control(p_adapter);
2373 /*RT_TRACE(COMP_INIT,DBG_LOUD,("Acquire Mutex in IQCalibrate\n"));*/
2374 for (i = 0; i < 3; i++) {
2376 _phy_iq_calibrate_8192c(p_adapter, result, i, false);
2379 is12simular = phy_simularity_compare(p_adapter, result, 0, 1);
2381 final_candidate = 0;
2387 is13simular = phy_simularity_compare(p_adapter, result, 0, 2);
2389 final_candidate = 0;
2393 is23simular = phy_simularity_compare(p_adapter, result, 1, 2);
2395 final_candidate = 1;
2397 for (i = 0; i < 8; i++)
2398 reg_tmp += result[3][i];
2401 final_candidate = 3;
2403 final_candidate = 0xFF;
2407 /* RT_TRACE(COMP_INIT,DBG_LOUD,("Release Mutex in IQCalibrate\n")); */
2408 release_cck_and_rw_pagea_control(p_adapter);
2410 for (i = 0; i < 4; i++) {
2411 rege94 = result[i][0];
2412 rege9c = result[i][1];
2413 regea4 = result[i][2];
2414 regeac = result[i][3];
2415 regeb4 = result[i][4];
2416 regebc = result[i][5];
2417 regec4 = result[i][6];
2418 regecc = result[i][7];
2419 RTPRINT(FINIT, INIT_IQK, ("IQK: rege94=%x rege9c=%x regea4=%x regeac=%x regeb4=%x regebc=%x regec4=%x regecc=%x\n ", rege94, rege9c, regea4, regeac, regeb4, regebc, regec4, regecc));
2422 if (final_candidate != 0xff) {
2423 p_hal_data->rege94 = rege94 = result[final_candidate][0];
2424 p_hal_data->rege9c = rege9c = result[final_candidate][1];
2425 regea4 = result[final_candidate][2];
2426 regeac = result[final_candidate][3];
2427 p_hal_data->regeb4 = regeb4 = result[final_candidate][4];
2428 p_hal_data->regebc = regebc = result[final_candidate][5];
2429 regec4 = result[final_candidate][6];
2430 regecc = result[final_candidate][7];
2431 RTPRINT(FINIT, INIT_IQK, ("IQK: final_candidate is %x\n", final_candidate));
2432 RTPRINT(FINIT, INIT_IQK, ("IQK: rege94=%x rege9c=%x regea4=%x regeac=%x regeb4=%x regebc=%x regec4=%x regecc=%x\n ", rege94, rege9c, regea4, regeac, regeb4, regebc, regec4, regecc));
2433 is_patha_ok = is_pathb_ok = true;
2435 rege94 = regeb4 = p_hal_data->rege94 = p_hal_data->regeb4 = 0x100; /* X default value */
2436 rege9c = regebc = p_hal_data->rege9c = p_hal_data->regebc = 0x0; /* Y default value */
2439 if ((rege94 != 0)/*&&(regea4 != 0)*/) {
2440 if (p_hal_data->current_band_type == BAND_ON_5G)
2441 phy_path_a_fill_iqk_matrix_5g_normal(p_adapter, is_patha_ok, result, final_candidate, (regea4 == 0));
2443 phy_path_a_fill_iqk_matrix(p_adapter, is_patha_ok, result, final_candidate, (regea4 == 0));
2447 if (IS_92C_SERIAL(p_hal_data->version_id) || IS_92D_SINGLEPHY(p_hal_data->version_id)) {
2448 if ((regeb4 != 0)/*&&(regec4 != 0)*/) {
2449 if (p_hal_data->current_band_type == BAND_ON_5G)
2450 phy_path_b_fill_iqk_matrix_5g_normal(p_adapter, is_pathb_ok, result, final_candidate, (regec4 == 0));
2452 phy_path_b_fill_iqk_matrix(p_adapter, is_pathb_ok, result, final_candidate, (regec4 == 0));
2456 phy_save_adda_registers(p_adapter, IQK_BB_REG_92C, p_hal_data->IQK_BB_backup_recover, 9);
2462 phy_lc_calibrate_8192c(
2463 struct _ADAPTER *p_adapter
2466 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
2467 boolean is_start_cont_tx = false, is_single_tone = false, is_carrier_suppression = false;
2468 PMGNT_INFO p_mgnt_info = &p_adapter->MgntInfo;
2469 PMGNT_INFO p_mgnt_info_buddy_adapter;
2470 u32 timeout = 2000, timecount = 0;
2471 struct _ADAPTER *buddy_adapter = p_adapter->buddy_adapter;
2474 is_start_cont_tx = p_adapter->mpt_ctx.is_start_cont_tx;
2475 is_single_tone = p_adapter->mpt_ctx.is_single_tone;
2476 is_carrier_suppression = p_adapter->mpt_ctx.is_carrier_suppression;
2479 #ifdef DISABLE_BB_RF
2483 /* ignore LCK when continuous Tx */
2484 if (is_start_cont_tx || is_single_tone || is_carrier_suppression)
2487 if (buddy_adapter != NULL &&
2488 ((p_adapter->interface_index == 0 && p_hal_data->current_band_type == BAND_ON_2_4G) ||
2489 (p_adapter->interface_index == 1 && p_hal_data->current_band_type == BAND_ON_5G))) {
2490 p_mgnt_info_buddy_adapter = &buddy_adapter->MgntInfo;
2491 while (p_mgnt_info_buddy_adapter->is_scan_in_progress && timecount < timeout) {
2497 while (p_mgnt_info->is_scan_in_progress && timecount < timeout) {
2502 p_hal_data->is_lck_in_progress = true;
2504 RTPRINT(FINIT, INIT_IQK, ("LCK:Start!!!interface %d currentband %x delay %d ms\n", p_adapter->interface_index, p_hal_data->current_band_type, timecount));
2506 /* if(IS_92C_SERIAL(p_hal_data->version_id) || IS_92D_SINGLEPHY(p_hal_data->version_id)) */
2507 if (IS_2T2R(p_hal_data->version_id))
2508 phy_lc_calibrate(p_adapter, true);
2511 phy_lc_calibrate(p_adapter, false);
2514 p_hal_data->is_lck_in_progress = false;
2516 RTPRINT(FINIT, INIT_IQK, ("LCK:Finish!!!interface %d\n", p_adapter->interface_index));
2522 phy_ap_calibrate_8192c(
2523 struct _ADAPTER *p_adapter,
2527 HAL_DATA_TYPE *p_hal_data = GET_HAL_DATA(p_adapter);
2529 /* default disable APK, because Tx NG issue, suggest by Jenyu, 2011.11.25 */
2532 #ifdef DISABLE_BB_RF
2536 #if FOR_BRAZIL_PRETEST != 1
2537 if (p_hal_data->is_ap_kdone)
2541 if (IS_92C_SERIAL(p_hal_data->version_id))
2542 _phy_ap_calibrate_8192c(p_adapter, delta, true);
2545 _phy_ap_calibrate_8192c(p_adapter, delta, false);
2553 /* 3============================================================
2555 * 3============================================================ */
2558 odm_reset_iqk_result(
2564 #if 1/* !(DM_ODM_SUPPORT_TYPE & ODM_AP) */
2565 u8 odm_get_right_chnl_place_for_iqk(u8 chnl)
2567 u8 channel_all[ODM_TARGET_CHNL_NUM_2G_5G] = {
2568 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 36, 38, 40, 42, 44, 46, 48, 50, 52, 54, 56, 58, 60, 62, 64, 100, 102, 104, 106, 108, 110, 112, 114, 116, 118, 120, 122, 124, 126, 128, 130, 132, 134, 136, 138, 140, 149, 151, 153, 155, 157, 159, 161, 163, 165
2574 for (place = 14; place < sizeof(channel_all); place++) {
2575 if (channel_all[place] == chnl)
2586 struct PHY_DM_STRUCT *p_dm_odm
2589 struct _ADAPTER *adapter = p_dm_odm->adapter;
2591 #if (DM_ODM_SUPPORT_TYPE == ODM_WIN)
2592 if (*p_dm_odm->p_is_fcs_mode_enable)
2598 if (p_dm_odm->is_linked) {
2599 if ((*p_dm_odm->p_channel != p_dm_odm->pre_channel) && (!*p_dm_odm->p_is_scan_in_process)) {
2600 p_dm_odm->pre_channel = *p_dm_odm->p_channel;
2601 p_dm_odm->linked_interval = 0;
2604 if (p_dm_odm->linked_interval < 3)
2605 p_dm_odm->linked_interval++;
2607 if (p_dm_odm->linked_interval == 2) {
2609 #if (RTL8814A_SUPPORT == 1)
2610 if (p_dm_odm->support_ic_type == ODM_RTL8814A)
2611 phy_iq_calibrate_8814a(p_dm_odm, false);
2614 #if (RTL8822B_SUPPORT == 1)
2615 if (p_dm_odm->support_ic_type == ODM_RTL8822B)
2616 phy_iq_calibrate_8822b(p_dm_odm, false);
2619 #if (RTL8821C_SUPPORT == 1)
2620 if (p_dm_odm->support_ic_type == ODM_RTL8821C)
2621 phy_iq_calibrate_8821c(p_dm_odm, false);
2624 #if (RTL8821A_SUPPORT == 1)
2625 if (p_dm_odm->support_ic_type == ODM_RTL8821)
2626 phy_iq_calibrate_8821a(p_dm_odm, false);
2629 #if (RTL8812A_SUPPORT == 1)
2630 if (p_dm_odm->support_ic_type == ODM_RTL8812)
2631 _phy_iq_calibrate_8812a(p_dm_odm, false);
2635 p_dm_odm->linked_interval = 0;
2639 void phydm_rf_init(void *p_dm_void)
2641 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
2642 odm_txpowertracking_init(p_dm_odm);
2644 #if (DM_ODM_SUPPORT_TYPE & (ODM_WIN | ODM_CE))
2645 odm_clear_txpowertracking_state(p_dm_odm);
2648 #if (DM_ODM_SUPPORT_TYPE & (ODM_AP))
2649 #if (RTL8814A_SUPPORT == 1)
2650 if (p_dm_odm->support_ic_type & ODM_RTL8814A)
2651 phy_iq_calibrate_8814a_init(p_dm_odm);
2657 void phydm_rf_watchdog(void *p_dm_void)
2659 struct PHY_DM_STRUCT *p_dm_odm = (struct PHY_DM_STRUCT *)p_dm_void;
2660 #if (DM_ODM_SUPPORT_TYPE & (ODM_WIN | ODM_CE))
2661 odm_txpowertracking_check(p_dm_odm);
2662 if (p_dm_odm->support_ic_type & ODM_IC_11AC_SERIES)
2663 odm_iq_calibrate(p_dm_odm);