1
0
Fork 0

staging: r8822be: Add phydm mini driver

The RTL8822BE, an 802.11ac wireless network card, is now appearing in
new computers. Its driver is being placed in staging to reduce the time
that users of this new card will have access to in-kernel drivers.

New Realtek wireless devices have a new method for PHY control and
dynamic management. The RTL8822BE is the first of these devices, thus
there is additional code required.

In the final version, this code will be a separate module; however,
it is combined with the r8822be driver to minimize the interference
with the drivers in the wireless tree.

Signed-off-by: Ping-Ke Shih <pkshih@realtek.com>
Signed-off-by: Larry Finger <Larry.Finger@lwfinger.net>
Cc: Yan-Hsuan Chuang <yhchuang@realtek.com>
Cc: Birming Chiu <birming@realtek.com>
Cc: Shaofu <shaofu@realtek.com>
Cc: Steven Ting <steventing@realtek.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
hifive-unleashed-5.1
Ping-Ke Shih 2017-08-17 12:46:49 -05:00 committed by Greg Kroah-Hartman
parent 938a0447f0
commit 9ce99b04b5
76 changed files with 33395 additions and 0 deletions

View File

@ -0,0 +1,965 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
#define CALCULATE_SWINGTALBE_OFFSET(_offset, _direction, _size, \
_delta_thermal) \
do { \
for (_offset = 0; _offset < _size; _offset++) { \
if (_delta_thermal < \
thermal_threshold[_direction][_offset]) { \
if (_offset != 0) \
_offset--; \
break; \
} \
} \
if (_offset >= _size) \
_offset = _size - 1; \
} while (0)
static inline void phydm_set_calibrate_info_up(
struct phy_dm_struct *dm, struct txpwrtrack_cfg *c, u8 delta,
struct dm_rf_calibration_struct *cali_info,
u8 *delta_swing_table_idx_tup_a, u8 *delta_swing_table_idx_tup_b,
u8 *delta_swing_table_idx_tup_c, u8 *delta_swing_table_idx_tup_d)
{
u8 p = 0;
for (p = ODM_RF_PATH_A; p < c->rf_path_count; p++) {
cali_info->delta_power_index_last[p] =
cali_info->delta_power_index
[p]; /*recording poer index offset*/
switch (p) {
case ODM_RF_PATH_B:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tup_b[%d] = %d\n",
delta, delta_swing_table_idx_tup_b[delta]);
cali_info->delta_power_index[p] =
delta_swing_table_idx_tup_b[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
delta_swing_table_idx_tup_b[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is higher and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_B] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
case ODM_RF_PATH_C:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tup_c[%d] = %d\n",
delta, delta_swing_table_idx_tup_c[delta]);
cali_info->delta_power_index[p] =
delta_swing_table_idx_tup_c[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
delta_swing_table_idx_tup_c[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is higher and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_C] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
case ODM_RF_PATH_D:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tup_d[%d] = %d\n",
delta, delta_swing_table_idx_tup_d[delta]);
cali_info->delta_power_index[p] =
delta_swing_table_idx_tup_d[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
delta_swing_table_idx_tup_d[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is higher and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_D] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
default:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tup_a[%d] = %d\n",
delta, delta_swing_table_idx_tup_a[delta]);
cali_info->delta_power_index[p] =
delta_swing_table_idx_tup_a[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
delta_swing_table_idx_tup_a[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is higher and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_A] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
}
}
}
static inline void phydm_set_calibrate_info_down(
struct phy_dm_struct *dm, struct txpwrtrack_cfg *c, u8 delta,
struct dm_rf_calibration_struct *cali_info,
u8 *delta_swing_table_idx_tdown_a, u8 *delta_swing_table_idx_tdown_b,
u8 *delta_swing_table_idx_tdown_c, u8 *delta_swing_table_idx_tdown_d)
{
u8 p = 0;
for (p = ODM_RF_PATH_A; p < c->rf_path_count; p++) {
cali_info->delta_power_index_last[p] =
cali_info->delta_power_index
[p]; /*recording poer index offset*/
switch (p) {
case ODM_RF_PATH_B:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tdown_b[%d] = %d\n",
delta,
delta_swing_table_idx_tdown_b[delta]);
cali_info->delta_power_index[p] =
-1 * delta_swing_table_idx_tdown_b[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
-1 * delta_swing_table_idx_tdown_b[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is lower and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_B] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
case ODM_RF_PATH_C:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tdown_c[%d] = %d\n",
delta,
delta_swing_table_idx_tdown_c[delta]);
cali_info->delta_power_index[p] =
-1 * delta_swing_table_idx_tdown_c[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
-1 * delta_swing_table_idx_tdown_c[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is lower and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_C] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
case ODM_RF_PATH_D:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tdown_d[%d] = %d\n",
delta,
delta_swing_table_idx_tdown_d[delta]);
cali_info->delta_power_index[p] =
-1 * delta_swing_table_idx_tdown_d[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
-1 * delta_swing_table_idx_tdown_d[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is lower and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_D] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
default:
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_swing_table_idx_tdown_a[%d] = %d\n",
delta,
delta_swing_table_idx_tdown_a[delta]);
cali_info->delta_power_index[p] =
-1 * delta_swing_table_idx_tdown_a[delta];
/*Record delta swing for mix mode pwr tracking*/
cali_info->absolute_ofdm_swing_idx[p] =
-1 * delta_swing_table_idx_tdown_a[delta];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"******Temp is lower and cali_info->absolute_ofdm_swing_idx[ODM_RF_PATH_A] = %d\n",
cali_info->absolute_ofdm_swing_idx[p]);
break;
}
}
}
static inline void phydm_odm_tx_power_set(struct phy_dm_struct *dm,
struct txpwrtrack_cfg *c,
u8 indexforchannel, u8 flag)
{
u8 p = 0;
if (dm->support_ic_type == ODM_RTL8188E ||
dm->support_ic_type == ODM_RTL8192E ||
dm->support_ic_type == ODM_RTL8821 ||
dm->support_ic_type == ODM_RTL8812 ||
dm->support_ic_type == ODM_RTL8723B ||
dm->support_ic_type == ODM_RTL8814A ||
dm->support_ic_type == ODM_RTL8703B ||
dm->support_ic_type == ODM_RTL8188F ||
dm->support_ic_type == ODM_RTL8822B ||
dm->support_ic_type == ODM_RTL8723D ||
dm->support_ic_type == ODM_RTL8821C ||
dm->support_ic_type == ODM_RTL8710B) { /* JJ ADD 20161014 */
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"**********Enter POWER Tracking MIX_MODE**********\n");
for (p = ODM_RF_PATH_A; p < c->rf_path_count; p++) {
if (flag == 0)
(*c->odm_tx_pwr_track_set_pwr)(dm, MIX_MODE, p,
0);
else
(*c->odm_tx_pwr_track_set_pwr)(dm, MIX_MODE, p,
indexforchannel);
}
} else {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"**********Enter POWER Tracking BBSWING_MODE**********\n");
for (p = ODM_RF_PATH_A; p < c->rf_path_count; p++)
(*c->odm_tx_pwr_track_set_pwr)(dm, BBSWING, p,
indexforchannel);
}
}
void configure_txpower_track(void *dm_void, struct txpwrtrack_cfg *config)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
/* JJ ADD 20161014 */
if (dm->support_ic_type == ODM_RTL8822B)
configure_txpower_track_8822b(config);
}
/* **********************************************************************
* <20121113, Kordan> This function should be called when tx_agc changed.
* Otherwise the previous compensation is gone, because we record the
* delta of temperature between two TxPowerTracking watch dogs.
*
* NOTE: If Tx BB swing or Tx scaling is varified during run-time, still
* need to call this function.
* ***********************************************************************/
void odm_clear_txpowertracking_state(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
struct rtl_efuse *rtlefu = rtl_efuse(rtlpriv);
u8 p = 0;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
cali_info->bb_swing_idx_cck_base = cali_info->default_cck_index;
cali_info->bb_swing_idx_cck = cali_info->default_cck_index;
dm->rf_calibrate_info.CCK_index = 0;
for (p = ODM_RF_PATH_A; p < MAX_RF_PATH; ++p) {
cali_info->bb_swing_idx_ofdm_base[p] =
cali_info->default_ofdm_index;
cali_info->bb_swing_idx_ofdm[p] = cali_info->default_ofdm_index;
cali_info->OFDM_index[p] = cali_info->default_ofdm_index;
cali_info->power_index_offset[p] = 0;
cali_info->delta_power_index[p] = 0;
cali_info->delta_power_index_last[p] = 0;
cali_info->absolute_ofdm_swing_idx[p] =
0; /* Initial Mix mode power tracking*/
cali_info->remnant_ofdm_swing_idx[p] = 0;
cali_info->kfree_offset[p] = 0;
}
cali_info->modify_tx_agc_flag_path_a =
false; /*Initial at Modify Tx Scaling mode*/
cali_info->modify_tx_agc_flag_path_b =
false; /*Initial at Modify Tx Scaling mode*/
cali_info->modify_tx_agc_flag_path_c =
false; /*Initial at Modify Tx Scaling mode*/
cali_info->modify_tx_agc_flag_path_d =
false; /*Initial at Modify Tx Scaling mode*/
cali_info->remnant_cck_swing_idx = 0;
cali_info->thermal_value = rtlefu->eeprom_thermalmeter;
cali_info->modify_tx_agc_value_cck = 0; /* modify by Mingzhi.Guo */
cali_info->modify_tx_agc_value_ofdm = 0; /* modify by Mingzhi.Guo */
}
void odm_txpowertracking_callback_thermal_meter(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
struct rtl_efuse *rtlefu = rtl_efuse(rtlpriv);
void *adapter = dm->adapter;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
u8 thermal_value = 0, delta, delta_LCK, delta_IQK, p = 0, i = 0;
s8 diff_DPK[4]; /* use 'for..loop' to initialize */
u8 thermal_value_avg_count = 0;
u32 thermal_value_avg = 0, regc80, regcd0, regcd4, regab4;
/* OFDM BB Swing should be less than +3.0dB (required by Arthur) */
u8 OFDM_min_index = 0;
/* get_right_chnl_place_for_iqk(hal_data->current_channel) */
u8 indexforchannel = 0;
u8 power_tracking_type = 0; /* no specify type */
u8 xtal_offset_eanble = 0;
struct txpwrtrack_cfg c;
/* 4 1. The following TWO tables decide the final index of
* OFDM/CCK swing table.
*/
u8 *delta_swing_table_idx_tup_a = NULL;
u8 *delta_swing_table_idx_tdown_a = NULL;
u8 *delta_swing_table_idx_tup_b = NULL;
u8 *delta_swing_table_idx_tdown_b = NULL;
/*for 8814 add by Yu Chen*/
u8 *delta_swing_table_idx_tup_c = NULL;
u8 *delta_swing_table_idx_tdown_c = NULL;
u8 *delta_swing_table_idx_tup_d = NULL;
u8 *delta_swing_table_idx_tdown_d = NULL;
/*for Xtal Offset by James.Tung*/
s8 *delta_swing_table_xtal_up = NULL;
s8 *delta_swing_table_xtal_down = NULL;
/* 4 2. Initialization ( 7 steps in total ) */
configure_txpower_track(dm, &c);
(*c.get_delta_swing_table)(dm, (u8 **)&delta_swing_table_idx_tup_a,
(u8 **)&delta_swing_table_idx_tdown_a,
(u8 **)&delta_swing_table_idx_tup_b,
(u8 **)&delta_swing_table_idx_tdown_b);
if (dm->support_ic_type & ODM_RTL8814A) /*for 8814 path C & D*/
(*c.get_delta_swing_table8814only)(
dm, (u8 **)&delta_swing_table_idx_tup_c,
(u8 **)&delta_swing_table_idx_tdown_c,
(u8 **)&delta_swing_table_idx_tup_d,
(u8 **)&delta_swing_table_idx_tdown_d);
/* JJ ADD 20161014 */
if (dm->support_ic_type &
(ODM_RTL8703B | ODM_RTL8723D | ODM_RTL8710B)) /*for Xtal Offset*/
(*c.get_delta_swing_xtal_table)(
dm, (s8 **)&delta_swing_table_xtal_up,
(s8 **)&delta_swing_table_xtal_down);
cali_info->txpowertracking_callback_cnt++; /*cosa add for debug*/
cali_info->is_txpowertracking_init = true;
/*cali_info->txpowertrack_control = hal_data->txpowertrack_control;
*<Kordan> We should keep updating ctrl variable according to HalData.
*<Kordan> rf_calibrate_info.rega24 will be initialized when
*ODM HW configuring, but MP configures with para files.
*/
if (dm->mp_mode)
cali_info->rega24 = 0x090e1317;
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"===>%s\n cali_info->bb_swing_idx_cck_base: %d, cali_info->bb_swing_idx_ofdm_base[A]: %d, cali_info->default_ofdm_index: %d\n",
__func__, cali_info->bb_swing_idx_cck_base,
cali_info->bb_swing_idx_ofdm_base[ODM_RF_PATH_A],
cali_info->default_ofdm_index);
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"cali_info->txpowertrack_control=%d, rtlefu->eeprom_thermalmeter %d\n",
cali_info->txpowertrack_control, rtlefu->eeprom_thermalmeter);
thermal_value =
(u8)odm_get_rf_reg(dm, ODM_RF_PATH_A, c.thermal_reg_addr,
0xfc00); /* 0x42: RF Reg[15:10] 88E */
/*add log by zhao he, check c80/c94/c14/ca0 value*/
if (dm->support_ic_type == ODM_RTL8723D) {
regc80 = odm_get_bb_reg(dm, 0xc80, MASKDWORD);
regcd0 = odm_get_bb_reg(dm, 0xcd0, MASKDWORD);
regcd4 = odm_get_bb_reg(dm, 0xcd4, MASKDWORD);
regab4 = odm_get_bb_reg(dm, 0xab4, 0x000007FF);
ODM_RT_TRACE(
dm, ODM_COMP_CALIBRATION,
"0xc80 = 0x%x 0xcd0 = 0x%x 0xcd4 = 0x%x 0xab4 = 0x%x\n",
regc80, regcd0, regcd4, regab4);
}
/* JJ ADD 20161014 */
if (dm->support_ic_type == ODM_RTL8710B) {
regc80 = odm_get_bb_reg(dm, 0xc80, MASKDWORD);
regcd0 = odm_get_bb_reg(dm, 0xcd0, MASKDWORD);
regcd4 = odm_get_bb_reg(dm, 0xcd4, MASKDWORD);
regab4 = odm_get_bb_reg(dm, 0xab4, 0x000007FF);
ODM_RT_TRACE(
dm, ODM_COMP_CALIBRATION,
"0xc80 = 0x%x 0xcd0 = 0x%x 0xcd4 = 0x%x 0xab4 = 0x%x\n",
regc80, regcd0, regcd4, regab4);
}
if (!cali_info->txpowertrack_control)
return;
/*4 3. Initialize ThermalValues of rf_calibrate_info*/
if (cali_info->is_reloadtxpowerindex)
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"reload ofdm index for band switch\n");
/*4 4. Calculate average thermal meter*/
cali_info->thermal_value_avg[cali_info->thermal_value_avg_index] =
thermal_value;
cali_info->thermal_value_avg_index++;
if (cali_info->thermal_value_avg_index ==
c.average_thermal_num) /*Average times = c.average_thermal_num*/
cali_info->thermal_value_avg_index = 0;
for (i = 0; i < c.average_thermal_num; i++) {
if (cali_info->thermal_value_avg[i]) {
thermal_value_avg += cali_info->thermal_value_avg[i];
thermal_value_avg_count++;
}
}
if (thermal_value_avg_count) {
/* Calculate Average thermal_value after average enough times */
thermal_value =
(u8)(thermal_value_avg / thermal_value_avg_count);
cali_info->thermal_value_delta =
thermal_value - rtlefu->eeprom_thermalmeter;
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"AVG Thermal Meter = 0x%X, EFUSE Thermal base = 0x%X\n",
thermal_value, rtlefu->eeprom_thermalmeter);
}
/* 4 5. Calculate delta, delta_LCK, delta_IQK. */
/* "delta" is used to determine whether thermal value changes or not*/
delta = (thermal_value > cali_info->thermal_value) ?
(thermal_value - cali_info->thermal_value) :
(cali_info->thermal_value - thermal_value);
delta_LCK = (thermal_value > cali_info->thermal_value_lck) ?
(thermal_value - cali_info->thermal_value_lck) :
(cali_info->thermal_value_lck - thermal_value);
delta_IQK = (thermal_value > cali_info->thermal_value_iqk) ?
(thermal_value - cali_info->thermal_value_iqk) :
(cali_info->thermal_value_iqk - thermal_value);
if (cali_info->thermal_value_iqk ==
0xff) { /*no PG, use thermal value for IQK*/
cali_info->thermal_value_iqk = thermal_value;
delta_IQK =
(thermal_value > cali_info->thermal_value_iqk) ?
(thermal_value - cali_info->thermal_value_iqk) :
(cali_info->thermal_value_iqk - thermal_value);
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"no PG, use thermal_value for IQK\n");
}
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
diff_DPK[p] = (s8)thermal_value - (s8)cali_info->dpk_thermal[p];
/*4 6. If necessary, do LCK.*/
if (!(dm->support_ic_type &
ODM_RTL8821)) { /*no PG, do LCK at initial status*/
if (cali_info->thermal_value_lck == 0xff) {
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"no PG, do LCK\n");
cali_info->thermal_value_lck = thermal_value;
/*Use RTLCK, so close power tracking driver LCK*/
if (!(dm->support_ic_type & ODM_RTL8814A) &&
c.phy_lc_calibrate)
(*c.phy_lc_calibrate)(dm);
delta_LCK =
(thermal_value > cali_info->thermal_value_lck) ?
(thermal_value -
cali_info->thermal_value_lck) :
(cali_info->thermal_value_lck -
thermal_value);
}
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"(delta, delta_LCK, delta_IQK) = (%d, %d, %d)\n",
delta, delta_LCK, delta_IQK);
/*Delta temperature is equal to or larger than 20 centigrade.*/
if (delta_LCK >= c.threshold_iqk) {
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_LCK(%d) >= threshold_iqk(%d)\n",
delta_LCK, c.threshold_iqk);
cali_info->thermal_value_lck = thermal_value;
/*Use RTLCK, so close power tracking driver LCK*/
if (!(dm->support_ic_type & ODM_RTL8814A) &&
c.phy_lc_calibrate)
(*c.phy_lc_calibrate)(dm);
}
}
/*3 7. If necessary, move the index of swing table to adjust Tx power.*/
if (delta > 0 && cali_info->txpowertrack_control) {
/* "delta" here is used to record the abs value of difference.*/
delta = thermal_value > rtlefu->eeprom_thermalmeter ?
(thermal_value - rtlefu->eeprom_thermalmeter) :
(rtlefu->eeprom_thermalmeter - thermal_value);
if (delta >= TXPWR_TRACK_TABLE_SIZE)
delta = TXPWR_TRACK_TABLE_SIZE - 1;
/*4 7.1 The Final Power index = BaseIndex + power_index_offset*/
if (thermal_value > rtlefu->eeprom_thermalmeter) {
phydm_set_calibrate_info_up(
dm, &c, delta, cali_info,
delta_swing_table_idx_tup_a,
delta_swing_table_idx_tup_b,
delta_swing_table_idx_tup_c,
delta_swing_table_idx_tup_d);
/* JJ ADD 20161014 */
if (dm->support_ic_type &
(ODM_RTL8703B | ODM_RTL8723D | ODM_RTL8710B)) {
/*Save xtal_offset from Xtal table*/
/*recording last Xtal offset*/
cali_info->xtal_offset_last =
cali_info->xtal_offset;
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"[Xtal] delta_swing_table_xtal_up[%d] = %d\n",
delta,
delta_swing_table_xtal_up[delta]);
cali_info->xtal_offset =
delta_swing_table_xtal_up[delta];
xtal_offset_eanble =
(cali_info->xtal_offset_last ==
cali_info->xtal_offset) ?
0 :
1;
}
} else {
phydm_set_calibrate_info_down(
dm, &c, delta, cali_info,
delta_swing_table_idx_tdown_a,
delta_swing_table_idx_tdown_b,
delta_swing_table_idx_tdown_c,
delta_swing_table_idx_tdown_d);
/* JJ ADD 20161014 */
if (dm->support_ic_type &
(ODM_RTL8703B | ODM_RTL8723D | ODM_RTL8710B)) {
/*Save xtal_offset from Xtal table*/
/*recording last Xtal offset*/
cali_info->xtal_offset_last =
cali_info->xtal_offset;
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"[Xtal] delta_swing_table_xtal_down[%d] = %d\n",
delta,
delta_swing_table_xtal_down[delta]);
cali_info->xtal_offset =
delta_swing_table_xtal_down[delta];
xtal_offset_eanble =
(cali_info->xtal_offset_last ==
cali_info->xtal_offset) ?
0 :
1;
}
}
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"\n\n=========================== [path-%d] Calculating power_index_offset===========================\n",
p);
if (cali_info->delta_power_index[p] ==
cali_info->delta_power_index_last[p]) {
/* If Thermal value changes but lookup table
* value still the same
*/
cali_info->power_index_offset[p] = 0;
} else {
/*Power idx diff between 2 times Pwr Tracking*/
cali_info->power_index_offset[p] =
cali_info->delta_power_index[p] -
cali_info->delta_power_index_last[p];
}
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"[path-%d] power_index_offset(%d) = delta_power_index(%d) - delta_power_index_last(%d)\n",
p, cali_info->power_index_offset[p],
cali_info->delta_power_index[p],
cali_info->delta_power_index_last[p]);
cali_info->OFDM_index[p] =
cali_info->bb_swing_idx_ofdm_base[p] +
cali_info->power_index_offset[p];
cali_info->CCK_index =
cali_info->bb_swing_idx_cck_base +
cali_info->power_index_offset[p];
cali_info->bb_swing_idx_cck = cali_info->CCK_index;
cali_info->bb_swing_idx_ofdm[p] =
cali_info->OFDM_index[p];
/*******Print BB Swing base and index Offset**********/
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"The 'CCK' final index(%d) = BaseIndex(%d) + power_index_offset(%d)\n",
cali_info->bb_swing_idx_cck,
cali_info->bb_swing_idx_cck_base,
cali_info->power_index_offset[p]);
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"The 'OFDM' final index(%d) = BaseIndex[%d](%d) + power_index_offset(%d)\n",
cali_info->bb_swing_idx_ofdm[p], p,
cali_info->bb_swing_idx_ofdm_base[p],
cali_info->power_index_offset[p]);
/*4 7.1 Handle boundary conditions of index.*/
if (cali_info->OFDM_index[p] >
c.swing_table_size_ofdm - 1)
cali_info->OFDM_index[p] =
c.swing_table_size_ofdm - 1;
else if (cali_info->OFDM_index[p] <= OFDM_min_index)
cali_info->OFDM_index[p] = OFDM_min_index;
}
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"\n\n========================================================================================================\n");
if (cali_info->CCK_index > c.swing_table_size_cck - 1)
cali_info->CCK_index = c.swing_table_size_cck - 1;
else if (cali_info->CCK_index <= 0)
cali_info->CCK_index = 0;
} else {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"The thermal meter is unchanged or TxPowerTracking OFF(%d): thermal_value: %d, cali_info->thermal_value: %d\n",
cali_info->txpowertrack_control, thermal_value,
cali_info->thermal_value);
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
cali_info->power_index_offset[p] = 0;
}
/*Print Swing base & current*/
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"TxPowerTracking: [CCK] Swing Current index: %d, Swing base index: %d\n",
cali_info->CCK_index, cali_info->bb_swing_idx_cck_base);
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"TxPowerTracking: [OFDM] Swing Current index: %d, Swing base index[%d]: %d\n",
cali_info->OFDM_index[p], p,
cali_info->bb_swing_idx_ofdm_base[p]);
if ((dm->support_ic_type & ODM_RTL8814A)) {
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"power_tracking_type=%d\n", power_tracking_type);
if (power_tracking_type == 0) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"**********Enter POWER Tracking MIX_MODE**********\n");
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
(*c.odm_tx_pwr_track_set_pwr)(dm, MIX_MODE, p,
0);
} else if (power_tracking_type == 1) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"**********Enter POWER Tracking MIX(2G) TSSI(5G) MODE**********\n");
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
(*c.odm_tx_pwr_track_set_pwr)(
dm, MIX_2G_TSSI_5G_MODE, p, 0);
} else if (power_tracking_type == 2) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"**********Enter POWER Tracking MIX(5G) TSSI(2G)MODE**********\n");
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
(*c.odm_tx_pwr_track_set_pwr)(
dm, MIX_5G_TSSI_2G_MODE, p, 0);
} else if (power_tracking_type == 3) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"**********Enter POWER Tracking TSSI MODE**********\n");
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
(*c.odm_tx_pwr_track_set_pwr)(dm, TSSI_MODE, p,
0);
}
/*Record last Power Tracking Thermal value*/
cali_info->thermal_value = thermal_value;
} else if ((cali_info->power_index_offset[ODM_RF_PATH_A] != 0 ||
cali_info->power_index_offset[ODM_RF_PATH_B] != 0 ||
cali_info->power_index_offset[ODM_RF_PATH_C] != 0 ||
cali_info->power_index_offset[ODM_RF_PATH_D] != 0) &&
cali_info->txpowertrack_control &&
(rtlefu->eeprom_thermalmeter != 0xff)) {
/* 4 7.2 Configure the Swing Table to adjust Tx Power. */
/*Always true after Tx Power is adjusted by power tracking.*/
cali_info->is_tx_power_changed = true;
/* 2012/04/23 MH According to Luke's suggestion, we can not
* write BB digital to increase TX power. Otherwise, EVM will
* be bad.
*/
/* 2012/04/25 MH Add for tx power tracking to set tx power in
* tx agc for 88E.
*/
if (thermal_value > cali_info->thermal_value) {
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++) {
/* print temperature increasing */
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"Temperature Increasing(%d): delta_pi: %d, delta_t: %d, Now_t: %d, EFUSE_t: %d, Last_t: %d\n",
p, cali_info->power_index_offset[p],
delta, thermal_value,
rtlefu->eeprom_thermalmeter,
cali_info->thermal_value);
}
} else if (thermal_value <
cali_info->thermal_value) { /*Low temperature*/
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++) {
/* print temperature decreasing */
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"Temperature Decreasing(%d): delta_pi: %d, delta_t: %d, Now_t: %d, EFUSE_t: %d, Last_t: %d\n",
p, cali_info->power_index_offset[p],
delta, thermal_value,
rtlefu->eeprom_thermalmeter,
cali_info->thermal_value);
}
}
if (thermal_value > rtlefu->eeprom_thermalmeter) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"Temperature(%d) higher than PG value(%d)\n",
thermal_value, rtlefu->eeprom_thermalmeter);
phydm_odm_tx_power_set(dm, &c, indexforchannel, 0);
} else {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"Temperature(%d) lower than PG value(%d)\n",
thermal_value, rtlefu->eeprom_thermalmeter);
phydm_odm_tx_power_set(dm, &c, indexforchannel, 1);
}
/*Record last time Power Tracking result as base.*/
cali_info->bb_swing_idx_cck_base = cali_info->bb_swing_idx_cck;
for (p = ODM_RF_PATH_A; p < c.rf_path_count; p++)
cali_info->bb_swing_idx_ofdm_base[p] =
cali_info->bb_swing_idx_ofdm[p];
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"cali_info->thermal_value = %d thermal_value= %d\n",
cali_info->thermal_value, thermal_value);
/*Record last Power Tracking Thermal value*/
cali_info->thermal_value = thermal_value;
}
if (dm->support_ic_type == ODM_RTL8703B ||
dm->support_ic_type == ODM_RTL8723D ||
dm->support_ic_type == ODM_RTL8710B) { /* JJ ADD 20161014 */
if (xtal_offset_eanble != 0 &&
cali_info->txpowertrack_control &&
(rtlefu->eeprom_thermalmeter != 0xff)) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"**********Enter Xtal Tracking**********\n");
if (thermal_value > rtlefu->eeprom_thermalmeter) {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"Temperature(%d) higher than PG value(%d)\n",
thermal_value,
rtlefu->eeprom_thermalmeter);
(*c.odm_txxtaltrack_set_xtal)(dm);
} else {
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"Temperature(%d) lower than PG value(%d)\n",
thermal_value,
rtlefu->eeprom_thermalmeter);
(*c.odm_txxtaltrack_set_xtal)(dm);
}
}
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"**********End Xtal Tracking**********\n");
}
if (!IS_HARDWARE_TYPE_8723B(adapter)) {
/* Delta temperature is equal to or larger than 20 centigrade
* (When threshold is 8).
*/
if (delta_IQK >= c.threshold_iqk) {
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"delta_IQK(%d) >= threshold_iqk(%d)\n",
delta_IQK, c.threshold_iqk);
if (!cali_info->is_iqk_in_progress)
(*c.do_iqk)(dm, delta_IQK, thermal_value, 8);
}
}
if (cali_info->dpk_thermal[ODM_RF_PATH_A] != 0) {
if (diff_DPK[ODM_RF_PATH_A] >= c.threshold_dpk) {
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x1);
odm_set_bb_reg(
dm, 0xcc4,
BIT(14) | BIT(13) | BIT(12) | BIT(11) | BIT(10),
(diff_DPK[ODM_RF_PATH_A] / c.threshold_dpk));
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x0);
} else if ((diff_DPK[ODM_RF_PATH_A] <= -1 * c.threshold_dpk)) {
s32 value = 0x20 +
(diff_DPK[ODM_RF_PATH_A] / c.threshold_dpk);
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x1);
odm_set_bb_reg(dm, 0xcc4, BIT(14) | BIT(13) | BIT(12) |
BIT(11) | BIT(10),
value);
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x0);
} else {
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x1);
odm_set_bb_reg(dm, 0xcc4, BIT(14) | BIT(13) | BIT(12) |
BIT(11) | BIT(10),
0);
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x0);
}
}
if (cali_info->dpk_thermal[ODM_RF_PATH_B] != 0) {
if (diff_DPK[ODM_RF_PATH_B] >= c.threshold_dpk) {
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x1);
odm_set_bb_reg(
dm, 0xec4,
BIT(14) | BIT(13) | BIT(12) | BIT(11) | BIT(10),
(diff_DPK[ODM_RF_PATH_B] / c.threshold_dpk));
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x0);
} else if ((diff_DPK[ODM_RF_PATH_B] <= -1 * c.threshold_dpk)) {
s32 value = 0x20 +
(diff_DPK[ODM_RF_PATH_B] / c.threshold_dpk);
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x1);
odm_set_bb_reg(dm, 0xec4, BIT(14) | BIT(13) | BIT(12) |
BIT(11) | BIT(10),
value);
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x0);
} else {
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x1);
odm_set_bb_reg(dm, 0xec4, BIT(14) | BIT(13) | BIT(12) |
BIT(11) | BIT(10),
0);
odm_set_bb_reg(dm, 0x82c, BIT(31), 0x0);
}
}
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK, "<===%s\n", __func__);
cali_info->tx_powercount = 0;
}
/* 3============================================================
* 3 IQ Calibration
* 3============================================================
*/
void odm_reset_iqk_result(void *dm_void) { return; }
u8 odm_get_right_chnl_place_for_iqk(u8 chnl)
{
u8 channel_all[ODM_TARGET_CHNL_NUM_2G_5G] = {
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};
u8 place = chnl;
if (chnl > 14) {
for (place = 14; place < sizeof(channel_all); place++) {
if (channel_all[place] == chnl)
return place - 13;
}
}
return 0;
}
static void odm_iq_calibrate(struct phy_dm_struct *dm)
{
void *adapter = dm->adapter;
if (IS_HARDWARE_TYPE_8812AU(adapter))
return;
if (dm->is_linked) {
if ((*dm->channel != dm->pre_channel) &&
(!*dm->is_scan_in_process)) {
dm->pre_channel = *dm->channel;
dm->linked_interval = 0;
}
if (dm->linked_interval < 3)
dm->linked_interval++;
if (dm->linked_interval == 2) {
if (IS_HARDWARE_TYPE_8814A(adapter))
;
else if (IS_HARDWARE_TYPE_8822B(adapter))
phy_iq_calibrate_8822b(dm, false);
}
} else {
dm->linked_interval = 0;
}
}
void phydm_rf_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
odm_txpowertracking_init(dm);
odm_clear_txpowertracking_state(dm);
}
void phydm_rf_watchdog(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
odm_txpowertracking_check(dm);
if (dm->support_ic_type & ODM_IC_11AC_SERIES)
odm_iq_calibrate(dm);
}

View File

@ -0,0 +1,85 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HAL_PHY_RF_H__
#define __HAL_PHY_RF_H__
#include "phydm_kfree.h"
#include "rtl8822b/phydm_iqk_8822b.h"
#include "phydm_powertracking_ce.h"
enum spur_cal_method { PLL_RESET, AFE_PHASE_SEL };
enum pwrtrack_method {
BBSWING,
TXAGC,
MIX_MODE,
TSSI_MODE,
MIX_2G_TSSI_5G_MODE,
MIX_5G_TSSI_2G_MODE
};
typedef void (*func_set_pwr)(void *, enum pwrtrack_method, u8, u8);
typedef void (*func_iqk)(void *, u8, u8, u8);
typedef void (*func_lck)(void *);
typedef void (*func_swing)(void *, u8 **, u8 **, u8 **, u8 **);
typedef void (*func_swing8814only)(void *, u8 **, u8 **, u8 **, u8 **);
typedef void (*func_swing_xtal)(void *, s8 **, s8 **);
typedef void (*func_set_xtal)(void *);
struct txpwrtrack_cfg {
u8 swing_table_size_cck;
u8 swing_table_size_ofdm;
u8 threshold_iqk;
u8 threshold_dpk;
u8 average_thermal_num;
u8 rf_path_count;
u32 thermal_reg_addr;
func_set_pwr odm_tx_pwr_track_set_pwr;
func_iqk do_iqk;
func_lck phy_lc_calibrate;
func_swing get_delta_swing_table;
func_swing8814only get_delta_swing_table8814only;
func_swing_xtal get_delta_swing_xtal_table;
func_set_xtal odm_txxtaltrack_set_xtal;
};
void configure_txpower_track(void *dm_void, struct txpwrtrack_cfg *config);
void odm_clear_txpowertracking_state(void *dm_void);
void odm_txpowertracking_callback_thermal_meter(void *dm);
#define ODM_TARGET_CHNL_NUM_2G_5G 59
void odm_reset_iqk_result(void *dm_void);
u8 odm_get_right_chnl_place_for_iqk(u8 chnl);
void phydm_rf_init(void *dm_void);
void phydm_rf_watchdog(void *dm_void);
#endif /* #ifndef __HAL_PHY_RF_H__ */

View File

@ -0,0 +1,24 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,946 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HALDMOUTSRC_H__
#define __HALDMOUTSRC_H__
/*============================================================*/
/*include files*/
/*============================================================*/
#include "phydm_pre_define.h"
#include "phydm_dig.h"
#include "phydm_edcaturbocheck.h"
#include "phydm_antdiv.h"
#include "phydm_dynamicbbpowersaving.h"
#include "phydm_rainfo.h"
#include "phydm_dynamictxpower.h"
#include "phydm_cfotracking.h"
#include "phydm_acs.h"
#include "phydm_adaptivity.h"
#include "phydm_iqk.h"
#include "phydm_dfs.h"
#include "phydm_ccx.h"
#include "txbf/phydm_hal_txbf_api.h"
#include "phydm_adc_sampling.h"
#include "phydm_dynamic_rx_path.h"
#include "phydm_psd.h"
#include "phydm_beamforming.h"
#include "phydm_noisemonitor.h"
#include "halphyrf_ce.h"
/*============================================================*/
/*Definition */
/*============================================================*/
/* Traffic load decision */
#define TRAFFIC_ULTRA_LOW 1
#define TRAFFIC_LOW 2
#define TRAFFIC_MID 3
#define TRAFFIC_HIGH 4
#define NONE 0
/*NBI API------------------------------------*/
#define NBI_ENABLE 1
#define NBI_DISABLE 2
#define NBI_TABLE_SIZE_128 27
#define NBI_TABLE_SIZE_256 59
#define NUM_START_CH_80M 7
#define NUM_START_CH_40M 14
#define CH_OFFSET_40M 2
#define CH_OFFSET_80M 6
/*CSI MASK API------------------------------------*/
#define CSI_MASK_ENABLE 1
#define CSI_MASK_DISABLE 2
/*------------------------------------------------*/
#define FFT_128_TYPE 1
#define FFT_256_TYPE 2
#define SET_SUCCESS 1
#define SET_ERROR 2
#define SET_NO_NEED 3
#define FREQ_POSITIVE 1
#define FREQ_NEGATIVE 2
#define PHYDM_WATCH_DOG_PERIOD 2
/*============================================================*/
/*structure and define*/
/*============================================================*/
/*2011/09/20 MH Add for AP/ADSLpseudo DM structuer requirement.*/
/*We need to remove to other position???*/
struct rtl8192cd_priv {
u8 temp;
};
struct dyn_primary_cca {
u8 pri_cca_flag;
u8 intf_flag;
u8 intf_type;
u8 dup_rts_flag;
u8 monitor_flag;
u8 ch_offset;
u8 mf_state;
};
#define dm_type_by_fw 0
#define dm_type_by_driver 1
/*Declare for common info*/
#define IQK_THRESHOLD 8
#define DPK_THRESHOLD 4
struct dm_phy_status_info {
/* */
/* Be care, if you want to add any element please insert between */
/* rx_pwdb_all & signal_strength. */
/* */
u8 rx_pwdb_all;
u8 signal_quality; /* in 0-100 index. */
s8 rx_mimo_signal_quality[4]; /* per-path's EVM translate to 0~100% */
u8 rx_mimo_evm_dbm[4]; /* per-path's original EVM (dbm) */
u8 rx_mimo_signal_strength[4]; /* in 0~100 index */
s16 cfo_short[4]; /* per-path's cfo_short */
s16 cfo_tail[4]; /* per-path's cfo_tail */
s8 rx_power; /* in dBm Translate from PWdB */
s8 recv_signal_power; /* Real power in dBm for this packet,
* no beautification and aggregation.
* Keep this raw info to be used for the other
* procedures.
*/
u8 bt_rx_rssi_percentage;
u8 signal_strength; /* in 0-100 index. */
s8 rx_pwr[4]; /* per-path's pwdb */
s8 rx_snr[4]; /* per-path's SNR */
/* s8 BB_Backup[13]; backup reg. */
u8 rx_count : 2; /* RX path counter---*/
u8 band_width : 2;
u8 rxsc : 4; /* sub-channel---*/
u8 bt_coex_pwr_adjust;
u8 channel; /* channel number---*/
bool is_mu_packet; /* is MU packet or not---*/
bool is_beamformed; /* BF packet---*/
};
struct dm_per_pkt_info {
u8 data_rate;
u8 station_id;
bool is_packet_match_bssid;
bool is_packet_to_self;
bool is_packet_beacon;
bool is_to_self;
u8 ppdu_cnt;
};
struct odm_phy_dbg_info {
/*ODM Write,debug info*/
s8 rx_snr_db[4];
u32 num_qry_phy_status;
u32 num_qry_phy_status_cck;
u32 num_qry_phy_status_ofdm;
u32 num_qry_mu_pkt;
u32 num_qry_bf_pkt;
u32 num_qry_mu_vht_pkt[40];
u32 num_qry_vht_pkt[40];
bool is_ldpc_pkt;
bool is_stbc_pkt;
u8 num_of_ppdu[4];
u8 gid_num[4];
u8 num_qry_beacon_pkt;
/* Others */
s32 rx_evm[4];
};
/*2011/20/20 MH For MP driver RT_WLAN_STA = struct rtl_sta_info*/
/*Please declare below ODM relative info in your STA info structure.*/
struct odm_sta_info {
/*Driver Write*/
bool is_used; /*record the sta status link or not?*/
u8 iot_peer; /*Enum value. HT_IOT_PEER_E*/
/*ODM Write*/
/*PHY_STATUS_INFO*/
u8 rssi_path[4];
u8 rssi_ave;
u8 RXEVM[4];
u8 RXSNR[4];
};
enum odm_cmninfo {
/*Fixed value*/
/*-----------HOOK BEFORE REG INIT-----------*/
ODM_CMNINFO_PLATFORM = 0,
ODM_CMNINFO_ABILITY,
ODM_CMNINFO_INTERFACE,
ODM_CMNINFO_MP_TEST_CHIP,
ODM_CMNINFO_IC_TYPE,
ODM_CMNINFO_CUT_VER,
ODM_CMNINFO_FAB_VER,
ODM_CMNINFO_RF_TYPE,
ODM_CMNINFO_RFE_TYPE,
ODM_CMNINFO_BOARD_TYPE,
ODM_CMNINFO_PACKAGE_TYPE,
ODM_CMNINFO_EXT_LNA,
ODM_CMNINFO_5G_EXT_LNA,
ODM_CMNINFO_EXT_PA,
ODM_CMNINFO_5G_EXT_PA,
ODM_CMNINFO_GPA,
ODM_CMNINFO_APA,
ODM_CMNINFO_GLNA,
ODM_CMNINFO_ALNA,
ODM_CMNINFO_EXT_TRSW,
ODM_CMNINFO_DPK_EN,
ODM_CMNINFO_EXT_LNA_GAIN,
ODM_CMNINFO_PATCH_ID,
ODM_CMNINFO_BINHCT_TEST,
ODM_CMNINFO_BWIFI_TEST,
ODM_CMNINFO_SMART_CONCURRENT,
ODM_CMNINFO_CONFIG_BB_RF,
ODM_CMNINFO_DOMAIN_CODE_2G,
ODM_CMNINFO_DOMAIN_CODE_5G,
ODM_CMNINFO_IQKFWOFFLOAD,
ODM_CMNINFO_IQKPAOFF,
ODM_CMNINFO_HUBUSBMODE,
ODM_CMNINFO_FWDWRSVDPAGEINPROGRESS,
ODM_CMNINFO_TX_TP,
ODM_CMNINFO_RX_TP,
ODM_CMNINFO_SOUNDING_SEQ,
ODM_CMNINFO_REGRFKFREEENABLE,
ODM_CMNINFO_RFKFREEENABLE,
ODM_CMNINFO_NORMAL_RX_PATH_CHANGE,
ODM_CMNINFO_EFUSE0X3D8,
ODM_CMNINFO_EFUSE0X3D7,
/*-----------HOOK BEFORE REG INIT-----------*/
/*Dynamic value:*/
/*--------- POINTER REFERENCE-----------*/
ODM_CMNINFO_MAC_PHY_MODE,
ODM_CMNINFO_TX_UNI,
ODM_CMNINFO_RX_UNI,
ODM_CMNINFO_WM_MODE,
ODM_CMNINFO_BAND,
ODM_CMNINFO_SEC_CHNL_OFFSET,
ODM_CMNINFO_SEC_MODE,
ODM_CMNINFO_BW,
ODM_CMNINFO_CHNL,
ODM_CMNINFO_FORCED_RATE,
ODM_CMNINFO_ANT_DIV,
ODM_CMNINFO_ADAPTIVITY,
ODM_CMNINFO_DMSP_GET_VALUE,
ODM_CMNINFO_BUDDY_ADAPTOR,
ODM_CMNINFO_DMSP_IS_MASTER,
ODM_CMNINFO_SCAN,
ODM_CMNINFO_POWER_SAVING,
ODM_CMNINFO_ONE_PATH_CCA,
ODM_CMNINFO_DRV_STOP,
ODM_CMNINFO_PNP_IN,
ODM_CMNINFO_INIT_ON,
ODM_CMNINFO_ANT_TEST,
ODM_CMNINFO_NET_CLOSED,
ODM_CMNINFO_FORCED_IGI_LB,
ODM_CMNINFO_P2P_LINK,
ODM_CMNINFO_FCS_MODE,
ODM_CMNINFO_IS1ANTENNA,
ODM_CMNINFO_RFDEFAULTPATH,
ODM_CMNINFO_DFS_MASTER_ENABLE,
ODM_CMNINFO_FORCE_TX_ANT_BY_TXDESC,
ODM_CMNINFO_SET_S0S1_DEFAULT_ANTENNA,
/*--------- POINTER REFERENCE-----------*/
/*------------CALL BY VALUE-------------*/
ODM_CMNINFO_WIFI_DIRECT,
ODM_CMNINFO_WIFI_DISPLAY,
ODM_CMNINFO_LINK_IN_PROGRESS,
ODM_CMNINFO_LINK,
ODM_CMNINFO_CMW500LINK,
ODM_CMNINFO_LPSPG,
ODM_CMNINFO_STATION_STATE,
ODM_CMNINFO_RSSI_MIN,
ODM_CMNINFO_DBG_COMP,
ODM_CMNINFO_DBG_LEVEL,
ODM_CMNINFO_RA_THRESHOLD_HIGH,
ODM_CMNINFO_RA_THRESHOLD_LOW,
ODM_CMNINFO_RF_ANTENNA_TYPE,
ODM_CMNINFO_WITH_EXT_ANTENNA_SWITCH,
ODM_CMNINFO_BE_FIX_TX_ANT,
ODM_CMNINFO_BT_ENABLED,
ODM_CMNINFO_BT_HS_CONNECT_PROCESS,
ODM_CMNINFO_BT_HS_RSSI,
ODM_CMNINFO_BT_OPERATION,
ODM_CMNINFO_BT_LIMITED_DIG,
ODM_CMNINFO_BT_DIG,
ODM_CMNINFO_BT_BUSY,
ODM_CMNINFO_BT_DISABLE_EDCA,
ODM_CMNINFO_AP_TOTAL_NUM,
ODM_CMNINFO_POWER_TRAINING,
ODM_CMNINFO_DFS_REGION_DOMAIN,
/*------------CALL BY VALUE-------------*/
/*Dynamic ptr array hook itms.*/
ODM_CMNINFO_STA_STATUS,
ODM_CMNINFO_MAX,
};
enum phydm_info_query {
PHYDM_INFO_FA_OFDM,
PHYDM_INFO_FA_CCK,
PHYDM_INFO_FA_TOTAL,
PHYDM_INFO_CCA_OFDM,
PHYDM_INFO_CCA_CCK,
PHYDM_INFO_CCA_ALL,
PHYDM_INFO_CRC32_OK_VHT,
PHYDM_INFO_CRC32_OK_HT,
PHYDM_INFO_CRC32_OK_LEGACY,
PHYDM_INFO_CRC32_OK_CCK,
PHYDM_INFO_CRC32_ERROR_VHT,
PHYDM_INFO_CRC32_ERROR_HT,
PHYDM_INFO_CRC32_ERROR_LEGACY,
PHYDM_INFO_CRC32_ERROR_CCK,
PHYDM_INFO_EDCCA_FLAG,
PHYDM_INFO_OFDM_ENABLE,
PHYDM_INFO_CCK_ENABLE,
PHYDM_INFO_DBG_PORT_0
};
enum phydm_api {
PHYDM_API_NBI = 1,
PHYDM_API_CSI_MASK,
};
/*2011/10/20 MH Define ODM support ability. ODM_CMNINFO_ABILITY*/
enum odm_ability {
/*BB ODM section BIT 0-19*/
ODM_BB_DIG = BIT(0),
ODM_BB_RA_MASK = BIT(1),
ODM_BB_DYNAMIC_TXPWR = BIT(2),
ODM_BB_FA_CNT = BIT(3),
ODM_BB_RSSI_MONITOR = BIT(4),
ODM_BB_CCK_PD = BIT(5),
ODM_BB_ANT_DIV = BIT(6),
ODM_BB_PWR_TRAIN = BIT(8),
ODM_BB_RATE_ADAPTIVE = BIT(9),
ODM_BB_PATH_DIV = BIT(10),
ODM_BB_ADAPTIVITY = BIT(13),
ODM_BB_CFO_TRACKING = BIT(14),
ODM_BB_NHM_CNT = BIT(15),
ODM_BB_PRIMARY_CCA = BIT(16),
ODM_BB_TXBF = BIT(17),
ODM_BB_DYNAMIC_ARFR = BIT(18),
ODM_MAC_EDCA_TURBO = BIT(20),
ODM_BB_DYNAMIC_RX_PATH = BIT(21),
/*RF ODM section BIT 24-31*/
ODM_RF_TX_PWR_TRACK = BIT(24),
ODM_RF_RX_GAIN_TRACK = BIT(25),
ODM_RF_CALIBRATION = BIT(26),
};
/*ODM_CMNINFO_ONE_PATH_CCA*/
enum odm_cca_path {
ODM_CCA_2R = 0,
ODM_CCA_1R_A = 1,
ODM_CCA_1R_B = 2,
};
enum cca_pathdiv_en {
CCA_PATHDIV_DISABLE = 0,
CCA_PATHDIV_ENABLE = 1,
};
enum phy_reg_pg_type {
PHY_REG_PG_RELATIVE_VALUE = 0,
PHY_REG_PG_EXACT_VALUE = 1
};
/*2011/09/22 MH Copy from SD4 defined structure.
*We use to support PHY DM integration.
*/
struct phy_dm_struct {
/*Add for different team use temporarily*/
void *adapter; /*For CE/NIC team*/
struct rtl8192cd_priv *priv; /*For AP/ADSL team*/
/*When you use adapter or priv pointer,
*you must make sure the pointer is ready.
*/
bool odm_ready;
struct rtl8192cd_priv fake_priv;
enum phy_reg_pg_type phy_reg_pg_value_type;
u8 phy_reg_pg_version;
u32 debug_components;
u32 fw_debug_components;
u32 debug_level;
u32 num_qry_phy_status_all; /*CCK + OFDM*/
u32 last_num_qry_phy_status_all;
u32 rx_pwdb_ave;
bool MPDIG_2G; /*off MPDIG*/
u8 times_2g;
bool is_init_hw_info_by_rfe;
/*------ ODM HANDLE, DRIVER NEEDS NOT TO HOOK------*/
bool is_cck_high_power;
u8 rf_path_rx_enable;
u8 control_channel;
/*------ ODM HANDLE, DRIVER NEEDS NOT TO HOOK------*/
/* 1 COMMON INFORMATION */
/*Init value*/
/*-----------HOOK BEFORE REG INIT-----------*/
/*ODM Platform info AP/ADSL/CE/MP = 1/2/3/4*/
u8 support_platform;
/* ODM Platform info WIN/AP/CE = 1/2/3 */
u8 normal_rx_path;
/*ODM Support Ability DIG/RATR/TX_PWR_TRACK/ ... = 1/2/3/...*/
u32 support_ability;
/*ODM PCIE/USB/SDIO = 1/2/3*/
u8 support_interface;
/*ODM composite or independent. Bit oriented/ 92C+92D+ .... or
*any other type = 1/2/3/...
*/
u32 support_ic_type;
/*cut version TestChip/A-cut/B-cut... = 0/1/2/3/...*/
u8 cut_version;
/*Fab version TSMC/UMC = 0/1*/
u8 fab_version;
/*RF type 4T4R/3T3R/2T2R/1T2R/1T1R/...*/
u8 rf_type;
u8 rfe_type;
/*Board type Normal/HighPower/MiniCard/SLIM/Combo/... = 0/1/2/3/4/...*/
/*Enable Function DPK OFF/ON = 0/1*/
u8 dpk_en;
u8 board_type;
u8 package_type;
u16 type_glna;
u16 type_gpa;
u16 type_alna;
u16 type_apa;
/*with external LNA NO/Yes = 0/1*/
u8 ext_lna; /*2G*/
u8 ext_lna_5g; /*5G*/
/*with external PA NO/Yes = 0/1*/
u8 ext_pa; /*2G*/
u8 ext_pa_5g; /*5G*/
/*with Efuse number*/
u8 efuse0x3d7;
u8 efuse0x3d8;
/*with external TRSW NO/Yes = 0/1*/
u8 ext_trsw;
u8 ext_lna_gain; /*2G*/
u8 patch_id; /*Customer ID*/
bool is_in_hct_test;
u8 wifi_test;
bool is_dual_mac_smart_concurrent;
u32 bk_support_ability;
u8 ant_div_type;
u8 with_extenal_ant_switch;
bool config_bbrf;
u8 odm_regulation_2_4g;
u8 odm_regulation_5g;
u8 iqk_fw_offload;
bool cck_new_agc;
u8 phydm_period;
u32 phydm_sys_up_time;
u8 num_rf_path;
/*-----------HOOK BEFORE REG INIT-----------*/
/*Dynamic value*/
/*--------- POINTER REFERENCE-----------*/
u8 u1_byte_temp;
bool BOOLEAN_temp;
void *PADAPTER_temp;
/*MAC PHY mode SMSP/DMSP/DMDP = 0/1/2*/
u8 *mac_phy_mode;
/*TX Unicast byte count*/
u64 *num_tx_bytes_unicast;
/*RX Unicast byte count*/
u64 *num_rx_bytes_unicast;
/*Wireless mode B/G/A/N = BIT0/BIT1/BIT2/BIT3*/
u8 *wireless_mode;
/*Frequence band 2.4G/5G = 0/1*/
u8 *band_type;
/*Secondary channel offset don't_care/below/above = 0/1/2*/
u8 *sec_ch_offset;
/*security mode Open/WEP/AES/TKIP = 0/1/2/3*/
u8 *security;
/*BW info 20M/40M/80M = 0/1/2*/
u8 *band_width;
/*Central channel location Ch1/Ch2/....*/
u8 *channel; /*central channel number*/
bool dpk_done;
/*Common info for 92D DMSP*/
bool *is_get_value_from_other_mac;
void **buddy_adapter;
bool *is_master_of_dmsp; /* MAC0: master, MAC1: slave */
/*Common info for status*/
bool *is_scan_in_process;
bool *is_power_saving;
/*CCA path 2-path/path-A/path-B = 0/1/2; using enum odm_cca_path.*/
u8 *one_path_cca;
u8 *antenna_test;
bool *is_net_closed;
u8 *pu1_forced_igi_lb;
bool *is_fcs_mode_enable;
/*--------- For 8723B IQK-----------*/
bool *is_1_antenna;
u8 *rf_default_path;
/* 0:S1, 1:S0 */
/*--------- POINTER REFERENCE-----------*/
u16 *forced_data_rate;
u8 *enable_antdiv;
u8 *enable_adaptivity;
u8 *hub_usb_mode;
bool *is_fw_dw_rsvd_page_in_progress;
u32 *current_tx_tp;
u32 *current_rx_tp;
u8 *sounding_seq;
/*------------CALL BY VALUE-------------*/
bool is_link_in_process;
bool is_wifi_direct;
bool is_wifi_display;
bool is_linked;
bool is_linkedcmw500;
bool is_in_lps_pg;
bool bsta_state;
u8 rssi_min;
u8 interface_index; /*Add for 92D dual MAC: 0--Mac0 1--Mac1*/
bool is_mp_chip;
bool is_one_entry_only;
bool mp_mode;
u32 one_entry_macid;
u8 pre_number_linked_client;
u8 number_linked_client;
u8 pre_number_active_client;
u8 number_active_client;
/*Common info for BTDM*/
bool is_bt_enabled; /*BT is enabled*/
bool is_bt_connect_process; /*BT HS is under connection progress.*/
u8 bt_hs_rssi; /*BT HS mode wifi rssi value.*/
bool is_bt_hs_operation; /*BT HS mode is under progress*/
u8 bt_hs_dig_val; /*use BT rssi to decide the DIG value*/
bool is_bt_disable_edca_turbo; /*Under some condition, don't enable*/
bool is_bt_busy; /*BT is busy.*/
bool is_bt_limited_dig; /*BT is busy.*/
bool is_disable_phy_api;
/*------------CALL BY VALUE-------------*/
u8 rssi_a;
u8 rssi_b;
u8 rssi_c;
u8 rssi_d;
u64 rssi_trsw;
u64 rssi_trsw_h;
u64 rssi_trsw_l;
u64 rssi_trsw_iso;
u8 tx_ant_status;
u8 rx_ant_status;
u8 cck_lna_idx;
u8 cck_vga_idx;
u8 curr_station_id;
u8 ofdm_agc_idx[4];
u8 rx_rate;
bool is_noisy_state;
u8 tx_rate;
u8 linked_interval;
u8 pre_channel;
u32 txagc_offset_value_a;
bool is_txagc_offset_positive_a;
u32 txagc_offset_value_b;
bool is_txagc_offset_positive_b;
u32 tx_tp;
u32 rx_tp;
u32 total_tp;
u64 cur_tx_ok_cnt;
u64 cur_rx_ok_cnt;
u64 last_tx_ok_cnt;
u64 last_rx_ok_cnt;
u32 bb_swing_offset_a;
bool is_bb_swing_offset_positive_a;
u32 bb_swing_offset_b;
bool is_bb_swing_offset_positive_b;
u8 igi_lower_bound;
u8 igi_upper_bound;
u8 antdiv_rssi;
u8 fat_comb_a;
u8 fat_comb_b;
u8 antdiv_intvl;
u8 ant_type;
u8 pre_ant_type;
u8 antdiv_period;
u8 evm_antdiv_period;
u8 antdiv_select;
u8 path_select;
u8 antdiv_evm_en;
u8 bdc_holdstate;
u8 ndpa_period;
bool h2c_rarpt_connect;
bool cck_agc_report_type;
u8 dm_dig_max_TH;
u8 dm_dig_min_TH;
u8 print_agc;
u8 traffic_load;
u8 pre_traffic_load;
/*8821C Antenna BTG/WLG/WLA Select*/
u8 current_rf_set_8821c;
u8 default_rf_set_8821c;
/*For Adaptivtiy*/
u16 nhm_cnt_0;
u16 nhm_cnt_1;
s8 TH_L2H_default;
s8 th_edcca_hl_diff_default;
s8 th_l2h_ini;
s8 th_edcca_hl_diff;
s8 th_l2h_ini_mode2;
s8 th_edcca_hl_diff_mode2;
bool carrier_sense_enable;
u8 adaptivity_igi_upper;
bool adaptivity_flag;
u8 dc_backoff;
bool adaptivity_enable;
u8 ap_total_num;
bool edcca_enable;
u8 pre_dbg_priority;
struct adaptivity_statistics adaptivity;
/*For Adaptivtiy*/
u8 last_usb_hub;
u8 tx_bf_data_rate;
u8 nbi_set_result;
u8 c2h_cmd_start;
u8 fw_debug_trace[60];
u8 pre_c2h_seq;
bool fw_buff_is_enpty;
u32 data_frame_num;
/*for noise detection*/
bool noisy_decision; /*b_noisy*/
bool pre_b_noisy;
u32 noisy_decision_smooth;
bool is_disable_dym_ecs;
struct odm_noise_monitor noise_level;
/*Define STA info.*/
/*odm_sta_info*/
/*2012/01/12 MH For MP,
*we need to reduce one array pointer for default port.??
*/
struct rtl_sta_info *odm_sta_info[ODM_ASSOCIATE_ENTRY_NUM];
u16 platform2phydm_macid_table[ODM_ASSOCIATE_ENTRY_NUM];
/* platform_macid_table[platform_macid] = phydm_macid */
s32 accumulate_pwdb[ODM_ASSOCIATE_ENTRY_NUM];
/*2012/02/14 MH Add to share 88E ra with other SW team.*/
/*We need to colelct all support abilit to a proper area.*/
bool ra_support88e;
struct odm_phy_dbg_info phy_dbg_info;
/*ODM Structure*/
struct fast_antenna_training dm_fat_table;
struct dig_thres dm_dig_table;
struct dyn_pwr_saving dm_ps_table;
struct dyn_primary_cca dm_pri_cca;
struct ra_table dm_ra_table;
struct false_alarm_stat false_alm_cnt;
struct false_alarm_stat flase_alm_cnt_buddy_adapter;
struct sw_antenna_switch dm_swat_table;
struct cfo_tracking dm_cfo_track;
struct acs_info dm_acs;
struct ccx_info dm_ccx_info;
struct psd_info dm_psd_table;
struct rt_adcsmp adcsmp;
struct dm_iqk_info IQK_info;
struct edca_turbo dm_edca_table;
u32 WMMEDCA_BE;
bool *is_driver_stopped;
bool *is_driver_is_going_to_pnp_set_power_sleep;
bool *pinit_adpt_in_progress;
/*PSD*/
bool is_user_assign_level;
u8 RSSI_BT; /*come from BT*/
bool is_psd_in_process;
bool is_psd_active;
bool is_dm_initial_gain_enable;
/*MPT DIG*/
struct timer_list mpt_dig_timer;
/*for rate adaptive, in fact, 88c/92c fw will handle this*/
u8 is_use_ra_mask;
/* for dynamic SoML control */
bool bsomlenabled;
struct odm_rate_adaptive rate_adaptive;
struct dm_rf_calibration_struct rf_calibrate_info;
u32 n_iqk_cnt;
u32 n_iqk_ok_cnt;
u32 n_iqk_fail_cnt;
/*Power Training*/
u8 force_power_training_state;
bool is_change_state;
u32 PT_score;
u64 ofdm_rx_cnt;
u64 cck_rx_cnt;
bool is_disable_power_training;
u8 dynamic_tx_high_power_lvl;
u8 last_dtp_lvl;
u32 tx_agc_ofdm_18_6;
u8 rx_pkt_type;
/*ODM relative time.*/
struct timer_list path_div_switch_timer;
/*2011.09.27 add for path Diversity*/
struct timer_list cck_path_diversity_timer;
struct timer_list fast_ant_training_timer;
struct timer_list sbdcnt_timer;
/*ODM relative workitem.*/
};
enum phydm_structure_type {
PHYDM_FALSEALMCNT,
PHYDM_CFOTRACK,
PHYDM_ADAPTIVITY,
PHYDM_ROMINFO,
};
enum odm_rf_content {
odm_radioa_txt = 0x1000,
odm_radiob_txt = 0x1001,
odm_radioc_txt = 0x1002,
odm_radiod_txt = 0x1003
};
enum odm_bb_config_type {
CONFIG_BB_PHY_REG,
CONFIG_BB_AGC_TAB,
CONFIG_BB_AGC_TAB_2G,
CONFIG_BB_AGC_TAB_5G,
CONFIG_BB_PHY_REG_PG,
CONFIG_BB_PHY_REG_MP,
CONFIG_BB_AGC_TAB_DIFF,
};
enum odm_rf_config_type {
CONFIG_RF_RADIO,
CONFIG_RF_TXPWR_LMT,
};
enum odm_fw_config_type {
CONFIG_FW_NIC,
CONFIG_FW_NIC_2,
CONFIG_FW_AP,
CONFIG_FW_AP_2,
CONFIG_FW_MP,
CONFIG_FW_WOWLAN,
CONFIG_FW_WOWLAN_2,
CONFIG_FW_AP_WOWLAN,
CONFIG_FW_BT,
};
/*status code*/
enum rt_status {
RT_STATUS_SUCCESS,
RT_STATUS_FAILURE,
RT_STATUS_PENDING,
RT_STATUS_RESOURCE,
RT_STATUS_INVALID_CONTEXT,
RT_STATUS_INVALID_PARAMETER,
RT_STATUS_NOT_SUPPORT,
RT_STATUS_OS_API_FAILED,
};
/*===========================================================*/
/*AGC RX High Power mode*/
/*===========================================================*/
#define lna_low_gain_1 0x64
#define lna_low_gain_2 0x5A
#define lna_low_gain_3 0x58
#define FA_RXHP_TH1 5000
#define FA_RXHP_TH2 1500
#define FA_RXHP_TH3 800
#define FA_RXHP_TH4 600
#define FA_RXHP_TH5 500
enum dm_1r_cca {
CCA_1R = 0,
CCA_2R = 1,
CCA_MAX = 2,
};
enum dm_rf {
rf_save = 0,
rf_normal = 1,
RF_MAX = 2,
};
/*check Sta pointer valid or not*/
#define IS_STA_VALID(sta) (sta)
u32 odm_convert_to_db(u32 value);
u32 odm_convert_to_linear(u32 value);
s32 odm_pwdb_conversion(s32 X, u32 total_bit, u32 decimal_bit);
s32 odm_sign_conversion(s32 value, u32 total_bit);
void odm_init_mp_driver_status(struct phy_dm_struct *dm);
void phydm_txcurrentcalibration(struct phy_dm_struct *dm);
void phydm_seq_sorting(void *dm_void, u32 *value, u32 *rank_idx, u32 *idx_out,
u8 seq_length);
void odm_dm_init(struct phy_dm_struct *dm);
void odm_dm_reset(struct phy_dm_struct *dm);
void phydm_support_ability_debug(void *dm_void, u32 *const dm_value, u32 *_used,
char *output, u32 *_out_len);
void phydm_config_ofdm_rx_path(struct phy_dm_struct *dm, u32 path);
void phydm_config_trx_path(void *dm_void, u32 *const dm_value, u32 *_used,
char *output, u32 *_out_len);
void odm_dm_watchdog(struct phy_dm_struct *dm);
void phydm_watchdog_mp(struct phy_dm_struct *dm);
void odm_cmn_info_init(struct phy_dm_struct *dm, enum odm_cmninfo cmn_info,
u32 value);
void odm_cmn_info_hook(struct phy_dm_struct *dm, enum odm_cmninfo cmn_info,
void *value);
void odm_cmn_info_ptr_array_hook(struct phy_dm_struct *dm,
enum odm_cmninfo cmn_info, u16 index,
void *value);
void odm_cmn_info_update(struct phy_dm_struct *dm, u32 cmn_info, u64 value);
u32 phydm_cmn_info_query(struct phy_dm_struct *dm,
enum phydm_info_query info_type);
void odm_init_all_timers(struct phy_dm_struct *dm);
void odm_cancel_all_timers(struct phy_dm_struct *dm);
void odm_release_all_timers(struct phy_dm_struct *dm);
void odm_asoc_entry_init(struct phy_dm_struct *dm);
void *phydm_get_structure(struct phy_dm_struct *dm, u8 structure_type);
/*===========================================================*/
/* The following is for compile only*/
/*===========================================================*/
#define IS_HARDWARE_TYPE_8188E(_adapter) false
#define IS_HARDWARE_TYPE_8188F(_adapter) false
#define IS_HARDWARE_TYPE_8703B(_adapter) false
#define IS_HARDWARE_TYPE_8723D(_adapter) false
#define IS_HARDWARE_TYPE_8821C(_adapter) false
#define IS_HARDWARE_TYPE_8812AU(_adapter) false
#define IS_HARDWARE_TYPE_8814A(_adapter) false
#define IS_HARDWARE_TYPE_8814AU(_adapter) false
#define IS_HARDWARE_TYPE_8814AE(_adapter) false
#define IS_HARDWARE_TYPE_8814AS(_adapter) false
#define IS_HARDWARE_TYPE_8723BU(_adapter) false
#define IS_HARDWARE_TYPE_8822BU(_adapter) false
#define IS_HARDWARE_TYPE_8822BS(_adapter) false
#define IS_HARDWARE_TYPE_JAGUAR(_adapter) \
(IS_HARDWARE_TYPE_8812(_adapter) || IS_HARDWARE_TYPE_8821(_adapter))
#define IS_HARDWARE_TYPE_8723AE(_adapter) false
#define IS_HARDWARE_TYPE_8192C(_adapter) false
#define IS_HARDWARE_TYPE_8192D(_adapter) false
#define RF_T_METER_92D 0x42
#define GET_RX_STATUS_DESC_RX_MCS(__prx_status_desc) \
LE_BITS_TO_1BYTE(__prx_status_desc + 12, 0, 6)
#define REG_CONFIG_RAM64X16 0xb2c
#define TARGET_CHNL_NUM_2G_5G 59
/* *********************************************************** */
void odm_dtc(struct phy_dm_struct *dm);
void phydm_noisy_detection(struct phy_dm_struct *dm);
void phydm_set_ext_switch(void *dm_void, u32 *const dm_value, u32 *_used,
char *output, u32 *_out_len);
void phydm_api_debug(void *dm_void, u32 function_map, u32 *const dm_value,
u32 *_used, char *output, u32 *_out_len);
u8 phydm_nbi_setting(void *dm_void, u32 enable, u32 channel, u32 bw,
u32 f_interference, u32 second_ch);
#endif /* __HALDMOUTSRC_H__ */

View File

@ -0,0 +1,200 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
u8 odm_get_auto_channel_select_result(void *dm_void, u8 band)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct acs_info *acs = &dm->dm_acs;
u8 result;
if (band == ODM_BAND_2_4G) {
ODM_RT_TRACE(
dm, ODM_COMP_ACS,
"[struct acs_info] %s(): clean_channel_2g(%d)\n",
__func__, acs->clean_channel_2g);
result = (u8)acs->clean_channel_2g;
} else {
ODM_RT_TRACE(
dm, ODM_COMP_ACS,
"[struct acs_info] %s(): clean_channel_5g(%d)\n",
__func__, acs->clean_channel_5g);
result = (u8)acs->clean_channel_5g;
}
return result;
}
static void odm_auto_channel_select_setting(void *dm_void, bool is_enable)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u16 period = 0x2710; /* 40ms in default */
u16 nhm_type = 0x7;
ODM_RT_TRACE(dm, ODM_COMP_ACS, "%s()=========>\n", __func__);
if (is_enable) {
/* 20 ms */
period = 0x1388;
nhm_type = 0x1;
}
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
/* PHY parameters initialize for ac series */
/* 0x990[31:16]=0x2710
* Time duration for NHM unit: 4us, 0x2710=40ms
*/
odm_write_2byte(dm, ODM_REG_CCX_PERIOD_11AC + 2, period);
} else if (dm->support_ic_type & ODM_IC_11N_SERIES) {
/* PHY parameters initialize for n series */
/* 0x894[31:16]=0x2710
* Time duration for NHM unit: 4us, 0x2710=40ms
*/
odm_write_2byte(dm, ODM_REG_CCX_PERIOD_11N + 2, period);
}
}
void odm_auto_channel_select_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct acs_info *acs = &dm->dm_acs;
u8 i;
if (!(dm->support_ability & ODM_BB_NHM_CNT))
return;
if (acs->is_force_acs_result)
return;
ODM_RT_TRACE(dm, ODM_COMP_ACS, "%s()=========>\n", __func__);
acs->clean_channel_2g = 1;
acs->clean_channel_5g = 36;
for (i = 0; i < ODM_MAX_CHANNEL_2G; ++i) {
acs->channel_info_2g[0][i] = 0;
acs->channel_info_2g[1][i] = 0;
}
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
for (i = 0; i < ODM_MAX_CHANNEL_5G; ++i) {
acs->channel_info_5g[0][i] = 0;
acs->channel_info_5g[1][i] = 0;
}
}
}
void odm_auto_channel_select_reset(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct acs_info *acs = &dm->dm_acs;
if (!(dm->support_ability & ODM_BB_NHM_CNT))
return;
if (acs->is_force_acs_result)
return;
ODM_RT_TRACE(dm, ODM_COMP_ACS, "%s()=========>\n", __func__);
odm_auto_channel_select_setting(dm, true); /* for 20ms measurement */
phydm_nhm_counter_statistics_reset(dm);
}
void odm_auto_channel_select(void *dm_void, u8 channel)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct acs_info *acs = &dm->dm_acs;
u8 channel_idx = 0, search_idx = 0;
u16 max_score = 0;
if (!(dm->support_ability & ODM_BB_NHM_CNT)) {
ODM_RT_TRACE(
dm, ODM_COMP_DIG,
"%s(): Return: support_ability ODM_BB_NHM_CNT is disabled\n",
__func__);
return;
}
if (acs->is_force_acs_result) {
ODM_RT_TRACE(
dm, ODM_COMP_DIG,
"%s(): Force 2G clean channel = %d, 5G clean channel = %d\n",
__func__, acs->clean_channel_2g, acs->clean_channel_5g);
return;
}
ODM_RT_TRACE(dm, ODM_COMP_ACS, "%s(): channel = %d=========>\n",
__func__, channel);
phydm_get_nhm_counter_statistics(dm);
odm_auto_channel_select_setting(dm, false);
if (channel >= 1 && channel <= 14) {
channel_idx = channel - 1;
acs->channel_info_2g[1][channel_idx]++;
if (acs->channel_info_2g[1][channel_idx] >= 2)
acs->channel_info_2g[0][channel_idx] =
(acs->channel_info_2g[0][channel_idx] >> 1) +
(acs->channel_info_2g[0][channel_idx] >> 2) +
(dm->nhm_cnt_0 >> 2);
else
acs->channel_info_2g[0][channel_idx] = dm->nhm_cnt_0;
ODM_RT_TRACE(dm, ODM_COMP_ACS, "%s(): nhm_cnt_0 = %d\n",
__func__, dm->nhm_cnt_0);
ODM_RT_TRACE(
dm, ODM_COMP_ACS,
"%s(): Channel_Info[0][%d] = %d, Channel_Info[1][%d] = %d\n",
__func__, channel_idx,
acs->channel_info_2g[0][channel_idx], channel_idx,
acs->channel_info_2g[1][channel_idx]);
for (search_idx = 0; search_idx < ODM_MAX_CHANNEL_2G;
search_idx++) {
if (acs->channel_info_2g[1][search_idx] != 0 &&
acs->channel_info_2g[0][search_idx] >= max_score) {
max_score = acs->channel_info_2g[0][search_idx];
acs->clean_channel_2g = search_idx + 1;
}
}
ODM_RT_TRACE(
dm, ODM_COMP_ACS,
"(1)%s(): 2G: clean_channel_2g = %d, max_score = %d\n",
__func__, acs->clean_channel_2g, max_score);
} else if (channel >= 36) {
/* Need to do */
acs->clean_channel_5g = channel;
}
}

View File

@ -0,0 +1,57 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMACS_H__
#define __PHYDMACS_H__
#define ACS_VERSION "1.1" /*20150729 by YuChen*/
#define CLM_VERSION "1.0"
#define ODM_MAX_CHANNEL_2G 14
#define ODM_MAX_CHANNEL_5G 24
/* For phydm_auto_channel_select_setting_ap() */
#define STORE_DEFAULT_NHM_SETTING 0
#define RESTORE_DEFAULT_NHM_SETTING 1
#define ACS_NHM_SETTING 2
struct acs_info {
bool is_force_acs_result;
u8 clean_channel_2g;
u8 clean_channel_5g;
/* channel_info[1]: channel score, channel_info[2]:channel_scan_times */
u16 channel_info_2g[2][ODM_MAX_CHANNEL_2G];
u16 channel_info_5g[2][ODM_MAX_CHANNEL_5G];
};
void odm_auto_channel_select_init(void *dm_void);
void odm_auto_channel_select_reset(void *dm_void);
void odm_auto_channel_select(void *dm_void, u8 channel);
u8 odm_get_auto_channel_select_result(void *dm_void, u8 band);
#endif /* #ifndef __PHYDMACS_H__ */

View File

@ -0,0 +1,941 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
void phydm_check_adaptivity(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
if (dm->support_ability & ODM_BB_ADAPTIVITY) {
if (adaptivity->dynamic_link_adaptivity ||
adaptivity->acs_for_adaptivity) {
if (dm->is_linked && !adaptivity->is_check) {
phydm_nhm_counter_statistics(dm);
phydm_check_environment(dm);
} else if (!dm->is_linked) {
adaptivity->is_check = false;
}
} else {
dm->adaptivity_enable = true;
if (dm->support_ic_type & (ODM_IC_11AC_GAIN_IDX_EDCCA |
ODM_IC_11N_GAIN_IDX_EDCCA))
dm->adaptivity_flag = false;
else
dm->adaptivity_flag = true;
}
} else {
dm->adaptivity_enable = false;
dm->adaptivity_flag = false;
}
}
void phydm_nhm_counter_statistics_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11N_SERIES) {
/*PHY parameters initialize for n series*/
/*0x894[31:16]=0x0xC350
*Time duration for NHM unit: us, 0xc350=200ms
*/
odm_write_2byte(dm, ODM_REG_CCX_PERIOD_11N + 2, 0xC350);
/*0x890[31:16]=0xffff th_9, th_10*/
odm_write_2byte(dm, ODM_REG_NHM_TH9_TH10_11N + 2, 0xffff);
/*0x898=0xffffff52 th_3, th_2, th_1, th_0*/
odm_write_4byte(dm, ODM_REG_NHM_TH3_TO_TH0_11N, 0xffffff50);
/*0x89c=0xffffffff th_7, th_6, th_5, th_4*/
odm_write_4byte(dm, ODM_REG_NHM_TH7_TO_TH4_11N, 0xffffffff);
/*0xe28[7:0]=0xff th_8*/
odm_set_bb_reg(dm, ODM_REG_FPGA0_IQK_11N, MASKBYTE0, 0xff);
/*0x890[10:8]=1 ignoreCCA ignore PHYTXON enable CCX*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N,
BIT(10) | BIT(9) | BIT(8), 0x1);
/*0xc0c[7]=1 max power among all RX ants*/
odm_set_bb_reg(dm, ODM_REG_OFDM_FA_RSTC_11N, BIT(7), 0x1);
} else if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
/*PHY parameters initialize for ac series*/
odm_write_2byte(dm, ODM_REG_CCX_PERIOD_11AC + 2, 0xC350);
/*0x994[31:16]=0xffff th_9, th_10*/
odm_write_2byte(dm, ODM_REG_NHM_TH9_TH10_11AC + 2, 0xffff);
/*0x998=0xffffff52 th_3, th_2, th_1, th_0*/
odm_write_4byte(dm, ODM_REG_NHM_TH3_TO_TH0_11AC, 0xffffff50);
/*0x99c=0xffffffff th_7, th_6, th_5, th_4*/
odm_write_4byte(dm, ODM_REG_NHM_TH7_TO_TH4_11AC, 0xffffffff);
/*0x9a0[7:0]=0xff th_8*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0, 0xff);
/*0x994[10:8]=1 ignoreCCA ignore PHYTXON enable CCX*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC,
BIT(8) | BIT(9) | BIT(10), 0x1);
/*0x9e8[7]=1 max power among all RX ants*/
odm_set_bb_reg(dm, ODM_REG_NHM_9E8_11AC, BIT(0), 0x1);
}
}
void phydm_nhm_counter_statistics(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (!(dm->support_ability & ODM_BB_NHM_CNT))
return;
/*Get NHM report*/
phydm_get_nhm_counter_statistics(dm);
/*Reset NHM counter*/
phydm_nhm_counter_statistics_reset(dm);
}
void phydm_get_nhm_counter_statistics(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u32 value32 = 0;
if (dm->support_ic_type & ODM_IC_11AC_SERIES)
value32 = odm_get_bb_reg(dm, ODM_REG_NHM_CNT_11AC, MASKDWORD);
else if (dm->support_ic_type & ODM_IC_11N_SERIES)
value32 = odm_get_bb_reg(dm, ODM_REG_NHM_CNT_11N, MASKDWORD);
dm->nhm_cnt_0 = (u8)(value32 & MASKBYTE0);
dm->nhm_cnt_1 = (u8)((value32 & MASKBYTE1) >> 8);
}
void phydm_nhm_counter_statistics_reset(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11N_SERIES) {
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(1), 0);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(1), 1);
} else if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(1), 0);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(1), 1);
}
}
void phydm_set_edcca_threshold(void *dm_void, s8 H2L, s8 L2H)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11N_SERIES)
odm_set_bb_reg(dm, REG_OFDM_0_ECCA_THRESHOLD,
MASKBYTE2 | MASKBYTE0,
(u32)((u8)L2H | (u8)H2L << 16));
else if (dm->support_ic_type & ODM_IC_11AC_SERIES)
odm_set_bb_reg(dm, REG_FPGA0_XB_LSSI_READ_BACK, MASKLWORD,
(u16)((u8)L2H | (u8)H2L << 8));
}
static void phydm_set_lna(void *dm_void, enum phydm_set_lna type)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & (ODM_RTL8188E | ODM_RTL8192E)) {
if (type == phydm_disable_lna) {
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x0000f);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0x37f82); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
if (dm->rf_type > ODM_1T1R) {
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x30, 0xfffff,
0x18000);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x31, 0xfffff,
0x0000f);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x32, 0xfffff,
0x37f82);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x0);
}
} else if (type == phydm_enable_lna) {
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x0000f);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0x77f82); /*back to normal*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
if (dm->rf_type > ODM_1T1R) {
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x30, 0xfffff,
0x18000);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x31, 0xfffff,
0x0000f);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x32, 0xfffff,
0x77f82);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x0);
}
}
} else if (dm->support_ic_type & ODM_RTL8723B) {
if (type == phydm_disable_lna) {
/*S0*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x0001f);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0xe6137); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
/*S1*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xed, 0x00020, 0x1);
odm_set_rf_reg(
dm, ODM_RF_PATH_A, 0x43, 0xfffff,
0x3008d); /*select Rx mode and disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xed, 0x00020, 0x0);
} else if (type == phydm_enable_lna) {
/*S0*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x0001f);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0xe6177); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
/*S1*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xed, 0x00020, 0x1);
odm_set_rf_reg(
dm, ODM_RF_PATH_A, 0x43, 0xfffff,
0x300bd); /*select Rx mode and disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xed, 0x00020, 0x0);
}
} else if (dm->support_ic_type & ODM_RTL8812) {
if (type == phydm_disable_lna) {
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x3f7ff);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0xc22bf); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
if (dm->rf_type > ODM_1T1R) {
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x31, 0xfffff,
0x3f7ff);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x32, 0xfffff,
0xc22bf); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x0);
}
} else if (type == phydm_enable_lna) {
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x3f7ff);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0xc26bf); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
if (dm->rf_type > ODM_1T1R) {
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x31, 0xfffff,
0x3f7ff);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x32, 0xfffff,
0xc26bf); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0xef, 0x80000,
0x0);
}
}
} else if (dm->support_ic_type & (ODM_RTL8821 | ODM_RTL8881A)) {
if (type == phydm_disable_lna) {
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x0002f);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0xfb09b); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
} else if (type == phydm_enable_lna) {
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x1);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x30, 0xfffff,
0x18000); /*select Rx mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x31, 0xfffff,
0x0002f);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x32, 0xfffff,
0xfb0bb); /*disable LNA*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0xef, 0x80000, 0x0);
}
}
}
void phydm_set_trx_mux(void *dm_void, enum phydm_trx_mux_type tx_mode,
enum phydm_trx_mux_type rx_mode)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11N_SERIES) {
/*set TXmod to standby mode to remove outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_CCK_RPT_FORMAT_11N,
BIT(3) | BIT(2) | BIT(1), tx_mode);
/*set RXmod to standby mode to remove outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_CCK_RPT_FORMAT_11N,
BIT(22) | BIT(21) | BIT(20), rx_mode);
if (dm->rf_type > ODM_1T1R) {
/*set TXmod to standby mode to rm outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_CCK_RPT_FORMAT_11N_B,
BIT(3) | BIT(2) | BIT(1), tx_mode);
/*set RXmod to standby mode to rm outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_CCK_RPT_FORMAT_11N_B,
BIT(22) | BIT(21) | BIT(20), rx_mode);
}
} else if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
/*set TXmod to standby mode to remove outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_TRMUX_11AC,
BIT(11) | BIT(10) | BIT(9) | BIT(8), tx_mode);
/*set RXmod to standby mode to remove outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_TRMUX_11AC,
BIT(7) | BIT(6) | BIT(5) | BIT(4), rx_mode);
if (dm->rf_type > ODM_1T1R) {
/*set TXmod to standby mode to rm outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_TRMUX_11AC_B,
BIT(11) | BIT(10) | BIT(9) | BIT(8),
tx_mode);
/*set RXmod to standby mode to rm outside noise affect*/
odm_set_bb_reg(dm, ODM_REG_TRMUX_11AC_B,
BIT(7) | BIT(6) | BIT(5) | BIT(4),
rx_mode);
}
}
}
void phydm_mac_edcca_state(void *dm_void, enum phydm_mac_edcca_type state)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (state == phydm_ignore_edcca) {
/*ignore EDCCA reg520[15]=1*/
odm_set_mac_reg(dm, REG_TX_PTCL_CTRL, BIT(15), 1);
} else { /*don't set MAC ignore EDCCA signal*/
/*don't ignore EDCCA reg520[15]=0*/
odm_set_mac_reg(dm, REG_TX_PTCL_CTRL, BIT(15), 0);
}
ODM_RT_TRACE(dm, PHYDM_COMP_ADAPTIVITY, "EDCCA enable state = %d\n",
state);
}
bool phydm_cal_nhm_cnt(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u16 base = 0;
base = dm->nhm_cnt_0 + dm->nhm_cnt_1;
if (base != 0) {
dm->nhm_cnt_0 = ((dm->nhm_cnt_0) << 8) / base;
dm->nhm_cnt_1 = ((dm->nhm_cnt_1) << 8) / base;
}
if ((dm->nhm_cnt_0 - dm->nhm_cnt_1) >= 100)
return true; /*clean environment*/
else
return false; /*noisy environment*/
}
void phydm_check_environment(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
bool is_clean_environment = false;
if (adaptivity->is_first_link) {
if (dm->support_ic_type &
(ODM_IC_11AC_GAIN_IDX_EDCCA | ODM_IC_11N_GAIN_IDX_EDCCA))
dm->adaptivity_flag = false;
else
dm->adaptivity_flag = true;
adaptivity->is_first_link = false;
return;
}
if (adaptivity->nhm_wait < 3) { /*Start enter NHM after 4 nhm_wait*/
adaptivity->nhm_wait++;
phydm_nhm_counter_statistics(dm);
return;
}
phydm_nhm_counter_statistics(dm);
is_clean_environment = phydm_cal_nhm_cnt(dm);
if (is_clean_environment) {
dm->th_l2h_ini =
adaptivity->th_l2h_ini_backup; /*adaptivity mode*/
dm->th_edcca_hl_diff = adaptivity->th_edcca_hl_diff_backup;
dm->adaptivity_enable = true;
if (dm->support_ic_type &
(ODM_IC_11AC_GAIN_IDX_EDCCA | ODM_IC_11N_GAIN_IDX_EDCCA))
dm->adaptivity_flag = false;
else
dm->adaptivity_flag = true;
} else {
if (!adaptivity->acs_for_adaptivity) {
dm->th_l2h_ini = dm->th_l2h_ini_mode2; /*mode2*/
dm->th_edcca_hl_diff = dm->th_edcca_hl_diff_mode2;
dm->adaptivity_flag = false;
dm->adaptivity_enable = false;
}
}
adaptivity->nhm_wait = 0;
adaptivity->is_first_link = true;
adaptivity->is_check = true;
}
void phydm_search_pwdb_lower_bound(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
u32 value32 = 0, reg_value32 = 0;
u8 cnt, try_count = 0;
u8 tx_edcca1 = 0, tx_edcca0 = 0;
bool is_adjust = true;
s8 th_l2h_dmc, th_h2l_dmc, igi_target = 0x32;
s8 diff;
u8 IGI = adaptivity->igi_base + 30 + (u8)dm->th_l2h_ini -
(u8)dm->th_edcca_hl_diff;
if (dm->support_ic_type & (ODM_RTL8723B | ODM_RTL8188E | ODM_RTL8192E |
ODM_RTL8812 | ODM_RTL8821 | ODM_RTL8881A)) {
phydm_set_lna(dm, phydm_disable_lna);
} else {
phydm_set_trx_mux(dm, phydm_standby_mode, phydm_standby_mode);
odm_pause_dig(dm, PHYDM_PAUSE, PHYDM_PAUSE_LEVEL_0, 0x7e);
}
diff = igi_target - (s8)IGI;
th_l2h_dmc = dm->th_l2h_ini + diff;
if (th_l2h_dmc > 10)
th_l2h_dmc = 10;
th_h2l_dmc = th_l2h_dmc - dm->th_edcca_hl_diff;
phydm_set_edcca_threshold(dm, th_h2l_dmc, th_l2h_dmc);
ODM_delay_ms(30);
while (is_adjust) {
if (dm->support_ic_type & ODM_IC_11N_SERIES) {
odm_set_bb_reg(dm, ODM_REG_DBG_RPT_11N, MASKDWORD, 0x0);
reg_value32 =
odm_get_bb_reg(dm, ODM_REG_RPT_11N, MASKDWORD);
} else if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, ODM_REG_DBG_RPT_11AC, MASKDWORD,
0x0);
reg_value32 =
odm_get_bb_reg(dm, ODM_REG_RPT_11AC, MASKDWORD);
}
while (reg_value32 & BIT(3) && try_count < 3) {
ODM_delay_ms(3);
try_count = try_count + 1;
if (dm->support_ic_type & ODM_IC_11N_SERIES)
reg_value32 = odm_get_bb_reg(
dm, ODM_REG_RPT_11N, MASKDWORD);
else if (dm->support_ic_type & ODM_IC_11AC_SERIES)
reg_value32 = odm_get_bb_reg(
dm, ODM_REG_RPT_11AC, MASKDWORD);
}
try_count = 0;
for (cnt = 0; cnt < 20; cnt++) {
if (dm->support_ic_type & ODM_IC_11N_SERIES) {
odm_set_bb_reg(dm, ODM_REG_DBG_RPT_11N,
MASKDWORD, 0x208);
value32 = odm_get_bb_reg(dm, ODM_REG_RPT_11N,
MASKDWORD);
} else if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, ODM_REG_DBG_RPT_11AC,
MASKDWORD, 0x209);
value32 = odm_get_bb_reg(dm, ODM_REG_RPT_11AC,
MASKDWORD);
}
if (value32 & BIT(30) &&
(dm->support_ic_type &
(ODM_RTL8723B | ODM_RTL8188E)))
tx_edcca1 = tx_edcca1 + 1;
else if (value32 & BIT(29))
tx_edcca1 = tx_edcca1 + 1;
else
tx_edcca0 = tx_edcca0 + 1;
}
if (tx_edcca1 > 1) {
IGI = IGI - 1;
th_l2h_dmc = th_l2h_dmc + 1;
if (th_l2h_dmc > 10)
th_l2h_dmc = 10;
th_h2l_dmc = th_l2h_dmc - dm->th_edcca_hl_diff;
phydm_set_edcca_threshold(dm, th_h2l_dmc, th_l2h_dmc);
if (th_l2h_dmc == 10) {
is_adjust = false;
adaptivity->h2l_lb = th_h2l_dmc;
adaptivity->l2h_lb = th_l2h_dmc;
dm->adaptivity_igi_upper = IGI;
}
tx_edcca1 = 0;
tx_edcca0 = 0;
} else {
is_adjust = false;
adaptivity->h2l_lb = th_h2l_dmc;
adaptivity->l2h_lb = th_l2h_dmc;
dm->adaptivity_igi_upper = IGI;
tx_edcca1 = 0;
tx_edcca0 = 0;
}
}
dm->adaptivity_igi_upper = dm->adaptivity_igi_upper - dm->dc_backoff;
adaptivity->h2l_lb = adaptivity->h2l_lb + dm->dc_backoff;
adaptivity->l2h_lb = adaptivity->l2h_lb + dm->dc_backoff;
if (dm->support_ic_type & (ODM_RTL8723B | ODM_RTL8188E | ODM_RTL8192E |
ODM_RTL8812 | ODM_RTL8821 | ODM_RTL8881A)) {
phydm_set_lna(dm, phydm_enable_lna);
} else {
phydm_set_trx_mux(dm, phydm_tx_mode, phydm_rx_mode);
odm_pause_dig(dm, PHYDM_RESUME, PHYDM_PAUSE_LEVEL_0, NONE);
}
phydm_set_edcca_threshold(dm, 0x7f, 0x7f); /*resume to no link state*/
}
static bool phydm_re_search_condition(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u8 adaptivity_igi_upper;
u8 count = 0;
adaptivity_igi_upper = dm->adaptivity_igi_upper + dm->dc_backoff;
if (adaptivity_igi_upper <= 0x26 && count < 3) {
count = count + 1;
return true;
}
return false;
}
void phydm_adaptivity_info_init(void *dm_void, enum phydm_adapinfo cmn_info,
u32 value)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
switch (cmn_info) {
case PHYDM_ADAPINFO_CARRIER_SENSE_ENABLE:
dm->carrier_sense_enable = (bool)value;
break;
case PHYDM_ADAPINFO_DCBACKOFF:
dm->dc_backoff = (u8)value;
break;
case PHYDM_ADAPINFO_DYNAMICLINKADAPTIVITY:
adaptivity->dynamic_link_adaptivity = (bool)value;
break;
case PHYDM_ADAPINFO_TH_L2H_INI:
dm->th_l2h_ini = (s8)value;
break;
case PHYDM_ADAPINFO_TH_EDCCA_HL_DIFF:
dm->th_edcca_hl_diff = (s8)value;
break;
case PHYDM_ADAPINFO_AP_NUM_TH:
adaptivity->ap_num_th = (u8)value;
break;
default:
break;
}
}
void phydm_adaptivity_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
s8 igi_target = 0x32;
if (!dm->carrier_sense_enable) {
if (dm->th_l2h_ini == 0)
dm->th_l2h_ini = 0xf5;
} else {
dm->th_l2h_ini = 0xa;
}
if (dm->th_edcca_hl_diff == 0)
dm->th_edcca_hl_diff = 7;
if (dm->wifi_test || dm->mp_mode) {
/*even no adaptivity, we still enable EDCCA, AP use mib ctrl*/
dm->edcca_enable = false;
} else {
dm->edcca_enable = true;
}
dm->adaptivity_igi_upper = 0;
dm->adaptivity_enable =
false; /*use this flag to decide enable or disable*/
dm->th_l2h_ini_mode2 = 20;
dm->th_edcca_hl_diff_mode2 = 8;
adaptivity->th_l2h_ini_backup = dm->th_l2h_ini;
adaptivity->th_edcca_hl_diff_backup = dm->th_edcca_hl_diff;
adaptivity->igi_base = 0x32;
adaptivity->igi_target = 0x1c;
adaptivity->h2l_lb = 0;
adaptivity->l2h_lb = 0;
adaptivity->nhm_wait = 0;
adaptivity->is_check = false;
adaptivity->is_first_link = true;
adaptivity->adajust_igi_level = 0;
adaptivity->is_stop_edcca = false;
adaptivity->backup_h2l = 0;
adaptivity->backup_l2h = 0;
phydm_mac_edcca_state(dm, phydm_dont_ignore_edcca);
/*Search pwdB lower bound*/
if (dm->support_ic_type & ODM_IC_11N_SERIES)
odm_set_bb_reg(dm, ODM_REG_DBG_RPT_11N, MASKDWORD, 0x208);
else if (dm->support_ic_type & ODM_IC_11AC_SERIES)
odm_set_bb_reg(dm, ODM_REG_DBG_RPT_11AC, MASKDWORD, 0x209);
if (dm->support_ic_type & ODM_IC_11N_GAIN_IDX_EDCCA) {
if (dm->support_ic_type & ODM_RTL8197F) {
/*set to page B1*/
odm_set_bb_reg(dm, ODM_REG_PAGE_B1_97F, BIT(30), 0x1);
/*0:rx_dfir, 1: dcnf_out, 2 :rx_iq, 3: rx_nbi_nf_out*/
odm_set_bb_reg(dm, ODM_REG_EDCCA_DCNF_97F,
BIT(27) | BIT(26), 0x1);
odm_set_bb_reg(dm, ODM_REG_PAGE_B1_97F, BIT(30), 0x0);
} else {
/*0:rx_dfir, 1: dcnf_out, 2 :rx_iq, 3: rx_nbi_nf_out*/
odm_set_bb_reg(dm, ODM_REG_EDCCA_DCNF_11N,
BIT(21) | BIT(20), 0x1);
}
}
/*8814a no need to find pwdB lower bound, maybe*/
if (dm->support_ic_type & ODM_IC_11AC_GAIN_IDX_EDCCA) {
/*0:rx_dfir, 1: dcnf_out, 2 :rx_iq, 3: rx_nbi_nf_out*/
odm_set_bb_reg(dm, ODM_REG_ACBB_EDCCA_ENHANCE,
BIT(29) | BIT(28), 0x1);
}
if (!(dm->support_ic_type &
(ODM_IC_11AC_GAIN_IDX_EDCCA | ODM_IC_11N_GAIN_IDX_EDCCA))) {
phydm_search_pwdb_lower_bound(dm);
if (phydm_re_search_condition(dm))
phydm_search_pwdb_lower_bound(dm);
}
/*we need to consider PwdB upper bound for 8814 later IC*/
adaptivity->adajust_igi_level =
(u8)((dm->th_l2h_ini + igi_target) - pwdb_upper_bound +
dfir_loss); /*IGI = L2H - PwdB - dfir_loss*/
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"th_l2h_ini = 0x%x, th_edcca_hl_diff = 0x%x, adaptivity->adajust_igi_level = 0x%x\n",
dm->th_l2h_ini, dm->th_edcca_hl_diff,
adaptivity->adajust_igi_level);
/*Check this later on Windows*/
/*phydm_set_edcca_threshold_api(dm, dig_tab->cur_ig_value);*/
}
void phydm_adaptivity(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dig_thres *dig_tab = &dm->dm_dig_table;
u8 IGI = dig_tab->cur_ig_value;
s8 th_l2h_dmc, th_h2l_dmc;
s8 diff = 0, igi_target;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
if (!dm->edcca_enable || adaptivity->is_stop_edcca) {
ODM_RT_TRACE(dm, PHYDM_COMP_ADAPTIVITY, "Disable EDCCA!!!\n");
return;
}
if (!(dm->support_ability & ODM_BB_ADAPTIVITY)) {
ODM_RT_TRACE(dm, PHYDM_COMP_ADAPTIVITY,
"adaptivity disable, enable EDCCA mode!!!\n");
dm->th_l2h_ini = dm->th_l2h_ini_mode2;
dm->th_edcca_hl_diff = dm->th_edcca_hl_diff_mode2;
}
ODM_RT_TRACE(dm, PHYDM_COMP_ADAPTIVITY, "%s() =====>\n", __func__);
ODM_RT_TRACE(dm, PHYDM_COMP_ADAPTIVITY,
"igi_base=0x%x, th_l2h_ini = %d, th_edcca_hl_diff = %d\n",
adaptivity->igi_base, dm->th_l2h_ini,
dm->th_edcca_hl_diff);
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
/*fix AC series when enable EDCCA hang issue*/
odm_set_bb_reg(dm, 0x800, BIT(10), 1); /*ADC_mask disable*/
odm_set_bb_reg(dm, 0x800, BIT(10), 0); /*ADC_mask enable*/
}
if (*dm->band_width == ODM_BW20M) /*CHANNEL_WIDTH_20*/
igi_target = adaptivity->igi_base;
else if (*dm->band_width == ODM_BW40M)
igi_target = adaptivity->igi_base + 2;
else if (*dm->band_width == ODM_BW80M)
igi_target = adaptivity->igi_base + 2;
else
igi_target = adaptivity->igi_base;
adaptivity->igi_target = (u8)igi_target;
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"band_width=%s, igi_target=0x%x, dynamic_link_adaptivity = %d, acs_for_adaptivity = %d\n",
(*dm->band_width == ODM_BW80M) ?
"80M" :
((*dm->band_width == ODM_BW40M) ? "40M" : "20M"),
igi_target, adaptivity->dynamic_link_adaptivity,
adaptivity->acs_for_adaptivity);
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"rssi_min = %d, adaptivity->adajust_igi_level= 0x%x, adaptivity_flag = %d, adaptivity_enable = %d\n",
dm->rssi_min, adaptivity->adajust_igi_level,
dm->adaptivity_flag, dm->adaptivity_enable);
if (adaptivity->dynamic_link_adaptivity && (!dm->is_linked) &&
!dm->adaptivity_enable) {
phydm_set_edcca_threshold(dm, 0x7f, 0x7f);
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"In DynamicLink mode(noisy) and No link, Turn off EDCCA!!\n");
return;
}
if (dm->support_ic_type &
(ODM_IC_11AC_GAIN_IDX_EDCCA | ODM_IC_11N_GAIN_IDX_EDCCA)) {
if ((adaptivity->adajust_igi_level > IGI) &&
dm->adaptivity_enable)
diff = adaptivity->adajust_igi_level - IGI;
th_l2h_dmc = dm->th_l2h_ini - diff + igi_target;
th_h2l_dmc = th_l2h_dmc - dm->th_edcca_hl_diff;
} else {
diff = igi_target - (s8)IGI;
th_l2h_dmc = dm->th_l2h_ini + diff;
if (th_l2h_dmc > 10 && dm->adaptivity_enable)
th_l2h_dmc = 10;
th_h2l_dmc = th_l2h_dmc - dm->th_edcca_hl_diff;
/*replace lower bound to prevent EDCCA always equal 1*/
if (th_h2l_dmc < adaptivity->h2l_lb)
th_h2l_dmc = adaptivity->h2l_lb;
if (th_l2h_dmc < adaptivity->l2h_lb)
th_l2h_dmc = adaptivity->l2h_lb;
}
ODM_RT_TRACE(dm, PHYDM_COMP_ADAPTIVITY,
"IGI=0x%x, th_l2h_dmc = %d, th_h2l_dmc = %d\n", IGI,
th_l2h_dmc, th_h2l_dmc);
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"adaptivity_igi_upper=0x%x, h2l_lb = 0x%x, l2h_lb = 0x%x\n",
dm->adaptivity_igi_upper, adaptivity->h2l_lb,
adaptivity->l2h_lb);
phydm_set_edcca_threshold(dm, th_h2l_dmc, th_l2h_dmc);
if (dm->adaptivity_enable)
odm_set_mac_reg(dm, REG_RD_CTRL, BIT(11), 1);
}
/*This is for solving USB can't Tx problem due to USB3.0 interference in 2.4G*/
void phydm_pause_edcca(void *dm_void, bool is_pasue_edcca)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
struct dig_thres *dig_tab = &dm->dm_dig_table;
u8 IGI = dig_tab->cur_ig_value;
s8 diff = 0;
if (is_pasue_edcca) {
adaptivity->is_stop_edcca = true;
if (dm->support_ic_type &
(ODM_IC_11AC_GAIN_IDX_EDCCA | ODM_IC_11N_GAIN_IDX_EDCCA)) {
if (adaptivity->adajust_igi_level > IGI)
diff = adaptivity->adajust_igi_level - IGI;
adaptivity->backup_l2h =
dm->th_l2h_ini - diff + adaptivity->igi_target;
adaptivity->backup_h2l =
adaptivity->backup_l2h - dm->th_edcca_hl_diff;
} else {
diff = adaptivity->igi_target - (s8)IGI;
adaptivity->backup_l2h = dm->th_l2h_ini + diff;
if (adaptivity->backup_l2h > 10)
adaptivity->backup_l2h = 10;
adaptivity->backup_h2l =
adaptivity->backup_l2h - dm->th_edcca_hl_diff;
/*replace lower bound to prevent EDCCA always equal 1*/
if (adaptivity->backup_h2l < adaptivity->h2l_lb)
adaptivity->backup_h2l = adaptivity->h2l_lb;
if (adaptivity->backup_l2h < adaptivity->l2h_lb)
adaptivity->backup_l2h = adaptivity->l2h_lb;
}
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"pauseEDCCA : L2Hbak = 0x%x, H2Lbak = 0x%x, IGI = 0x%x\n",
adaptivity->backup_l2h, adaptivity->backup_h2l, IGI);
/*Disable EDCCA*/
phydm_pause_edcca_work_item_callback(dm);
} else {
adaptivity->is_stop_edcca = false;
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"resumeEDCCA : L2Hbak = 0x%x, H2Lbak = 0x%x, IGI = 0x%x\n",
adaptivity->backup_l2h, adaptivity->backup_h2l, IGI);
/*Resume EDCCA*/
phydm_resume_edcca_work_item_callback(dm);
}
}
void phydm_pause_edcca_work_item_callback(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11N_SERIES)
odm_set_bb_reg(dm, REG_OFDM_0_ECCA_THRESHOLD,
MASKBYTE2 | MASKBYTE0, (u32)(0x7f | 0x7f << 16));
else if (dm->support_ic_type & ODM_IC_11AC_SERIES)
odm_set_bb_reg(dm, REG_FPGA0_XB_LSSI_READ_BACK, MASKLWORD,
(u16)(0x7f | 0x7f << 8));
}
void phydm_resume_edcca_work_item_callback(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
if (dm->support_ic_type & ODM_IC_11N_SERIES)
odm_set_bb_reg(dm, REG_OFDM_0_ECCA_THRESHOLD,
MASKBYTE2 | MASKBYTE0,
(u32)((u8)adaptivity->backup_l2h |
(u8)adaptivity->backup_h2l << 16));
else if (dm->support_ic_type & ODM_IC_11AC_SERIES)
odm_set_bb_reg(dm, REG_FPGA0_XB_LSSI_READ_BACK, MASKLWORD,
(u16)((u8)adaptivity->backup_l2h |
(u8)adaptivity->backup_h2l << 8));
}
void phydm_set_edcca_threshold_api(void *dm_void, u8 IGI)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct adaptivity_statistics *adaptivity =
(struct adaptivity_statistics *)phydm_get_structure(
dm, PHYDM_ADAPTIVITY);
s8 th_l2h_dmc, th_h2l_dmc;
s8 diff = 0, igi_target = 0x32;
if (dm->support_ability & ODM_BB_ADAPTIVITY) {
if (dm->support_ic_type &
(ODM_IC_11AC_GAIN_IDX_EDCCA | ODM_IC_11N_GAIN_IDX_EDCCA)) {
if (adaptivity->adajust_igi_level > IGI)
diff = adaptivity->adajust_igi_level - IGI;
th_l2h_dmc = dm->th_l2h_ini - diff + igi_target;
th_h2l_dmc = th_l2h_dmc - dm->th_edcca_hl_diff;
} else {
diff = igi_target - (s8)IGI;
th_l2h_dmc = dm->th_l2h_ini + diff;
if (th_l2h_dmc > 10)
th_l2h_dmc = 10;
th_h2l_dmc = th_l2h_dmc - dm->th_edcca_hl_diff;
/*replace lower bound to prevent EDCCA always equal 1*/
if (th_h2l_dmc < adaptivity->h2l_lb)
th_h2l_dmc = adaptivity->h2l_lb;
if (th_l2h_dmc < adaptivity->l2h_lb)
th_l2h_dmc = adaptivity->l2h_lb;
}
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"API :IGI=0x%x, th_l2h_dmc = %d, th_h2l_dmc = %d\n",
IGI, th_l2h_dmc, th_h2l_dmc);
ODM_RT_TRACE(
dm, PHYDM_COMP_ADAPTIVITY,
"API :adaptivity_igi_upper=0x%x, h2l_lb = 0x%x, l2h_lb = 0x%x\n",
dm->adaptivity_igi_upper, adaptivity->h2l_lb,
adaptivity->l2h_lb);
phydm_set_edcca_threshold(dm, th_h2l_dmc, th_l2h_dmc);
}
}

View File

@ -0,0 +1,119 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMADAPTIVITY_H__
#define __PHYDMADAPTIVITY_H__
/*20160902 changed by Kevin, refine method for searching pwdb lower bound*/
#define ADAPTIVITY_VERSION "9.3.5"
#define pwdb_upper_bound 7
#define dfir_loss 5
enum phydm_adapinfo {
PHYDM_ADAPINFO_CARRIER_SENSE_ENABLE = 0,
PHYDM_ADAPINFO_DCBACKOFF,
PHYDM_ADAPINFO_DYNAMICLINKADAPTIVITY,
PHYDM_ADAPINFO_TH_L2H_INI,
PHYDM_ADAPINFO_TH_EDCCA_HL_DIFF,
PHYDM_ADAPINFO_AP_NUM_TH
};
enum phydm_set_lna {
phydm_disable_lna = 0,
phydm_enable_lna = 1,
};
enum phydm_trx_mux_type {
phydm_shutdown = 0,
phydm_standby_mode = 1,
phydm_tx_mode = 2,
phydm_rx_mode = 3
};
enum phydm_mac_edcca_type {
phydm_ignore_edcca = 0,
phydm_dont_ignore_edcca = 1
};
struct adaptivity_statistics {
s8 th_l2h_ini_backup;
s8 th_edcca_hl_diff_backup;
s8 igi_base;
u8 igi_target;
u8 nhm_wait;
s8 h2l_lb;
s8 l2h_lb;
bool is_first_link;
bool is_check;
bool dynamic_link_adaptivity;
u8 ap_num_th;
u8 adajust_igi_level;
bool acs_for_adaptivity;
s8 backup_l2h;
s8 backup_h2l;
bool is_stop_edcca;
};
void phydm_pause_edcca(void *dm_void, bool is_pasue_edcca);
void phydm_check_adaptivity(void *dm_void);
void phydm_check_environment(void *dm_void);
void phydm_nhm_counter_statistics_init(void *dm_void);
void phydm_nhm_counter_statistics(void *dm_void);
void phydm_nhm_counter_statistics_reset(void *dm_void);
void phydm_get_nhm_counter_statistics(void *dm_void);
void phydm_mac_edcca_state(void *dm_void, enum phydm_mac_edcca_type state);
void phydm_set_edcca_threshold(void *dm_void, s8 H2L, s8 L2H);
void phydm_set_trx_mux(void *dm_void, enum phydm_trx_mux_type tx_mode,
enum phydm_trx_mux_type rx_mode);
bool phydm_cal_nhm_cnt(void *dm_void);
void phydm_search_pwdb_lower_bound(void *dm_void);
void phydm_adaptivity_info_init(void *dm_void, enum phydm_adapinfo cmn_info,
u32 value);
void phydm_adaptivity_init(void *dm_void);
void phydm_adaptivity(void *dm_void);
void phydm_set_edcca_threshold_api(void *dm_void, u8 IGI);
void phydm_pause_edcca_work_item_callback(void *dm_void);
void phydm_resume_edcca_work_item_callback(void *dm_void);
#endif

View File

@ -0,0 +1,628 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
static bool phydm_la_buffer_allocate(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
struct rt_adcsmp_string *adc_smp_buf = &adc_smp->adc_smp_buf;
bool ret = false;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, "[LA mode BufferAllocate]\n");
if (adc_smp_buf->length == 0) {
odm_allocate_memory(dm, (void **)&adc_smp_buf->octet,
adc_smp_buf->buffer_size);
if (!adc_smp_buf->octet) {
ret = false;
} else {
adc_smp_buf->length = adc_smp_buf->buffer_size;
ret = true;
}
}
return ret;
}
static void phydm_la_get_tx_pkt_buf(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
struct rt_adcsmp_string *adc_smp_buf = &adc_smp->adc_smp_buf;
u32 i = 0, value32, data_l = 0, data_h = 0;
u32 addr, finish_addr;
u32 end_addr = (adc_smp_buf->start_pos + adc_smp_buf->buffer_size) -
1; /*end_addr = 0x3ffff;*/
bool is_round_up;
static u32 page = 0xFF;
u32 smp_cnt = 0, smp_number = 0, addr_8byte = 0;
odm_memory_set(dm, adc_smp_buf->octet, 0, adc_smp_buf->length);
odm_write_1byte(dm, 0x0106, 0x69);
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, "GetTxPktBuf\n");
value32 = odm_read_4byte(dm, 0x7c0);
is_round_up = (bool)((value32 & BIT(31)) >> 31);
/*Reg7C0[30:16]: finish addr (unit: 8byte)*/
finish_addr = (value32 & 0x7FFF0000) >> 16;
if (is_round_up) {
addr = (finish_addr + 1) << 3;
ODM_RT_TRACE(
dm, ODM_COMP_UNCOND,
"is_round_up = ((%d)), finish_addr=((0x%x)), 0x7c0=((0x%x))\n",
is_round_up, finish_addr, value32);
/*Byte to 64Byte*/
smp_number = ((adc_smp_buf->buffer_size) >> 3);
} else {
addr = adc_smp_buf->start_pos;
addr_8byte = addr >> 3;
if (addr_8byte > finish_addr)
smp_number = addr_8byte - finish_addr;
else
smp_number = finish_addr - addr_8byte;
ODM_RT_TRACE(
dm, ODM_COMP_UNCOND,
"is_round_up = ((%d)), finish_addr=((0x%x * 8Byte)), Start_Addr = ((0x%x * 8Byte)), smp_number = ((%d))\n",
is_round_up, finish_addr, addr_8byte, smp_number);
}
if (dm->support_ic_type & ODM_RTL8197F) {
/*64K byte*/
for (addr = 0x0, i = 0; addr < end_addr; addr += 8, i += 2) {
if ((addr & 0xfff) == 0)
odm_set_bb_reg(dm, 0x0140, MASKLWORD,
0x780 + (addr >> 12));
data_l = odm_get_bb_reg(dm, 0x8000 + (addr & 0xfff),
MASKDWORD);
data_h = odm_get_bb_reg(dm, 0x8000 + (addr & 0xfff) + 4,
MASKDWORD);
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, "%08x%08x\n", data_h,
data_l);
}
} else {
while (addr != (finish_addr << 3)) {
if (page != (addr >> 12)) {
/*Reg140=0x780+(addr>>12),
*addr=0x30~0x3F, total 16 pages
*/
page = (addr >> 12);
}
odm_set_bb_reg(dm, 0x0140, MASKLWORD, 0x780 + page);
/*pDataL = 0x8000+(addr&0xfff);*/
data_l = odm_get_bb_reg(dm, 0x8000 + (addr & 0xfff),
MASKDWORD);
data_h = odm_get_bb_reg(dm, 0x8000 + (addr & 0xfff) + 4,
MASKDWORD);
adc_smp_buf->octet[i] = data_h;
adc_smp_buf->octet[i + 1] = data_l;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, "%08x%08x\n", data_h,
data_l);
i = i + 2;
if ((addr + 8) >= end_addr)
addr = adc_smp_buf->start_pos;
else
addr = addr + 8;
smp_cnt++;
if (smp_cnt >= (smp_number - 1))
break;
}
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, "smp_cnt = ((%d))\n",
smp_cnt);
}
}
static void phydm_la_mode_set_mac_iq_dump(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
u32 reg_value;
odm_write_1byte(dm, 0x7c0, 0); /*clear all 0x7c0*/
odm_set_mac_reg(dm, 0x7c0, BIT(0), 1); /*Enable LA mode HW block*/
if (adc_smp->la_trig_mode == PHYDM_MAC_TRIG) {
adc_smp->is_bb_trigger = 0;
odm_set_mac_reg(dm, 0x7c0, BIT(2),
1); /*polling bit for MAC mode*/
odm_set_mac_reg(
dm, 0x7c0, BIT(4) | BIT(3),
adc_smp->la_trigger_edge); /*trigger mode for MAC*/
ODM_RT_TRACE(
dm, ODM_COMP_UNCOND,
"[MAC_trig] ref_mask = ((0x%x)), ref_value = ((0x%x)), dbg_port = ((0x%x))\n",
adc_smp->la_mac_ref_mask, adc_smp->la_trig_sig_sel,
adc_smp->la_dbg_port);
/*[Set MAC Debug Port]*/
odm_set_mac_reg(dm, 0xF4, BIT(16), 1);
odm_set_mac_reg(dm, 0x38, 0xff0000, adc_smp->la_dbg_port);
odm_set_mac_reg(dm, 0x7c4, MASKDWORD, adc_smp->la_mac_ref_mask);
odm_set_mac_reg(dm, 0x7c8, MASKDWORD, adc_smp->la_trig_sig_sel);
} else {
adc_smp->is_bb_trigger = 1;
odm_set_mac_reg(dm, 0x7c0, BIT(1),
1); /*polling bit for BB ADC mode*/
if (adc_smp->la_trig_mode == PHYDM_ADC_MAC_TRIG) {
odm_set_mac_reg(
dm, 0x7c0, BIT(3),
1); /*polling bit for MAC trigger event*/
odm_set_mac_reg(dm, 0x7c0, BIT(7) | BIT(6),
adc_smp->la_trig_sig_sel);
if (adc_smp->la_trig_sig_sel == ADCSMP_TRIG_REG)
odm_set_mac_reg(
dm, 0x7c0, BIT(5),
1); /* manual trigger 0x7C0[5] = 0->1*/
}
}
reg_value = odm_get_bb_reg(dm, 0x7c0, 0xff);
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"4. [Set MAC IQ dump] 0x7c0[7:0] = ((0x%x))\n", reg_value);
}
static void phydm_la_mode_set_dma_type(void *dm_void, u8 la_dma_type)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"2. [LA mode DMA setting] Dma_type = ((%d))\n",
la_dma_type);
if (dm->support_ic_type & ODM_N_ANTDIV_SUPPORT)
odm_set_bb_reg(dm, 0x9a0, 0xf00, la_dma_type); /*0x9A0[11:8]*/
else
odm_set_bb_reg(dm, odm_adc_trigger_jaguar2, 0xf00,
la_dma_type); /*0x95C[11:8]*/
}
static void phydm_adc_smp_start(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
u8 tmp_u1b;
u8 while_cnt = 0;
u8 polling_ok = false, target_polling_bit;
phydm_la_mode_bb_setting(dm);
phydm_la_mode_set_dma_type(dm, adc_smp->la_dma_type);
phydm_la_mode_set_trigger_time(dm, adc_smp->la_trigger_time);
if (dm->support_ic_type & ODM_RTL8197F) {
odm_set_bb_reg(dm, 0xd00, BIT(26), 0x1);
} else { /*for 8814A and 8822B?*/
odm_write_1byte(dm, 0x198c, 0x7);
odm_write_1byte(dm, 0x8b4, 0x80);
/* odm_set_bb_reg(dm, 0x8b4, BIT(7), 1); */
}
phydm_la_mode_set_mac_iq_dump(dm);
/* return; */
target_polling_bit = (adc_smp->is_bb_trigger) ? BIT(1) : BIT(2);
do { /*Poll time always use 100ms, when it exceed 2s, break while loop*/
tmp_u1b = odm_read_1byte(dm, 0x7c0);
if (adc_smp->adc_smp_state != ADCSMP_STATE_SET) {
ODM_RT_TRACE(
dm, ODM_COMP_UNCOND,
"[state Error] adc_smp_state != ADCSMP_STATE_SET\n");
break;
} else if (tmp_u1b & target_polling_bit) {
ODM_delay_ms(100);
while_cnt = while_cnt + 1;
continue;
} else {
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"[LA Query OK] polling_bit=((0x%x))\n",
target_polling_bit);
polling_ok = true;
if (dm->support_ic_type & ODM_RTL8197F)
odm_set_bb_reg(dm, 0x7c0, BIT(0), 0x0);
break;
}
} while (while_cnt < 20);
if (adc_smp->adc_smp_state == ADCSMP_STATE_SET) {
if (polling_ok)
phydm_la_get_tx_pkt_buf(dm);
else
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"[Polling timeout]\n");
}
if (adc_smp->adc_smp_state == ADCSMP_STATE_SET)
adc_smp->adc_smp_state = ADCSMP_STATE_QUERY;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"[LA mode] LA_pattern_count = ((%d))\n",
adc_smp->la_count);
adc_smp_stop(dm);
if (adc_smp->la_count == 0) {
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"LA Dump finished ---------->\n\n\n");
/**/
} else {
adc_smp->la_count--;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"LA Dump more ---------->\n\n\n");
adc_smp_set(dm, adc_smp->la_trig_mode, adc_smp->la_trig_sig_sel,
adc_smp->la_dma_type, adc_smp->la_trigger_time, 0);
}
}
void adc_smp_set(void *dm_void, u8 trig_mode, u32 trig_sig_sel,
u8 dma_data_sig_sel, u32 trigger_time, u16 polling_time)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
bool is_set_success = true;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
adc_smp->la_trig_mode = trig_mode;
adc_smp->la_trig_sig_sel = trig_sig_sel;
adc_smp->la_dma_type = dma_data_sig_sel;
adc_smp->la_trigger_time = trigger_time;
if (adc_smp->adc_smp_state != ADCSMP_STATE_IDLE)
is_set_success = false;
else if (adc_smp->adc_smp_buf.length == 0)
is_set_success = phydm_la_buffer_allocate(dm);
if (is_set_success) {
adc_smp->adc_smp_state = ADCSMP_STATE_SET;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"[LA Set Success] LA_State=((%d))\n",
adc_smp->adc_smp_state);
phydm_adc_smp_start(dm);
} else {
ODM_RT_TRACE(dm, ODM_COMP_UNCOND,
"[LA Set Fail] LA_State=((%d))\n",
adc_smp->adc_smp_state);
}
}
void adc_smp_query(void *dm_void, void *output, u32 out_len, u32 *pused)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
struct rt_adcsmp_string *adc_smp_buf = &adc_smp->adc_smp_buf;
u32 used = *pused;
u32 i;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, "%s adc_smp_state %d", __func__,
adc_smp->adc_smp_state);
for (i = 0; i < (adc_smp_buf->length >> 2) - 2; i += 2) {
PHYDM_SNPRINTF(output + used, out_len - used, "%08x%08x\n",
adc_smp_buf->octet[i],
adc_smp_buf->octet[i + 1]);
}
PHYDM_SNPRINTF(output + used, out_len - used, "\n");
*pused = used;
}
s32 adc_smp_get_sample_counts(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
struct rt_adcsmp_string *adc_smp_buf = &adc_smp->adc_smp_buf;
return (adc_smp_buf->length >> 2) - 2;
}
s32 adc_smp_query_single_data(void *dm_void, void *output, u32 out_len,
u32 index)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
struct rt_adcsmp_string *adc_smp_buf = &adc_smp->adc_smp_buf;
u32 used = 0;
if (adc_smp->adc_smp_state != ADCSMP_STATE_QUERY) {
PHYDM_SNPRINTF(output + used, out_len - used,
"Error: la data is not ready yet ...\n");
return -1;
}
if (index < ((adc_smp_buf->length >> 2) - 2)) {
PHYDM_SNPRINTF(output + used, out_len - used, "%08x%08x\n",
adc_smp_buf->octet[index],
adc_smp_buf->octet[index + 1]);
}
return 0;
}
void adc_smp_stop(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
adc_smp->adc_smp_state = ADCSMP_STATE_IDLE;
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, "[LA_Stop] LA_state = ((%d))\n",
adc_smp->adc_smp_state);
}
void adc_smp_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
struct rt_adcsmp_string *adc_smp_buf = &adc_smp->adc_smp_buf;
adc_smp->adc_smp_state = ADCSMP_STATE_IDLE;
if (dm->support_ic_type & ODM_RTL8814A) {
adc_smp_buf->start_pos = 0x30000;
adc_smp_buf->buffer_size = 0x10000;
} else if (dm->support_ic_type & ODM_RTL8822B) {
adc_smp_buf->start_pos = 0x20000;
adc_smp_buf->buffer_size = 0x20000;
} else if (dm->support_ic_type & ODM_RTL8197F) {
adc_smp_buf->start_pos = 0x00000;
adc_smp_buf->buffer_size = 0x10000;
} else if (dm->support_ic_type & ODM_RTL8821C) {
adc_smp_buf->start_pos = 0x8000;
adc_smp_buf->buffer_size = 0x8000;
}
}
void adc_smp_de_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
struct rt_adcsmp_string *adc_smp_buf = &adc_smp->adc_smp_buf;
adc_smp_stop(dm);
if (adc_smp_buf->length != 0x0) {
odm_free_memory(dm, adc_smp_buf->octet, adc_smp_buf->length);
adc_smp_buf->length = 0x0;
}
}
void phydm_la_mode_bb_setting(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
u8 trig_mode = adc_smp->la_trig_mode;
u32 trig_sig_sel = adc_smp->la_trig_sig_sel;
u32 dbg_port = adc_smp->la_dbg_port;
u8 is_trigger_edge = adc_smp->la_trigger_edge;
u8 sampling_rate = adc_smp->la_smp_rate;
ODM_RT_TRACE(
dm, ODM_COMP_UNCOND,
"1. [LA mode bb_setting] trig_mode = ((%d)), dbg_port = ((0x%x)), Trig_Edge = ((%d)), smp_rate = ((%d)), Trig_Sel = ((0x%x))\n",
trig_mode, dbg_port, is_trigger_edge, sampling_rate,
trig_sig_sel);
if (trig_mode == PHYDM_MAC_TRIG)
trig_sig_sel = 0; /*ignore this setting*/
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
if (trig_mode == PHYDM_ADC_RF0_TRIG) {
/*DBGOUT_RFC_a[31:0]*/
odm_set_bb_reg(dm, 0x8f8,
BIT(25) | BIT(24) | BIT(23) | BIT(22),
9);
} else if (trig_mode == PHYDM_ADC_RF1_TRIG) {
/*DBGOUT_RFC_b[31:0]*/
odm_set_bb_reg(dm, 0x8f8,
BIT(25) | BIT(24) | BIT(23) | BIT(22),
8);
} else {
odm_set_bb_reg(dm, 0x8f8,
BIT(25) | BIT(24) | BIT(23) | BIT(22),
0);
}
/*
* (0:) '{ofdm_dbg[31:0]}'
* (1:) '{cca,crc32_fail,dbg_ofdm[29:0]}'
* (2:) '{vbon,crc32_fail,dbg_ofdm[29:0]}'
* (3:) '{cca,crc32_ok,dbg_ofdm[29:0]}'
* (4:) '{vbon,crc32_ok,dbg_ofdm[29:0]}'
* (5:) '{dbg_iqk_anta}'
* (6:) '{cca,ofdm_crc_ok,dbg_dp_anta[29:0]}'
* (7:) '{dbg_iqk_antb}'
* (8:) '{DBGOUT_RFC_b[31:0]}'
* (9:) '{DBGOUT_RFC_a[31:0]}'
* (a:) '{dbg_ofdm}'
* (b:) '{dbg_cck}'
*/
/*disable dbg clk gating*/
odm_set_bb_reg(dm, 0x198C, BIT(2) | BIT(1) | BIT(0), 7);
/*0x95C[4:0], BB debug port bit*/
odm_set_bb_reg(dm, 0x95C, 0x1f, trig_sig_sel);
odm_set_bb_reg(dm, 0x8FC, MASKDWORD, dbg_port);
/*0: posedge, 1: negedge*/
odm_set_bb_reg(dm, 0x95C, BIT(31), is_trigger_edge);
odm_set_bb_reg(dm, 0x95c, 0xe0, sampling_rate);
/* (0:) '80MHz'
* (1:) '40MHz'
* (2:) '20MHz'
* (3:) '10MHz'
* (4:) '5MHz'
* (5:) '2.5MHz'
* (6:) '1.25MHz'
* (7:) '160MHz (for BW160 ic)'
*/
} else {
/*0x9A0[4:0], BB debug port bit*/
odm_set_bb_reg(dm, 0x9a0, 0x1f, trig_sig_sel);
odm_set_bb_reg(dm, 0x908, MASKDWORD, dbg_port);
/*0: posedge, 1: negedge*/
odm_set_bb_reg(dm, 0x9A0, BIT(31), is_trigger_edge);
odm_set_bb_reg(dm, 0x9A0, 0xe0, sampling_rate);
/* (0:) '80MHz'
* (1:) '40MHz'
* (2:) '20MHz'
* (3:) '10MHz'
* (4:) '5MHz'
* (5:) '2.5MHz'
* (6:) '1.25MHz'
* (7:) '160MHz (for BW160 ic)'
*/
}
}
void phydm_la_mode_set_trigger_time(void *dm_void, u32 trigger_time_mu_sec)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u8 trigger_time_unit_num;
u32 time_unit = 0;
if (trigger_time_mu_sec < 128)
time_unit = 0; /*unit: 1mu sec*/
else if (trigger_time_mu_sec < 256)
time_unit = 1; /*unit: 2mu sec*/
else if (trigger_time_mu_sec < 512)
time_unit = 2; /*unit: 4mu sec*/
else if (trigger_time_mu_sec < 1024)
time_unit = 3; /*unit: 8mu sec*/
else if (trigger_time_mu_sec < 2048)
time_unit = 4; /*unit: 16mu sec*/
else if (trigger_time_mu_sec < 4096)
time_unit = 5; /*unit: 32mu sec*/
else if (trigger_time_mu_sec < 8192)
time_unit = 6; /*unit: 64mu sec*/
trigger_time_unit_num = (u8)(trigger_time_mu_sec >> time_unit);
ODM_RT_TRACE(
dm, ODM_COMP_UNCOND,
"3. [Set Trigger Time] Trig_Time = ((%d)) * unit = ((2^%d us))\n",
trigger_time_unit_num, time_unit);
odm_set_mac_reg(dm, 0x7cc, BIT(20) | BIT(19) | BIT(18), time_unit);
odm_set_mac_reg(dm, 0x7c0, 0x7f00, (trigger_time_unit_num & 0x7f));
}
void phydm_lamode_trigger_setting(void *dm_void, char input[][16], u32 *_used,
char *output, u32 *_out_len, u32 input_num)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rt_adcsmp *adc_smp = &dm->adcsmp;
u8 trig_mode, dma_data_sig_sel;
u32 trig_sig_sel;
bool is_enable_la_mode;
u32 trigger_time_mu_sec;
char help[] = "-h";
u32 var1[10] = {0};
u32 used = *_used;
u32 out_len = *_out_len;
if (dm->support_ic_type & PHYDM_IC_SUPPORT_LA_MODE) {
PHYDM_SSCANF(input[1], DCMD_DECIMAL, &var1[0]);
is_enable_la_mode = (bool)var1[0];
/*dbg_print("echo cmd input_num = %d\n", input_num);*/
if ((strcmp(input[1], help) == 0)) {
PHYDM_SNPRINTF(
output + used, out_len - used,
"{En} {0:BB,1:BB_MAC,2:RF0,3:RF1,4:MAC}\n {BB:dbg_port[bit],BB_MAC:0-ok/1-fail/2-cca,MAC:ref} {DMA type} {TrigTime}\n {polling_time/ref_mask} {dbg_port} {0:P_Edge, 1:N_Edge} {SpRate:0-80M,1-40M,2-20M} {Capture num}\n");
/**/
} else if ((is_enable_la_mode == 1)) {
PHYDM_SSCANF(input[2], DCMD_DECIMAL, &var1[1]);
trig_mode = (u8)var1[1];
if (trig_mode == PHYDM_MAC_TRIG)
PHYDM_SSCANF(input[3], DCMD_HEX, &var1[2]);
else
PHYDM_SSCANF(input[3], DCMD_DECIMAL, &var1[2]);
trig_sig_sel = var1[2];
PHYDM_SSCANF(input[4], DCMD_DECIMAL, &var1[3]);
PHYDM_SSCANF(input[5], DCMD_DECIMAL, &var1[4]);
PHYDM_SSCANF(input[6], DCMD_HEX, &var1[5]);
PHYDM_SSCANF(input[7], DCMD_HEX, &var1[6]);
PHYDM_SSCANF(input[8], DCMD_DECIMAL, &var1[7]);
PHYDM_SSCANF(input[9], DCMD_DECIMAL, &var1[8]);
PHYDM_SSCANF(input[10], DCMD_DECIMAL, &var1[9]);
dma_data_sig_sel = (u8)var1[3];
trigger_time_mu_sec = var1[4]; /*unit: us*/
adc_smp->la_mac_ref_mask = var1[5];
adc_smp->la_dbg_port = var1[6];
adc_smp->la_trigger_edge = (u8)var1[7];
adc_smp->la_smp_rate = (u8)(var1[8] & 0x7);
adc_smp->la_count = var1[9];
ODM_RT_TRACE(
dm, ODM_COMP_UNCOND,
"echo lamode %d %d %d %d %d %d %x %d %d %d\n",
var1[0], var1[1], var1[2], var1[3], var1[4],
var1[5], var1[6], var1[7], var1[8], var1[9]);
PHYDM_SNPRINTF(
output + used, out_len - used,
"a.En= ((1)), b.mode = ((%d)), c.Trig_Sel = ((0x%x)), d.Dma_type = ((%d))\n",
trig_mode, trig_sig_sel, dma_data_sig_sel);
PHYDM_SNPRINTF(
output + used, out_len - used,
"e.Trig_Time = ((%dus)), f.mac_ref_mask = ((0x%x)), g.dbg_port = ((0x%x))\n",
trigger_time_mu_sec, adc_smp->la_mac_ref_mask,
adc_smp->la_dbg_port);
PHYDM_SNPRINTF(
output + used, out_len - used,
"h.Trig_edge = ((%d)), i.smp rate = ((%d MHz)), j.Cap_num = ((%d))\n",
adc_smp->la_trigger_edge,
(80 >> adc_smp->la_smp_rate),
adc_smp->la_count);
adc_smp_set(dm, trig_mode, trig_sig_sel,
dma_data_sig_sel, trigger_time_mu_sec, 0);
} else {
adc_smp_stop(dm);
PHYDM_SNPRINTF(output + used, out_len - used,
"Disable LA mode\n");
}
}
}

View File

@ -0,0 +1,96 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __INC_ADCSMP_H
#define __INC_ADCSMP_H
#define DYNAMIC_LA_MODE "1.0" /*2016.07.15 Dino */
struct rt_adcsmp_string {
u32 *octet;
u32 length;
u32 buffer_size;
u32 start_pos;
};
enum rt_adcsmp_trig_sel {
PHYDM_ADC_BB_TRIG = 0,
PHYDM_ADC_MAC_TRIG = 1,
PHYDM_ADC_RF0_TRIG = 2,
PHYDM_ADC_RF1_TRIG = 3,
PHYDM_MAC_TRIG = 4
};
enum rt_adcsmp_trig_sig_sel {
ADCSMP_TRIG_CRCOK = 0,
ADCSMP_TRIG_CRCFAIL = 1,
ADCSMP_TRIG_CCA = 2,
ADCSMP_TRIG_REG = 3
};
enum rt_adcsmp_state {
ADCSMP_STATE_IDLE = 0,
ADCSMP_STATE_SET = 1,
ADCSMP_STATE_QUERY = 2
};
struct rt_adcsmp {
struct rt_adcsmp_string adc_smp_buf;
enum rt_adcsmp_state adc_smp_state;
u8 la_trig_mode;
u32 la_trig_sig_sel;
u8 la_dma_type;
u32 la_trigger_time;
u32 la_mac_ref_mask;
u32 la_dbg_port;
u8 la_trigger_edge;
u8 la_smp_rate;
u32 la_count;
u8 is_bb_trigger;
u8 la_work_item_index;
};
void adc_smp_set(void *dm_void, u8 trig_mode, u32 trig_sig_sel,
u8 dma_data_sig_sel, u32 trigger_time, u16 polling_time);
void adc_smp_query(void *dm_void, void *output, u32 out_len, u32 *pused);
s32 adc_smp_get_sample_counts(void *dm_void);
s32 adc_smp_query_single_data(void *dm_void, void *output, u32 out_len,
u32 index);
void adc_smp_stop(void *dm_void);
void adc_smp_init(void *dm_void);
void adc_smp_de_init(void *dm_void);
void phydm_la_mode_bb_setting(void *dm_void);
void phydm_la_mode_set_trigger_time(void *dm_void, u32 trigger_time_mu_sec);
void phydm_lamode_trigger_setting(void *dm_void, char input[][16], u32 *_used,
char *output, u32 *_out_len, u32 input_num);
#endif

View File

@ -0,0 +1,83 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
/* ******************************************************
* when antenna test utility is on or some testing need to disable antenna
* diversity, call this function to disable all ODM related mechanisms which
* will switch antenna.
* *******************************************************/
void odm_stop_antenna_switch_dm(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
/* disable ODM antenna diversity */
dm->support_ability &= ~ODM_BB_ANT_DIV;
ODM_RT_TRACE(dm, ODM_COMP_ANT_DIV, "STOP Antenna Diversity\n");
}
void phydm_enable_antenna_diversity(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
dm->support_ability |= ODM_BB_ANT_DIV;
ODM_RT_TRACE(dm, ODM_COMP_ANT_DIV,
"AntDiv is enabled & Re-Init AntDiv\n");
odm_antenna_diversity_init(dm);
}
void odm_set_ant_config(void *dm_void, u8 ant_setting /* 0=A, 1=B, 2=C, .... */
)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type == ODM_RTL8723B) {
if (ant_setting == 0) /* ant A*/
odm_set_bb_reg(dm, 0x948, MASKDWORD, 0x00000000);
else if (ant_setting == 1)
odm_set_bb_reg(dm, 0x948, MASKDWORD, 0x00000280);
} else if (dm->support_ic_type == ODM_RTL8723D) {
if (ant_setting == 0) /* ant A*/
odm_set_bb_reg(dm, 0x948, MASKLWORD, 0x0000);
else if (ant_setting == 1)
odm_set_bb_reg(dm, 0x948, MASKLWORD, 0x0280);
}
}
/* ****************************************************** */
void odm_sw_ant_div_rest_after_link(void *dm_void) {}
void odm_ant_div_reset(void *dm_void) {}
void odm_antenna_diversity_init(void *dm_void) {}
void odm_antenna_diversity(void *dm_void) {}

View File

@ -0,0 +1,301 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMANTDIV_H__
#define __PHYDMANTDIV_H__
/* 2.0 2014.11.04
* 2.1 2015.01.13 Dino
* 2.2 2015.01.16 Dino
* 3.1 2015.07.29 YuChen, remove 92c 92d 8723a
* 3.2 2015.08.11 Stanley, disable antenna diversity when BT is enable for 8723B
* 3.3 2015.08.12 Stanley. 8723B does not need to check the antenna is control
* by BT, because antenna diversity only works when BT is disable
* or radio off
* 3.4 2015.08.28 Dino 1.Add 8821A Smart Antenna 2. Add 8188F SW S0S1 Antenna
* Diversity
* 3.5 2015.10.07 Stanley Always check antenna detection result from BT-coex.
* for 8723B, not from PHYDM
* 3.6 2015.11.16 Stanley
* 3.7 2015.11.20 Dino Add SmartAnt FAT Patch
* 3.8 2015.12.21 Dino, Add SmartAnt dynamic training packet num
* 3.9 2016.01.05 Dino, Add SmartAnt cmd for converting single & two smtant, and
* add cmd for adjust truth table
*/
#define ANTDIV_VERSION "3.9"
/* 1 ============================================================
* 1 Definition
* 1 ============================================================
*/
#define ANTDIV_INIT 0xff
#define MAIN_ANT 1 /*ant A or ant Main or S1*/
#define AUX_ANT 2 /*AntB or ant Aux or S0*/
#define MAX_ANT 3 /* 3 for AP using*/
#define ANT1_2G 0 /* = ANT2_5G for 8723D BTG S1 RX S0S1 diversity for 8723D,
* TX fixed at S1
*/
#define ANT2_2G 1 /* = ANT1_5G for 8723D BTG S0 RX S0S1 diversity for 8723D,
* TX fixed at S1
*/
/*smart antenna*/
#define SUPPORT_RF_PATH_NUM 4
#define SUPPORT_BEAM_PATTERN_NUM 4
#define NUM_ANTENNA_8821A 2
#define SUPPORT_BEAM_SET_PATTERN_NUM 8
#define NO_FIX_TX_ANT 0
#define FIX_TX_AT_MAIN 1
#define FIX_AUX_AT_MAIN 2
/* Antenna Diversty Control type */
#define ODM_AUTO_ANT 0
#define ODM_FIX_MAIN_ANT 1
#define ODM_FIX_AUX_ANT 2
#define ODM_N_ANTDIV_SUPPORT \
(ODM_RTL8188E | ODM_RTL8192E | ODM_RTL8723B | ODM_RTL8188F | \
ODM_RTL8723D | ODM_RTL8195A)
#define ODM_AC_ANTDIV_SUPPORT \
(ODM_RTL8821 | ODM_RTL8881A | ODM_RTL8812 | ODM_RTL8821C | \
ODM_RTL8822B | ODM_RTL8814B)
#define ODM_ANTDIV_SUPPORT (ODM_N_ANTDIV_SUPPORT | ODM_AC_ANTDIV_SUPPORT)
#define ODM_SMART_ANT_SUPPORT (ODM_RTL8188E | ODM_RTL8192E)
#define ODM_HL_SMART_ANT_TYPE1_SUPPORT (ODM_RTL8821 | ODM_RTL8822B)
#define ODM_ANTDIV_2G_SUPPORT_IC \
(ODM_RTL8188E | ODM_RTL8192E | ODM_RTL8723B | ODM_RTL8881A | \
ODM_RTL8188F | ODM_RTL8723D)
#define ODM_ANTDIV_5G_SUPPORT_IC \
(ODM_RTL8821 | ODM_RTL8881A | ODM_RTL8812 | ODM_RTL8821C)
#define ODM_EVM_ENHANCE_ANTDIV_SUPPORT_IC (ODM_RTL8192E)
#define ODM_ANTDIV_2G BIT(0)
#define ODM_ANTDIV_5G BIT(1)
#define ANTDIV_ON 1
#define ANTDIV_OFF 0
#define FAT_ON 1
#define FAT_OFF 0
#define TX_BY_DESC 1
#define TX_BY_REG 0
#define RSSI_METHOD 0
#define EVM_METHOD 1
#define CRC32_METHOD 2
#define INIT_ANTDIV_TIMMER 0
#define CANCEL_ANTDIV_TIMMER 1
#define RELEASE_ANTDIV_TIMMER 2
#define CRC32_FAIL 1
#define CRC32_OK 0
#define evm_rssi_th_high 25
#define evm_rssi_th_low 20
#define NORMAL_STATE_MIAN 1
#define NORMAL_STATE_AUX 2
#define TRAINING_STATE 3
#define FORCE_RSSI_DIFF 10
#define CSI_ON 1
#define CSI_OFF 0
#define DIVON_CSIOFF 1
#define DIVOFF_CSION 2
#define BDC_DIV_TRAIN_STATE 0
#define bdc_bfer_train_state 1
#define BDC_DECISION_STATE 2
#define BDC_BF_HOLD_STATE 3
#define BDC_DIV_HOLD_STATE 4
#define BDC_MODE_1 1
#define BDC_MODE_2 2
#define BDC_MODE_3 3
#define BDC_MODE_4 4
#define BDC_MODE_NULL 0xff
/*SW S0S1 antenna diversity*/
#define SWAW_STEP_INIT 0xff
#define SWAW_STEP_PEEK 0
#define SWAW_STEP_DETERMINE 1
#define RSSI_CHECK_RESET_PERIOD 10
#define RSSI_CHECK_THRESHOLD 50
/*Hong Lin Smart antenna*/
#define HL_SMTANT_2WIRE_DATA_LEN 24
/* 1 ============================================================
* 1 structure
* 1 ============================================================
*/
struct sw_antenna_switch {
u8 double_chk_flag; /*If current antenna RSSI > "RSSI_CHECK_THRESHOLD",
*than check this antenna again
*/
u8 try_flag;
s32 pre_rssi;
u8 cur_antenna;
u8 pre_antenna;
u8 rssi_trying;
u8 reset_idx;
u8 train_time;
u8 train_time_flag; /*base on RSSI difference between two antennas*/
struct timer_list phydm_sw_antenna_switch_timer;
u32 pkt_cnt_sw_ant_div_by_ctrl_frame;
bool is_sw_ant_div_by_ctrl_frame;
/* AntDect (Before link Antenna Switch check) need to be moved*/
u16 single_ant_counter;
u16 dual_ant_counter;
u16 aux_fail_detec_counter;
u16 retry_counter;
u8 swas_no_link_state;
u32 swas_no_link_bk_reg948;
bool ANTA_ON; /*To indicate ant A is or not*/
bool ANTB_ON; /*To indicate ant B is on or not*/
bool pre_aux_fail_detec;
bool rssi_ant_dect_result;
u8 ant_5g;
u8 ant_2g;
};
struct fast_antenna_training {
u8 bssid[6];
u8 antsel_rx_keep_0;
u8 antsel_rx_keep_1;
u8 antsel_rx_keep_2;
u8 antsel_rx_keep_3;
u32 ant_sum_rssi[7];
u32 ant_rssi_cnt[7];
u32 ant_ave_rssi[7];
u8 fat_state;
u32 train_idx;
u8 antsel_a[ODM_ASSOCIATE_ENTRY_NUM];
u8 antsel_b[ODM_ASSOCIATE_ENTRY_NUM];
u8 antsel_c[ODM_ASSOCIATE_ENTRY_NUM];
u16 main_ant_sum[ODM_ASSOCIATE_ENTRY_NUM];
u16 aux_ant_sum[ODM_ASSOCIATE_ENTRY_NUM];
u16 main_ant_cnt[ODM_ASSOCIATE_ENTRY_NUM];
u16 aux_ant_cnt[ODM_ASSOCIATE_ENTRY_NUM];
u16 main_ant_sum_cck[ODM_ASSOCIATE_ENTRY_NUM];
u16 aux_ant_sum_cck[ODM_ASSOCIATE_ENTRY_NUM];
u16 main_ant_cnt_cck[ODM_ASSOCIATE_ENTRY_NUM];
u16 aux_ant_cnt_cck[ODM_ASSOCIATE_ENTRY_NUM];
u8 rx_idle_ant;
u8 ant_div_on_off;
bool is_become_linked;
u32 min_max_rssi;
u8 idx_ant_div_counter_2g;
u8 idx_ant_div_counter_5g;
u8 ant_div_2g_5g;
u32 cck_ctrl_frame_cnt_main;
u32 cck_ctrl_frame_cnt_aux;
u32 ofdm_ctrl_frame_cnt_main;
u32 ofdm_ctrl_frame_cnt_aux;
u32 main_ant_ctrl_frame_sum;
u32 aux_ant_ctrl_frame_sum;
u32 main_ant_ctrl_frame_cnt;
u32 aux_ant_ctrl_frame_cnt;
u8 b_fix_tx_ant;
bool fix_ant_bfee;
bool enable_ctrl_frame_antdiv;
bool use_ctrl_frame_antdiv;
u8 hw_antsw_occur;
u8 *p_force_tx_ant_by_desc;
u8 force_tx_ant_by_desc; /*A temp value, will hook to driver team's
*outer parameter later
*/
u8 *p_default_s0_s1;
u8 default_s0_s1;
};
/* 1 ============================================================
* 1 enumeration
* 1 ============================================================
*/
/*Fast antenna training*/
enum fat_state {
FAT_BEFORE_LINK_STATE = 0,
FAT_PREPARE_STATE = 1,
FAT_TRAINING_STATE = 2,
FAT_DECISION_STATE = 3
};
enum ant_div_type {
NO_ANTDIV = 0xFF,
CG_TRX_HW_ANTDIV = 0x01,
CGCS_RX_HW_ANTDIV = 0x02,
FIXED_HW_ANTDIV = 0x03,
CG_TRX_SMART_ANTDIV = 0x04,
CGCS_RX_SW_ANTDIV = 0x05,
/*8723B intrnal switch S0 S1*/
S0S1_SW_ANTDIV = 0x06,
/*TRX S0S1 diversity for 8723D*/
S0S1_TRX_HW_ANTDIV = 0x07,
/*Hong-Lin Smart antenna use for 8821AE which is a 2 ant. entitys, and
*each ant. is equipped with 4 antenna patterns
*/
HL_SW_SMART_ANT_TYPE1 = 0x10,
/*Hong-Bo Smart antenna use for 8822B which is a 2 ant. entitys*/
HL_SW_SMART_ANT_TYPE2 = 0x11,
};
/* 1 ============================================================
* 1 function prototype
* 1 ============================================================
*/
void odm_stop_antenna_switch_dm(void *dm_void);
void phydm_enable_antenna_diversity(void *dm_void);
void odm_set_ant_config(void *dm_void, u8 ant_setting /* 0=A, 1=B, 2=C, .... */
);
#define sw_ant_div_rest_after_link odm_sw_ant_div_rest_after_link
void odm_sw_ant_div_rest_after_link(void *dm_void);
void odm_ant_div_reset(void *dm_void);
void odm_antenna_diversity_init(void *dm_void);
void odm_antenna_diversity(void *dm_void);
#endif /*#ifndef __ODMANTDIV_H__*/

View File

@ -0,0 +1,48 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __INC_PHYDM_BEAMFORMING_H
#define __INC_PHYDM_BEAMFORMING_H
/*Beamforming Related*/
#include "txbf/halcomtxbf.h"
#include "txbf/haltxbfjaguar.h"
#include "txbf/haltxbf8822b.h"
#include "txbf/haltxbfinterface.h"
#define beamforming_gid_paid(adapter, tcb)
#define phydm_acting_determine(dm, type) false
#define beamforming_enter(dm, sta_idx)
#define beamforming_leave(dm, RA)
#define beamforming_end_fw(dm)
#define beamforming_control_v1(dm, RA, AID, mode, BW, rate) true
#define beamforming_control_v2(dm, idx, mode, BW, period) true
#define phydm_beamforming_end_sw(dm, _status)
#define beamforming_timer_callback(dm)
#define phydm_beamforming_init(dm)
#define phydm_beamforming_control_v2(dm, _idx, _mode, _BW, _period) false
#define beamforming_watchdog(dm)
#define phydm_beamforming_watchdog(dm)
#endif

View File

@ -0,0 +1,457 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
/*Set NHM period, threshold, disable ignore cca or not,
*disable ignore txon or not
*/
void phydm_nhm_setting(void *dm_void, u8 nhm_setting)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct ccx_info *ccx_info = &dm->dm_ccx_info;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
if (nhm_setting == SET_NHM_SETTING) {
/*Set inexclude_cca, inexclude_txon*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(9),
ccx_info->nhm_inexclude_cca);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(10),
ccx_info->nhm_inexclude_txon);
/*Set NHM period*/
odm_set_bb_reg(dm, ODM_REG_CCX_PERIOD_11AC, MASKHWORD,
ccx_info->NHM_period);
/*Set NHM threshold*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE0, ccx_info->NHM_th[0]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE1, ccx_info->NHM_th[1]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE2, ccx_info->NHM_th[2]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE3, ccx_info->NHM_th[3]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE0, ccx_info->NHM_th[4]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE1, ccx_info->NHM_th[5]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE2, ccx_info->NHM_th[6]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE3, ccx_info->NHM_th[7]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0,
ccx_info->NHM_th[8]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE2,
ccx_info->NHM_th[9]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE3,
ccx_info->NHM_th[10]);
/*CCX EN*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(8),
CCX_EN);
} else if (nhm_setting == STORE_NHM_SETTING) {
/*Store prev. disable_ignore_cca, disable_ignore_txon*/
ccx_info->NHM_inexclude_cca_restore =
(enum nhm_inexclude_cca)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(9));
ccx_info->NHM_inexclude_txon_restore =
(enum nhm_inexclude_txon)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(10));
/*Store pervious NHM period*/
ccx_info->NHM_period_restore = (u16)odm_get_bb_reg(
dm, ODM_REG_CCX_PERIOD_11AC, MASKHWORD);
/*Store NHM threshold*/
ccx_info->NHM_th_restore[0] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE0);
ccx_info->NHM_th_restore[1] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE1);
ccx_info->NHM_th_restore[2] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE2);
ccx_info->NHM_th_restore[3] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE3);
ccx_info->NHM_th_restore[4] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE0);
ccx_info->NHM_th_restore[5] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE1);
ccx_info->NHM_th_restore[6] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE2);
ccx_info->NHM_th_restore[7] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE3);
ccx_info->NHM_th_restore[8] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0);
ccx_info->NHM_th_restore[9] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE2);
ccx_info->NHM_th_restore[10] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE3);
} else if (nhm_setting == RESTORE_NHM_SETTING) {
/*Set disable_ignore_cca, disable_ignore_txon*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(9),
ccx_info->NHM_inexclude_cca_restore);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(10),
ccx_info->NHM_inexclude_txon_restore);
/*Set NHM period*/
odm_set_bb_reg(dm, ODM_REG_CCX_PERIOD_11AC, MASKHWORD,
ccx_info->NHM_period);
/*Set NHM threshold*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE0, ccx_info->NHM_th_restore[0]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE1, ccx_info->NHM_th_restore[1]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE2, ccx_info->NHM_th_restore[2]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11AC,
MASKBYTE3, ccx_info->NHM_th_restore[3]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE0, ccx_info->NHM_th_restore[4]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE1, ccx_info->NHM_th_restore[5]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE2, ccx_info->NHM_th_restore[6]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11AC,
MASKBYTE3, ccx_info->NHM_th_restore[7]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0,
ccx_info->NHM_th_restore[8]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE2,
ccx_info->NHM_th_restore[9]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE3,
ccx_info->NHM_th_restore[10]);
} else {
return;
}
}
else if (dm->support_ic_type & ODM_IC_11N_SERIES) {
if (nhm_setting == SET_NHM_SETTING) {
/*Set disable_ignore_cca, disable_ignore_txon*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(9),
ccx_info->nhm_inexclude_cca);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(10),
ccx_info->nhm_inexclude_txon);
/*Set NHM period*/
odm_set_bb_reg(dm, ODM_REG_CCX_PERIOD_11N, MASKHWORD,
ccx_info->NHM_period);
/*Set NHM threshold*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE0, ccx_info->NHM_th[0]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE1, ccx_info->NHM_th[1]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE2, ccx_info->NHM_th[2]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE3, ccx_info->NHM_th[3]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE0, ccx_info->NHM_th[4]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE1, ccx_info->NHM_th[5]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE2, ccx_info->NHM_th[6]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE3, ccx_info->NHM_th[7]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH8_11N, MASKBYTE0,
ccx_info->NHM_th[8]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE2,
ccx_info->NHM_th[9]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE3,
ccx_info->NHM_th[10]);
/*CCX EN*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(8),
CCX_EN);
} else if (nhm_setting == STORE_NHM_SETTING) {
/*Store prev. disable_ignore_cca, disable_ignore_txon*/
ccx_info->NHM_inexclude_cca_restore =
(enum nhm_inexclude_cca)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11N, BIT(9));
ccx_info->NHM_inexclude_txon_restore =
(enum nhm_inexclude_txon)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11N, BIT(10));
/*Store pervious NHM period*/
ccx_info->NHM_period_restore = (u16)odm_get_bb_reg(
dm, ODM_REG_CCX_PERIOD_11N, MASKHWORD);
/*Store NHM threshold*/
ccx_info->NHM_th_restore[0] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE0);
ccx_info->NHM_th_restore[1] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE1);
ccx_info->NHM_th_restore[2] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE2);
ccx_info->NHM_th_restore[3] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE3);
ccx_info->NHM_th_restore[4] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE0);
ccx_info->NHM_th_restore[5] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE1);
ccx_info->NHM_th_restore[6] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE2);
ccx_info->NHM_th_restore[7] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE3);
ccx_info->NHM_th_restore[8] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH8_11N, MASKBYTE0);
ccx_info->NHM_th_restore[9] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE2);
ccx_info->NHM_th_restore[10] = (u8)odm_get_bb_reg(
dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE3);
} else if (nhm_setting == RESTORE_NHM_SETTING) {
/*Set disable_ignore_cca, disable_ignore_txon*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(9),
ccx_info->NHM_inexclude_cca_restore);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(10),
ccx_info->NHM_inexclude_txon_restore);
/*Set NHM period*/
odm_set_bb_reg(dm, ODM_REG_CCX_PERIOD_11N, MASKHWORD,
ccx_info->NHM_period_restore);
/*Set NHM threshold*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE0, ccx_info->NHM_th_restore[0]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE1, ccx_info->NHM_th_restore[1]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE2, ccx_info->NHM_th_restore[2]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH3_TO_TH0_11N,
MASKBYTE3, ccx_info->NHM_th_restore[3]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE0, ccx_info->NHM_th_restore[4]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE1, ccx_info->NHM_th_restore[5]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE2, ccx_info->NHM_th_restore[6]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH7_TO_TH4_11N,
MASKBYTE3, ccx_info->NHM_th_restore[7]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH8_11N, MASKBYTE0,
ccx_info->NHM_th_restore[8]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE2,
ccx_info->NHM_th_restore[9]);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE3,
ccx_info->NHM_th_restore[10]);
} else {
return;
}
}
}
void phydm_nhm_trigger(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
/*Trigger NHM*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(1), 0);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(1), 1);
} else if (dm->support_ic_type & ODM_IC_11N_SERIES) {
/*Trigger NHM*/
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(1), 0);
odm_set_bb_reg(dm, ODM_REG_NHM_TH9_TH10_11N, BIT(1), 1);
}
}
void phydm_get_nhm_result(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u32 value32;
struct ccx_info *ccx_info = &dm->dm_ccx_info;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT_11AC);
ccx_info->NHM_result[0] = (u8)(value32 & MASKBYTE0);
ccx_info->NHM_result[1] = (u8)((value32 & MASKBYTE1) >> 8);
ccx_info->NHM_result[2] = (u8)((value32 & MASKBYTE2) >> 16);
ccx_info->NHM_result[3] = (u8)((value32 & MASKBYTE3) >> 24);
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT7_TO_CNT4_11AC);
ccx_info->NHM_result[4] = (u8)(value32 & MASKBYTE0);
ccx_info->NHM_result[5] = (u8)((value32 & MASKBYTE1) >> 8);
ccx_info->NHM_result[6] = (u8)((value32 & MASKBYTE2) >> 16);
ccx_info->NHM_result[7] = (u8)((value32 & MASKBYTE3) >> 24);
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT11_TO_CNT8_11AC);
ccx_info->NHM_result[8] = (u8)(value32 & MASKBYTE0);
ccx_info->NHM_result[9] = (u8)((value32 & MASKBYTE1) >> 8);
ccx_info->NHM_result[10] = (u8)((value32 & MASKBYTE2) >> 16);
ccx_info->NHM_result[11] = (u8)((value32 & MASKBYTE3) >> 24);
/*Get NHM duration*/
value32 = odm_read_4byte(dm, ODM_REG_NHM_DUR_READY_11AC);
ccx_info->NHM_duration = (u16)(value32 & MASKLWORD);
}
else if (dm->support_ic_type & ODM_IC_11N_SERIES) {
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT_11N);
ccx_info->NHM_result[0] = (u8)(value32 & MASKBYTE0);
ccx_info->NHM_result[1] = (u8)((value32 & MASKBYTE1) >> 8);
ccx_info->NHM_result[2] = (u8)((value32 & MASKBYTE2) >> 16);
ccx_info->NHM_result[3] = (u8)((value32 & MASKBYTE3) >> 24);
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT7_TO_CNT4_11N);
ccx_info->NHM_result[4] = (u8)(value32 & MASKBYTE0);
ccx_info->NHM_result[5] = (u8)((value32 & MASKBYTE1) >> 8);
ccx_info->NHM_result[6] = (u8)((value32 & MASKBYTE2) >> 16);
ccx_info->NHM_result[7] = (u8)((value32 & MASKBYTE3) >> 24);
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT9_TO_CNT8_11N);
ccx_info->NHM_result[8] = (u8)((value32 & MASKBYTE2) >> 16);
ccx_info->NHM_result[9] = (u8)((value32 & MASKBYTE3) >> 24);
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT10_TO_CNT11_11N);
ccx_info->NHM_result[10] = (u8)((value32 & MASKBYTE2) >> 16);
ccx_info->NHM_result[11] = (u8)((value32 & MASKBYTE3) >> 24);
/*Get NHM duration*/
value32 = odm_read_4byte(dm, ODM_REG_NHM_CNT10_TO_CNT11_11N);
ccx_info->NHM_duration = (u16)(value32 & MASKLWORD);
}
}
bool phydm_check_nhm_ready(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u32 value32 = 0;
u8 i;
bool ret = false;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
value32 =
odm_get_bb_reg(dm, ODM_REG_CLM_RESULT_11AC, MASKDWORD);
for (i = 0; i < 200; i++) {
ODM_delay_ms(1);
if (odm_get_bb_reg(dm, ODM_REG_NHM_DUR_READY_11AC,
BIT(17))) {
ret = 1;
break;
}
}
}
else if (dm->support_ic_type & ODM_IC_11N_SERIES) {
value32 = odm_get_bb_reg(dm, ODM_REG_CLM_READY_11N, MASKDWORD);
for (i = 0; i < 200; i++) {
ODM_delay_ms(1);
if (odm_get_bb_reg(dm, ODM_REG_NHM_DUR_READY_11AC,
BIT(17))) {
ret = 1;
break;
}
}
}
return ret;
}
void phydm_clm_setting(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct ccx_info *ccx_info = &dm->dm_ccx_info;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, ODM_REG_CCX_PERIOD_11AC, MASKLWORD,
ccx_info->CLM_period); /*4us sample 1 time*/
odm_set_bb_reg(dm, ODM_REG_CLM_11AC, BIT(8),
0x1); /*Enable CCX for CLM*/
} else if (dm->support_ic_type & ODM_IC_11N_SERIES) {
odm_set_bb_reg(dm, ODM_REG_CCX_PERIOD_11N, MASKLWORD,
ccx_info->CLM_period); /*4us sample 1 time*/
odm_set_bb_reg(dm, ODM_REG_CLM_11N, BIT(8),
0x1); /*Enable CCX for CLM*/
}
ODM_RT_TRACE(dm, ODM_COMP_CCX, "[%s] : CLM period = %dus\n", __func__,
ccx_info->CLM_period * 4);
}
void phydm_clm_trigger(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, ODM_REG_CLM_11AC, BIT(0),
0x0); /*Trigger CLM*/
odm_set_bb_reg(dm, ODM_REG_CLM_11AC, BIT(0), 0x1);
} else if (dm->support_ic_type & ODM_IC_11N_SERIES) {
odm_set_bb_reg(dm, ODM_REG_CLM_11N, BIT(0),
0x0); /*Trigger CLM*/
odm_set_bb_reg(dm, ODM_REG_CLM_11N, BIT(0), 0x1);
}
}
bool phydm_check_cl_mready(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u32 value32 = 0;
bool ret = false;
if (dm->support_ic_type & ODM_IC_11AC_SERIES)
value32 = odm_get_bb_reg(
dm, ODM_REG_CLM_RESULT_11AC,
MASKDWORD); /*make sure CLM calc is ready*/
else if (dm->support_ic_type & ODM_IC_11N_SERIES)
value32 = odm_get_bb_reg(
dm, ODM_REG_CLM_READY_11N,
MASKDWORD); /*make sure CLM calc is ready*/
if ((dm->support_ic_type & ODM_IC_11AC_SERIES) && (value32 & BIT(16)))
ret = true;
else if ((dm->support_ic_type & ODM_IC_11N_SERIES) &&
(value32 & BIT(16)))
ret = true;
else
ret = false;
ODM_RT_TRACE(dm, ODM_COMP_CCX, "[%s] : CLM ready = %d\n", __func__,
ret);
return ret;
}
void phydm_get_cl_mresult(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct ccx_info *ccx_info = &dm->dm_ccx_info;
u32 value32 = 0;
if (dm->support_ic_type & ODM_IC_11AC_SERIES)
value32 = odm_get_bb_reg(dm, ODM_REG_CLM_RESULT_11AC,
MASKDWORD); /*read CLM calc result*/
else if (dm->support_ic_type & ODM_IC_11N_SERIES)
value32 = odm_get_bb_reg(dm, ODM_REG_CLM_RESULT_11N,
MASKDWORD); /*read CLM calc result*/
ccx_info->CLM_result = (u16)(value32 & MASKLWORD);
ODM_RT_TRACE(dm, ODM_COMP_CCX, "[%s] : CLM result = %dus\n", __func__,
ccx_info->CLM_result * 4);
}

View File

@ -0,0 +1,83 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMCCX_H__
#define __PHYDMCCX_H__
#define CCX_EN 1
#define SET_NHM_SETTING 0
#define STORE_NHM_SETTING 1
#define RESTORE_NHM_SETTING 2
enum nhm_inexclude_cca { NHM_EXCLUDE_CCA, NHM_INCLUDE_CCA };
enum nhm_inexclude_txon { NHM_EXCLUDE_TXON, NHM_INCLUDE_TXON };
struct ccx_info {
/*Settings*/
u8 NHM_th[11];
u16 NHM_period; /* 4us per unit */
u16 CLM_period; /* 4us per unit */
enum nhm_inexclude_txon nhm_inexclude_txon;
enum nhm_inexclude_cca nhm_inexclude_cca;
/*Previous Settings*/
u8 NHM_th_restore[11];
u16 NHM_period_restore; /* 4us per unit */
u16 CLM_period_restore; /* 4us per unit */
enum nhm_inexclude_txon NHM_inexclude_txon_restore;
enum nhm_inexclude_cca NHM_inexclude_cca_restore;
/*Report*/
u8 NHM_result[12];
u16 NHM_duration;
u16 CLM_result;
bool echo_NHM_en;
bool echo_CLM_en;
u8 echo_IGI;
};
/*NHM*/
void phydm_nhm_setting(void *dm_void, u8 nhm_setting);
void phydm_nhm_trigger(void *dm_void);
void phydm_get_nhm_result(void *dm_void);
bool phydm_check_nhm_ready(void *dm_void);
/*CLM*/
void phydm_clm_setting(void *dm_void);
void phydm_clm_trigger(void *dm_void);
bool phydm_check_cl_mready(void *dm_void);
void phydm_get_cl_mresult(void *dm_void);
#endif

View File

@ -0,0 +1,343 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
static void odm_set_crystal_cap(void *dm_void, u8 crystal_cap)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct cfo_tracking *cfo_track =
(struct cfo_tracking *)phydm_get_structure(dm, PHYDM_CFOTRACK);
if (cfo_track->crystal_cap == crystal_cap)
return;
cfo_track->crystal_cap = crystal_cap;
if (dm->support_ic_type & (ODM_RTL8188E | ODM_RTL8188F)) {
/* write 0x24[22:17] = 0x24[16:11] = crystal_cap */
crystal_cap = crystal_cap & 0x3F;
odm_set_bb_reg(dm, REG_AFE_XTAL_CTRL, 0x007ff800,
(crystal_cap | (crystal_cap << 6)));
} else if (dm->support_ic_type & ODM_RTL8812) {
/* write 0x2C[30:25] = 0x2C[24:19] = crystal_cap */
crystal_cap = crystal_cap & 0x3F;
odm_set_bb_reg(dm, REG_MAC_PHY_CTRL, 0x7FF80000,
(crystal_cap | (crystal_cap << 6)));
} else if ((dm->support_ic_type & (ODM_RTL8703B | ODM_RTL8723B |
ODM_RTL8192E | ODM_RTL8821))) {
/* 0x2C[23:18] = 0x2C[17:12] = crystal_cap */
crystal_cap = crystal_cap & 0x3F;
odm_set_bb_reg(dm, REG_MAC_PHY_CTRL, 0x00FFF000,
(crystal_cap | (crystal_cap << 6)));
} else if (dm->support_ic_type & ODM_RTL8814A) {
/* write 0x2C[26:21] = 0x2C[20:15] = crystal_cap */
crystal_cap = crystal_cap & 0x3F;
odm_set_bb_reg(dm, REG_MAC_PHY_CTRL, 0x07FF8000,
(crystal_cap | (crystal_cap << 6)));
} else if (dm->support_ic_type & (ODM_RTL8822B | ODM_RTL8821C)) {
/* write 0x24[30:25] = 0x28[6:1] = crystal_cap */
crystal_cap = crystal_cap & 0x3F;
odm_set_bb_reg(dm, REG_AFE_XTAL_CTRL, 0x7e000000, crystal_cap);
odm_set_bb_reg(dm, REG_AFE_PLL_CTRL, 0x7e, crystal_cap);
} else {
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): Use default setting.\n", __func__);
odm_set_bb_reg(dm, REG_MAC_PHY_CTRL, 0xFFF000,
(crystal_cap | (crystal_cap << 6)));
}
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING, "%s(): crystal_cap = 0x%x\n",
__func__, crystal_cap);
/* JJ modified 20161115 */
}
static u8 odm_get_default_crytaltal_cap(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u8 crystal_cap = 0x20;
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
struct rtl_efuse *rtlefuse = rtl_efuse(rtlpriv);
crystal_cap = rtlefuse->crystalcap;
crystal_cap = crystal_cap & 0x3f;
return crystal_cap;
}
static void odm_set_atc_status(void *dm_void, bool atc_status)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct cfo_tracking *cfo_track =
(struct cfo_tracking *)phydm_get_structure(dm, PHYDM_CFOTRACK);
if (cfo_track->is_atc_status == atc_status)
return;
odm_set_bb_reg(dm, ODM_REG(BB_ATC, dm), ODM_BIT(BB_ATC, dm),
atc_status);
cfo_track->is_atc_status = atc_status;
}
static bool odm_get_atc_status(void *dm_void)
{
bool atc_status;
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
atc_status = (bool)odm_get_bb_reg(dm, ODM_REG(BB_ATC, dm),
ODM_BIT(BB_ATC, dm));
return atc_status;
}
void odm_cfo_tracking_reset(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct cfo_tracking *cfo_track =
(struct cfo_tracking *)phydm_get_structure(dm, PHYDM_CFOTRACK);
cfo_track->def_x_cap = odm_get_default_crytaltal_cap(dm);
cfo_track->is_adjust = true;
if (cfo_track->crystal_cap > cfo_track->def_x_cap) {
odm_set_crystal_cap(dm, cfo_track->crystal_cap - 1);
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): approch default value (0x%x)\n", __func__,
cfo_track->crystal_cap);
} else if (cfo_track->crystal_cap < cfo_track->def_x_cap) {
odm_set_crystal_cap(dm, cfo_track->crystal_cap + 1);
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): approch default value (0x%x)\n", __func__,
cfo_track->crystal_cap);
}
odm_set_atc_status(dm, true);
}
void odm_cfo_tracking_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct cfo_tracking *cfo_track =
(struct cfo_tracking *)phydm_get_structure(dm, PHYDM_CFOTRACK);
cfo_track->crystal_cap = odm_get_default_crytaltal_cap(dm);
cfo_track->def_x_cap = cfo_track->crystal_cap;
cfo_track->is_atc_status = odm_get_atc_status(dm);
cfo_track->is_adjust = true;
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING, "%s()=========>\n", __func__);
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): is_atc_status = %d, crystal_cap = 0x%x\n", __func__,
cfo_track->is_atc_status, cfo_track->def_x_cap);
/* Crystal cap. control by WiFi */
if (dm->support_ic_type & ODM_RTL8822B)
odm_set_bb_reg(dm, 0x10, 0x40, 0x1);
}
void odm_cfo_tracking(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct cfo_tracking *cfo_track =
(struct cfo_tracking *)phydm_get_structure(dm, PHYDM_CFOTRACK);
s32 cfo_ave = 0;
u32 cfo_rpt_sum, cfo_khz_avg[4] = {0};
s32 cfo_ave_diff;
s8 crystal_cap = cfo_track->crystal_cap;
u8 adjust_xtal = 1, i, valid_path_cnt = 0;
/* 4 Support ability */
if (!(dm->support_ability & ODM_BB_CFO_TRACKING)) {
ODM_RT_TRACE(
dm, ODM_COMP_CFO_TRACKING,
"%s(): Return: support_ability ODM_BB_CFO_TRACKING is disabled\n",
__func__);
return;
}
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING, "%s()=========>\n", __func__);
if (!dm->is_linked || !dm->is_one_entry_only) {
/* 4 No link or more than one entry */
odm_cfo_tracking_reset(dm);
ODM_RT_TRACE(
dm, ODM_COMP_CFO_TRACKING,
"%s(): Reset: is_linked = %d, is_one_entry_only = %d\n",
__func__, dm->is_linked, dm->is_one_entry_only);
} else {
/* 3 1. CFO Tracking */
/* 4 1.1 No new packet */
if (cfo_track->packet_count == cfo_track->packet_count_pre) {
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): packet counter doesn't change\n",
__func__);
return;
}
cfo_track->packet_count_pre = cfo_track->packet_count;
/* 4 1.2 Calculate CFO */
for (i = 0; i < dm->num_rf_path; i++) {
if (cfo_track->CFO_cnt[i] == 0)
continue;
valid_path_cnt++;
cfo_rpt_sum =
(u32)((cfo_track->CFO_tail[i] < 0) ?
(0 - cfo_track->CFO_tail[i]) :
cfo_track->CFO_tail[i]);
cfo_khz_avg[i] = CFO_HW_RPT_2_MHZ(cfo_rpt_sum) /
cfo_track->CFO_cnt[i];
ODM_RT_TRACE(
dm, ODM_COMP_CFO_TRACKING,
"[path %d] cfo_rpt_sum = (( %d )), CFO_cnt = (( %d )) , CFO_avg= (( %s%d )) kHz\n",
i, cfo_rpt_sum, cfo_track->CFO_cnt[i],
((cfo_track->CFO_tail[i] < 0) ? "-" : " "),
cfo_khz_avg[i]);
}
for (i = 0; i < valid_path_cnt; i++) {
if (cfo_track->CFO_tail[i] < 0) {
/* */
cfo_ave += (0 - (s32)cfo_khz_avg[i]);
} else {
cfo_ave += (s32)cfo_khz_avg[i];
}
}
if (valid_path_cnt >= 2)
cfo_ave = cfo_ave / valid_path_cnt;
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"valid_path_cnt = ((%d)), cfo_ave = ((%d kHz))\n",
valid_path_cnt, cfo_ave);
/*reset counter*/
for (i = 0; i < dm->num_rf_path; i++) {
cfo_track->CFO_tail[i] = 0;
cfo_track->CFO_cnt[i] = 0;
}
/* 4 1.3 Avoid abnormal large CFO */
cfo_ave_diff = (cfo_track->CFO_ave_pre >= cfo_ave) ?
(cfo_track->CFO_ave_pre - cfo_ave) :
(cfo_ave - cfo_track->CFO_ave_pre);
if (cfo_ave_diff > 20 && cfo_track->large_cfo_hit == 0 &&
!cfo_track->is_adjust) {
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): first large CFO hit\n", __func__);
cfo_track->large_cfo_hit = 1;
return;
}
cfo_track->large_cfo_hit = 0;
cfo_track->CFO_ave_pre = cfo_ave;
/* 4 1.4 Dynamic Xtal threshold */
if (!cfo_track->is_adjust) {
if (cfo_ave > CFO_TH_XTAL_HIGH ||
cfo_ave < (-CFO_TH_XTAL_HIGH))
cfo_track->is_adjust = true;
} else {
if (cfo_ave < CFO_TH_XTAL_LOW &&
cfo_ave > (-CFO_TH_XTAL_LOW))
cfo_track->is_adjust = false;
}
/* 4 1.5 BT case: Disable CFO tracking */
if (dm->is_bt_enabled) {
cfo_track->is_adjust = false;
odm_set_crystal_cap(dm, cfo_track->def_x_cap);
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): Disable CFO tracking for BT!!\n",
__func__);
}
/* 4 1.7 Adjust Crystal Cap. */
if (cfo_track->is_adjust) {
if (cfo_ave > CFO_TH_XTAL_LOW)
crystal_cap = crystal_cap + adjust_xtal;
else if (cfo_ave < (-CFO_TH_XTAL_LOW))
crystal_cap = crystal_cap - adjust_xtal;
if (crystal_cap > 0x3f)
crystal_cap = 0x3f;
else if (crystal_cap < 0)
crystal_cap = 0;
odm_set_crystal_cap(dm, (u8)crystal_cap);
}
ODM_RT_TRACE(
dm, ODM_COMP_CFO_TRACKING,
"%s(): Crystal cap = 0x%x, Default Crystal cap = 0x%x\n",
__func__, cfo_track->crystal_cap, cfo_track->def_x_cap);
if (dm->support_ic_type & ODM_IC_11AC_SERIES)
return;
/* 3 2. Dynamic ATC switch */
if (cfo_ave < CFO_TH_ATC && cfo_ave > -CFO_TH_ATC) {
odm_set_atc_status(dm, false);
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): Disable ATC!!\n", __func__);
} else {
odm_set_atc_status(dm, true);
ODM_RT_TRACE(dm, ODM_COMP_CFO_TRACKING,
"%s(): Enable ATC!!\n", __func__);
}
}
}
void odm_parsing_cfo(void *dm_void, void *pktinfo_void, s8 *pcfotail, u8 num_ss)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dm_per_pkt_info *pktinfo =
(struct dm_per_pkt_info *)pktinfo_void;
struct cfo_tracking *cfo_track =
(struct cfo_tracking *)phydm_get_structure(dm, PHYDM_CFOTRACK);
u8 i;
if (!(dm->support_ability & ODM_BB_CFO_TRACKING))
return;
if (pktinfo->is_packet_match_bssid) {
if (num_ss > dm->num_rf_path) /*For fool proof*/
num_ss = dm->num_rf_path;
/* 3 Update CFO report for path-A & path-B */
/* Only paht-A and path-B have CFO tail and short CFO */
for (i = 0; i < num_ss; i++) {
cfo_track->CFO_tail[i] += pcfotail[i];
cfo_track->CFO_cnt[i]++;
}
/* 3 Update packet counter */
if (cfo_track->packet_count == 0xffffffff)
cfo_track->packet_count = 0;
else
cfo_track->packet_count++;
}
}

View File

@ -0,0 +1,60 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMCFOTRACK_H__
#define __PHYDMCFOTRACK_H__
#define CFO_TRACKING_VERSION "1.4" /*2015.10.01 Stanley, Modify for 8822B*/
#define CFO_TH_XTAL_HIGH 20 /* kHz */
#define CFO_TH_XTAL_LOW 10 /* kHz */
#define CFO_TH_ATC 80 /* kHz */
struct cfo_tracking {
bool is_atc_status;
bool large_cfo_hit;
bool is_adjust;
u8 crystal_cap;
u8 def_x_cap;
s32 CFO_tail[4];
u32 CFO_cnt[4];
s32 CFO_ave_pre;
u32 packet_count;
u32 packet_count_pre;
bool is_force_xtal_cap;
bool is_reset;
};
void odm_cfo_tracking_reset(void *dm_void);
void odm_cfo_tracking_init(void *dm_void);
void odm_cfo_tracking(void *dm_void);
void odm_parsing_cfo(void *dm_void, void *pktinfo_void, s8 *pcfotail,
u8 num_ss);
#endif

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,175 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODM_DBG_H__
#define __ODM_DBG_H__
/*#define DEBUG_VERSION "1.1"*/ /*2015.07.29 YuChen*/
/*#define DEBUG_VERSION "1.2"*/ /*2015.08.28 Dino*/
#define DEBUG_VERSION "1.3" /*2016.04.28 YuChen*/
#define ODM_DBG_TRACE 5
/*FW DBG MSG*/
#define RATE_DECISION BIT(0)
#define INIT_RA_TABLE BIT(1)
#define RATE_UP BIT(2)
#define RATE_DOWN BIT(3)
#define TRY_DONE BIT(4)
#define RA_H2C BIT(5)
#define F_RATE_AP_RPT BIT(7)
/* -----------------------------------------------------------------------------
* Define the tracing components
*
* -----------------------------------------------------------------------------
*/
/*BB FW Functions*/
#define PHYDM_FW_COMP_RA BIT(0)
#define PHYDM_FW_COMP_MU BIT(1)
#define PHYDM_FW_COMP_PATH_DIV BIT(2)
#define PHYDM_FW_COMP_PHY_CONFIG BIT(3)
/*BB Driver Functions*/
#define ODM_COMP_DIG BIT(0)
#define ODM_COMP_RA_MASK BIT(1)
#define ODM_COMP_DYNAMIC_TXPWR BIT(2)
#define ODM_COMP_FA_CNT BIT(3)
#define ODM_COMP_RSSI_MONITOR BIT(4)
#define ODM_COMP_SNIFFER BIT(5)
#define ODM_COMP_ANT_DIV BIT(6)
#define ODM_COMP_DFS BIT(7)
#define ODM_COMP_NOISY_DETECT BIT(8)
#define ODM_COMP_RATE_ADAPTIVE BIT(9)
#define ODM_COMP_PATH_DIV BIT(10)
#define ODM_COMP_CCX BIT(11)
#define ODM_COMP_DYNAMIC_PRICCA BIT(12)
/*BIT13 TBD*/
#define ODM_COMP_MP BIT(14)
#define ODM_COMP_CFO_TRACKING BIT(15)
#define ODM_COMP_ACS BIT(16)
#define PHYDM_COMP_ADAPTIVITY BIT(17)
#define PHYDM_COMP_RA_DBG BIT(18)
#define PHYDM_COMP_TXBF BIT(19)
/* MAC Functions */
#define ODM_COMP_EDCA_TURBO BIT(20)
#define ODM_COMP_DYNAMIC_RX_PATH BIT(21)
#define ODM_FW_DEBUG_TRACE BIT(22)
/* RF Functions */
/*BIT23 TBD*/
#define ODM_COMP_TX_PWR_TRACK BIT(24)
/*BIT25 TBD*/
#define ODM_COMP_CALIBRATION BIT(26)
/* Common Functions */
/*BIT27 TBD*/
#define ODM_PHY_CONFIG BIT(28)
#define ODM_COMP_INIT BIT(29)
#define ODM_COMP_COMMON BIT(30)
#define ODM_COMP_API BIT(31)
#define ODM_COMP_UNCOND 0xFFFFFFFF
/*------------------------Export Marco Definition---------------------------*/
#define config_phydm_read_txagc_check(data) (data != INVALID_TXAGC_DATA)
#define ODM_RT_TRACE(dm, comp, fmt, ...) \
do { \
if (((comp) & dm->debug_components) || \
((comp) == ODM_COMP_UNCOND)) \
RT_TRACE(dm->adapter, COMP_PHYDM, DBG_DMESG, fmt, \
##__VA_ARGS__); \
} while (0)
#define BB_DBGPORT_PRIORITY_3 3 /*Debug function (the highest priority)*/
#define BB_DBGPORT_PRIORITY_2 2 /*Check hang function & Strong function*/
#define BB_DBGPORT_PRIORITY_1 1 /*Watch dog function*/
#define BB_DBGPORT_RELEASE 0 /*Init value (the lowest priority)*/
void phydm_init_debug_setting(struct phy_dm_struct *dm);
u8 phydm_set_bb_dbg_port(void *dm_void, u8 curr_dbg_priority, u32 debug_port);
void phydm_release_bb_dbg_port(void *dm_void);
u32 phydm_get_bb_dbg_port_value(void *dm_void);
void phydm_basic_dbg_message(void *dm_void);
#define PHYDM_DBGPRINT 0
#define MAX_ARGC 20
#define MAX_ARGV 16
#define DCMD_DECIMAL "%d"
#define DCMD_CHAR "%c"
#define DCMD_HEX "%x"
#define PHYDM_SSCANF(x, y, z) \
do { \
if (sscanf(x, y, z) != 1) \
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, \
"%s:%d sscanf fail!", __func__, \
__LINE__); \
} while (0)
#define PHYDM_VAST_INFO_SNPRINTF(msg, ...) \
do { \
snprintf(msg, ##__VA_ARGS__); \
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, output); \
} while (0)
#if (PHYDM_DBGPRINT == 1)
#define PHYDM_SNPRINTF(msg, ...) \
do { \
snprintf(msg, ##__VA_ARGS__); \
ODM_RT_TRACE(dm, ODM_COMP_UNCOND, output); \
} while (0)
#else
#define PHYDM_SNPRINTF(msg, ...) \
do { \
if (out_len > used) \
used += snprintf(msg, ##__VA_ARGS__); \
} while (0)
#endif
void phydm_basic_profile(void *dm_void, u32 *_used, char *output,
u32 *_out_len);
s32 phydm_cmd(struct phy_dm_struct *dm, char *input, u32 in_len, u8 flag,
char *output, u32 out_len);
void phydm_cmd_parser(struct phy_dm_struct *dm, char input[][16], u32 input_num,
u8 flag, char *output, u32 out_len);
bool phydm_api_trx_mode(struct phy_dm_struct *dm, enum odm_rf_path tx_path,
enum odm_rf_path rx_path, bool is_tx2_path);
void phydm_fw_trace_en_h2c(void *dm_void, bool enable, u32 fw_debug_component,
u32 monitor_mode, u32 macid);
void phydm_fw_trace_handler(void *dm_void, u8 *cmd_buf, u8 cmd_len);
void phydm_fw_trace_handler_code(void *dm_void, u8 *buffer, u8 cmd_len);
void phydm_fw_trace_handler_8051(void *dm_void, u8 *cmd_buf, u8 cmd_len);
#endif /* __ODM_DBG_H__ */

View File

@ -0,0 +1,59 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDM_DFS_H__
#define __PHYDM_DFS_H__
#define DFS_VERSION "0.0"
/* ============================================================
* Definition
* ============================================================
*/
/* ============================================================
* 1 structure
* ============================================================
*/
/* ============================================================
* enumeration
* ============================================================
*/
enum phydm_dfs_region_domain {
PHYDM_DFS_DOMAIN_UNKNOWN = 0,
PHYDM_DFS_DOMAIN_FCC = 1,
PHYDM_DFS_DOMAIN_MKK = 2,
PHYDM_DFS_DOMAIN_ETSI = 3,
};
/* ============================================================
* function prototype
* ============================================================
*/
#define phydm_dfs_master_enabled(dm) false
#endif /*#ifndef __PHYDM_DFS_H__ */

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,241 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMDIG_H__
#define __PHYDMDIG_H__
#define DIG_VERSION "1.32" /* 2016.09.02 YuChen. add CCK PD for 8197F*/
/* Pause DIG & CCKPD */
#define DM_DIG_MAX_PAUSE_TYPE 0x7
enum dig_goupcheck_level {
DIG_GOUPCHECK_LEVEL_0,
DIG_GOUPCHECK_LEVEL_1,
DIG_GOUPCHECK_LEVEL_2
};
struct dig_thres {
bool is_stop_dig; /* for debug */
bool is_ignore_dig;
bool is_psd_in_progress;
u8 dig_enable_flag;
u8 dig_ext_port_stage;
int rssi_low_thresh;
int rssi_high_thresh;
u32 fa_low_thresh;
u32 fa_high_thresh;
u8 cur_sta_connect_state;
u8 pre_sta_connect_state;
u8 cur_multi_sta_connect_state;
u8 pre_ig_value;
u8 cur_ig_value;
u8 backup_ig_value; /* MP DIG */
u8 bt30_cur_igi;
u8 igi_backup;
s8 backoff_val;
s8 backoff_val_range_max;
s8 backoff_val_range_min;
u8 rx_gain_range_max;
u8 rx_gain_range_min;
u8 rssi_val_min;
u8 pre_cck_cca_thres;
u8 cur_cck_cca_thres;
u8 pre_cck_pd_state;
u8 cur_cck_pd_state;
u8 cck_pd_backup;
u8 pause_cckpd_level;
u8 pause_cckpd_value[DM_DIG_MAX_PAUSE_TYPE + 1];
u8 large_fa_hit;
u8 large_fa_timeout; /*if (large_fa_hit), monitor "large_fa_timeout"
*sec, if timeout, large_fa_hit=0
*/
u8 forbidden_igi;
u32 recover_cnt;
u8 dig_dynamic_min_0;
u8 dig_dynamic_min_1;
bool is_media_connect_0;
bool is_media_connect_1;
u32 ant_div_rssi_max;
u32 rssi_max;
u8 *is_p2p_in_process;
u8 pause_dig_level;
u8 pause_dig_value[DM_DIG_MAX_PAUSE_TYPE + 1];
u32 cck_fa_ma;
enum dig_goupcheck_level dig_go_up_check_level;
u8 aaa_default;
u8 rf_gain_idx;
u8 agc_table_idx;
u8 big_jump_lmt[16];
u8 enable_adjust_big_jump : 1;
u8 big_jump_step1 : 3;
u8 big_jump_step2 : 2;
u8 big_jump_step3 : 2;
};
struct false_alarm_stat {
u32 cnt_parity_fail;
u32 cnt_rate_illegal;
u32 cnt_crc8_fail;
u32 cnt_mcs_fail;
u32 cnt_ofdm_fail;
u32 cnt_ofdm_fail_pre; /* For RTL8881A */
u32 cnt_cck_fail;
u32 cnt_all;
u32 cnt_all_pre;
u32 cnt_fast_fsync;
u32 cnt_sb_search_fail;
u32 cnt_ofdm_cca;
u32 cnt_cck_cca;
u32 cnt_cca_all;
u32 cnt_bw_usc; /* Gary */
u32 cnt_bw_lsc; /* Gary */
u32 cnt_cck_crc32_error;
u32 cnt_cck_crc32_ok;
u32 cnt_ofdm_crc32_error;
u32 cnt_ofdm_crc32_ok;
u32 cnt_ht_crc32_error;
u32 cnt_ht_crc32_ok;
u32 cnt_vht_crc32_error;
u32 cnt_vht_crc32_ok;
u32 cnt_crc32_error_all;
u32 cnt_crc32_ok_all;
bool cck_block_enable;
bool ofdm_block_enable;
u32 dbg_port0;
bool edcca_flag;
};
enum dm_dig_op {
DIG_TYPE_THRESH_HIGH = 0,
DIG_TYPE_THRESH_LOW = 1,
DIG_TYPE_BACKOFF = 2,
DIG_TYPE_RX_GAIN_MIN = 3,
DIG_TYPE_RX_GAIN_MAX = 4,
DIG_TYPE_ENABLE = 5,
DIG_TYPE_DISABLE = 6,
DIG_OP_TYPE_MAX
};
enum phydm_pause_type { PHYDM_PAUSE = BIT(0), PHYDM_RESUME = BIT(1) };
enum phydm_pause_level {
/* number of pause level can't exceed DM_DIG_MAX_PAUSE_TYPE */
PHYDM_PAUSE_LEVEL_0 = 0,
PHYDM_PAUSE_LEVEL_1 = 1,
PHYDM_PAUSE_LEVEL_2 = 2,
PHYDM_PAUSE_LEVEL_3 = 3,
PHYDM_PAUSE_LEVEL_4 = 4,
PHYDM_PAUSE_LEVEL_5 = 5,
PHYDM_PAUSE_LEVEL_6 = 6,
PHYDM_PAUSE_LEVEL_7 = DM_DIG_MAX_PAUSE_TYPE /* maximum level */
};
#define DM_DIG_THRESH_HIGH 40
#define DM_DIG_THRESH_LOW 35
#define DM_FALSEALARM_THRESH_LOW 400
#define DM_FALSEALARM_THRESH_HIGH 1000
#define DM_DIG_MAX_NIC 0x3e
#define DM_DIG_MIN_NIC 0x20
#define DM_DIG_MAX_OF_MIN_NIC 0x3e
#define DM_DIG_MAX_AP 0x3e
#define DM_DIG_MIN_AP 0x20
#define DM_DIG_MAX_OF_MIN 0x2A /* 0x32 */
#define DM_DIG_MIN_AP_DFS 0x20
#define DM_DIG_MAX_NIC_HP 0x46
#define DM_DIG_MIN_NIC_HP 0x2e
#define DM_DIG_MAX_AP_HP 0x42
#define DM_DIG_MIN_AP_HP 0x30
/* vivi 92c&92d has different definition, 20110504
* this is for 92c
*/
#define DM_DIG_FA_TH0 0x200 /* 0x20 */
#define DM_DIG_FA_TH1 0x300
#define DM_DIG_FA_TH2 0x400
/* this is for 92d */
#define DM_DIG_FA_TH0_92D 0x100
#define DM_DIG_FA_TH1_92D 0x400
#define DM_DIG_FA_TH2_92D 0x600
#define DM_DIG_BACKOFF_MAX 12
#define DM_DIG_BACKOFF_MIN -4
#define DM_DIG_BACKOFF_DEFAULT 10
#define DM_DIG_FA_TH0_LPS 4 /* -> 4 in lps */
#define DM_DIG_FA_TH1_LPS 15 /* -> 15 lps */
#define DM_DIG_FA_TH2_LPS 30 /* -> 30 lps */
#define RSSI_OFFSET_DIG 0x05
#define LARGE_FA_TIMEOUT 60
void odm_change_dynamic_init_gain_thresh(void *dm_void, u32 dm_type,
u32 dm_value);
void odm_write_dig(void *dm_void, u8 current_igi);
void odm_pause_dig(void *dm_void, enum phydm_pause_type pause_type,
enum phydm_pause_level pause_level, u8 igi_value);
void odm_dig_init(void *dm_void);
void odm_DIG(void *dm_void);
void odm_dig_by_rssi_lps(void *dm_void);
void odm_false_alarm_counter_statistics(void *dm_void);
void odm_pause_cck_packet_detection(void *dm_void,
enum phydm_pause_type pause_type,
enum phydm_pause_level pause_level,
u8 cck_pd_threshold);
void odm_cck_packet_detection_thresh(void *dm_void);
void odm_write_cck_cca_thres(void *dm_void, u8 cur_cck_cca_thres);
bool phydm_dig_go_up_check(void *dm_void);
#endif

View File

@ -0,0 +1,37 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMDYMICRXPATH_H__
#define __PHYDMDYMICRXPATH_H__
#define DYNAMIC_RX_PATH_VERSION "1.0" /*2016.07.15 Dino */
#define DRP_RSSI_TH 35
#define INIT_DRP_TIMMER 0
#define CANCEL_DRP_TIMMER 1
#define RELEASE_DRP_TIMMER 2
#endif

View File

@ -0,0 +1,129 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
static inline void phydm_update_rf_state(struct phy_dm_struct *dm,
struct dyn_pwr_saving *dm_ps_table,
int _rssi_up_bound,
int _rssi_low_bound,
int _is_force_in_normal)
{
if (_is_force_in_normal) {
dm_ps_table->cur_rf_state = rf_normal;
return;
}
if (dm->rssi_min == 0xFF) {
dm_ps_table->cur_rf_state = RF_MAX;
return;
}
if (dm_ps_table->pre_rf_state == rf_normal) {
if (dm->rssi_min >= _rssi_up_bound)
dm_ps_table->cur_rf_state = rf_save;
else
dm_ps_table->cur_rf_state = rf_normal;
} else {
if (dm->rssi_min <= _rssi_low_bound)
dm_ps_table->cur_rf_state = rf_normal;
else
dm_ps_table->cur_rf_state = rf_save;
}
}
void odm_dynamic_bb_power_saving_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dyn_pwr_saving *dm_ps_table = &dm->dm_ps_table;
dm_ps_table->pre_cca_state = CCA_MAX;
dm_ps_table->cur_cca_state = CCA_MAX;
dm_ps_table->pre_rf_state = RF_MAX;
dm_ps_table->cur_rf_state = RF_MAX;
dm_ps_table->rssi_val_min = 0;
dm_ps_table->initialize = 0;
}
void odm_rf_saving(void *dm_void, u8 is_force_in_normal)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dyn_pwr_saving *dm_ps_table = &dm->dm_ps_table;
u8 rssi_up_bound = 30;
u8 rssi_low_bound = 25;
if (dm->patch_id == 40) { /* RT_CID_819x_FUNAI_TV */
rssi_up_bound = 50;
rssi_low_bound = 45;
}
if (dm_ps_table->initialize == 0) {
dm_ps_table->reg874 =
(odm_get_bb_reg(dm, 0x874, MASKDWORD) & 0x1CC000) >> 14;
dm_ps_table->regc70 =
(odm_get_bb_reg(dm, 0xc70, MASKDWORD) & BIT(3)) >> 3;
dm_ps_table->reg85c =
(odm_get_bb_reg(dm, 0x85c, MASKDWORD) & 0xFF000000) >>
24;
dm_ps_table->rega74 =
(odm_get_bb_reg(dm, 0xa74, MASKDWORD) & 0xF000) >> 12;
/* Reg818 = phy_query_bb_reg(adapter, 0x818, MASKDWORD); */
dm_ps_table->initialize = 1;
}
phydm_update_rf_state(dm, dm_ps_table, rssi_up_bound, rssi_low_bound,
is_force_in_normal);
if (dm_ps_table->pre_rf_state != dm_ps_table->cur_rf_state) {
if (dm_ps_table->cur_rf_state == rf_save) {
odm_set_bb_reg(dm, 0x874, 0x1C0000,
0x2); /* reg874[20:18]=3'b010 */
odm_set_bb_reg(dm, 0xc70, BIT(3),
0); /* regc70[3]=1'b0 */
odm_set_bb_reg(dm, 0x85c, 0xFF000000,
0x63); /* reg85c[31:24]=0x63 */
odm_set_bb_reg(dm, 0x874, 0xC000,
0x2); /* reg874[15:14]=2'b10 */
odm_set_bb_reg(dm, 0xa74, 0xF000,
0x3); /* RegA75[7:4]=0x3 */
odm_set_bb_reg(dm, 0x818, BIT(28),
0x0); /* Reg818[28]=1'b0 */
odm_set_bb_reg(dm, 0x818, BIT(28),
0x1); /* Reg818[28]=1'b1 */
} else {
odm_set_bb_reg(dm, 0x874, 0x1CC000,
dm_ps_table->reg874);
odm_set_bb_reg(dm, 0xc70, BIT(3), dm_ps_table->regc70);
odm_set_bb_reg(dm, 0x85c, 0xFF000000,
dm_ps_table->reg85c);
odm_set_bb_reg(dm, 0xa74, 0xF000, dm_ps_table->rega74);
odm_set_bb_reg(dm, 0x818, BIT(28), 0x0);
}
dm_ps_table->pre_rf_state = dm_ps_table->cur_rf_state;
}
}

View File

@ -0,0 +1,50 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMDYNAMICBBPOWERSAVING_H__
#define __PHYDMDYNAMICBBPOWERSAVING_H__
#define DYNAMIC_BBPWRSAV_VERSION "1.1"
struct dyn_pwr_saving {
u8 pre_cca_state;
u8 cur_cca_state;
u8 pre_rf_state;
u8 cur_rf_state;
int rssi_val_min;
u8 initialize;
u32 reg874, regc70, reg85c, rega74;
};
#define dm_rf_saving odm_rf_saving
void odm_rf_saving(void *dm_void, u8 is_force_in_normal);
void odm_dynamic_bb_power_saving_init(void *dm_void);
#endif

View File

@ -0,0 +1,102 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
void odm_dynamic_tx_power_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
dm->last_dtp_lvl = tx_high_pwr_level_normal;
dm->dynamic_tx_high_power_lvl = tx_high_pwr_level_normal;
dm->tx_agc_ofdm_18_6 =
odm_get_bb_reg(dm, 0xC24, MASKDWORD); /*TXAGC {18M 12M 9M 6M}*/
}
void odm_dynamic_tx_power_save_power_index(void *dm_void) {}
void odm_dynamic_tx_power_restore_power_index(void *dm_void) {}
void odm_dynamic_tx_power_write_power_index(void *dm_void, u8 value)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u8 index;
u32 power_index_reg[6] = {0xc90, 0xc91, 0xc92, 0xc98, 0xc99, 0xc9a};
for (index = 0; index < 6; index++)
odm_write_1byte(dm, power_index_reg[index], value);
}
static void odm_dynamic_tx_power_nic_ce(void *dm_void) {}
void odm_dynamic_tx_power(void *dm_void)
{
/* */
/* For AP/ADSL use struct rtl8192cd_priv* */
/* For CE/NIC use struct void* */
/* */
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (!(dm->support_ability & ODM_BB_DYNAMIC_TXPWR))
return;
/* 2011/09/29 MH In HW integration first stage, we provide 4 different
* handle to operate at the same time.
* In the stage2/3, we need to prive universal interface and merge all
* HW dynamic mechanism.
*/
switch (dm->support_platform) {
case ODM_WIN:
odm_dynamic_tx_power_nic(dm);
break;
case ODM_CE:
odm_dynamic_tx_power_nic_ce(dm);
break;
case ODM_AP:
odm_dynamic_tx_power_ap(dm);
break;
default:
break;
}
}
void odm_dynamic_tx_power_nic(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (!(dm->support_ability & ODM_BB_DYNAMIC_TXPWR))
return;
}
void odm_dynamic_tx_power_ap(void *dm_void
)
{
}
void odm_dynamic_tx_power_8821(void *dm_void, u8 *desc, u8 mac_id) {}

View File

@ -0,0 +1,64 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMDYNAMICTXPOWER_H__
#define __PHYDMDYNAMICTXPOWER_H__
/*#define DYNAMIC_TXPWR_VERSION "1.0"*/
/*#define DYNAMIC_TXPWR_VERSION "1.3" */ /*2015.08.26, Add 8814 Dynamic TX pwr*/
#define DYNAMIC_TXPWR_VERSION "1.4" /*2015.11.06,Add CE 8821A Dynamic TX pwr*/
#define TX_POWER_NEAR_FIELD_THRESH_LVL2 74
#define TX_POWER_NEAR_FIELD_THRESH_LVL1 60
#define tx_high_pwr_level_normal 0
#define tx_high_pwr_level_level1 1
#define tx_high_pwr_level_level2 2
#define tx_high_pwr_level_bt1 3
#define tx_high_pwr_level_bt2 4
#define tx_high_pwr_level_15 5
#define tx_high_pwr_level_35 6
#define tx_high_pwr_level_50 7
#define tx_high_pwr_level_70 8
#define tx_high_pwr_level_100 9
void odm_dynamic_tx_power_init(void *dm_void);
void odm_dynamic_tx_power_restore_power_index(void *dm_void);
void odm_dynamic_tx_power_nic(void *dm_void);
void odm_dynamic_tx_power_save_power_index(void *dm_void);
void odm_dynamic_tx_power_write_power_index(void *dm_void, u8 value);
void odm_dynamic_tx_power_8821(void *dm_void, u8 *desc, u8 mac_id);
void odm_dynamic_tx_power(void *dm_void);
void odm_dynamic_tx_power_ap(void *dm_void);
#endif

View File

@ -0,0 +1,139 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
void odm_edca_turbo_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
dm->dm_edca_table.is_current_turbo_edca = false;
dm->dm_edca_table.is_cur_rdl_state = false;
ODM_RT_TRACE(dm, ODM_COMP_EDCA_TURBO, "Orginial VO PARAM: 0x%x\n",
odm_read_4byte(dm, ODM_EDCA_VO_PARAM));
ODM_RT_TRACE(dm, ODM_COMP_EDCA_TURBO, "Orginial VI PARAM: 0x%x\n",
odm_read_4byte(dm, ODM_EDCA_VI_PARAM));
ODM_RT_TRACE(dm, ODM_COMP_EDCA_TURBO, "Orginial BE PARAM: 0x%x\n",
odm_read_4byte(dm, ODM_EDCA_BE_PARAM));
ODM_RT_TRACE(dm, ODM_COMP_EDCA_TURBO, "Orginial BK PARAM: 0x%x\n",
odm_read_4byte(dm, ODM_EDCA_BK_PARAM));
} /* ODM_InitEdcaTurbo */
void odm_edca_turbo_check(void *dm_void)
{
/* For AP/ADSL use struct rtl8192cd_priv* */
/* For CE/NIC use struct void* */
/* 2011/09/29 MH In HW integration first stage, we provide 4 different
* handle to operate at the same time.
* In the stage2/3, we need to prive universal interface and merge all
* HW dynamic mechanism.
*/
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
ODM_RT_TRACE(dm, ODM_COMP_EDCA_TURBO,
"%s========================>\n", __func__);
if (!(dm->support_ability & ODM_MAC_EDCA_TURBO))
return;
switch (dm->support_platform) {
case ODM_WIN:
break;
case ODM_CE:
odm_edca_turbo_check_ce(dm);
break;
}
ODM_RT_TRACE(dm, ODM_COMP_EDCA_TURBO,
"<========================%s\n", __func__);
} /* odm_CheckEdcaTurbo */
void odm_edca_turbo_check_ce(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
u64 cur_txok_cnt = 0;
u64 cur_rxok_cnt = 0;
u32 edca_be_ul = 0x5ea42b;
u32 edca_be_dl = 0x5ea42b;
u32 edca_be = 0x5ea42b;
bool is_cur_rdlstate;
bool edca_turbo_on = false;
if (dm->wifi_test)
return;
if (!dm->is_linked) {
rtlpriv->dm.is_any_nonbepkts = false;
return;
}
if (rtlpriv->dm.dbginfo.num_non_be_pkt > 0x100)
rtlpriv->dm.is_any_nonbepkts = true;
rtlpriv->dm.dbginfo.num_non_be_pkt = 0;
cur_txok_cnt = rtlpriv->stats.txbytesunicast_inperiod;
cur_rxok_cnt = rtlpriv->stats.rxbytesunicast_inperiod;
/*b_bias_on_rx = false;*/
edca_turbo_on = ((!rtlpriv->dm.is_any_nonbepkts) &&
(!rtlpriv->dm.disable_framebursting)) ?
true :
false;
if (rtlpriv->mac80211.mode == WIRELESS_MODE_B)
goto label_exit;
if (edca_turbo_on) {
is_cur_rdlstate =
(cur_rxok_cnt > cur_txok_cnt * 4) ? true : false;
edca_be = is_cur_rdlstate ? edca_be_dl : edca_be_ul;
rtl_write_dword(rtlpriv, REG_EDCA_BE_PARAM_8822B, edca_be);
rtlpriv->dm.is_cur_rdlstate = is_cur_rdlstate;
rtlpriv->dm.current_turbo_edca = true;
} else {
if (rtlpriv->dm.current_turbo_edca) {
u8 tmp = AC0_BE;
rtlpriv->cfg->ops->set_hw_reg(rtlpriv->hw,
HW_VAR_AC_PARAM,
(u8 *)(&tmp));
rtlpriv->dm.current_turbo_edca = false;
}
}
label_exit:
rtlpriv->dm.is_any_nonbepkts = false;
}

View File

@ -0,0 +1,44 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMEDCATURBOCHECK_H__
#define __PHYDMEDCATURBOCHECK_H__
/*#define EDCATURBO_VERSION "2.1"*/
#define EDCATURBO_VERSION "2.3" /*2015.07.29 by YuChen*/
struct edca_turbo {
bool is_current_turbo_edca;
bool is_cur_rdl_state;
u32 prv_traffic_idx; /* edca turbo */
};
void odm_edca_turbo_check(void *dm_void);
void odm_edca_turbo_init(void *dm_void);
void odm_edca_turbo_check_ce(void *dm_void);
#endif

View File

@ -0,0 +1,33 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDM_FEATURES_H__
#define __PHYDM_FEATURES
/*phydm debyg report & tools*/
/*Antenna Diversity*/
#endif

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,510 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HALHWOUTSRC_H__
#define __HALHWOUTSRC_H__
/*--------------------------Define -------------------------------------------*/
#define CCK_RSSI_INIT_COUNT 5
#define RA_RSSI_STATE_INIT 0
#define RA_RSSI_STATE_SEND 1
#define RA_RSSI_STATE_HOLD 2
#define CFO_HW_RPT_2_MHZ(val) ((val << 1) + (val >> 1))
/* ((X* 3125) / 10)>>7 = (X*10)>>2 = X*2.5 = X<<1 + X>>1 */
#define AGC_DIFF_CONFIG_MP(ic, band) \
(odm_read_and_config_mp_##ic##_agc_tab_diff( \
dm, array_mp_##ic##_agc_tab_diff_##band, \
sizeof(array_mp_##ic##_agc_tab_diff_##band) / sizeof(u32)))
#define AGC_DIFF_CONFIG_TC(ic, band) \
(odm_read_and_config_tc_##ic##_agc_tab_diff( \
dm, array_tc_##ic##_agc_tab_diff_##band, \
sizeof(array_tc_##ic##_agc_tab_diff_##band) / sizeof(u32)))
#define AGC_DIFF_CONFIG(ic, band) \
do { \
if (dm->is_mp_chip) \
AGC_DIFF_CONFIG_MP(ic, band); \
else \
AGC_DIFF_CONFIG_TC(ic, band); \
} while (0)
/* ************************************************************
* structure and define
* *************************************************************/
struct phy_rx_agc_info {
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 gain : 7, trsw : 1;
#else
u8 trsw : 1, gain : 7;
#endif
};
struct phy_status_rpt_8192cd {
struct phy_rx_agc_info path_agc[2];
u8 ch_corr[2];
u8 cck_sig_qual_ofdm_pwdb_all;
u8 cck_agc_rpt_ofdm_cfosho_a;
u8 cck_rpt_b_ofdm_cfosho_b;
u8 rsvd_1; /*ch_corr_msb;*/
u8 noise_power_db_msb;
s8 path_cfotail[2];
u8 pcts_mask[2];
s8 stream_rxevm[2];
u8 path_rxsnr[2];
u8 noise_power_db_lsb;
u8 rsvd_2[3];
u8 stream_csi[2];
u8 stream_target_csi[2];
s8 sig_evm;
u8 rsvd_3;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 antsel_rx_keep_2 : 1; /*ex_intf_flg:1;*/
u8 sgi_en : 1;
u8 rxsc : 2;
u8 idle_long : 1;
u8 r_ant_train_en : 1;
u8 ant_sel_b : 1;
u8 ant_sel : 1;
#else /*_BIG_ENDIAN_ */
u8 ant_sel : 1;
u8 ant_sel_b : 1;
u8 r_ant_train_en : 1;
u8 idle_long : 1;
u8 rxsc : 2;
u8 sgi_en : 1;
u8 antsel_rx_keep_2 : 1; /*ex_intf_flg:1;*/
#endif
};
struct phy_status_rpt_8812 {
/* DWORD 0*/
u8 gain_trsw[2]; /*path-A and path-B {TRSW, gain[6:0] }*/
u8 chl_num_LSB; /*channel number[7:0]*/
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 chl_num_MSB : 2; /*channel number[9:8]*/
u8 sub_chnl : 4; /*sub-channel location[3:0]*/
u8 r_RFMOD : 2; /*RF mode[1:0]*/
#else /*_BIG_ENDIAN_ */
u8 r_RFMOD : 2;
u8 sub_chnl : 4;
u8 chl_num_MSB : 2;
#endif
/* DWORD 1*/
u8 pwdb_all; /*CCK signal quality / OFDM pwdb all*/
s8 cfosho[2]; /*DW1 byte 1 DW1 byte2 */
/*CCK AGC report and CCK_BB_Power / OFDM path-A and path-B short CFO*/
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
/*this should be checked again
*because the definition of 8812 and 8814 is different
*/
u8 resvd_0 : 6;
u8 bt_RF_ch_MSB : 2; /*8812A:2'b0, 8814A: bt rf channel keep[7:6]*/
#else /*_BIG_ENDIAN_*/
u8 bt_RF_ch_MSB : 2;
u8 resvd_0 : 6;
#endif
/* DWORD 2*/
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 ant_div_sw_a : 1; /*8812A: ant_div_sw_a, 8814A: 1'b0*/
u8 ant_div_sw_b : 1; /*8812A: ant_div_sw_b, 8814A: 1'b0*/
u8 bt_RF_ch_LSB : 6; /*8812A: 6'b0, 8814A: bt rf channel keep[5:0]*/
#else /*_BIG_ENDIAN_ */
u8 bt_RF_ch_LSB : 6;
u8 ant_div_sw_b : 1;
u8 ant_div_sw_a : 1;
#endif
s8 cfotail[2]; /*DW2 byte 1 DW2 byte 2 path-A and path-B CFO tail*/
u8 PCTS_MSK_RPT_0; /*PCTS mask report[7:0]*/
u8 PCTS_MSK_RPT_1; /*PCTS mask report[15:8]*/
/* DWORD 3*/
s8 rxevm[2]; /*DW3 byte 1 DW3 byte 2 stream 1 and stream 2 RX EVM*/
s8 rxsnr[2]; /*DW3 byte 3 DW4 byte 0 path-A and path-B RX SNR*/
/* DWORD 4*/
u8 PCTS_MSK_RPT_2; /*PCTS mask report[23:16]*/
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 PCTS_MSK_RPT_3 : 6; /*PCTS mask report[29:24]*/
u8 pcts_rpt_valid : 1; /*pcts_rpt_valid*/
u8 resvd_1 : 1; /*1'b0*/
#else /*_BIG_ENDIAN_*/
u8 resvd_1 : 1;
u8 pcts_rpt_valid : 1;
u8 PCTS_MSK_RPT_3 : 6;
#endif
s8 rxevm_cd[2]; /*DW 4 byte 3 DW5 byte 0 */
/* 8812A: 16'b0, 8814A: stream 3 and stream 4 RX EVM*/
/* DWORD 5*/
u8 csi_current[2]; /*DW5 byte 1 DW5 byte 2 */
/* 8812A: stream 1 and 2 CSI, 8814A: path-C and path-D RX SNR*/
u8 gain_trsw_cd[2]; /*DW5 byte 3 DW6 byte 0 */
/* path-C and path-D {TRSW, gain[6:0] }*/
/* DWORD 6*/
s8 sigevm; /*signal field EVM*/
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 antidx_antc : 3; /*8812A: 3'b0 8814A: antidx_antc[2:0]*/
u8 antidx_antd : 3; /*8812A: 3'b0 8814A: antidx_antd[2:0]*/
u8 dpdt_ctrl_keep : 1; /*8812A: 1'b0 8814A: dpdt_ctrl_keep*/
u8 GNT_BT_keep : 1; /*8812A: 1'b0 8814A: GNT_BT_keep*/
#else /*_BIG_ENDIAN_*/
u8 GNT_BT_keep : 1;
u8 dpdt_ctrl_keep : 1;
u8 antidx_antd : 3;
u8 antidx_antc : 3;
#endif
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 antidx_anta : 3; /*antidx_anta[2:0]*/
u8 antidx_antb : 3; /*antidx_antb[2:0]*/
u8 hw_antsw_occur : 2; /*1'b0*/
#else /*_BIG_ENDIAN_*/
u8 hw_antsw_occur : 2;
u8 antidx_antb : 3;
u8 antidx_anta : 3;
#endif
};
void phydm_reset_rssi_for_dm(struct phy_dm_struct *dm, u8 station_id);
void odm_init_rssi_for_dm(struct phy_dm_struct *dm);
void odm_phy_status_query(struct phy_dm_struct *dm,
struct dm_phy_status_info *phy_info, u8 *phy_status,
struct dm_per_pkt_info *pktinfo);
void odm_mac_status_query(struct phy_dm_struct *dm, u8 *mac_status, u8 mac_id,
bool is_packet_match_bssid, bool is_packet_to_self,
bool is_packet_beacon);
enum hal_status
odm_config_rf_with_tx_pwr_track_header_file(struct phy_dm_struct *dm);
enum hal_status
odm_config_rf_with_header_file(struct phy_dm_struct *dm,
enum odm_rf_config_type config_type,
enum odm_rf_radio_path e_rf_path);
enum hal_status
odm_config_bb_with_header_file(struct phy_dm_struct *dm,
enum odm_bb_config_type config_type);
enum hal_status odm_config_mac_with_header_file(struct phy_dm_struct *dm);
enum hal_status
odm_config_fw_with_header_file(struct phy_dm_struct *dm,
enum odm_fw_config_type config_type,
u8 *p_firmware, u32 *size);
u32 odm_get_hw_img_version(struct phy_dm_struct *dm);
s32 odm_signal_scale_mapping(struct phy_dm_struct *dm, s32 curr_sig);
/*For 8822B only!! need to move to FW finally */
/*==============================================*/
void phydm_rx_phy_status_new_type(struct phy_dm_struct *phydm, u8 *phy_status,
struct dm_per_pkt_info *pktinfo,
struct dm_phy_status_info *phy_info);
bool phydm_query_is_mu_api(struct phy_dm_struct *phydm, u8 ppdu_idx,
u8 *p_data_rate, u8 *p_gid);
struct phy_status_rpt_jaguar2_type0 {
/* DW0 */
u8 page_num;
u8 pwdb;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 gain : 6;
u8 rsvd_0 : 1;
u8 trsw : 1;
#else
u8 trsw : 1;
u8 rsvd_0 : 1;
u8 gain : 6;
#endif
u8 rsvd_1;
/* DW1 */
u8 rsvd_2;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 rxsc : 4;
u8 agc_table : 4;
#else
u8 agc_table : 4;
u8 rxsc : 4;
#endif
u8 channel;
u8 band;
/* DW2 */
u16 length;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 antidx_a : 3;
u8 antidx_b : 3;
u8 rsvd_3 : 2;
u8 antidx_c : 3;
u8 antidx_d : 3;
u8 rsvd_4 : 2;
#else
u8 rsvd_3 : 2;
u8 antidx_b : 3;
u8 antidx_a : 3;
u8 rsvd_4 : 2;
u8 antidx_d : 3;
u8 antidx_c : 3;
#endif
/* DW3 */
u8 signal_quality;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 vga : 5;
u8 lna_l : 3;
u8 bb_power : 6;
u8 rsvd_9 : 1;
u8 lna_h : 1;
#else
u8 lna_l : 3;
u8 vga : 5;
u8 lna_h : 1;
u8 rsvd_9 : 1;
u8 bb_power : 6;
#endif
u8 rsvd_5;
/* DW4 */
u32 rsvd_6;
/* DW5 */
u32 rsvd_7;
/* DW6 */
u32 rsvd_8;
};
struct phy_status_rpt_jaguar2_type1 {
/* DW0 and DW1 */
u8 page_num;
u8 pwdb[4];
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 l_rxsc : 4;
u8 ht_rxsc : 4;
#else
u8 ht_rxsc : 4;
u8 l_rxsc : 4;
#endif
u8 channel;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 band : 2;
u8 rsvd_0 : 1;
u8 hw_antsw_occu : 1;
u8 gnt_bt : 1;
u8 ldpc : 1;
u8 stbc : 1;
u8 beamformed : 1;
#else
u8 beamformed : 1;
u8 stbc : 1;
u8 ldpc : 1;
u8 gnt_bt : 1;
u8 hw_antsw_occu : 1;
u8 rsvd_0 : 1;
u8 band : 2;
#endif
/* DW2 */
u16 lsig_length;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 antidx_a : 3;
u8 antidx_b : 3;
u8 rsvd_1 : 2;
u8 antidx_c : 3;
u8 antidx_d : 3;
u8 rsvd_2 : 2;
#else
u8 rsvd_1 : 2;
u8 antidx_b : 3;
u8 antidx_a : 3;
u8 rsvd_2 : 2;
u8 antidx_d : 3;
u8 antidx_c : 3;
#endif
/* DW3 */
u8 paid;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 paid_msb : 1;
u8 gid : 6;
u8 rsvd_3 : 1;
#else
u8 rsvd_3 : 1;
u8 gid : 6;
u8 paid_msb : 1;
#endif
u8 intf_pos;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 intf_pos_msb : 1;
u8 rsvd_4 : 2;
u8 nb_intf_flag : 1;
u8 rf_mode : 2;
u8 rsvd_5 : 2;
#else
u8 rsvd_5 : 2;
u8 rf_mode : 2;
u8 nb_intf_flag : 1;
u8 rsvd_4 : 2;
u8 intf_pos_msb : 1;
#endif
/* DW4 */
s8 rxevm[4]; /* s(8,1) */
/* DW5 */
s8 cfo_tail[4]; /* s(8,7) */
/* DW6 */
s8 rxsnr[4]; /* s(8,1) */
};
struct phy_status_rpt_jaguar2_type2 {
/* DW0 ane DW1 */
u8 page_num;
u8 pwdb[4];
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 l_rxsc : 4;
u8 ht_rxsc : 4;
#else
u8 ht_rxsc : 4;
u8 l_rxsc : 4;
#endif
u8 channel;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 band : 2;
u8 rsvd_0 : 1;
u8 hw_antsw_occu : 1;
u8 gnt_bt : 1;
u8 ldpc : 1;
u8 stbc : 1;
u8 beamformed : 1;
#else
u8 beamformed : 1;
u8 stbc : 1;
u8 ldpc : 1;
u8 gnt_bt : 1;
u8 hw_antsw_occu : 1;
u8 rsvd_0 : 1;
u8 band : 2;
#endif
/* DW2 */
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 shift_l_map : 6;
u8 rsvd_1 : 2;
#else
u8 rsvd_1 : 2;
u8 shift_l_map : 6;
#endif
u8 cnt_pw2cca;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 agc_table_a : 4;
u8 agc_table_b : 4;
u8 agc_table_c : 4;
u8 agc_table_d : 4;
#else
u8 agc_table_b : 4;
u8 agc_table_a : 4;
u8 agc_table_d : 4;
u8 agc_table_c : 4;
#endif
/* DW3 ~ DW6*/
u8 cnt_cca2agc_rdy;
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 gain_a : 6;
u8 rsvd_2 : 1;
u8 trsw_a : 1;
u8 gain_b : 6;
u8 rsvd_3 : 1;
u8 trsw_b : 1;
u8 gain_c : 6;
u8 rsvd_4 : 1;
u8 trsw_c : 1;
u8 gain_d : 6;
u8 rsvd_5 : 1;
u8 trsw_d : 1;
u8 aagc_step_a : 2;
u8 aagc_step_b : 2;
u8 aagc_step_c : 2;
u8 aagc_step_d : 2;
#else
u8 trsw_a : 1;
u8 rsvd_2 : 1;
u8 gain_a : 6;
u8 trsw_b : 1;
u8 rsvd_3 : 1;
u8 gain_b : 6;
u8 trsw_c : 1;
u8 rsvd_4 : 1;
u8 gain_c : 6;
u8 trsw_d : 1;
u8 rsvd_5 : 1;
u8 gain_d : 6;
u8 aagc_step_d : 2;
u8 aagc_step_c : 2;
u8 aagc_step_b : 2;
u8 aagc_step_a : 2;
#endif
u8 ht_aagc_gain[4];
u8 dagc_gain[4];
#if (ODM_ENDIAN_TYPE == ODM_ENDIAN_LITTLE)
u8 counter : 6;
u8 rsvd_6 : 2;
u8 syn_count : 5;
u8 rsvd_7 : 3;
#else
u8 rsvd_6 : 2;
u8 counter : 6;
u8 rsvd_7 : 3;
u8 syn_count : 5;
#endif
};
u32 query_phydm_trx_capability(struct phy_dm_struct *dm);
u32 query_phydm_stbc_capability(struct phy_dm_struct *dm);
u32 query_phydm_ldpc_capability(struct phy_dm_struct *dm);
u32 query_phydm_txbf_parameters(struct phy_dm_struct *dm);
u32 query_phydm_txbf_capability(struct phy_dm_struct *dm);
#endif /*#ifndef __HALHWOUTSRC_H__*/

View File

@ -0,0 +1,341 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
/*
* ODM IO Relative API.
*/
u8 odm_read_1byte(struct phy_dm_struct *dm, u32 reg_addr)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
return rtl_read_byte(rtlpriv, reg_addr);
}
u16 odm_read_2byte(struct phy_dm_struct *dm, u32 reg_addr)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
return rtl_read_word(rtlpriv, reg_addr);
}
u32 odm_read_4byte(struct phy_dm_struct *dm, u32 reg_addr)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
return rtl_read_dword(rtlpriv, reg_addr);
}
void odm_write_1byte(struct phy_dm_struct *dm, u32 reg_addr, u8 data)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
rtl_write_byte(rtlpriv, reg_addr, data);
}
void odm_write_2byte(struct phy_dm_struct *dm, u32 reg_addr, u16 data)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
rtl_write_word(rtlpriv, reg_addr, data);
}
void odm_write_4byte(struct phy_dm_struct *dm, u32 reg_addr, u32 data)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
rtl_write_dword(rtlpriv, reg_addr, data);
}
void odm_set_mac_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask,
u32 data)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
rtl_set_bbreg(rtlpriv->hw, reg_addr, bit_mask, data);
}
u32 odm_get_mac_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
return rtl_get_bbreg(rtlpriv->hw, reg_addr, bit_mask);
}
void odm_set_bb_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask,
u32 data)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
rtl_set_bbreg(rtlpriv->hw, reg_addr, bit_mask, data);
}
u32 odm_get_bb_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
return rtl_get_bbreg(rtlpriv->hw, reg_addr, bit_mask);
}
void odm_set_rf_reg(struct phy_dm_struct *dm, enum odm_rf_radio_path e_rf_path,
u32 reg_addr, u32 bit_mask, u32 data)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
rtl_set_rfreg(rtlpriv->hw, (enum radio_path)e_rf_path, reg_addr,
bit_mask, data);
}
u32 odm_get_rf_reg(struct phy_dm_struct *dm, enum odm_rf_radio_path e_rf_path,
u32 reg_addr, u32 bit_mask)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
return rtl_get_rfreg(rtlpriv->hw, (enum radio_path)e_rf_path, reg_addr,
bit_mask);
}
/*
* ODM Memory relative API.
*/
void odm_allocate_memory(struct phy_dm_struct *dm, void **ptr, u32 length)
{
*ptr = kmalloc(length, GFP_ATOMIC);
}
/* length could be ignored, used to detect memory leakage. */
void odm_free_memory(struct phy_dm_struct *dm, void *ptr, u32 length)
{
kfree(ptr);
}
void odm_move_memory(struct phy_dm_struct *dm, void *p_dest, void *src,
u32 length)
{
memcpy(p_dest, src, length);
}
void odm_memory_set(struct phy_dm_struct *dm, void *pbuf, s8 value, u32 length)
{
memset(pbuf, value, length);
}
s32 odm_compare_memory(struct phy_dm_struct *dm, void *p_buf1, void *buf2,
u32 length)
{
return memcmp(p_buf1, buf2, length);
}
/*
* ODM MISC relative API.
*/
void odm_acquire_spin_lock(struct phy_dm_struct *dm, enum rt_spinlock_type type)
{
}
void odm_release_spin_lock(struct phy_dm_struct *dm, enum rt_spinlock_type type)
{
}
/*
* ODM Timer relative API.
*/
void odm_stall_execution(u32 us_delay) { udelay(us_delay); }
void ODM_delay_ms(u32 ms) { mdelay(ms); }
void ODM_delay_us(u32 us) { udelay(us); }
void ODM_sleep_ms(u32 ms) { msleep(ms); }
void ODM_sleep_us(u32 us) { usleep_range(us, us + 1); }
void odm_set_timer(struct phy_dm_struct *dm, struct timer_list *timer,
u32 ms_delay)
{
mod_timer(timer, jiffies + msecs_to_jiffies(ms_delay));
}
void odm_initialize_timer(struct phy_dm_struct *dm, struct timer_list *timer,
void *call_back_func, void *context,
const char *sz_id)
{
init_timer(timer);
timer->function = call_back_func;
timer->data = (unsigned long)dm;
/*mod_timer(timer, jiffies+RTL_MILISECONDS_TO_JIFFIES(10)); */
}
void odm_cancel_timer(struct phy_dm_struct *dm, struct timer_list *timer)
{
del_timer(timer);
}
void odm_release_timer(struct phy_dm_struct *dm, struct timer_list *timer) {}
static u8 phydm_trans_h2c_id(struct phy_dm_struct *dm, u8 phydm_h2c_id)
{
u8 platform_h2c_id = phydm_h2c_id;
switch (phydm_h2c_id) {
/* 1 [0] */
case ODM_H2C_RSSI_REPORT:
break;
/* 1 [3] */
case ODM_H2C_WIFI_CALIBRATION:
break;
/* 1 [4] */
case ODM_H2C_IQ_CALIBRATION:
break;
/* 1 [5] */
case ODM_H2C_RA_PARA_ADJUST:
break;
/* 1 [6] */
case PHYDM_H2C_DYNAMIC_TX_PATH:
break;
/* [7]*/
case PHYDM_H2C_FW_TRACE_EN:
platform_h2c_id = 0x49;
break;
case PHYDM_H2C_TXBF:
break;
case PHYDM_H2C_MU:
platform_h2c_id = 0x4a; /*H2C_MU*/
break;
default:
platform_h2c_id = phydm_h2c_id;
break;
}
return platform_h2c_id;
}
/*ODM FW relative API.*/
void odm_fill_h2c_cmd(struct phy_dm_struct *dm, u8 phydm_h2c_id, u32 cmd_len,
u8 *cmd_buffer)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
u8 platform_h2c_id;
platform_h2c_id = phydm_trans_h2c_id(dm, phydm_h2c_id);
ODM_RT_TRACE(dm, PHYDM_COMP_RA_DBG,
"[H2C] platform_h2c_id = ((0x%x))\n", platform_h2c_id);
rtlpriv->cfg->ops->fill_h2c_cmd(rtlpriv->hw, platform_h2c_id, cmd_len,
cmd_buffer);
}
u8 phydm_c2H_content_parsing(void *dm_void, u8 c2h_cmd_id, u8 c2h_cmd_len,
u8 *tmp_buf)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u8 extend_c2h_sub_id = 0;
u8 find_c2h_cmd = true;
switch (c2h_cmd_id) {
case PHYDM_C2H_DBG:
phydm_fw_trace_handler(dm, tmp_buf, c2h_cmd_len);
break;
case PHYDM_C2H_RA_RPT:
phydm_c2h_ra_report_handler(dm, tmp_buf, c2h_cmd_len);
break;
case PHYDM_C2H_RA_PARA_RPT:
odm_c2h_ra_para_report_handler(dm, tmp_buf, c2h_cmd_len);
break;
case PHYDM_C2H_DYNAMIC_TX_PATH_RPT:
break;
case PHYDM_C2H_IQK_FINISH:
break;
case PHYDM_C2H_DBG_CODE:
phydm_fw_trace_handler_code(dm, tmp_buf, c2h_cmd_len);
break;
case PHYDM_C2H_EXTEND:
extend_c2h_sub_id = tmp_buf[0];
if (extend_c2h_sub_id == PHYDM_EXTEND_C2H_DBG_PRINT)
phydm_fw_trace_handler_8051(dm, tmp_buf, c2h_cmd_len);
break;
default:
find_c2h_cmd = false;
break;
}
return find_c2h_cmd;
}
u64 odm_get_current_time(struct phy_dm_struct *dm) { return jiffies; }
u64 odm_get_progressing_time(struct phy_dm_struct *dm, u64 start_time)
{
return jiffies_to_msecs(jiffies - (u32)start_time);
}
void odm_set_tx_power_index_by_rate_section(struct phy_dm_struct *dm,
u8 rf_path, u8 channel,
u8 rate_section)
{
void *adapter = dm->adapter;
phy_set_tx_power_index_by_rs(adapter, channel, rf_path, rate_section);
}
u8 odm_get_tx_power_index(struct phy_dm_struct *dm, u8 rf_path, u8 tx_rate,
u8 band_width, u8 channel)
{
void *adapter = dm->adapter;
return phy_get_tx_power_index(adapter, (enum odm_rf_radio_path)rf_path,
tx_rate, band_width, channel);
}

View File

@ -0,0 +1,205 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODM_INTERFACE_H__
#define __ODM_INTERFACE_H__
#define INTERFACE_VERSION "1.1" /*2015.07.29 YuChen*/
/*
* =========== Constant/Structure/Enum/... Define
*/
/*
* =========== Macro Define
*/
#define _reg_all(_name) ODM_##_name
#define _reg_ic(_name, _ic) ODM_##_name##_ic
#define _bit_all(_name) BIT_##_name
#define _bit_ic(_name, _ic) BIT_##_name##_ic
/* _cat: implemented by Token-Pasting Operator. */
/*===================================
*
* #define ODM_REG_DIG_11N 0xC50
* #define ODM_REG_DIG_11AC 0xDDD
*
* ODM_REG(DIG,_pdm_odm)
* ===================================
*/
#define _reg_11N(_name) ODM_REG_##_name##_11N
#define _reg_11AC(_name) ODM_REG_##_name##_11AC
#define _bit_11N(_name) ODM_BIT_##_name##_11N
#define _bit_11AC(_name) ODM_BIT_##_name##_11AC
#define _cat(_name, _ic_type, _func) \
(((_ic_type) & ODM_IC_11N_SERIES) ? _func##_11N(_name) : \
_func##_11AC(_name))
/* _name: name of register or bit.
* Example: "ODM_REG(R_A_AGC_CORE1, dm)"
* gets "ODM_R_A_AGC_CORE1" or "ODM_R_A_AGC_CORE1_8192C",
* depends on support_ic_type.
*/
#define ODM_REG(_name, _pdm_odm) _cat(_name, _pdm_odm->support_ic_type, _reg)
#define ODM_BIT(_name, _pdm_odm) _cat(_name, _pdm_odm->support_ic_type, _bit)
enum phydm_h2c_cmd {
PHYDM_H2C_TXBF = 0x41,
ODM_H2C_RSSI_REPORT = 0x42,
ODM_H2C_IQ_CALIBRATION = 0x45,
ODM_H2C_RA_PARA_ADJUST = 0x47,
PHYDM_H2C_DYNAMIC_TX_PATH = 0x48,
PHYDM_H2C_FW_TRACE_EN = 0x49,
ODM_H2C_WIFI_CALIBRATION = 0x6d,
PHYDM_H2C_MU = 0x4a,
ODM_MAX_H2CCMD
};
enum phydm_c2h_evt {
PHYDM_C2H_DBG = 0,
PHYDM_C2H_LB = 1,
PHYDM_C2H_XBF = 2,
PHYDM_C2H_TX_REPORT = 3,
PHYDM_C2H_INFO = 9,
PHYDM_C2H_BT_MP = 11,
PHYDM_C2H_RA_RPT = 12,
PHYDM_C2H_RA_PARA_RPT = 14,
PHYDM_C2H_DYNAMIC_TX_PATH_RPT = 15,
PHYDM_C2H_IQK_FINISH = 17, /*0x11*/
PHYDM_C2H_DBG_CODE = 0xFE,
PHYDM_C2H_EXTEND = 0xFF,
};
enum phydm_extend_c2h_evt {
PHYDM_EXTEND_C2H_DBG_PRINT = 0
};
/*
* =========== Extern Variable ??? It should be forbidden.
*/
/*
* =========== EXtern Function Prototype
*/
u8 odm_read_1byte(struct phy_dm_struct *dm, u32 reg_addr);
u16 odm_read_2byte(struct phy_dm_struct *dm, u32 reg_addr);
u32 odm_read_4byte(struct phy_dm_struct *dm, u32 reg_addr);
void odm_write_1byte(struct phy_dm_struct *dm, u32 reg_addr, u8 data);
void odm_write_2byte(struct phy_dm_struct *dm, u32 reg_addr, u16 data);
void odm_write_4byte(struct phy_dm_struct *dm, u32 reg_addr, u32 data);
void odm_set_mac_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask,
u32 data);
u32 odm_get_mac_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask);
void odm_set_bb_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask,
u32 data);
u32 odm_get_bb_reg(struct phy_dm_struct *dm, u32 reg_addr, u32 bit_mask);
void odm_set_rf_reg(struct phy_dm_struct *dm, enum odm_rf_radio_path e_rf_path,
u32 reg_addr, u32 bit_mask, u32 data);
u32 odm_get_rf_reg(struct phy_dm_struct *dm, enum odm_rf_radio_path e_rf_path,
u32 reg_addr, u32 bit_mask);
/*
* Memory Relative Function.
*/
void odm_allocate_memory(struct phy_dm_struct *dm, void **ptr, u32 length);
void odm_free_memory(struct phy_dm_struct *dm, void *ptr, u32 length);
void odm_move_memory(struct phy_dm_struct *dm, void *p_dest, void *src,
u32 length);
s32 odm_compare_memory(struct phy_dm_struct *dm, void *p_buf1, void *buf2,
u32 length);
void odm_memory_set(struct phy_dm_struct *dm, void *pbuf, s8 value, u32 length);
/*
* ODM MISC-spin lock relative API.
*/
void odm_acquire_spin_lock(struct phy_dm_struct *dm,
enum rt_spinlock_type type);
void odm_release_spin_lock(struct phy_dm_struct *dm,
enum rt_spinlock_type type);
/*
* ODM Timer relative API.
*/
void odm_stall_execution(u32 us_delay);
void ODM_delay_ms(u32 ms);
void ODM_delay_us(u32 us);
void ODM_sleep_ms(u32 ms);
void ODM_sleep_us(u32 us);
void odm_set_timer(struct phy_dm_struct *dm, struct timer_list *timer,
u32 ms_delay);
void odm_initialize_timer(struct phy_dm_struct *dm, struct timer_list *timer,
void *call_back_func, void *context,
const char *sz_id);
void odm_cancel_timer(struct phy_dm_struct *dm, struct timer_list *timer);
void odm_release_timer(struct phy_dm_struct *dm, struct timer_list *timer);
/*
* ODM FW relative API.
*/
void odm_fill_h2c_cmd(struct phy_dm_struct *dm, u8 element_id, u32 cmd_len,
u8 *cmd_buffer);
u8 phydm_c2H_content_parsing(void *dm_void, u8 c2h_cmd_id, u8 c2h_cmd_len,
u8 *tmp_buf);
u64 odm_get_current_time(struct phy_dm_struct *dm);
u64 odm_get_progressing_time(struct phy_dm_struct *dm, u64 start_time);
void odm_set_tx_power_index_by_rate_section(struct phy_dm_struct *dm,
u8 rf_path, u8 channel,
u8 rate_section);
u8 odm_get_tx_power_index(struct phy_dm_struct *dm, u8 rf_path, u8 tx_rate,
u8 band_width, u8 channel);
#endif /* __ODM_INTERFACE_H__ */

View File

@ -0,0 +1,76 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMIQK_H__
#define __PHYDMIQK_H__
/*--------------------------Define Parameters-------------------------------*/
#define LOK_delay 1
#define WBIQK_delay 10
#define TX_IQK 0
#define RX_IQK 1
#define TXIQK 0
#define RXIQK1 1
#define RXIQK2 2
#define GSRXK1 0
#define GSRXK2 1
#define kcount_limit_80m 2
#define kcount_limit_others 4
#define rxiqk_gs_limit 4
#define NUM 4
/*----------------------End Define Parameters-------------------------------*/
struct dm_iqk_info {
bool lok_fail[NUM];
bool iqk_fail[2][NUM];
u32 iqc_matrix[2][NUM];
u8 iqk_times;
u32 rf_reg18;
u32 lna_idx;
u8 rxiqk_step;
u8 tmp1bcc;
u8 kcount;
u32 iqk_channel[2];
bool iqk_fail_report[2][4][2]; /*channel/path/TRX(TX:0, RX:1) */
u32 iqk_cfir_real[2][4][2]
[8]; /*channel / path / TRX(TX:0, RX:1) / CFIR_real*/
u32 iqk_cfir_imag[2][4][2]
[8]; /*channel / path / TRX(TX:0, RX:1) / CFIR_imag*/
u8 retry_count[2][4][3]; /* channel / path / (TXK:0, RXK1:1, RXK2:2) */
u8 gs_retry_count[2][4][2]; /* channel / path / (GSRXK1:0, GSRXK2:1) */
u8 rxiqk_fail_code[2][4]; /* channel / path
* 0:SRXK1 fail, 1:RXK1 fail 2:RXK2 fail
*/
u32 lok_idac[2][4]; /*channel / path*/
u16 rxiqk_agc[2][4]; /*channel / path*/
u32 bypass_iqk[2][4]; /*channel / 0xc94/0xe94*/
u32 tmp_gntwl;
bool is_btg;
bool isbnd;
};
#endif

View File

@ -0,0 +1,228 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*============================================================*/
/*include files*/
/*============================================================*/
#include "mp_precomp.h"
#include "phydm_precomp.h"
/*<YuChen, 150720> Add for KFree Feature Requested by RF David.*/
/*This is a phydm API*/
static void phydm_set_kfree_to_rf_8814a(void *dm_void, u8 e_rf_path, u8 data)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
bool is_odd;
if ((data % 2) != 0) { /*odd->positive*/
data = data - 1;
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(19),
1);
is_odd = true;
} else { /*even->negative*/
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(19),
0);
is_odd = false;
}
ODM_RT_TRACE(dm, ODM_COMP_MP, "%s(): RF_0x55[19]= %d\n", __func__,
is_odd);
switch (data) {
case 0:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
0);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 0);
cali_info->kfree_offset[e_rf_path] = 0;
break;
case 2:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
1);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 0);
cali_info->kfree_offset[e_rf_path] = 0;
break;
case 4:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
0);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 1);
cali_info->kfree_offset[e_rf_path] = 1;
break;
case 6:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
1);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 1);
cali_info->kfree_offset[e_rf_path] = 1;
break;
case 8:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
0);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 2);
cali_info->kfree_offset[e_rf_path] = 2;
break;
case 10:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
1);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 2);
cali_info->kfree_offset[e_rf_path] = 2;
break;
case 12:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
0);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 3);
cali_info->kfree_offset[e_rf_path] = 3;
break;
case 14:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
1);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 3);
cali_info->kfree_offset[e_rf_path] = 3;
break;
case 16:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
0);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 4);
cali_info->kfree_offset[e_rf_path] = 4;
break;
case 18:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
1);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 4);
cali_info->kfree_offset[e_rf_path] = 4;
break;
case 20:
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET, BIT(14),
0);
odm_set_rf_reg(dm, e_rf_path, REG_RF_TX_GAIN_OFFSET,
BIT(17) | BIT(16) | BIT(15), 5);
cali_info->kfree_offset[e_rf_path] = 5;
break;
default:
break;
}
if (!is_odd) {
/*that means Kfree offset is negative, we need to record it.*/
cali_info->kfree_offset[e_rf_path] =
(-1) * cali_info->kfree_offset[e_rf_path];
ODM_RT_TRACE(dm, ODM_COMP_MP, "%s(): kfree_offset = %d\n",
__func__, cali_info->kfree_offset[e_rf_path]);
} else {
ODM_RT_TRACE(dm, ODM_COMP_MP, "%s(): kfree_offset = %d\n",
__func__, cali_info->kfree_offset[e_rf_path]);
}
}
static void phydm_set_kfree_to_rf(void *dm_void, u8 e_rf_path, u8 data)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_RTL8814A)
phydm_set_kfree_to_rf_8814a(dm, e_rf_path, data);
}
void phydm_config_kfree(void *dm_void, u8 channel_to_sw, u8 *kfree_table)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
u8 rfpath = 0, max_rf_path = 0;
u8 channel_idx = 0;
if (dm->support_ic_type & ODM_RTL8814A)
max_rf_path = 4; /*0~3*/
else if (dm->support_ic_type &
(ODM_RTL8812 | ODM_RTL8192E | ODM_RTL8822B))
max_rf_path = 2; /*0~1*/
else
max_rf_path = 1;
ODM_RT_TRACE(dm, ODM_COMP_MP, "===>%s()\n", __func__);
if (cali_info->reg_rf_kfree_enable == 2) {
ODM_RT_TRACE(dm, ODM_COMP_MP,
"%s(): reg_rf_kfree_enable == 2, Disable\n",
__func__);
return;
}
if (cali_info->reg_rf_kfree_enable != 1 &&
cali_info->reg_rf_kfree_enable != 0) {
ODM_RT_TRACE(dm, ODM_COMP_MP, "<===%s()\n", __func__);
return;
}
ODM_RT_TRACE(dm, ODM_COMP_MP, "%s(): reg_rf_kfree_enable == true\n",
__func__);
/*Make sure the targetval is defined*/
if (((cali_info->reg_rf_kfree_enable == 1) &&
(kfree_table[0] != 0xFF)) ||
cali_info->rf_kfree_enable) {
/*if kfree_table[0] == 0xff, means no Kfree*/
if (*dm->band_type == ODM_BAND_2_4G) {
if (channel_to_sw <= 14 && channel_to_sw >= 1)
channel_idx = PHYDM_2G;
} else if (*dm->band_type == ODM_BAND_5G) {
if (channel_to_sw >= 36 && channel_to_sw <= 48)
channel_idx = PHYDM_5GLB1;
if (channel_to_sw >= 52 && channel_to_sw <= 64)
channel_idx = PHYDM_5GLB2;
if (channel_to_sw >= 100 && channel_to_sw <= 120)
channel_idx = PHYDM_5GMB1;
if (channel_to_sw >= 124 && channel_to_sw <= 144)
channel_idx = PHYDM_5GMB2;
if (channel_to_sw >= 149 && channel_to_sw <= 177)
channel_idx = PHYDM_5GHB;
}
for (rfpath = ODM_RF_PATH_A; rfpath < max_rf_path; rfpath++) {
ODM_RT_TRACE(dm, ODM_COMP_MP, "%s(): PATH_%d: %#x\n",
__func__, rfpath,
kfree_table[channel_idx * max_rf_path +
rfpath]);
phydm_set_kfree_to_rf(
dm, rfpath,
kfree_table[channel_idx * max_rf_path +
rfpath]);
}
} else {
ODM_RT_TRACE(
dm, ODM_COMP_MP,
"%s(): targetval not defined, Don't execute KFree Process.\n",
__func__);
return;
}
ODM_RT_TRACE(dm, ODM_COMP_MP, "<===%s()\n", __func__);
}

View File

@ -0,0 +1,42 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMKFREE_H__
#define __PHYDKFREE_H__
#define KFREE_VERSION "1.0"
enum phydm_kfree_channeltosw {
PHYDM_2G = 0,
PHYDM_5GLB1 = 1,
PHYDM_5GLB2 = 2,
PHYDM_5GMB1 = 3,
PHYDM_5GMB2 = 4,
PHYDM_5GHB = 5,
};
void phydm_config_kfree(void *dm_void, u8 channel_to_sw, u8 *kfree_table);
#endif

View File

@ -0,0 +1,330 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* include files
* *************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
#include "phydm_noisemonitor.h"
/* *************************************************
* This function is for inband noise test utility only
* To obtain the inband noise level(dbm), do the following.
* 1. disable DIG and Power Saving
* 2. Set initial gain = 0x1a
* 3. Stop updating idle time pwer report (for driver read)
* - 0x80c[25]
*
* **************************************************/
#define VALID_MIN -35
#define VALID_MAX 10
#define VALID_CNT 5
static inline void phydm_set_noise_data_sum(struct noise_level *noise_data,
u8 max_rf_path)
{
u8 rf_path;
for (rf_path = ODM_RF_PATH_A; rf_path < max_rf_path; rf_path++) {
if (noise_data->valid_cnt[rf_path])
noise_data->sum[rf_path] /=
noise_data->valid_cnt[rf_path];
else
noise_data->sum[rf_path] = 0;
}
}
static s16 odm_inband_noise_monitor_n_series(struct phy_dm_struct *dm,
u8 is_pause_dig, u8 igi_value,
u32 max_time)
{
u32 tmp4b;
u8 max_rf_path = 0, rf_path;
u8 reg_c50, reg_c58, valid_done = 0;
struct noise_level noise_data;
u64 start = 0, func_start = 0, func_end = 0;
func_start = odm_get_current_time(dm);
dm->noise_level.noise_all = 0;
if ((dm->rf_type == ODM_1T2R) || (dm->rf_type == ODM_2T2R))
max_rf_path = 2;
else
max_rf_path = 1;
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "%s() ==>\n", __func__);
odm_memory_set(dm, &noise_data, 0, sizeof(struct noise_level));
/* */
/* step 1. Disable DIG && Set initial gain. */
/* */
if (is_pause_dig)
odm_pause_dig(dm, PHYDM_PAUSE, PHYDM_PAUSE_LEVEL_1, igi_value);
/* */
/* step 2. Disable all power save for read registers */
/* */
/* dcmd_DebugControlPowerSave(adapter, PSDisable); */
/* */
/* step 3. Get noise power level */
/* */
start = odm_get_current_time(dm);
while (1) {
/* Stop updating idle time pwer report (for driver read) */
odm_set_bb_reg(dm, REG_FPGA0_TX_GAIN_STAGE, BIT(25), 1);
/* Read Noise Floor Report */
tmp4b = odm_get_bb_reg(dm, 0x8f8, MASKDWORD);
ODM_RT_TRACE(dm, ODM_COMP_COMMON,
"Noise Floor Report (0x8f8) = 0x%08x\n", tmp4b);
/* update idle time pwer report per 5us */
odm_set_bb_reg(dm, REG_FPGA0_TX_GAIN_STAGE, BIT(25), 0);
noise_data.value[ODM_RF_PATH_A] = (u8)(tmp4b & 0xff);
noise_data.value[ODM_RF_PATH_B] = (u8)((tmp4b & 0xff00) >> 8);
ODM_RT_TRACE(dm, ODM_COMP_COMMON,
"value_a = 0x%x(%d), value_b = 0x%x(%d)\n",
noise_data.value[ODM_RF_PATH_A],
noise_data.value[ODM_RF_PATH_A],
noise_data.value[ODM_RF_PATH_B],
noise_data.value[ODM_RF_PATH_B]);
for (rf_path = ODM_RF_PATH_A; rf_path < max_rf_path;
rf_path++) {
noise_data.sval[rf_path] =
(s8)noise_data.value[rf_path];
noise_data.sval[rf_path] /= 2;
}
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "sval_a = %d, sval_b = %d\n",
noise_data.sval[ODM_RF_PATH_A],
noise_data.sval[ODM_RF_PATH_B]);
for (rf_path = ODM_RF_PATH_A; rf_path < max_rf_path;
rf_path++) {
if (!(noise_data.valid_cnt[rf_path] < VALID_CNT) ||
!(noise_data.sval[rf_path] < VALID_MAX &&
noise_data.sval[rf_path] >= VALID_MIN)) {
continue;
}
noise_data.valid_cnt[rf_path]++;
noise_data.sum[rf_path] += noise_data.sval[rf_path];
ODM_RT_TRACE(dm, ODM_COMP_COMMON,
"rf_path:%d Valid sval = %d\n", rf_path,
noise_data.sval[rf_path]);
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "Sum of sval = %d,\n",
noise_data.sum[rf_path]);
if (noise_data.valid_cnt[rf_path] == VALID_CNT) {
valid_done++;
ODM_RT_TRACE(
dm, ODM_COMP_COMMON,
"After divided, rf_path:%d,sum = %d\n",
rf_path, noise_data.sum[rf_path]);
}
}
if ((valid_done == max_rf_path) ||
(odm_get_progressing_time(dm, start) > max_time)) {
phydm_set_noise_data_sum(&noise_data, max_rf_path);
break;
}
}
reg_c50 = (u8)odm_get_bb_reg(dm, REG_OFDM_0_XA_AGC_CORE1, MASKBYTE0);
reg_c50 &= ~BIT(7);
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "0x%x = 0x%02x(%d)\n",
REG_OFDM_0_XA_AGC_CORE1, reg_c50, reg_c50);
dm->noise_level.noise[ODM_RF_PATH_A] =
(u8)(-110 + reg_c50 + noise_data.sum[ODM_RF_PATH_A]);
dm->noise_level.noise_all += dm->noise_level.noise[ODM_RF_PATH_A];
if (max_rf_path == 2) {
reg_c58 = (u8)odm_get_bb_reg(dm, REG_OFDM_0_XB_AGC_CORE1,
MASKBYTE0);
reg_c58 &= ~BIT(7);
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "0x%x = 0x%02x(%d)\n",
REG_OFDM_0_XB_AGC_CORE1, reg_c58, reg_c58);
dm->noise_level.noise[ODM_RF_PATH_B] =
(u8)(-110 + reg_c58 + noise_data.sum[ODM_RF_PATH_B]);
dm->noise_level.noise_all +=
dm->noise_level.noise[ODM_RF_PATH_B];
}
dm->noise_level.noise_all /= max_rf_path;
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "noise_a = %d, noise_b = %d\n",
dm->noise_level.noise[ODM_RF_PATH_A],
dm->noise_level.noise[ODM_RF_PATH_B]);
/* */
/* step 4. Recover the Dig */
/* */
if (is_pause_dig)
odm_pause_dig(dm, PHYDM_RESUME, PHYDM_PAUSE_LEVEL_1, igi_value);
func_end = odm_get_progressing_time(dm, func_start);
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "%s() <==\n", __func__);
return dm->noise_level.noise_all;
}
static s16 odm_inband_noise_monitor_ac_series(struct phy_dm_struct *dm,
u8 is_pause_dig, u8 igi_value,
u32 max_time)
{
s32 rxi_buf_anta, rxq_buf_anta; /*rxi_buf_antb, rxq_buf_antb;*/
s32 value32, pwdb_A = 0, sval, noise, sum;
bool pd_flag;
u8 valid_cnt;
u64 start = 0, func_start = 0, func_end = 0;
if (!(dm->support_ic_type & (ODM_RTL8812 | ODM_RTL8821 | ODM_RTL8814A)))
return 0;
func_start = odm_get_current_time(dm);
dm->noise_level.noise_all = 0;
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "%s() ==>\n", __func__);
/* step 1. Disable DIG && Set initial gain. */
if (is_pause_dig)
odm_pause_dig(dm, PHYDM_PAUSE, PHYDM_PAUSE_LEVEL_1, igi_value);
/* step 2. Disable all power save for read registers */
/*dcmd_DebugControlPowerSave(adapter, PSDisable); */
/* step 3. Get noise power level */
start = odm_get_current_time(dm);
/* reset counters */
sum = 0;
valid_cnt = 0;
/* step 3. Get noise power level */
while (1) {
/*Set IGI=0x1C */
odm_write_dig(dm, 0x1C);
/*stop CK320&CK88 */
odm_set_bb_reg(dm, 0x8B4, BIT(6), 1);
/*Read path-A */
odm_set_bb_reg(dm, 0x8FC, MASKDWORD, 0x200); /*set debug port*/
value32 = odm_get_bb_reg(dm, 0xFA0,
MASKDWORD); /*read debug port*/
rxi_buf_anta = (value32 & 0xFFC00) >>
10; /*rxi_buf_anta=RegFA0[19:10]*/
rxq_buf_anta = value32 & 0x3FF; /*rxq_buf_anta=RegFA0[19:10]*/
pd_flag = (bool)((value32 & BIT(31)) >> 31);
/*Not in packet detection period or Tx state */
if ((!pd_flag) || (rxi_buf_anta != 0x200)) {
/*sign conversion*/
rxi_buf_anta = odm_sign_conversion(rxi_buf_anta, 10);
rxq_buf_anta = odm_sign_conversion(rxq_buf_anta, 10);
pwdb_A = odm_pwdb_conversion(
rxi_buf_anta * rxi_buf_anta +
rxq_buf_anta * rxq_buf_anta,
20, 18); /*S(10,9)*S(10,9)=S(20,18)*/
ODM_RT_TRACE(
dm, ODM_COMP_COMMON,
"pwdb_A= %d dB, rxi_buf_anta= 0x%x, rxq_buf_anta= 0x%x\n",
pwdb_A, rxi_buf_anta & 0x3FF,
rxq_buf_anta & 0x3FF);
}
/*Start CK320&CK88*/
odm_set_bb_reg(dm, 0x8B4, BIT(6), 0);
/*BB Reset*/
odm_write_1byte(dm, 0x02, odm_read_1byte(dm, 0x02) & (~BIT(0)));
odm_write_1byte(dm, 0x02, odm_read_1byte(dm, 0x02) | BIT(0));
/*PMAC Reset*/
odm_write_1byte(dm, 0xB03,
odm_read_1byte(dm, 0xB03) & (~BIT(0)));
odm_write_1byte(dm, 0xB03, odm_read_1byte(dm, 0xB03) | BIT(0));
/*CCK Reset*/
if (odm_read_1byte(dm, 0x80B) & BIT(4)) {
odm_write_1byte(dm, 0x80B,
odm_read_1byte(dm, 0x80B) & (~BIT(4)));
odm_write_1byte(dm, 0x80B,
odm_read_1byte(dm, 0x80B) | BIT(4));
}
sval = pwdb_A;
if ((sval < 0 && sval >= -27) && (valid_cnt < VALID_CNT)) {
valid_cnt++;
sum += sval;
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "Valid sval = %d\n",
sval);
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "Sum of sval = %d,\n",
sum);
if ((valid_cnt >= VALID_CNT) ||
(odm_get_progressing_time(dm, start) > max_time)) {
sum /= VALID_CNT;
ODM_RT_TRACE(dm, ODM_COMP_COMMON,
"After divided, sum = %d\n", sum);
break;
}
}
}
/*ADC backoff is 12dB,*/
/*Ptarget=0x1C-110=-82dBm*/
noise = sum + 12 + 0x1C - 110;
/*Offset*/
noise = noise - 3;
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "noise = %d\n", noise);
dm->noise_level.noise_all = (s16)noise;
/* step 4. Recover the Dig*/
if (is_pause_dig)
odm_pause_dig(dm, PHYDM_RESUME, PHYDM_PAUSE_LEVEL_1, igi_value);
func_end = odm_get_progressing_time(dm, func_start);
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "%s() <==\n", __func__);
return dm->noise_level.noise_all;
}
s16 odm_inband_noise_monitor(void *dm_void, u8 is_pause_dig, u8 igi_value,
u32 max_time)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
if (dm->support_ic_type & ODM_IC_11AC_SERIES)
return odm_inband_noise_monitor_ac_series(dm, is_pause_dig,
igi_value, max_time);
else
return odm_inband_noise_monitor_n_series(dm, is_pause_dig,
igi_value, max_time);
}

View File

@ -0,0 +1,46 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODMNOISEMONITOR_H__
#define __ODMNOISEMONITOR_H__
#define ODM_MAX_CHANNEL_NUM 38 /* 14+24 */
struct noise_level {
u8 value[MAX_RF_PATH];
s8 sval[MAX_RF_PATH];
s32 sum[MAX_RF_PATH];
u8 valid[MAX_RF_PATH];
u8 valid_cnt[MAX_RF_PATH];
};
struct odm_noise_monitor {
s8 noise[MAX_RF_PATH];
s16 noise_all;
};
s16 odm_inband_noise_monitor(void *dm_void, u8 is_pause_dig, u8 igi_value,
u32 max_time);
#endif

View File

@ -0,0 +1,644 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*============================================================ */
/* include files */
/*============================================================ */
#include "mp_precomp.h"
#include "phydm_precomp.h"
/* ************************************************************
* Global var
* *************************************************************/
u32 ofdm_swing_table[OFDM_TABLE_SIZE] = {
0x7f8001fe, /* 0, +6.0dB */
0x788001e2, /* 1, +5.5dB */
0x71c001c7, /* 2, +5.0dB*/
0x6b8001ae, /* 3, +4.5dB*/
0x65400195, /* 4, +4.0dB*/
0x5fc0017f, /* 5, +3.5dB*/
0x5a400169, /* 6, +3.0dB*/
0x55400155, /* 7, +2.5dB*/
0x50800142, /* 8, +2.0dB*/
0x4c000130, /* 9, +1.5dB*/
0x47c0011f, /* 10, +1.0dB*/
0x43c0010f, /* 11, +0.5dB*/
0x40000100, /* 12, +0dB*/
0x3c8000f2, /* 13, -0.5dB*/
0x390000e4, /* 14, -1.0dB*/
0x35c000d7, /* 15, -1.5dB*/
0x32c000cb, /* 16, -2.0dB*/
0x300000c0, /* 17, -2.5dB*/
0x2d4000b5, /* 18, -3.0dB*/
0x2ac000ab, /* 19, -3.5dB*/
0x288000a2, /* 20, -4.0dB*/
0x26000098, /* 21, -4.5dB*/
0x24000090, /* 22, -5.0dB*/
0x22000088, /* 23, -5.5dB*/
0x20000080, /* 24, -6.0dB*/
0x1e400079, /* 25, -6.5dB*/
0x1c800072, /* 26, -7.0dB*/
0x1b00006c, /* 27. -7.5dB*/
0x19800066, /* 28, -8.0dB*/
0x18000060, /* 29, -8.5dB*/
0x16c0005b, /* 30, -9.0dB*/
0x15800056, /* 31, -9.5dB*/
0x14400051, /* 32, -10.0dB*/
0x1300004c, /* 33, -10.5dB*/
0x12000048, /* 34, -11.0dB*/
0x11000044, /* 35, -11.5dB*/
0x10000040, /* 36, -12.0dB*/
};
u8 cck_swing_table_ch1_ch13[CCK_TABLE_SIZE][8] = {
{0x36, 0x35, 0x2e, 0x25, 0x1c, 0x12, 0x09, 0x04}, /* 0, +0dB */
{0x33, 0x32, 0x2b, 0x23, 0x1a, 0x11, 0x08, 0x04}, /* 1, -0.5dB */
{0x30, 0x2f, 0x29, 0x21, 0x19, 0x10, 0x08, 0x03}, /* 2, -1.0dB*/
{0x2d, 0x2d, 0x27, 0x1f, 0x18, 0x0f, 0x08, 0x03}, /* 3, -1.5dB*/
{0x2b, 0x2a, 0x25, 0x1e, 0x16, 0x0e, 0x07, 0x03}, /* 4, -2.0dB */
{0x28, 0x28, 0x22, 0x1c, 0x15, 0x0d, 0x07, 0x03}, /* 5, -2.5dB*/
{0x26, 0x25, 0x21, 0x1b, 0x14, 0x0d, 0x06, 0x03}, /* 6, -3.0dB*/
{0x24, 0x23, 0x1f, 0x19, 0x13, 0x0c, 0x06, 0x03}, /* 7, -3.5dB*/
{0x22, 0x21, 0x1d, 0x18, 0x11, 0x0b, 0x06, 0x02}, /* 8, -4.0dB */
{0x20, 0x20, 0x1b, 0x16, 0x11, 0x08, 0x05, 0x02}, /* 9, -4.5dB*/
{0x1f, 0x1e, 0x1a, 0x15, 0x10, 0x0a, 0x05, 0x02}, /* 10, -5.0dB */
{0x1d, 0x1c, 0x18, 0x14, 0x0f, 0x0a, 0x05, 0x02}, /* 11, -5.5dB*/
{0x1b, 0x1a, 0x17, 0x13, 0x0e, 0x09, 0x04,
0x02}, /* 12, -6.0dB <== default */
{0x1a, 0x19, 0x16, 0x12, 0x0d, 0x09, 0x04, 0x02}, /* 13, -6.5dB*/
{0x18, 0x17, 0x15, 0x11, 0x0c, 0x08, 0x04, 0x02}, /* 14, -7.0dB */
{0x17, 0x16, 0x13, 0x10, 0x0c, 0x08, 0x04, 0x02}, /* 15, -7.5dB*/
{0x16, 0x15, 0x12, 0x0f, 0x0b, 0x07, 0x04, 0x01}, /* 16, -8.0dB */
{0x14, 0x14, 0x11, 0x0e, 0x0b, 0x07, 0x03, 0x02}, /* 17, -8.5dB*/
{0x13, 0x13, 0x10, 0x0d, 0x0a, 0x06, 0x03, 0x01}, /* 18, -9.0dB */
{0x12, 0x12, 0x0f, 0x0c, 0x09, 0x06, 0x03, 0x01}, /* 19, -9.5dB*/
{0x11, 0x11, 0x0f, 0x0c, 0x09, 0x06, 0x03, 0x01}, /* 20, -10.0dB*/
{0x10, 0x10, 0x0e, 0x0b, 0x08, 0x05, 0x03, 0x01}, /* 21, -10.5dB*/
{0x0f, 0x0f, 0x0d, 0x0b, 0x08, 0x05, 0x03, 0x01}, /* 22, -11.0dB*/
{0x0e, 0x0e, 0x0c, 0x0a, 0x08, 0x05, 0x02, 0x01}, /* 23, -11.5dB*/
{0x0d, 0x0d, 0x0c, 0x0a, 0x07, 0x05, 0x02, 0x01}, /* 24, -12.0dB*/
{0x0d, 0x0c, 0x0b, 0x09, 0x07, 0x04, 0x02, 0x01}, /* 25, -12.5dB*/
{0x0c, 0x0c, 0x0a, 0x09, 0x06, 0x04, 0x02, 0x01}, /* 26, -13.0dB*/
{0x0b, 0x0b, 0x0a, 0x08, 0x06, 0x04, 0x02, 0x01}, /* 27, -13.5dB*/
{0x0b, 0x0a, 0x09, 0x08, 0x06, 0x04, 0x02, 0x01}, /* 28, -14.0dB*/
{0x0a, 0x0a, 0x09, 0x07, 0x05, 0x03, 0x02, 0x01}, /* 29, -14.5dB*/
{0x0a, 0x09, 0x08, 0x07, 0x05, 0x03, 0x02, 0x01}, /* 30, -15.0dB*/
{0x09, 0x09, 0x08, 0x06, 0x05, 0x03, 0x01, 0x01}, /* 31, -15.5dB*/
{0x09, 0x08, 0x07, 0x06, 0x04, 0x03, 0x01, 0x01} /* 32, -16.0dB*/
};
u8 cck_swing_table_ch14[CCK_TABLE_SIZE][8] = {
{0x36, 0x35, 0x2e, 0x1b, 0x00, 0x00, 0x00, 0x00}, /* 0, +0dB */
{0x33, 0x32, 0x2b, 0x19, 0x00, 0x00, 0x00, 0x00}, /* 1, -0.5dB */
{0x30, 0x2f, 0x29, 0x18, 0x00, 0x00, 0x00, 0x00}, /* 2, -1.0dB */
{0x2d, 0x2d, 0x17, 0x17, 0x00, 0x00, 0x00, 0x00}, /* 3, -1.5dB*/
{0x2b, 0x2a, 0x25, 0x15, 0x00, 0x00, 0x00, 0x00}, /* 4, -2.0dB */
{0x28, 0x28, 0x24, 0x14, 0x00, 0x00, 0x00, 0x00}, /* 5, -2.5dB*/
{0x26, 0x25, 0x21, 0x13, 0x00, 0x00, 0x00, 0x00}, /* 6, -3.0dB */
{0x24, 0x23, 0x1f, 0x12, 0x00, 0x00, 0x00, 0x00}, /* 7, -3.5dB */
{0x22, 0x21, 0x1d, 0x11, 0x00, 0x00, 0x00, 0x00}, /* 8, -4.0dB */
{0x20, 0x20, 0x1b, 0x10, 0x00, 0x00, 0x00, 0x00}, /* 9, -4.5dB*/
{0x1f, 0x1e, 0x1a, 0x0f, 0x00, 0x00, 0x00, 0x00}, /* 10, -5.0dB */
{0x1d, 0x1c, 0x18, 0x0e, 0x00, 0x00, 0x00, 0x00}, /* 11, -5.5dB*/
{0x1b, 0x1a, 0x17, 0x0e, 0x00, 0x00, 0x00,
0x00}, /* 12, -6.0dB <== default*/
{0x1a, 0x19, 0x16, 0x0d, 0x00, 0x00, 0x00, 0x00}, /* 13, -6.5dB */
{0x18, 0x17, 0x15, 0x0c, 0x00, 0x00, 0x00, 0x00}, /* 14, -7.0dB */
{0x17, 0x16, 0x13, 0x0b, 0x00, 0x00, 0x00, 0x00}, /* 15, -7.5dB*/
{0x16, 0x15, 0x12, 0x0b, 0x00, 0x00, 0x00, 0x00}, /* 16, -8.0dB */
{0x14, 0x14, 0x11, 0x0a, 0x00, 0x00, 0x00, 0x00}, /* 17, -8.5dB*/
{0x13, 0x13, 0x10, 0x0a, 0x00, 0x00, 0x00, 0x00}, /* 18, -9.0dB */
{0x12, 0x12, 0x0f, 0x09, 0x00, 0x00, 0x00, 0x00}, /* 19, -9.5dB*/
{0x11, 0x11, 0x0f, 0x09, 0x00, 0x00, 0x00, 0x00}, /* 20, -10.0dB*/
{0x10, 0x10, 0x0e, 0x08, 0x00, 0x00, 0x00, 0x00}, /* 21, -10.5dB*/
{0x0f, 0x0f, 0x0d, 0x08, 0x00, 0x00, 0x00, 0x00}, /* 22, -11.0dB*/
{0x0e, 0x0e, 0x0c, 0x07, 0x00, 0x00, 0x00, 0x00}, /* 23, -11.5dB*/
{0x0d, 0x0d, 0x0c, 0x07, 0x00, 0x00, 0x00, 0x00}, /* 24, -12.0dB*/
{0x0d, 0x0c, 0x0b, 0x06, 0x00, 0x00, 0x00, 0x00}, /* 25, -12.5dB*/
{0x0c, 0x0c, 0x0a, 0x06, 0x00, 0x00, 0x00, 0x00}, /* 26, -13.0dB*/
{0x0b, 0x0b, 0x0a, 0x06, 0x00, 0x00, 0x00, 0x00}, /* 27, -13.5dB*/
{0x0b, 0x0a, 0x09, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 28, -14.0dB*/
{0x0a, 0x0a, 0x09, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 29, -14.5dB*/
{0x0a, 0x09, 0x08, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 30, -15.0dB*/
{0x09, 0x09, 0x08, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 31, -15.5dB*/
{0x09, 0x08, 0x07, 0x04, 0x00, 0x00, 0x00, 0x00} /* 32, -16.0dB*/
};
u32 ofdm_swing_table_new[OFDM_TABLE_SIZE] = {
0x0b40002d, /* 0, -15.0dB */
0x0c000030, /* 1, -14.5dB*/
0x0cc00033, /* 2, -14.0dB*/
0x0d800036, /* 3, -13.5dB*/
0x0e400039, /* 4, -13.0dB */
0x0f00003c, /* 5, -12.5dB*/
0x10000040, /* 6, -12.0dB*/
0x11000044, /* 7, -11.5dB*/
0x12000048, /* 8, -11.0dB*/
0x1300004c, /* 9, -10.5dB*/
0x14400051, /* 10, -10.0dB*/
0x15800056, /* 11, -9.5dB*/
0x16c0005b, /* 12, -9.0dB*/
0x18000060, /* 13, -8.5dB*/
0x19800066, /* 14, -8.0dB*/
0x1b00006c, /* 15, -7.5dB*/
0x1c800072, /* 16, -7.0dB*/
0x1e400079, /* 17, -6.5dB*/
0x20000080, /* 18, -6.0dB*/
0x22000088, /* 19, -5.5dB*/
0x24000090, /* 20, -5.0dB*/
0x26000098, /* 21, -4.5dB*/
0x288000a2, /* 22, -4.0dB*/
0x2ac000ab, /* 23, -3.5dB*/
0x2d4000b5, /* 24, -3.0dB*/
0x300000c0, /* 25, -2.5dB*/
0x32c000cb, /* 26, -2.0dB*/
0x35c000d7, /* 27, -1.5dB*/
0x390000e4, /* 28, -1.0dB*/
0x3c8000f2, /* 29, -0.5dB*/
0x40000100, /* 30, +0dB*/
0x43c0010f, /* 31, +0.5dB*/
0x47c0011f, /* 32, +1.0dB*/
0x4c000130, /* 33, +1.5dB*/
0x50800142, /* 34, +2.0dB*/
0x55400155, /* 35, +2.5dB*/
0x5a400169, /* 36, +3.0dB*/
0x5fc0017f, /* 37, +3.5dB*/
0x65400195, /* 38, +4.0dB*/
0x6b8001ae, /* 39, +4.5dB*/
0x71c001c7, /* 40, +5.0dB*/
0x788001e2, /* 41, +5.5dB*/
0x7f8001fe /* 42, +6.0dB*/
};
u8 cck_swing_table_ch1_ch14_88f[CCK_TABLE_SIZE_88F][16] = {
{0x44, 0x42, 0x3C, 0x33, 0x28, 0x1C, 0x13, 0x0B, 0x05, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-16dB*/
{0x48, 0x46, 0x3F, 0x36, 0x2A, 0x1E, 0x14, 0x0B, 0x05, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-15.5dB*/
{0x4D, 0x4A, 0x43, 0x39, 0x2C, 0x20, 0x15, 0x0C, 0x06, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-15dB*/
{0x51, 0x4F, 0x47, 0x3C, 0x2F, 0x22, 0x16, 0x0D, 0x06, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-14.5dB*/
{0x56, 0x53, 0x4B, 0x40, 0x32, 0x24, 0x17, 0x0E, 0x06, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-14dB*/
{0x5B, 0x58, 0x50, 0x43, 0x35, 0x26, 0x19, 0x0E, 0x07, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-13.5dB*/
{0x60, 0x5D, 0x54, 0x47, 0x38, 0x28, 0x1A, 0x0F, 0x07, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-13dB*/
{0x66, 0x63, 0x59, 0x4C, 0x3B, 0x2B, 0x1C, 0x10, 0x08, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-12.5dB*/
{0x6C, 0x69, 0x5F, 0x50, 0x3F, 0x2D, 0x1E, 0x11, 0x08, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-12dB*/
{0x73, 0x6F, 0x64, 0x55, 0x42, 0x30, 0x1F, 0x12, 0x08, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-11.5dB*/
{0x79, 0x76, 0x6A, 0x5A, 0x46, 0x33, 0x21, 0x13, 0x09, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-11dB*/
{0x81, 0x7C, 0x71, 0x5F, 0x4A, 0x36, 0x23, 0x14, 0x0A, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-10.5dB*/
{0x88, 0x84, 0x77, 0x65, 0x4F, 0x39, 0x25, 0x15, 0x0A, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-10dB*/
{0x90, 0x8C, 0x7E, 0x6B, 0x54, 0x3C, 0x27, 0x17, 0x0B, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-9.5dB*/
{0x99, 0x94, 0x86, 0x71, 0x58, 0x40, 0x2A, 0x18, 0x0B, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-9dB*/
{0xA2, 0x9D, 0x8E, 0x78, 0x5E, 0x43, 0x2C, 0x19, 0x0C, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-8.5dB*/
{0xAC, 0xA6, 0x96, 0x7F, 0x63, 0x47, 0x2F, 0x1B, 0x0D, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-8dB*/
{0xB6, 0xB0, 0x9F, 0x87, 0x69, 0x4C, 0x32, 0x1D, 0x0D, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-7.5dB*/
{0xC1, 0xBA, 0xA8, 0x8F, 0x6F, 0x50, 0x35, 0x1E, 0x0E, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-7dB*/
{0xCC, 0xC5, 0xB2, 0x97, 0x76, 0x55, 0x38, 0x20, 0x0F, 0x05, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-6.5dB*/
{0xD8, 0xD1, 0xBD, 0xA0, 0x7D, 0x5A, 0x3B, 0x22, 0x10, 0x05, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00} /*-6dB*/
};
u8 cck_swing_table_ch1_ch13_88f[CCK_TABLE_SIZE_88F][16] = {
{0x44, 0x42, 0x3C, 0x33, 0x28, 0x1C, 0x13, 0x0B, 0x05, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-16dB*/
{0x48, 0x46, 0x3F, 0x36, 0x2A, 0x1E, 0x14, 0x0B, 0x05, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-15.5dB*/
{0x4D, 0x4A, 0x43, 0x39, 0x2C, 0x20, 0x15, 0x0C, 0x06, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-15dB*/
{0x51, 0x4F, 0x47, 0x3C, 0x2F, 0x22, 0x16, 0x0D, 0x06, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-14.5dB*/
{0x56, 0x53, 0x4B, 0x40, 0x32, 0x24, 0x17, 0x0E, 0x06, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-14dB*/
{0x5B, 0x58, 0x50, 0x43, 0x35, 0x26, 0x19, 0x0E, 0x07, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-13.5dB*/
{0x60, 0x5D, 0x54, 0x47, 0x38, 0x28, 0x1A, 0x0F, 0x07, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-13dB*/
{0x66, 0x63, 0x59, 0x4C, 0x3B, 0x2B, 0x1C, 0x10, 0x08, 0x02, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-12.5dB*/
{0x6C, 0x69, 0x5F, 0x50, 0x3F, 0x2D, 0x1E, 0x11, 0x08, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-12dB*/
{0x73, 0x6F, 0x64, 0x55, 0x42, 0x30, 0x1F, 0x12, 0x08, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-11.5dB*/
{0x79, 0x76, 0x6A, 0x5A, 0x46, 0x33, 0x21, 0x13, 0x09, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-11dB*/
{0x81, 0x7C, 0x71, 0x5F, 0x4A, 0x36, 0x23, 0x14, 0x0A, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-10.5dB*/
{0x88, 0x84, 0x77, 0x65, 0x4F, 0x39, 0x25, 0x15, 0x0A, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-10dB*/
{0x90, 0x8C, 0x7E, 0x6B, 0x54, 0x3C, 0x27, 0x17, 0x0B, 0x03, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-9.5dB*/
{0x99, 0x94, 0x86, 0x71, 0x58, 0x40, 0x2A, 0x18, 0x0B, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-9dB*/
{0xA2, 0x9D, 0x8E, 0x78, 0x5E, 0x43, 0x2C, 0x19, 0x0C, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-8.5dB*/
{0xAC, 0xA6, 0x96, 0x7F, 0x63, 0x47, 0x2F, 0x1B, 0x0D, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-8dB*/
{0xB6, 0xB0, 0x9F, 0x87, 0x69, 0x4C, 0x32, 0x1D, 0x0D, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-7.5dB*/
{0xC1, 0xBA, 0xA8, 0x8F, 0x6F, 0x50, 0x35, 0x1E, 0x0E, 0x04, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-7dB*/
{0xCC, 0xC5, 0xB2, 0x97, 0x76, 0x55, 0x38, 0x20, 0x0F, 0x05, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-6.5dB*/
{0xD8, 0xD1, 0xBD, 0xA0, 0x7D, 0x5A, 0x3B, 0x22, 0x10, 0x05, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00} /*-6dB*/
};
u8 cck_swing_table_ch14_88f[CCK_TABLE_SIZE_88F][16] = {
{0x44, 0x42, 0x3C, 0x28, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-16dB*/
{0x48, 0x46, 0x3F, 0x2A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-15.5dB*/
{0x4D, 0x4A, 0x43, 0x2C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-15dB*/
{0x51, 0x4F, 0x47, 0x2F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-14.5dB*/
{0x56, 0x53, 0x4B, 0x32, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-14dB*/
{0x5B, 0x58, 0x50, 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-13.5dB*/
{0x60, 0x5D, 0x54, 0x38, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-13dB*/
{0x66, 0x63, 0x59, 0x3B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-12.5dB*/
{0x6C, 0x69, 0x5F, 0x3F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-12dB*/
{0x73, 0x6F, 0x64, 0x42, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-11.5dB*/
{0x79, 0x76, 0x6A, 0x46, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-11dB*/
{0x81, 0x7C, 0x71, 0x4A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-10.5dB*/
{0x88, 0x84, 0x77, 0x4F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-10dB*/
{0x90, 0x8C, 0x7E, 0x54, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-9.5dB*/
{0x99, 0x94, 0x86, 0x58, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-9dB*/
{0xA2, 0x9D, 0x8E, 0x5E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-8.5dB*/
{0xAC, 0xA6, 0x96, 0x63, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-8dB*/
{0xB6, 0xB0, 0x9F, 0x69, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-7.5dB*/
{0xC1, 0xBA, 0xA8, 0x6F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-7dB*/
{0xCC, 0xC5, 0xB2, 0x76, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00}, /*-6.5dB*/
{0xD8, 0xD1, 0xBD, 0x7D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00} /*-6dB*/
};
u8 cck_swing_table_ch1_ch13_new[CCK_TABLE_SIZE][8] = {
{0x09, 0x08, 0x07, 0x06, 0x04, 0x03, 0x01, 0x01}, /* 0, -16.0dB*/
{0x09, 0x09, 0x08, 0x06, 0x05, 0x03, 0x01, 0x01}, /* 1, -15.5dB*/
{0x0a, 0x09, 0x08, 0x07, 0x05, 0x03, 0x02, 0x01}, /* 2, -15.0dB*/
{0x0a, 0x0a, 0x09, 0x07, 0x05, 0x03, 0x02, 0x01}, /* 3, -14.5dB*/
{0x0b, 0x0a, 0x09, 0x08, 0x06, 0x04, 0x02, 0x01}, /* 4, -14.0dB*/
{0x0b, 0x0b, 0x0a, 0x08, 0x06, 0x04, 0x02, 0x01}, /* 5, -13.5dB*/
{0x0c, 0x0c, 0x0a, 0x09, 0x06, 0x04, 0x02, 0x01}, /* 6, -13.0dB*/
{0x0d, 0x0c, 0x0b, 0x09, 0x07, 0x04, 0x02, 0x01}, /* 7, -12.5dB*/
{0x0d, 0x0d, 0x0c, 0x0a, 0x07, 0x05, 0x02, 0x01}, /* 8, -12.0dB*/
{0x0e, 0x0e, 0x0c, 0x0a, 0x08, 0x05, 0x02, 0x01}, /* 9, -11.5dB*/
{0x0f, 0x0f, 0x0d, 0x0b, 0x08, 0x05, 0x03, 0x01}, /* 10, -11.0dB*/
{0x10, 0x10, 0x0e, 0x0b, 0x08, 0x05, 0x03, 0x01}, /* 11, -10.5dB*/
{0x11, 0x11, 0x0f, 0x0c, 0x09, 0x06, 0x03, 0x01}, /* 12, -10.0dB*/
{0x12, 0x12, 0x0f, 0x0c, 0x09, 0x06, 0x03, 0x01}, /* 13, -9.5dB*/
{0x13, 0x13, 0x10, 0x0d, 0x0a, 0x06, 0x03, 0x01}, /* 14, -9.0dB */
{0x14, 0x14, 0x11, 0x0e, 0x0b, 0x07, 0x03, 0x02}, /* 15, -8.5dB*/
{0x16, 0x15, 0x12, 0x0f, 0x0b, 0x07, 0x04, 0x01}, /* 16, -8.0dB */
{0x17, 0x16, 0x13, 0x10, 0x0c, 0x08, 0x04, 0x02}, /* 17, -7.5dB*/
{0x18, 0x17, 0x15, 0x11, 0x0c, 0x08, 0x04, 0x02}, /* 18, -7.0dB */
{0x1a, 0x19, 0x16, 0x12, 0x0d, 0x09, 0x04, 0x02}, /* 19, -6.5dB*/
{0x1b, 0x1a, 0x17, 0x13, 0x0e, 0x09, 0x04, 0x02}, /*20, -6.0dB */
{0x1d, 0x1c, 0x18, 0x14, 0x0f, 0x0a, 0x05, 0x02}, /* 21, -5.5dB*/
{0x1f, 0x1e, 0x1a, 0x15, 0x10, 0x0a, 0x05, 0x02}, /* 22, -5.0dB */
{0x20, 0x20, 0x1b, 0x16, 0x11, 0x08, 0x05, 0x02}, /* 23, -4.5dB*/
{0x22, 0x21, 0x1d, 0x18, 0x11, 0x0b, 0x06, 0x02}, /* 24, -4.0dB */
{0x24, 0x23, 0x1f, 0x19, 0x13, 0x0c, 0x06, 0x03}, /* 25, -3.5dB*/
{0x26, 0x25, 0x21, 0x1b, 0x14, 0x0d, 0x06, 0x03}, /* 26, -3.0dB*/
{0x28, 0x28, 0x22, 0x1c, 0x15, 0x0d, 0x07, 0x03}, /* 27, -2.5dB*/
{0x2b, 0x2a, 0x25, 0x1e, 0x16, 0x0e, 0x07, 0x03}, /* 28, -2.0dB */
{0x2d, 0x2d, 0x27, 0x1f, 0x18, 0x0f, 0x08, 0x03}, /* 29, -1.5dB*/
{0x30, 0x2f, 0x29, 0x21, 0x19, 0x10, 0x08, 0x03}, /* 30, -1.0dB*/
{0x33, 0x32, 0x2b, 0x23, 0x1a, 0x11, 0x08, 0x04}, /* 31, -0.5dB*/
{0x36, 0x35, 0x2e, 0x25, 0x1c, 0x12, 0x09, 0x04} /* 32, +0dB*/
};
u8 cck_swing_table_ch14_new[CCK_TABLE_SIZE][8] = {
{0x09, 0x08, 0x07, 0x04, 0x00, 0x00, 0x00, 0x00}, /* 0, -16.0dB*/
{0x09, 0x09, 0x08, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 1, -15.5dB*/
{0x0a, 0x09, 0x08, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 2, -15.0dB*/
{0x0a, 0x0a, 0x09, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 3, -14.5dB*/
{0x0b, 0x0a, 0x09, 0x05, 0x00, 0x00, 0x00, 0x00}, /* 4, -14.0dB*/
{0x0b, 0x0b, 0x0a, 0x06, 0x00, 0x00, 0x00, 0x00}, /*5, -13.5dB*/
{0x0c, 0x0c, 0x0a, 0x06, 0x00, 0x00, 0x00, 0x00}, /* 6, -13.0dB*/
{0x0d, 0x0c, 0x0b, 0x06, 0x00, 0x00, 0x00, 0x00}, /* 7, -12.5dB*/
{0x0d, 0x0d, 0x0c, 0x07, 0x00, 0x00, 0x00, 0x00}, /* 8, -12.0dB*/
{0x0e, 0x0e, 0x0c, 0x07, 0x00, 0x00, 0x00, 0x00}, /* 9, -11.5dB*/
{0x0f, 0x0f, 0x0d, 0x08, 0x00, 0x00, 0x00, 0x00}, /* 10, -11.0dB*/
{0x10, 0x10, 0x0e, 0x08, 0x00, 0x00, 0x00, 0x00}, /*11, -10.5dB*/
{0x11, 0x11, 0x0f, 0x09, 0x00, 0x00, 0x00, 0x00}, /* 12, -10.0dB*/
{0x12, 0x12, 0x0f, 0x09, 0x00, 0x00, 0x00, 0x00}, /* 13, -9.5dB*/
{0x13, 0x13, 0x10, 0x0a, 0x00, 0x00, 0x00, 0x00}, /*14, -9.0dB */
{0x14, 0x14, 0x11, 0x0a, 0x00, 0x00, 0x00, 0x00}, /* 15, -8.5dB*/
{0x16, 0x15, 0x12, 0x0b, 0x00, 0x00, 0x00, 0x00}, /* 16, -8.0dB */
{0x17, 0x16, 0x13, 0x0b, 0x00, 0x00, 0x00, 0x00}, /* 17, -7.5dB*/
{0x18, 0x17, 0x15, 0x0c, 0x00, 0x00, 0x00, 0x00}, /* 18, -7.0dB */
{0x1a, 0x19, 0x16, 0x0d, 0x00, 0x00, 0x00, 0x00}, /* 19, -6.5dB */
{0x1b, 0x1a, 0x17, 0x0e, 0x00, 0x00, 0x00, 0x00}, /* 20, -6.0dB */
{0x1d, 0x1c, 0x18, 0x0e, 0x00, 0x00, 0x00, 0x00}, /* 21, -5.5dB*/
{0x1f, 0x1e, 0x1a, 0x0f, 0x00, 0x00, 0x00, 0x00}, /* 22, -5.0dB */
{0x20, 0x20, 0x1b, 0x10, 0x00, 0x00, 0x00, 0x00}, /*23, -4.5dB*/
{0x22, 0x21, 0x1d, 0x11, 0x00, 0x00, 0x00, 0x00}, /* 24, -4.0dB */
{0x24, 0x23, 0x1f, 0x12, 0x00, 0x00, 0x00, 0x00}, /* 25, -3.5dB */
{0x26, 0x25, 0x21, 0x13, 0x00, 0x00, 0x00, 0x00}, /* 26, -3.0dB */
{0x28, 0x28, 0x24, 0x14, 0x00, 0x00, 0x00, 0x00}, /*27, -2.5dB*/
{0x2b, 0x2a, 0x25, 0x15, 0x00, 0x00, 0x00, 0x00}, /* 28, -2.0dB */
{0x2d, 0x2d, 0x17, 0x17, 0x00, 0x00, 0x00, 0x00}, /*29, -1.5dB*/
{0x30, 0x2f, 0x29, 0x18, 0x00, 0x00, 0x00, 0x00}, /* 30, -1.0dB */
{0x33, 0x32, 0x2b, 0x19, 0x00, 0x00, 0x00, 0x00}, /* 31, -0.5dB */
{0x36, 0x35, 0x2e, 0x1b, 0x00, 0x00, 0x00, 0x00} /* 32, +0dB */
};
u32 cck_swing_table_ch1_ch14_8723d[CCK_TABLE_SIZE_8723D] = {
0x0CD, /*0 , -20dB*/
0x0D9, 0x0E6, 0x0F3, 0x102, 0x111, 0x121, 0x132, 0x144, 0x158, 0x16C,
0x182, 0x198, 0x1B1, 0x1CA, 0x1E5, 0x202, 0x221, 0x241, 0x263, 0x287,
0x2AE, 0x2D6, 0x301, 0x32F, 0x35F, 0x392, 0x3C9, 0x402, 0x43F, 0x47F,
0x4C3, 0x50C, 0x558, 0x5A9, 0x5FF, 0x65A, 0x6BA, 0x720, 0x78C, 0x7FF,
};
/* JJ ADD 20161014 */
u32 cck_swing_table_ch1_ch14_8710b[CCK_TABLE_SIZE_8710B] = {
0x0CD, /*0 , -20dB*/
0x0D9, 0x0E6, 0x0F3, 0x102, 0x111, 0x121, 0x132, 0x144, 0x158, 0x16C,
0x182, 0x198, 0x1B1, 0x1CA, 0x1E5, 0x202, 0x221, 0x241, 0x263, 0x287,
0x2AE, 0x2D6, 0x301, 0x32F, 0x35F, 0x392, 0x3C9, 0x402, 0x43F, 0x47F,
0x4C3, 0x50C, 0x558, 0x5A9, 0x5FF, 0x65A, 0x6BA, 0x720, 0x78C, 0x7FF,
};
u32 tx_scaling_table_jaguar[TXSCALE_TABLE_SIZE] = {
0x081, /* 0, -12.0dB*/
0x088, /* 1, -11.5dB*/
0x090, /* 2, -11.0dB*/
0x099, /* 3, -10.5dB*/
0x0A2, /* 4, -10.0dB*/
0x0AC, /* 5, -9.5dB*/
0x0B6, /* 6, -9.0dB*/
0x0C0, /*7, -8.5dB*/
0x0CC, /* 8, -8.0dB*/
0x0D8, /* 9, -7.5dB*/
0x0E5, /* 10, -7.0dB*/
0x0F2, /* 11, -6.5dB*/
0x101, /* 12, -6.0dB*/
0x110, /* 13, -5.5dB*/
0x120, /* 14, -5.0dB*/
0x131, /* 15, -4.5dB*/
0x143, /* 16, -4.0dB*/
0x156, /* 17, -3.5dB*/
0x16A, /* 18, -3.0dB*/
0x180, /* 19, -2.5dB*/
0x197, /* 20, -2.0dB*/
0x1AF, /* 21, -1.5dB*/
0x1C8, /* 22, -1.0dB*/
0x1E3, /* 23, -0.5dB*/
0x200, /* 24, +0 dB*/
0x21E, /* 25, +0.5dB*/
0x23E, /* 26, +1.0dB*/
0x261, /* 27, +1.5dB*/
0x285, /* 28, +2.0dB*/
0x2AB, /* 29, +2.5dB*/
0x2D3, /*30, +3.0dB*/
0x2FE, /* 31, +3.5dB*/
0x32B, /* 32, +4.0dB*/
0x35C, /* 33, +4.5dB*/
0x38E, /* 34, +5.0dB*/
0x3C4, /* 35, +5.5dB*/
0x3FE /* 36, +6.0dB */
};
void odm_txpowertracking_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
odm_txpowertracking_thermal_meter_init(dm);
}
static u8 get_swing_index(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u8 i = 0;
u32 bb_swing;
u32 swing_table_size;
u32 *swing_table;
if (dm->support_ic_type == ODM_RTL8188E ||
dm->support_ic_type == ODM_RTL8723B ||
dm->support_ic_type == ODM_RTL8192E ||
dm->support_ic_type == ODM_RTL8188F ||
dm->support_ic_type == ODM_RTL8703B) {
bb_swing = odm_get_bb_reg(dm, REG_OFDM_0_XA_TX_IQ_IMBALANCE,
0xFFC00000);
swing_table = ofdm_swing_table_new;
swing_table_size = OFDM_TABLE_SIZE;
} else {
{
bb_swing = 0;
swing_table = ofdm_swing_table;
swing_table_size = OFDM_TABLE_SIZE;
}
}
for (i = 0; i < swing_table_size; ++i) {
u32 table_value = swing_table[i];
if (table_value >= 0x100000)
table_value >>= 22;
if (bb_swing == table_value)
break;
}
return i;
}
void odm_txpowertracking_thermal_meter_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u8 default_swing_index = get_swing_index(dm);
u8 p = 0;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
struct rtl_efuse *rtlefu = rtl_efuse(rtlpriv);
cali_info->is_txpowertracking = true;
cali_info->tx_powercount = 0;
cali_info->is_txpowertracking_init = false;
if (!dm->mp_mode)
cali_info->txpowertrack_control = true;
else
cali_info->txpowertrack_control = false;
if (!dm->mp_mode)
cali_info->txpowertrack_control = true;
ODM_RT_TRACE(dm, ODM_COMP_CALIBRATION, "dm txpowertrack_control = %d\n",
cali_info->txpowertrack_control);
/* dm->rf_calibrate_info.txpowertrack_control = true; */
cali_info->thermal_value = rtlefu->eeprom_thermalmeter;
cali_info->thermal_value_iqk = rtlefu->eeprom_thermalmeter;
cali_info->thermal_value_lck = rtlefu->eeprom_thermalmeter;
if (!cali_info->default_bb_swing_index_flag) {
/*The index of "0 dB" in SwingTable.*/
if (dm->support_ic_type == ODM_RTL8188E ||
dm->support_ic_type == ODM_RTL8723B ||
dm->support_ic_type == ODM_RTL8192E ||
dm->support_ic_type == ODM_RTL8703B) {
cali_info->default_ofdm_index =
(default_swing_index >= OFDM_TABLE_SIZE) ?
30 :
default_swing_index;
cali_info->default_cck_index = 20;
} else if (dm->support_ic_type ==
ODM_RTL8188F) { /*add by Mingzhi.Guo 2015-03-23*/
cali_info->default_ofdm_index = 28; /*OFDM: -1dB*/
cali_info->default_cck_index = 20; /*CCK:-6dB*/
} else if (dm->support_ic_type ==
ODM_RTL8723D) { /*add by zhaohe 2015-10-27*/
cali_info->default_ofdm_index = 28; /*OFDM: -1dB*/
cali_info->default_cck_index = 28; /*CCK: -6dB*/
} else if (dm->support_ic_type ==
ODM_RTL8710B) { /* JJ ADD 20161014 */
cali_info->default_ofdm_index = 28; /*OFDM: -1dB*/
cali_info->default_cck_index = 28; /*CCK: -6dB*/
} else {
cali_info->default_ofdm_index =
(default_swing_index >= TXSCALE_TABLE_SIZE) ?
24 :
default_swing_index;
cali_info->default_cck_index = 24;
}
cali_info->default_bb_swing_index_flag = true;
}
cali_info->bb_swing_idx_cck_base = cali_info->default_cck_index;
cali_info->CCK_index = cali_info->default_cck_index;
for (p = ODM_RF_PATH_A; p < MAX_RF_PATH; ++p) {
cali_info->bb_swing_idx_ofdm_base[p] =
cali_info->default_ofdm_index;
cali_info->OFDM_index[p] = cali_info->default_ofdm_index;
cali_info->delta_power_index[p] = 0;
cali_info->delta_power_index_last[p] = 0;
cali_info->power_index_offset[p] = 0;
}
cali_info->modify_tx_agc_value_ofdm = 0;
cali_info->modify_tx_agc_value_cck = 0;
}
void odm_txpowertracking_check(void *dm_void)
{
/* 2011/09/29 MH In HW integration first stage, we provide 4 different
* handle to operate at the same time.
* In the stage2/3, we need to prive universal interface and merge all
* HW dynamic mechanism.
*/
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
switch (dm->support_platform) {
case ODM_WIN:
odm_txpowertracking_check_mp(dm);
break;
case ODM_CE:
odm_txpowertracking_check_ce(dm);
break;
case ODM_AP:
odm_txpowertracking_check_ap(dm);
break;
default:
break;
}
}
void odm_txpowertracking_check_ce(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
void *adapter = dm->adapter;
if (!(dm->support_ability & ODM_RF_TX_PWR_TRACK))
return;
if (!dm->rf_calibrate_info.tm_trigger) {
if (IS_HARDWARE_TYPE_8188E(adapter) ||
IS_HARDWARE_TYPE_8188F(adapter) ||
IS_HARDWARE_TYPE_8192E(adapter) ||
IS_HARDWARE_TYPE_8723B(adapter) ||
IS_HARDWARE_TYPE_JAGUAR(adapter) ||
IS_HARDWARE_TYPE_8814A(adapter) ||
IS_HARDWARE_TYPE_8703B(adapter) ||
IS_HARDWARE_TYPE_8723D(adapter) ||
IS_HARDWARE_TYPE_8822B(adapter) ||
IS_HARDWARE_TYPE_8821C(adapter) ||
(dm->support_ic_type == ODM_RTL8710B)) /* JJ ADD 20161014 */
odm_set_rf_reg(dm, ODM_RF_PATH_A, RF_T_METER_NEW,
(BIT(17) | BIT(16)), 0x03);
else
odm_set_rf_reg(dm, ODM_RF_PATH_A, RF_T_METER_OLD,
RFREGOFFSETMASK, 0x60);
dm->rf_calibrate_info.tm_trigger = 1;
return;
}
odm_txpowertracking_callback_thermal_meter(dm);
dm->rf_calibrate_info.tm_trigger = 0;
}
void odm_txpowertracking_check_mp(void *dm_void) {}
void odm_txpowertracking_check_ap(void *dm_void) {}

View File

@ -0,0 +1,293 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMPOWERTRACKING_H__
#define __PHYDMPOWERTRACKING_H__
#define POWRTRACKING_VERSION "1.1"
#define DPK_DELTA_MAPPING_NUM 13
#define index_mapping_HP_NUM 15
#define OFDM_TABLE_SIZE 43
#define CCK_TABLE_SIZE 33
#define CCK_TABLE_SIZE_88F 21
#define TXSCALE_TABLE_SIZE 37
#define CCK_TABLE_SIZE_8723D 41
/* JJ ADD 20161014 */
#define CCK_TABLE_SIZE_8710B 41
#define TXPWR_TRACK_TABLE_SIZE 30
#define DELTA_SWINGIDX_SIZE 30
#define DELTA_SWINTSSI_SIZE 61
#define BAND_NUM 4
#define AVG_THERMAL_NUM 8
#define HP_THERMAL_NUM 8
#define IQK_MAC_REG_NUM 4
#define IQK_ADDA_REG_NUM 16
#define IQK_BB_REG_NUM_MAX 10
#define IQK_BB_REG_NUM 9
#define iqk_matrix_reg_num 8
extern u32 ofdm_swing_table[OFDM_TABLE_SIZE];
extern u8 cck_swing_table_ch1_ch13[CCK_TABLE_SIZE][8];
extern u8 cck_swing_table_ch14[CCK_TABLE_SIZE][8];
extern u32 ofdm_swing_table_new[OFDM_TABLE_SIZE];
extern u8 cck_swing_table_ch1_ch13_new[CCK_TABLE_SIZE][8];
extern u8 cck_swing_table_ch14_new[CCK_TABLE_SIZE][8];
extern u8 cck_swing_table_ch1_ch14_88f[CCK_TABLE_SIZE_88F][16];
extern u8 cck_swing_table_ch1_ch13_88f[CCK_TABLE_SIZE_88F][16];
extern u8 cck_swing_table_ch14_88f[CCK_TABLE_SIZE_88F][16];
extern u32 cck_swing_table_ch1_ch14_8723d[CCK_TABLE_SIZE_8723D];
/* JJ ADD 20161014 */
extern u32 cck_swing_table_ch1_ch14_8710b[CCK_TABLE_SIZE_8710B];
extern u32 tx_scaling_table_jaguar[TXSCALE_TABLE_SIZE];
/* <20121018, Kordan> In case fail to read TxPowerTrack.txt,
* we use the table of 88E as the default table.
*/
#define dm_check_txpowertracking odm_txpowertracking_check
struct iqk_matrix_regs_setting {
bool is_iqk_done;
s32 value[3][iqk_matrix_reg_num];
bool is_bw_iqk_result_saved[3];
};
struct dm_rf_calibration_struct {
/* for tx power tracking */
u32 rega24; /* for TempCCK */
s32 rege94;
s32 rege9c;
s32 regeb4;
s32 regebc;
u8 tx_powercount;
bool is_txpowertracking_init;
bool is_txpowertracking;
/* for mp mode, turn off txpwrtracking as default */
u8 txpowertrack_control;
u8 tm_trigger;
u8 internal_pa_5g[2]; /* pathA / pathB */
u8 thermal_meter
[2]; /* thermal_meter, index 0 for RFIC0, and 1 for RFIC1 */
u8 thermal_value;
u8 thermal_value_lck;
u8 thermal_value_iqk;
s8 thermal_value_delta; /* delta of thermal_value and efuse thermal */
u8 thermal_value_dpk;
u8 thermal_value_avg[AVG_THERMAL_NUM];
u8 thermal_value_avg_index;
u8 thermal_value_rx_gain;
u8 thermal_value_crystal;
u8 thermal_value_dpk_store;
u8 thermal_value_dpk_track;
bool txpowertracking_in_progress;
bool is_reloadtxpowerindex;
u8 is_rf_pi_enable;
u32 txpowertracking_callback_cnt; /* cosa add for debug */
/* ---------------------- Tx power Tracking ------------------------- */
u8 is_cck_in_ch14;
u8 CCK_index;
u8 OFDM_index[MAX_RF_PATH];
s8 power_index_offset[MAX_RF_PATH];
s8 delta_power_index[MAX_RF_PATH];
s8 delta_power_index_last[MAX_RF_PATH];
bool is_tx_power_changed;
s8 xtal_offset;
s8 xtal_offset_last;
u8 thermal_value_hp[HP_THERMAL_NUM];
u8 thermal_value_hp_index;
struct iqk_matrix_regs_setting
iqk_matrix_reg_setting[IQK_MATRIX_SETTINGS_NUM];
u8 delta_lck;
s8 bb_swing_diff_2g, bb_swing_diff_5g; /* Unit: dB */
u8 delta_swing_table_idx_2g_cck_a_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2g_cck_a_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2g_cck_b_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2g_cck_b_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2g_cck_c_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2g_cck_c_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2g_cck_d_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2g_cck_d_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2ga_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2ga_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2gb_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2gb_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2gc_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2gc_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2gd_p[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2gd_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5ga_p[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5ga_n[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5gb_p[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5gb_n[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5gc_p[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5gc_n[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5gd_p[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_5gd_n[BAND_NUM][DELTA_SWINGIDX_SIZE];
u8 delta_swing_tssi_table_2g_cck_a[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_2g_cck_b[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_2g_cck_c[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_2g_cck_d[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_2ga[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_2gb[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_2gc[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_2gd[DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_5ga[BAND_NUM][DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_5gb[BAND_NUM][DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_5gc[BAND_NUM][DELTA_SWINTSSI_SIZE];
u8 delta_swing_tssi_table_5gd[BAND_NUM][DELTA_SWINTSSI_SIZE];
s8 delta_swing_table_xtal_p[DELTA_SWINGIDX_SIZE];
s8 delta_swing_table_xtal_n[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2ga_p_8188e[DELTA_SWINGIDX_SIZE];
u8 delta_swing_table_idx_2ga_n_8188e[DELTA_SWINGIDX_SIZE];
u8 bb_swing_idx_ofdm[MAX_RF_PATH];
u8 bb_swing_idx_ofdm_current;
u8 bb_swing_idx_ofdm_base[MAX_RF_PATH];
bool default_bb_swing_index_flag;
bool bb_swing_flag_ofdm;
u8 bb_swing_idx_cck;
u8 bb_swing_idx_cck_current;
u8 bb_swing_idx_cck_base;
u8 default_ofdm_index;
u8 default_cck_index;
bool bb_swing_flag_cck;
s8 absolute_ofdm_swing_idx[MAX_RF_PATH];
s8 remnant_ofdm_swing_idx[MAX_RF_PATH];
s8 absolute_cck_swing_idx[MAX_RF_PATH];
s8 remnant_cck_swing_idx;
s8 modify_tx_agc_value; /*Remnat compensate value at tx_agc */
bool modify_tx_agc_flag_path_a;
bool modify_tx_agc_flag_path_b;
bool modify_tx_agc_flag_path_c;
bool modify_tx_agc_flag_path_d;
bool modify_tx_agc_flag_path_a_cck;
s8 kfree_offset[MAX_RF_PATH];
/* ------------------------------------------------------------------ */
/* for IQK */
u32 regc04;
u32 reg874;
u32 regc08;
u32 regb68;
u32 regb6c;
u32 reg870;
u32 reg860;
u32 reg864;
bool is_iqk_initialized;
bool is_lck_in_progress;
bool is_antenna_detected;
bool is_need_iqk;
bool is_iqk_in_progress;
bool is_iqk_pa_off;
u8 delta_iqk;
u32 ADDA_backup[IQK_ADDA_REG_NUM];
u32 IQK_MAC_backup[IQK_MAC_REG_NUM];
u32 IQK_BB_backup_recover[9];
/* { {S1: 0xc94, 0xc80, 0xc4c} , {S0: 0xc9c, 0xc88, 0xc4c}} */
u32 IQK_BB_backup[IQK_BB_REG_NUM];
u32 tx_iqc_8723b[2][3][2];
/* { {S1: 0xc14, 0xca0} , {S0: 0xc14, 0xca0}} */
u32 rx_iqc_8723b[2][2][2];
/* { {S1: 0xc94, 0xc80, 0xc4c} , {S0: 0xc9c, 0xc88, 0xc4c}}*/
u32 tx_iqc_8703b[3][2];
/* { {S1: 0xc14, 0xca0} , {S0: 0xc14, 0xca0}}*/
u32 rx_iqc_8703b[2][2];
/* { {S1: 0xc94, 0xc80, 0xc4c} , {S0: 0xc9c, 0xc88, 0xc4c}}*/
u32 tx_iqc_8723d[2][3][2];
/* { {S1: 0xc14, 0xca0} , {S0: 0xc14, 0xca0}}*/
u32 rx_iqc_8723d[2][2][2];
/* JJ ADD 20161014 */
/* { {S1: 0xc94, 0xc80, 0xc4c} , {S0: 0xc9c, 0xc88, 0xc4c}}*/
u32 tx_iqc_8710b[2][3][2];
/* { {S1: 0xc14, 0xca0} , {S0: 0xc14, 0xca0}}*/
u32 rx_iqc_8710b[2][2][2];
u8 iqk_step;
u8 kcount;
u8 retry_count[4][2]; /* [4]: path ABCD, [2] TXK, RXK */
bool is_mp_mode;
/* <James> IQK time measurement */
u64 iqk_start_time;
u64 iqk_progressing_time;
u64 iqk_total_progressing_time;
u32 lok_result;
/* for APK */
u32 ap_koutput[2][2]; /* path A/B; output1_1a/output1_2a */
u8 is_ap_kdone;
u8 is_apk_thermal_meter_ignore;
/* DPK */
bool is_dpk_fail;
u8 is_dp_done;
u8 is_dp_path_aok;
u8 is_dp_path_bok;
u32 tx_lok[2];
u32 dpk_tx_agc;
s32 dpk_gain;
u32 dpk_thermal[4];
s8 modify_tx_agc_value_ofdm;
s8 modify_tx_agc_value_cck;
/*Add by Yuchen for Kfree Phydm*/
u8 reg_rf_kfree_enable; /*for registry*/
u8 rf_kfree_enable; /*for efuse enable check*/
};
void odm_txpowertracking_check(void *dm_void);
void odm_txpowertracking_init(void *dm_void);
void odm_txpowertracking_check_ap(void *dm_void);
void odm_txpowertracking_thermal_meter_init(void *dm_void);
void odm_txpowertracking_init(void *dm_void);
void odm_txpowertracking_check_mp(void *dm_void);
void odm_txpowertracking_check_ce(void *dm_void);
#endif

View File

@ -0,0 +1,613 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMPREDEFINE_H__
#define __PHYDMPREDEFINE_H__
/* 1 ============================================================
* 1 Definition
* 1 ============================================================
*/
#define PHYDM_CODE_BASE "PHYDM_TRUNK"
#define PHYDM_RELEASE_DATE "00000000"
/* Max path of IC */
#define MAX_PATH_NUM_8188E 1
#define MAX_PATH_NUM_8192E 2
#define MAX_PATH_NUM_8723B 1
#define MAX_PATH_NUM_8812A 2
#define MAX_PATH_NUM_8821A 1
#define MAX_PATH_NUM_8814A 4
#define MAX_PATH_NUM_8822B 2
#define MAX_PATH_NUM_8821B 2
#define MAX_PATH_NUM_8703B 1
#define MAX_PATH_NUM_8188F 1
#define MAX_PATH_NUM_8723D 1
#define MAX_PATH_NUM_8197F 2
#define MAX_PATH_NUM_8821C 1
/* JJ ADD 20161014 */
#define MAX_PATH_NUM_8710B 1
/* Max RF path */
#define ODM_RF_PATH_MAX 2
#define ODM_RF_PATH_MAX_JAGUAR 4
/*Bit define path*/
#define PHYDM_A BIT(0)
#define PHYDM_B BIT(1)
#define PHYDM_C BIT(2)
#define PHYDM_D BIT(3)
#define PHYDM_AB (BIT(0) | BIT(1))
#define PHYDM_AC (BIT(0) | BIT(2))
#define PHYDM_AD (BIT(0) | BIT(3))
#define PHYDM_BC (BIT(1) | BIT(2))
#define PHYDM_BD (BIT(1) | BIT(3))
#define PHYDM_CD (BIT(2) | BIT(3))
#define PHYDM_ABC (BIT(0) | BIT(1) | BIT(2))
#define PHYDM_ABD (BIT(0) | BIT(1) | BIT(3))
#define PHYDM_ACD (BIT(0) | BIT(2) | BIT(3))
#define PHYDM_BCD (BIT(1) | BIT(2) | BIT(3))
#define PHYDM_ABCD (BIT(0) | BIT(1) | BIT(2) | BIT(3))
/* number of entry */
/* defined in wifi.h (32+1) */
#define ODM_ASSOCIATE_ENTRY_NUM ASSOCIATE_ENTRY_NUM
#define RX_SMOOTH_FACTOR 20
/* -----MGN rate--------------------------------- */
enum ODM_MGN_RATE {
ODM_MGN_1M = 0x02,
ODM_MGN_2M = 0x04,
ODM_MGN_5_5M = 0x0B,
ODM_MGN_6M = 0x0C,
ODM_MGN_9M = 0x12,
ODM_MGN_11M = 0x16,
ODM_MGN_12M = 0x18,
ODM_MGN_18M = 0x24,
ODM_MGN_24M = 0x30,
ODM_MGN_36M = 0x48,
ODM_MGN_48M = 0x60,
ODM_MGN_54M = 0x6C,
ODM_MGN_MCS32 = 0x7F,
ODM_MGN_MCS0,
ODM_MGN_MCS1,
ODM_MGN_MCS2,
ODM_MGN_MCS3,
ODM_MGN_MCS4,
ODM_MGN_MCS5,
ODM_MGN_MCS6,
ODM_MGN_MCS7,
ODM_MGN_MCS8,
ODM_MGN_MCS9,
ODM_MGN_MCS10,
ODM_MGN_MCS11,
ODM_MGN_MCS12,
ODM_MGN_MCS13,
ODM_MGN_MCS14,
ODM_MGN_MCS15,
ODM_MGN_MCS16,
ODM_MGN_MCS17,
ODM_MGN_MCS18,
ODM_MGN_MCS19,
ODM_MGN_MCS20,
ODM_MGN_MCS21,
ODM_MGN_MCS22,
ODM_MGN_MCS23,
ODM_MGN_MCS24,
ODM_MGN_MCS25,
ODM_MGN_MCS26,
ODM_MGN_MCS27,
ODM_MGN_MCS28,
ODM_MGN_MCS29,
ODM_MGN_MCS30,
ODM_MGN_MCS31,
ODM_MGN_VHT1SS_MCS0,
ODM_MGN_VHT1SS_MCS1,
ODM_MGN_VHT1SS_MCS2,
ODM_MGN_VHT1SS_MCS3,
ODM_MGN_VHT1SS_MCS4,
ODM_MGN_VHT1SS_MCS5,
ODM_MGN_VHT1SS_MCS6,
ODM_MGN_VHT1SS_MCS7,
ODM_MGN_VHT1SS_MCS8,
ODM_MGN_VHT1SS_MCS9,
ODM_MGN_VHT2SS_MCS0,
ODM_MGN_VHT2SS_MCS1,
ODM_MGN_VHT2SS_MCS2,
ODM_MGN_VHT2SS_MCS3,
ODM_MGN_VHT2SS_MCS4,
ODM_MGN_VHT2SS_MCS5,
ODM_MGN_VHT2SS_MCS6,
ODM_MGN_VHT2SS_MCS7,
ODM_MGN_VHT2SS_MCS8,
ODM_MGN_VHT2SS_MCS9,
ODM_MGN_VHT3SS_MCS0,
ODM_MGN_VHT3SS_MCS1,
ODM_MGN_VHT3SS_MCS2,
ODM_MGN_VHT3SS_MCS3,
ODM_MGN_VHT3SS_MCS4,
ODM_MGN_VHT3SS_MCS5,
ODM_MGN_VHT3SS_MCS6,
ODM_MGN_VHT3SS_MCS7,
ODM_MGN_VHT3SS_MCS8,
ODM_MGN_VHT3SS_MCS9,
ODM_MGN_VHT4SS_MCS0,
ODM_MGN_VHT4SS_MCS1,
ODM_MGN_VHT4SS_MCS2,
ODM_MGN_VHT4SS_MCS3,
ODM_MGN_VHT4SS_MCS4,
ODM_MGN_VHT4SS_MCS5,
ODM_MGN_VHT4SS_MCS6,
ODM_MGN_VHT4SS_MCS7,
ODM_MGN_VHT4SS_MCS8,
ODM_MGN_VHT4SS_MCS9,
ODM_MGN_UNKNOWN
};
#define ODM_MGN_MCS0_SG 0xc0
#define ODM_MGN_MCS1_SG 0xc1
#define ODM_MGN_MCS2_SG 0xc2
#define ODM_MGN_MCS3_SG 0xc3
#define ODM_MGN_MCS4_SG 0xc4
#define ODM_MGN_MCS5_SG 0xc5
#define ODM_MGN_MCS6_SG 0xc6
#define ODM_MGN_MCS7_SG 0xc7
#define ODM_MGN_MCS8_SG 0xc8
#define ODM_MGN_MCS9_SG 0xc9
#define ODM_MGN_MCS10_SG 0xca
#define ODM_MGN_MCS11_SG 0xcb
#define ODM_MGN_MCS12_SG 0xcc
#define ODM_MGN_MCS13_SG 0xcd
#define ODM_MGN_MCS14_SG 0xce
#define ODM_MGN_MCS15_SG 0xcf
/* -----DESC rate--------------------------------- */
#define ODM_RATEMCS15_SG 0x1c
#define ODM_RATEMCS32 0x20
/* CCK Rates, TxHT = 0 */
#define ODM_RATE1M 0x00
#define ODM_RATE2M 0x01
#define ODM_RATE5_5M 0x02
#define ODM_RATE11M 0x03
/* OFDM Rates, TxHT = 0 */
#define ODM_RATE6M 0x04
#define ODM_RATE9M 0x05
#define ODM_RATE12M 0x06
#define ODM_RATE18M 0x07
#define ODM_RATE24M 0x08
#define ODM_RATE36M 0x09
#define ODM_RATE48M 0x0A
#define ODM_RATE54M 0x0B
/* MCS Rates, TxHT = 1 */
#define ODM_RATEMCS0 0x0C
#define ODM_RATEMCS1 0x0D
#define ODM_RATEMCS2 0x0E
#define ODM_RATEMCS3 0x0F
#define ODM_RATEMCS4 0x10
#define ODM_RATEMCS5 0x11
#define ODM_RATEMCS6 0x12
#define ODM_RATEMCS7 0x13
#define ODM_RATEMCS8 0x14
#define ODM_RATEMCS9 0x15
#define ODM_RATEMCS10 0x16
#define ODM_RATEMCS11 0x17
#define ODM_RATEMCS12 0x18
#define ODM_RATEMCS13 0x19
#define ODM_RATEMCS14 0x1A
#define ODM_RATEMCS15 0x1B
#define ODM_RATEMCS16 0x1C
#define ODM_RATEMCS17 0x1D
#define ODM_RATEMCS18 0x1E
#define ODM_RATEMCS19 0x1F
#define ODM_RATEMCS20 0x20
#define ODM_RATEMCS21 0x21
#define ODM_RATEMCS22 0x22
#define ODM_RATEMCS23 0x23
#define ODM_RATEMCS24 0x24
#define ODM_RATEMCS25 0x25
#define ODM_RATEMCS26 0x26
#define ODM_RATEMCS27 0x27
#define ODM_RATEMCS28 0x28
#define ODM_RATEMCS29 0x29
#define ODM_RATEMCS30 0x2A
#define ODM_RATEMCS31 0x2B
#define ODM_RATEVHTSS1MCS0 0x2C
#define ODM_RATEVHTSS1MCS1 0x2D
#define ODM_RATEVHTSS1MCS2 0x2E
#define ODM_RATEVHTSS1MCS3 0x2F
#define ODM_RATEVHTSS1MCS4 0x30
#define ODM_RATEVHTSS1MCS5 0x31
#define ODM_RATEVHTSS1MCS6 0x32
#define ODM_RATEVHTSS1MCS7 0x33
#define ODM_RATEVHTSS1MCS8 0x34
#define ODM_RATEVHTSS1MCS9 0x35
#define ODM_RATEVHTSS2MCS0 0x36
#define ODM_RATEVHTSS2MCS1 0x37
#define ODM_RATEVHTSS2MCS2 0x38
#define ODM_RATEVHTSS2MCS3 0x39
#define ODM_RATEVHTSS2MCS4 0x3A
#define ODM_RATEVHTSS2MCS5 0x3B
#define ODM_RATEVHTSS2MCS6 0x3C
#define ODM_RATEVHTSS2MCS7 0x3D
#define ODM_RATEVHTSS2MCS8 0x3E
#define ODM_RATEVHTSS2MCS9 0x3F
#define ODM_RATEVHTSS3MCS0 0x40
#define ODM_RATEVHTSS3MCS1 0x41
#define ODM_RATEVHTSS3MCS2 0x42
#define ODM_RATEVHTSS3MCS3 0x43
#define ODM_RATEVHTSS3MCS4 0x44
#define ODM_RATEVHTSS3MCS5 0x45
#define ODM_RATEVHTSS3MCS6 0x46
#define ODM_RATEVHTSS3MCS7 0x47
#define ODM_RATEVHTSS3MCS8 0x48
#define ODM_RATEVHTSS3MCS9 0x49
#define ODM_RATEVHTSS4MCS0 0x4A
#define ODM_RATEVHTSS4MCS1 0x4B
#define ODM_RATEVHTSS4MCS2 0x4C
#define ODM_RATEVHTSS4MCS3 0x4D
#define ODM_RATEVHTSS4MCS4 0x4E
#define ODM_RATEVHTSS4MCS5 0x4F
#define ODM_RATEVHTSS4MCS6 0x50
#define ODM_RATEVHTSS4MCS7 0x51
#define ODM_RATEVHTSS4MCS8 0x52
#define ODM_RATEVHTSS4MCS9 0x53
#define ODM_NUM_RATE_IDX (ODM_RATEVHTSS4MCS9 + 1)
/* 1 ============================================================
* 1 enumeration
* 1 ============================================================
*/
/* ODM_CMNINFO_INTERFACE */
enum odm_interface {
ODM_ITRF_PCIE = 0x1,
ODM_ITRF_USB = 0x2,
ODM_ITRF_SDIO = 0x4,
ODM_ITRF_ALL = 0x7,
};
/* ODM_CMNINFO_IC_TYPE */
enum odm_ic_type {
ODM_RTL8188E = BIT(0),
ODM_RTL8812 = BIT(1),
ODM_RTL8821 = BIT(2),
ODM_RTL8192E = BIT(3),
ODM_RTL8723B = BIT(4),
ODM_RTL8814A = BIT(5),
ODM_RTL8881A = BIT(6),
ODM_RTL8822B = BIT(7),
ODM_RTL8703B = BIT(8),
ODM_RTL8195A = BIT(9),
ODM_RTL8188F = BIT(10),
ODM_RTL8723D = BIT(11),
ODM_RTL8197F = BIT(12),
ODM_RTL8821C = BIT(13),
ODM_RTL8814B = BIT(14),
ODM_RTL8198F = BIT(15),
/* JJ ADD 20161014 */
ODM_RTL8710B = BIT(16),
};
/* JJ ADD 20161014 */
#define ODM_IC_1SS \
(ODM_RTL8188E | ODM_RTL8188F | ODM_RTL8723B | ODM_RTL8703B | \
ODM_RTL8723D | ODM_RTL8881A | ODM_RTL8821 | ODM_RTL8821C | \
ODM_RTL8195A | ODM_RTL8710B)
#define ODM_IC_2SS (ODM_RTL8192E | ODM_RTL8197F | ODM_RTL8812 | ODM_RTL8822B)
#define ODM_IC_3SS (ODM_RTL8814A)
#define ODM_IC_4SS (ODM_RTL8814B | ODM_RTL8198F)
/* JJ ADD 20161014 */
#define ODM_IC_11N_SERIES \
(ODM_RTL8188E | ODM_RTL8192E | ODM_RTL8723B | ODM_RTL8703B | \
ODM_RTL8188F | ODM_RTL8723D | ODM_RTL8197F | ODM_RTL8710B)
#define ODM_IC_11AC_SERIES \
(ODM_RTL8812 | ODM_RTL8821 | ODM_RTL8814A | ODM_RTL8881A | \
ODM_RTL8822B | ODM_RTL8821C)
#define ODM_IC_11AC_1_SERIES (ODM_RTL8812 | ODM_RTL8821 | ODM_RTL8881A)
#define ODM_IC_11AC_2_SERIES (ODM_RTL8814A | ODM_RTL8822B | ODM_RTL8821C)
#define ODM_IC_TXBF_SUPPORT \
(ODM_RTL8192E | ODM_RTL8812 | ODM_RTL8821 | ODM_RTL8814A | \
ODM_RTL8881A | ODM_RTL8822B | ODM_RTL8197F | ODM_RTL8821C)
#define ODM_IC_11N_GAIN_IDX_EDCCA \
(ODM_RTL8195A | ODM_RTL8703B | ODM_RTL8188F | ODM_RTL8723D | \
ODM_RTL8197F | ODM_RTL8710B)
#define ODM_IC_11AC_GAIN_IDX_EDCCA (ODM_RTL8814A | ODM_RTL8822B | ODM_RTL8821C)
#define ODM_IC_PHY_STATUE_NEW_TYPE \
(ODM_RTL8197F | ODM_RTL8822B | ODM_RTL8723D | ODM_RTL8821C | \
ODM_RTL8710B)
#define PHYDM_IC_8051_SERIES \
(ODM_RTL8881A | ODM_RTL8812 | ODM_RTL8821 | ODM_RTL8188E | \
ODM_RTL8192E | ODM_RTL8723B | ODM_RTL8703B | ODM_RTL8188F)
#define PHYDM_IC_3081_SERIES \
(ODM_RTL8814A | ODM_RTL8822B | ODM_RTL8197F | ODM_RTL8821C)
#define PHYDM_IC_SUPPORT_LA_MODE \
(ODM_RTL8814A | ODM_RTL8822B | ODM_RTL8197F | ODM_RTL8821C)
/* JJ ADD 20161014 */
/* ODM_CMNINFO_CUT_VER */
enum odm_cut_version {
ODM_CUT_A = 0,
ODM_CUT_B = 1,
ODM_CUT_C = 2,
ODM_CUT_D = 3,
ODM_CUT_E = 4,
ODM_CUT_F = 5,
ODM_CUT_I = 8,
ODM_CUT_J = 9,
ODM_CUT_K = 10,
ODM_CUT_TEST = 15,
};
/* ODM_CMNINFO_FAB_VER */
enum odm_fab {
ODM_TSMC = 0,
ODM_UMC = 1,
};
/* ODM_CMNINFO_RF_TYPE
*
* For example 1T2R (A+AB = BIT(0)|BIT(4)|BIT(5))
*/
enum odm_rf_path {
ODM_RF_A = BIT(0),
ODM_RF_B = BIT(1),
ODM_RF_C = BIT(2),
ODM_RF_D = BIT(3),
};
enum odm_rf_tx_num {
ODM_1T = 1,
ODM_2T = 2,
ODM_3T = 3,
ODM_4T = 4,
};
enum odm_rf_type {
ODM_1T1R,
ODM_1T2R,
ODM_2T2R,
ODM_2T2R_GREEN,
ODM_2T3R,
ODM_2T4R,
ODM_3T3R,
ODM_3T4R,
ODM_4T4R,
ODM_XTXR
};
enum odm_mac_phy_mode {
ODM_SMSP = 0,
ODM_DMSP = 1,
ODM_DMDP = 2,
};
enum odm_bt_coexist {
ODM_BT_BUSY = 1,
ODM_BT_ON = 2,
ODM_BT_OFF = 3,
ODM_BT_NONE = 4,
};
/* ODM_CMNINFO_OP_MODE */
enum odm_operation_mode {
ODM_NO_LINK = BIT(0),
ODM_LINK = BIT(1),
ODM_SCAN = BIT(2),
ODM_POWERSAVE = BIT(3),
ODM_AP_MODE = BIT(4),
ODM_CLIENT_MODE = BIT(5),
ODM_AD_HOC = BIT(6),
ODM_WIFI_DIRECT = BIT(7),
ODM_WIFI_DISPLAY = BIT(8),
};
/* ODM_CMNINFO_WM_MODE */
enum odm_wireless_mode {
ODM_WM_UNKNOWN = 0x0,
ODM_WM_B = BIT(0),
ODM_WM_G = BIT(1),
ODM_WM_A = BIT(2),
ODM_WM_N24G = BIT(3),
ODM_WM_N5G = BIT(4),
ODM_WM_AUTO = BIT(5),
ODM_WM_AC = BIT(6),
};
/* ODM_CMNINFO_BAND */
enum odm_band_type {
ODM_BAND_2_4G = 0,
ODM_BAND_5G,
ODM_BAND_ON_BOTH,
ODM_BANDMAX
};
/* ODM_CMNINFO_SEC_CHNL_OFFSET */
enum phydm_sec_chnl_offset {
PHYDM_DONT_CARE = 0,
PHYDM_BELOW = 1,
PHYDM_ABOVE = 2
};
/* ODM_CMNINFO_SEC_MODE */
enum odm_security {
ODM_SEC_OPEN = 0,
ODM_SEC_WEP40 = 1,
ODM_SEC_TKIP = 2,
ODM_SEC_RESERVE = 3,
ODM_SEC_AESCCMP = 4,
ODM_SEC_WEP104 = 5,
ODM_WEP_WPA_MIXED = 6, /* WEP + WPA */
ODM_SEC_SMS4 = 7,
};
/* ODM_CMNINFO_BW */
enum odm_bw {
ODM_BW20M = 0,
ODM_BW40M = 1,
ODM_BW80M = 2,
ODM_BW160M = 3,
ODM_BW5M = 4,
ODM_BW10M = 5,
ODM_BW_MAX = 6
};
/* ODM_CMNINFO_CHNL */
/* ODM_CMNINFO_BOARD_TYPE */
enum odm_board_type {
ODM_BOARD_DEFAULT = 0, /* The DEFAULT case. */
ODM_BOARD_MINICARD = BIT(0), /* 0 = non-mini card, 1= mini card. */
ODM_BOARD_SLIM = BIT(1), /* 0 = non-slim card, 1 = slim card */
ODM_BOARD_BT = BIT(2), /* 0 = without BT card, 1 = with BT */
ODM_BOARD_EXT_PA =
BIT(3), /* 0 = no 2G ext-PA, 1 = existing 2G ext-PA */
ODM_BOARD_EXT_LNA =
BIT(4), /* 0 = no 2G ext-LNA, 1 = existing 2G ext-LNA */
ODM_BOARD_EXT_TRSW =
BIT(5), /* 0 = no ext-TRSW, 1 = existing ext-TRSW */
ODM_BOARD_EXT_PA_5G =
BIT(6), /* 0 = no 5G ext-PA, 1 = existing 5G ext-PA */
ODM_BOARD_EXT_LNA_5G =
BIT(7), /* 0 = no 5G ext-LNA, 1 = existing 5G ext-LNA */
};
enum odm_package_type {
ODM_PACKAGE_DEFAULT = 0,
ODM_PACKAGE_QFN68 = BIT(0),
ODM_PACKAGE_TFBGA90 = BIT(1),
ODM_PACKAGE_TFBGA79 = BIT(2),
};
enum odm_type_gpa {
TYPE_GPA0 = 0x0000,
TYPE_GPA1 = 0x0055,
TYPE_GPA2 = 0x00AA,
TYPE_GPA3 = 0x00FF,
TYPE_GPA4 = 0x5500,
TYPE_GPA5 = 0x5555,
TYPE_GPA6 = 0x55AA,
TYPE_GPA7 = 0x55FF,
TYPE_GPA8 = 0xAA00,
TYPE_GPA9 = 0xAA55,
TYPE_GPA10 = 0xAAAA,
TYPE_GPA11 = 0xAAFF,
TYPE_GPA12 = 0xFF00,
TYPE_GPA13 = 0xFF55,
TYPE_GPA14 = 0xFFAA,
TYPE_GPA15 = 0xFFFF,
};
enum odm_type_apa {
TYPE_APA0 = 0x0000,
TYPE_APA1 = 0x0055,
TYPE_APA2 = 0x00AA,
TYPE_APA3 = 0x00FF,
TYPE_APA4 = 0x5500,
TYPE_APA5 = 0x5555,
TYPE_APA6 = 0x55AA,
TYPE_APA7 = 0x55FF,
TYPE_APA8 = 0xAA00,
TYPE_APA9 = 0xAA55,
TYPE_APA10 = 0xAAAA,
TYPE_APA11 = 0xAAFF,
TYPE_APA12 = 0xFF00,
TYPE_APA13 = 0xFF55,
TYPE_APA14 = 0xFFAA,
TYPE_APA15 = 0xFFFF,
};
enum odm_type_glna {
TYPE_GLNA0 = 0x0000,
TYPE_GLNA1 = 0x0055,
TYPE_GLNA2 = 0x00AA,
TYPE_GLNA3 = 0x00FF,
TYPE_GLNA4 = 0x5500,
TYPE_GLNA5 = 0x5555,
TYPE_GLNA6 = 0x55AA,
TYPE_GLNA7 = 0x55FF,
TYPE_GLNA8 = 0xAA00,
TYPE_GLNA9 = 0xAA55,
TYPE_GLNA10 = 0xAAAA,
TYPE_GLNA11 = 0xAAFF,
TYPE_GLNA12 = 0xFF00,
TYPE_GLNA13 = 0xFF55,
TYPE_GLNA14 = 0xFFAA,
TYPE_GLNA15 = 0xFFFF,
};
enum odm_type_alna {
TYPE_ALNA0 = 0x0000,
TYPE_ALNA1 = 0x0055,
TYPE_ALNA2 = 0x00AA,
TYPE_ALNA3 = 0x00FF,
TYPE_ALNA4 = 0x5500,
TYPE_ALNA5 = 0x5555,
TYPE_ALNA6 = 0x55AA,
TYPE_ALNA7 = 0x55FF,
TYPE_ALNA8 = 0xAA00,
TYPE_ALNA9 = 0xAA55,
TYPE_ALNA10 = 0xAAAA,
TYPE_ALNA11 = 0xAAFF,
TYPE_ALNA12 = 0xFF00,
TYPE_ALNA13 = 0xFF55,
TYPE_ALNA14 = 0xFFAA,
TYPE_ALNA15 = 0xFFFF,
};
enum odm_rf_radio_path {
ODM_RF_PATH_A = 0, /* Radio path A */
ODM_RF_PATH_B = 1, /* Radio path B */
ODM_RF_PATH_C = 2, /* Radio path C */
ODM_RF_PATH_D = 3, /* Radio path D */
ODM_RF_PATH_AB,
ODM_RF_PATH_AC,
ODM_RF_PATH_AD,
ODM_RF_PATH_BC,
ODM_RF_PATH_BD,
ODM_RF_PATH_CD,
ODM_RF_PATH_ABC,
ODM_RF_PATH_ACD,
ODM_RF_PATH_BCD,
ODM_RF_PATH_ABCD,
/* ODM_RF_PATH_MAX, */ /* Max RF number 90 support */
};
enum odm_parameter_init {
ODM_PRE_SETTING = 0,
ODM_POST_SETTING = 1,
};
#endif

View File

@ -0,0 +1,85 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODM_PRECOMP_H__
#define __ODM_PRECOMP_H__
#include "phydm_types.h"
/* 2 Config Flags and Structs - defined by each ODM type */
#include "../wifi.h"
#include "rtl_phydm.h"
/* 2 OutSrc Header Files */
#include "phydm.h"
#include "phydm_hwconfig.h"
#include "phydm_debug.h"
#include "phydm_regdefine11ac.h"
#include "phydm_regdefine11n.h"
#include "phydm_interface.h"
#include "phydm_reg.h"
#include "phydm_adc_sampling.h"
/* JJ ADD 20161014 */
#include "../halmac/halmac_reg2.h"
#define LDPC_HT_ENABLE_RX BIT(0)
#define LDPC_HT_ENABLE_TX BIT(1)
#define LDPC_HT_TEST_TX_ENABLE BIT(2)
#define LDPC_HT_CAP_TX BIT(3)
#define STBC_HT_ENABLE_RX BIT(0)
#define STBC_HT_ENABLE_TX BIT(1)
#define STBC_HT_TEST_TX_ENABLE BIT(2)
#define STBC_HT_CAP_TX BIT(3)
#define LDPC_VHT_ENABLE_RX BIT(0)
#define LDPC_VHT_ENABLE_TX BIT(1)
#define LDPC_VHT_TEST_TX_ENABLE BIT(2)
#define LDPC_VHT_CAP_TX BIT(3)
#define STBC_VHT_ENABLE_RX BIT(0)
#define STBC_VHT_ENABLE_TX BIT(1)
#define STBC_VHT_TEST_TX_ENABLE BIT(2)
#define STBC_VHT_CAP_TX BIT(3)
#include "rtl8822b/halhwimg8822b_mac.h"
#include "rtl8822b/halhwimg8822b_rf.h"
#include "rtl8822b/halhwimg8822b_bb.h"
#include "rtl8822b/phydm_regconfig8822b.h"
#include "rtl8822b/halphyrf_8822b.h"
#include "rtl8822b/phydm_rtl8822b.h"
#include "rtl8822b/phydm_hal_api8822b.h"
#include "rtl8822b/version_rtl8822b.h"
#include "../halmac/halmac_reg_8822b.h"
/* JJ ADD 20161014 */
#endif /* __ODM_PRECOMP_H__ */

View File

@ -0,0 +1,422 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*============================================================
* include files
*============================================================
*/
#include "mp_precomp.h"
#include "phydm_precomp.h"
u32 phydm_get_psd_data(void *dm_void, u32 psd_tone_idx, u32 igi)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct psd_info *dm_psd_table = &dm->dm_psd_table;
u32 psd_report = 0;
odm_set_bb_reg(dm, dm_psd_table->psd_reg, 0x3ff, psd_tone_idx);
odm_set_bb_reg(dm, dm_psd_table->psd_reg, BIT(22),
1); /*PSD trigger start*/
ODM_delay_us(10);
odm_set_bb_reg(dm, dm_psd_table->psd_reg, BIT(22),
0); /*PSD trigger stop*/
psd_report = odm_get_bb_reg(dm, dm_psd_table->psd_report_reg, 0xffff);
psd_report = odm_convert_to_db(psd_report) + igi;
return psd_report;
}
static u8 phydm_psd_stop_trx(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
u32 i;
u8 trx_idle_success = false;
u32 dbg_port_value = 0;
/*[Stop TRX]----------------------------------------------------------*/
if (!phydm_set_bb_dbg_port(dm, BB_DBGPORT_PRIORITY_3,
0x0)) /*set debug port to 0x0*/
return STOP_TRX_FAIL;
for (i = 0; i < 10000; i++) {
dbg_port_value = phydm_get_bb_dbg_port_value(dm);
if ((dbg_port_value & (BIT(17) | BIT(3))) ==
0) /* PHYTXON && CCA_all */ {
ODM_RT_TRACE(dm, ODM_COMP_API,
"PSD wait for ((%d)) times\n", i);
trx_idle_success = true;
break;
}
}
if (trx_idle_success) {
/*pause all TX queue*/
odm_set_bb_reg(dm, 0x520, 0xff0000, 0xff);
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
/*disable CCK block*/
odm_set_bb_reg(dm, 0x808, BIT(28), 0);
/*disable OFDM RX CCA*/
odm_set_bb_reg(dm, 0x838, BIT(1), 1);
} else {
/*TBD*/
/* disable whole CCK block */
odm_set_bb_reg(dm, 0x800, BIT(24), 0);
/*[ Set IQK Matrix = 0 ] equivalent to [ Turn off CCA]*/
odm_set_bb_reg(dm, 0xC14, MASKDWORD, 0x0);
}
} else {
return STOP_TRX_FAIL;
}
phydm_release_bb_dbg_port(dm);
return STOP_TRX_SUCCESS;
}
static u8 psd_result_cali_tone_8821[7] = {21, 28, 33, 93, 98, 105, 127};
static u8 psd_result_cali_val_8821[7] = {67, 69, 71, 72, 71, 69, 67};
void phydm_psd(void *dm_void, u32 igi, u16 start_point, u16 stop_point)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct psd_info *dm_psd_table = &dm->dm_psd_table;
u32 i = 0, mod_tone_idx;
u32 t = 0;
u16 fft_max_half_bw;
u32 psd_igi_a_reg;
u32 psd_igi_b_reg;
u16 psd_fc_channel = dm_psd_table->psd_fc_channel;
u8 ag_rf_mode_reg = 0;
u8 rf_reg18_9_8 = 0;
u32 psd_result_tmp = 0;
u8 psd_result = 0;
u8 psd_result_cali_tone[7] = {0};
u8 psd_result_cali_val[7] = {0};
u8 noise_table_idx = 0;
if (dm->support_ic_type == ODM_RTL8821) {
odm_move_memory(dm, psd_result_cali_tone,
psd_result_cali_tone_8821, 7);
odm_move_memory(dm, psd_result_cali_val,
psd_result_cali_val_8821, 7);
}
dm_psd_table->psd_in_progress = 1;
/*[Stop DIG]*/
dm->support_ability &= ~(ODM_BB_DIG);
dm->support_ability &= ~(ODM_BB_FA_CNT);
ODM_RT_TRACE(dm, ODM_COMP_API, "PSD Start =>\n");
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
psd_igi_a_reg = 0xc50;
psd_igi_b_reg = 0xe50;
} else {
psd_igi_a_reg = 0xc50;
psd_igi_b_reg = 0xc58;
}
/*[back up IGI]*/
dm_psd_table->initial_gain_backup =
odm_get_bb_reg(dm, psd_igi_a_reg, 0xff);
odm_set_bb_reg(dm, psd_igi_a_reg, 0xff,
0x6e); /*IGI target at 0dBm & make it can't CCA*/
odm_set_bb_reg(dm, psd_igi_b_reg, 0xff,
0x6e); /*IGI target at 0dBm & make it can't CCA*/
ODM_delay_us(10);
if (phydm_psd_stop_trx(dm) == STOP_TRX_FAIL) {
ODM_RT_TRACE(dm, ODM_COMP_API, "STOP_TRX_FAIL\n");
return;
}
/*[Set IGI]*/
odm_set_bb_reg(dm, psd_igi_a_reg, 0xff, igi);
odm_set_bb_reg(dm, psd_igi_b_reg, 0xff, igi);
/*[Backup RF Reg]*/
dm_psd_table->rf_0x18_bkp =
odm_get_rf_reg(dm, ODM_RF_PATH_A, 0x18, RFREGOFFSETMASK);
if (psd_fc_channel > 14) {
rf_reg18_9_8 = 1;
if (psd_fc_channel >= 36 && psd_fc_channel <= 64)
ag_rf_mode_reg = 0x1;
else if (psd_fc_channel >= 100 && psd_fc_channel <= 140)
ag_rf_mode_reg = 0x3;
else if (psd_fc_channel > 140)
ag_rf_mode_reg = 0x5;
}
/* Set RF fc*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x18, 0xff, psd_fc_channel);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x18, 0x300, rf_reg18_9_8);
/*2b'11: 20MHz, 2b'10: 40MHz, 2b'01: 80MHz */
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x18, 0xc00,
dm_psd_table->psd_bw_rf_reg);
/* Set RF ag fc mode*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x18, 0xf0000, ag_rf_mode_reg);
ODM_RT_TRACE(dm, ODM_COMP_API, "0xc50=((0x%x))\n",
odm_get_bb_reg(dm, 0xc50, MASKDWORD));
ODM_RT_TRACE(dm, ODM_COMP_API, "RF0x18=((0x%x))\n",
odm_get_rf_reg(dm, ODM_RF_PATH_A, 0x18, RFREGOFFSETMASK));
/*[Stop 3-wires]*/
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, 0xc00, 0xf, 0x4); /* hardware 3-wire off */
odm_set_bb_reg(dm, 0xe00, 0xf, 0x4); /* hardware 3-wire off */
} else {
odm_set_bb_reg(dm, 0x88c, 0xf00000,
0xf); /* 3 wire Disable 88c[23:20]=0xf */
}
ODM_delay_us(10);
if (stop_point > (dm_psd_table->fft_smp_point - 1))
stop_point = (dm_psd_table->fft_smp_point - 1);
if (start_point > (dm_psd_table->fft_smp_point - 1))
start_point = (dm_psd_table->fft_smp_point - 1);
if (start_point > stop_point)
stop_point = start_point;
if (stop_point > 127) /* limit of psd_result[128] */
stop_point = 127;
for (i = start_point; i <= stop_point; i++) {
fft_max_half_bw = (dm_psd_table->fft_smp_point) >> 1;
if (i < fft_max_half_bw)
mod_tone_idx = i + fft_max_half_bw;
else
mod_tone_idx = i - fft_max_half_bw;
psd_result_tmp = 0;
for (t = 0; t < dm_psd_table->sw_avg_time; t++)
psd_result_tmp +=
phydm_get_psd_data(dm, mod_tone_idx, igi);
psd_result =
(u8)((psd_result_tmp / dm_psd_table->sw_avg_time)) -
dm_psd_table->psd_pwr_common_offset;
if (dm_psd_table->fft_smp_point == 128 &&
(dm_psd_table->noise_k_en)) {
if (i > psd_result_cali_tone[noise_table_idx])
noise_table_idx++;
if (noise_table_idx > 6)
noise_table_idx = 6;
if (psd_result >= psd_result_cali_val[noise_table_idx])
psd_result =
psd_result -
psd_result_cali_val[noise_table_idx];
else
psd_result = 0;
dm_psd_table->psd_result[i] = psd_result;
}
ODM_RT_TRACE(dm, ODM_COMP_API, "[%d] N_cali = %d, PSD = %d\n",
mod_tone_idx, psd_result_cali_val[noise_table_idx],
psd_result);
}
/*[Start 3-wires]*/
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, 0xc00, 0xf, 0x7); /* hardware 3-wire on */
odm_set_bb_reg(dm, 0xe00, 0xf, 0x7); /* hardware 3-wire on */
} else {
odm_set_bb_reg(dm, 0x88c, 0xf00000,
0x0); /* 3 wire enable 88c[23:20]=0x0 */
}
ODM_delay_us(10);
/*[Revert Reg]*/
odm_set_bb_reg(dm, 0x520, 0xff0000, 0x0); /*start all TX queue*/
odm_set_bb_reg(dm, 0x808, BIT(28), 1); /*enable CCK block*/
odm_set_bb_reg(dm, 0x838, BIT(1), 0); /*enable OFDM RX CCA*/
odm_set_bb_reg(dm, psd_igi_a_reg, 0xff,
dm_psd_table->initial_gain_backup);
odm_set_bb_reg(dm, psd_igi_b_reg, 0xff,
dm_psd_table->initial_gain_backup);
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x18, RFREGOFFSETMASK,
dm_psd_table->rf_0x18_bkp);
ODM_RT_TRACE(dm, ODM_COMP_API, "PSD finished\n\n");
dm->support_ability |= ODM_BB_DIG;
dm->support_ability |= ODM_BB_FA_CNT;
dm_psd_table->psd_in_progress = 0;
}
void phydm_psd_para_setting(void *dm_void, u8 sw_avg_time, u8 hw_avg_time,
u8 i_q_setting, u16 fft_smp_point, u8 ant_sel,
u8 psd_input, u8 channel, u8 noise_k_en)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct psd_info *dm_psd_table = &dm->dm_psd_table;
u8 fft_smp_point_idx = 0;
dm_psd_table->fft_smp_point = fft_smp_point;
if (sw_avg_time == 0)
sw_avg_time = 1;
dm_psd_table->sw_avg_time = sw_avg_time;
dm_psd_table->psd_fc_channel = channel;
dm_psd_table->noise_k_en = noise_k_en;
if (fft_smp_point == 128)
fft_smp_point_idx = 0;
else if (fft_smp_point == 256)
fft_smp_point_idx = 1;
else if (fft_smp_point == 512)
fft_smp_point_idx = 2;
else if (fft_smp_point == 1024)
fft_smp_point_idx = 3;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
odm_set_bb_reg(dm, 0x910, BIT(11) | BIT(10), i_q_setting);
odm_set_bb_reg(dm, 0x910, BIT(13) | BIT(12), hw_avg_time);
odm_set_bb_reg(dm, 0x910, BIT(15) | BIT(14), fft_smp_point_idx);
odm_set_bb_reg(dm, 0x910, BIT(17) | BIT(16), ant_sel);
odm_set_bb_reg(dm, 0x910, BIT(23), psd_input);
}
/*bw = (*dm->band_width); //ODM_BW20M */
/*channel = *(dm->channel);*/
}
void phydm_psd_init(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct psd_info *dm_psd_table = &dm->dm_psd_table;
ODM_RT_TRACE(dm, ODM_COMP_API, "PSD para init\n");
dm_psd_table->psd_in_progress = false;
if (dm->support_ic_type & ODM_IC_11AC_SERIES) {
dm_psd_table->psd_reg = 0x910;
dm_psd_table->psd_report_reg = 0xF44;
if (ODM_IC_11AC_2_SERIES)
dm_psd_table->psd_bw_rf_reg =
1; /*2b'11: 20MHz, 2b'10: 40MHz, 2b'01: 80MHz */
else
dm_psd_table->psd_bw_rf_reg =
2; /*2b'11: 20MHz, 2b'10: 40MHz, 2b'01: 80MHz */
} else {
dm_psd_table->psd_reg = 0x808;
dm_psd_table->psd_report_reg = 0x8B4;
dm_psd_table->psd_bw_rf_reg =
2; /*2b'11: 20MHz, 2b'10: 40MHz, 2b'01: 80MHz */
}
if (dm->support_ic_type == ODM_RTL8812)
dm_psd_table->psd_pwr_common_offset = 0;
else if (dm->support_ic_type == ODM_RTL8821)
dm_psd_table->psd_pwr_common_offset = 0;
else
dm_psd_table->psd_pwr_common_offset = 0;
phydm_psd_para_setting(dm, 1, 2, 3, 128, 0, 0, 7, 0);
/*phydm_psd(dm, 0x3c, 0, 127);*/ /* target at -50dBm */
}
void phydm_psd_debug(void *dm_void, char input[][16], u32 *_used, char *output,
u32 *_out_len, u32 input_num)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
char help[] = "-h";
u32 var1[10] = {0};
u32 used = *_used;
u32 out_len = *_out_len;
u8 i;
if ((strcmp(input[1], help) == 0)) {
PHYDM_SNPRINTF(
output + used, out_len - used,
"{0} {sw_avg} {hw_avg 0:3} {1:I,2:Q,3:IQ} {fft_point: 128*(1:4)} {path_sel 0~3} {0:ADC, 1:RXIQC} {CH} {noise_k}\n");
PHYDM_SNPRINTF(output + used, out_len - used,
"{1} {IGI(hex)} {start_point} {stop_point}\n");
return;
}
PHYDM_SSCANF(input[1], DCMD_DECIMAL, &var1[0]);
if (var1[0] == 0) {
for (i = 1; i < 10; i++) {
if (input[i + 1])
PHYDM_SSCANF(input[i + 1], DCMD_DECIMAL,
&var1[i]);
}
PHYDM_SNPRINTF(
output + used, out_len - used,
"sw_avg_time=((%d)), hw_avg_time=((%d)), IQ=((%d)), fft=((%d)), path=((%d)), input =((%d)) ch=((%d)), noise_k=((%d))\n",
var1[1], var1[2], var1[3], var1[4], var1[5], var1[6],
(u8)var1[7], (u8)var1[8]);
phydm_psd_para_setting(dm, (u8)var1[1], (u8)var1[2],
(u8)var1[3], (u16)var1[4], (u8)var1[5],
(u8)var1[6], (u8)var1[7], (u8)var1[8]);
} else if (var1[0] == 1) {
PHYDM_SSCANF(input[2], DCMD_HEX, &var1[1]);
PHYDM_SSCANF(input[3], DCMD_DECIMAL, &var1[2]);
PHYDM_SSCANF(input[4], DCMD_DECIMAL, &var1[3]);
PHYDM_SNPRINTF(
output + used, out_len - used,
"IGI=((0x%x)), start_point=((%d)), stop_point=((%d))\n",
var1[1], var1[2], var1[3]);
dm->debug_components |= ODM_COMP_API;
phydm_psd(dm, var1[1], (u16)var1[2], (u16)var1[3]);
dm->debug_components &= (~ODM_COMP_API);
}
}
u8 phydm_get_psd_result_table(void *dm_void, int index)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct psd_info *dm_psd_table = &dm->dm_psd_table;
u8 temp_result = 0;
if (index < 128)
temp_result = dm_psd_table->psd_result[index];
return temp_result;
}

View File

@ -0,0 +1,67 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMPSD_H__
#define __PHYDMPSD_H__
/*#define PSD_VERSION "1.0"*/ /*2016.09.22 Dino*/
#define PSD_VERSION "1.1" /*2016.10.07 Dino, Add Option for PSD Tone index
*Selection
*/
#define STOP_TRX_SUCCESS 1
#define STOP_TRX_FAIL 0
struct psd_info {
u8 psd_in_progress;
u32 psd_reg;
u32 psd_report_reg;
u8 psd_pwr_common_offset;
u16 sw_avg_time;
u16 fft_smp_point;
u32 initial_gain_backup;
u32 rf_0x18_bkp;
u16 psd_fc_channel;
u32 psd_bw_rf_reg;
u8 psd_result[128];
u8 noise_k_en;
};
u32 phydm_get_psd_data(void *dm_void, u32 psd_tone_idx, u32 igi);
void phydm_psd_debug(void *dm_void, char input[][16], u32 *_used, char *output,
u32 *_out_len, u32 input_num);
void phydm_psd(void *dm_void, u32 igi, u16 start_point, u16 stop_point);
void phydm_psd_para_setting(void *dm_void, u8 sw_avg_time, u8 hw_avg_time,
u8 i_q_setting, u16 fft_smp_point, u8 ant_sel,
u8 psd_input, u8 channel, u8 noise_k_en);
void phydm_psd_init(void *dm_void);
u8 phydm_get_psd_result_table(void *dm_void, int index);
#endif

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,269 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDMRAINFO_H__
#define __PHYDMRAINFO_H__
/*#define RAINFO_VERSION "2.0"*/ /*2014.11.04*/
/*#define RAINFO_VERSION "3.0"*/ /*2015.01.13 Dino*/
/*#define RAINFO_VERSION "3.1"*/ /*2015.01.14 Dino*/
/*#define RAINFO_VERSION "3.3"*/ /*2015.07.29 YuChen*/
/*#define RAINFO_VERSION "3.4"*/ /*2015.12.15 Stanley*/
/*#define RAINFO_VERSION "4.0"*/ /*2016.03.24 Dino, Add more RA mask
*state and Phydm-lize partial ra mask
*function
*/
/*#define RAINFO_VERSION "4.1"*/ /*2016.04.20 Dino, Add new function to
*adjust PCR RA threshold
*/
/*#define RAINFO_VERSION "4.2"*/ /*2016.05.17 Dino, Add H2C debug cmd */
#define RAINFO_VERSION "4.3" /*2016.07.11 Dino, Fix RA hang in CCK 1M problem*/
#define FORCED_UPDATE_RAMASK_PERIOD 5
#define H2C_0X42_LENGTH 5
#define H2C_MAX_LENGTH 7
#define RA_FLOOR_UP_GAP 3
#define RA_FLOOR_TABLE_SIZE 7
#define ACTIVE_TP_THRESHOLD 150
#define RA_RETRY_DESCEND_NUM 2
#define RA_RETRY_LIMIT_LOW 4
#define RA_RETRY_LIMIT_HIGH 32
#define RAINFO_BE_RX_STATE BIT(0) /* 1:RX */ /* ULDL */
#define RAINFO_STBC_STATE BIT(1)
/* #define RAINFO_LDPC_STATE BIT2 */
#define RAINFO_NOISY_STATE BIT(2) /* set by Noisy_Detection */
#define RAINFO_SHURTCUT_STATE BIT(3)
#define RAINFO_SHURTCUT_FLAG BIT(4)
#define RAINFO_INIT_RSSI_RATE_STATE BIT(5)
#define RAINFO_BF_STATE BIT(6)
#define RAINFO_BE_TX_STATE BIT(7) /* 1:TX */
#define RA_MASK_CCK 0xf
#define RA_MASK_OFDM 0xff0
#define RA_MASK_HT1SS 0xff000
#define RA_MASK_HT2SS 0xff00000
/*#define RA_MASK_MCS3SS */
#define RA_MASK_HT4SS 0xff0
#define RA_MASK_VHT1SS 0x3ff000
#define RA_MASK_VHT2SS 0xffc00000
#define RA_FIRST_MACID 0
#define ap_init_rate_adaptive_state odm_rate_adaptive_state_ap_init
#define DM_RATR_STA_INIT 0
#define DM_RATR_STA_HIGH 1
#define DM_RATR_STA_MIDDLE 2
#define DM_RATR_STA_LOW 3
#define DM_RATR_STA_ULTRA_LOW 4
enum phydm_ra_arfr_num {
ARFR_0_RATE_ID = 0x9,
ARFR_1_RATE_ID = 0xa,
ARFR_2_RATE_ID = 0xb,
ARFR_3_RATE_ID = 0xc,
ARFR_4_RATE_ID = 0xd,
ARFR_5_RATE_ID = 0xe
};
enum phydm_ra_dbg_para {
RADBG_PCR_TH_OFFSET = 0,
RADBG_RTY_PENALTY = 1,
RADBG_N_HIGH = 2,
RADBG_N_LOW = 3,
RADBG_TRATE_UP_TABLE = 4,
RADBG_TRATE_DOWN_TABLE = 5,
RADBG_TRYING_NECESSARY = 6,
RADBG_TDROPING_NECESSARY = 7,
RADBG_RATE_UP_RTY_RATIO = 8,
RADBG_RATE_DOWN_RTY_RATIO = 9, /* u8 */
RADBG_DEBUG_MONITOR1 = 0xc,
RADBG_DEBUG_MONITOR2 = 0xd,
RADBG_DEBUG_MONITOR3 = 0xe,
RADBG_DEBUG_MONITOR4 = 0xf,
RADBG_DEBUG_MONITOR5 = 0x10,
NUM_RA_PARA
};
enum phydm_wireless_mode {
PHYDM_WIRELESS_MODE_UNKNOWN = 0x00,
PHYDM_WIRELESS_MODE_A = 0x01,
PHYDM_WIRELESS_MODE_B = 0x02,
PHYDM_WIRELESS_MODE_G = 0x04,
PHYDM_WIRELESS_MODE_AUTO = 0x08,
PHYDM_WIRELESS_MODE_N_24G = 0x10,
PHYDM_WIRELESS_MODE_N_5G = 0x20,
PHYDM_WIRELESS_MODE_AC_5G = 0x40,
PHYDM_WIRELESS_MODE_AC_24G = 0x80,
PHYDM_WIRELESS_MODE_AC_ONLY = 0x100,
PHYDM_WIRELESS_MODE_MAX = 0x800,
PHYDM_WIRELESS_MODE_ALL = 0xFFFF
};
enum phydm_rateid_idx {
PHYDM_BGN_40M_2SS = 0,
PHYDM_BGN_40M_1SS = 1,
PHYDM_BGN_20M_2SS = 2,
PHYDM_BGN_20M_1SS = 3,
PHYDM_GN_N2SS = 4,
PHYDM_GN_N1SS = 5,
PHYDM_BG = 6,
PHYDM_G = 7,
PHYDM_B_20M = 8,
PHYDM_ARFR0_AC_2SS = 9,
PHYDM_ARFR1_AC_1SS = 10,
PHYDM_ARFR2_AC_2G_1SS = 11,
PHYDM_ARFR3_AC_2G_2SS = 12,
PHYDM_ARFR4_AC_3SS = 13,
PHYDM_ARFR5_N_3SS = 14
};
enum phydm_rf_type_def {
PHYDM_RF_1T1R = 0,
PHYDM_RF_1T2R,
PHYDM_RF_2T2R,
PHYDM_RF_2T2R_GREEN,
PHYDM_RF_2T3R,
PHYDM_RF_2T4R,
PHYDM_RF_3T3R,
PHYDM_RF_3T4R,
PHYDM_RF_4T4R,
PHYDM_RF_MAX_TYPE
};
enum phydm_bw {
PHYDM_BW_20 = 0,
PHYDM_BW_40,
PHYDM_BW_80,
PHYDM_BW_80_80,
PHYDM_BW_160,
PHYDM_BW_10,
PHYDM_BW_5
};
struct ra_table {
u8 firstconnect;
u8 link_tx_rate[ODM_ASSOCIATE_ENTRY_NUM];
u8 highest_client_tx_order;
u16 highest_client_tx_rate_order;
u8 power_tracking_flag;
u8 RA_threshold_offset;
u8 RA_offset_direction;
u8 force_update_ra_mask_count;
};
struct odm_rate_adaptive {
/* dm_type_by_fw/dm_type_by_driver */
u8 type;
/* if RSSI > high_rssi_thresh => ratr_state is DM_RATR_STA_HIGH */
u8 high_rssi_thresh;
/* if RSSI <= low_rssi_thresh => ratr_state is DM_RATR_STA_LOW */
u8 low_rssi_thresh;
/* Cur RSSI level, DM_RATR_STA_HIGH/DM_RATR_STA_MIDDLE/DM_RATR_STA_LOW*/
u8 ratr_state;
/* if RSSI > ldpc_thres => switch from LPDC to BCC */
u8 ldpc_thres;
bool is_lower_rts_rate;
bool is_use_ldpc;
};
void phydm_h2C_debug(void *dm_void, u32 *const dm_value, u32 *_used,
char *output, u32 *_out_len);
void phydm_RA_debug_PCR(void *dm_void, u32 *const dm_value, u32 *_used,
char *output, u32 *_out_len);
void odm_c2h_ra_para_report_handler(void *dm_void, u8 *cmd_buf, u8 cmd_len);
void odm_ra_para_adjust(void *dm_void);
void phydm_ra_dynamic_retry_count(void *dm_void);
void phydm_ra_dynamic_retry_limit(void *dm_void);
void phydm_ra_dynamic_rate_id_on_assoc(void *dm_void, u8 wireless_mode,
u8 init_rate_id);
void phydm_print_rate(void *dm_void, u8 rate, u32 dbg_component);
void phydm_c2h_ra_report_handler(void *dm_void, u8 *cmd_buf, u8 cmd_len);
u8 phydm_rate_order_compute(void *dm_void, u8 rate_idx);
void phydm_ra_info_watchdog(void *dm_void);
void phydm_ra_info_init(void *dm_void);
void odm_rssi_monitor_init(void *dm_void);
void phydm_modify_RA_PCR_threshold(void *dm_void, u8 RA_offset_direction,
u8 RA_threshold_offset);
void odm_rssi_monitor_check(void *dm_void);
void phydm_init_ra_info(void *dm_void);
u8 phydm_vht_en_mapping(void *dm_void, u32 wireless_mode);
u8 phydm_rate_id_mapping(void *dm_void, u32 wireless_mode, u8 rf_type, u8 bw);
void phydm_update_hal_ra_mask(void *dm_void, u32 wireless_mode, u8 rf_type,
u8 BW, u8 mimo_ps_enable, u8 disable_cck_rate,
u32 *ratr_bitmap_msb_in, u32 *ratr_bitmap_in,
u8 tx_rate_level);
void odm_rate_adaptive_mask_init(void *dm_void);
void odm_refresh_rate_adaptive_mask(void *dm_void);
void odm_refresh_rate_adaptive_mask_mp(void *dm_void);
void odm_refresh_rate_adaptive_mask_ce(void *dm_void);
void odm_refresh_rate_adaptive_mask_apadsl(void *dm_void);
u8 phydm_RA_level_decision(void *dm_void, u32 rssi, u8 ratr_state);
bool odm_ra_state_check(void *dm_void, s32 RSSI, bool is_force_update,
u8 *ra_tr_state);
void odm_refresh_basic_rate_mask(void *dm_void);
void odm_ra_post_action_on_assoc(void *dm);
u8 odm_find_rts_rate(void *dm_void, u8 tx_rate, bool is_erp_protect);
void odm_update_noisy_state(void *dm_void, bool is_noisy_state_from_c2h);
void phydm_update_pwr_track(void *dm_void, u8 rate);
#endif /*#ifndef __ODMRAINFO_H__*/

View File

@ -0,0 +1,151 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/* ************************************************************
* File Name: odm_reg.h
*
* Description:
*
* This file is for general register definition.
*
*
* *************************************************************/
#ifndef __HAL_ODM_REG_H__
#define __HAL_ODM_REG_H__
/*
* Register Definition
*/
/* MAC REG */
#define ODM_BB_RESET 0x002
#define ODM_DUMMY 0x4fe
#define RF_T_METER_OLD 0x24
#define RF_T_METER_NEW 0x42
#define ODM_EDCA_VO_PARAM 0x500
#define ODM_EDCA_VI_PARAM 0x504
#define ODM_EDCA_BE_PARAM 0x508
#define ODM_EDCA_BK_PARAM 0x50C
#define ODM_TXPAUSE 0x522
/* LTE_COEX */
#define REG_LTECOEX_CTRL 0x07C0
#define REG_LTECOEX_WRITE_DATA 0x07C4
#define REG_LTECOEX_READ_DATA 0x07C8
#define REG_LTECOEX_PATH_CONTROL 0x70
/* BB REG */
#define ODM_FPGA_PHY0_PAGE8 0x800
#define ODM_PSD_SETTING 0x808
#define ODM_AFE_SETTING 0x818
#define ODM_TXAGC_B_6_18 0x830
#define ODM_TXAGC_B_24_54 0x834
#define ODM_TXAGC_B_MCS32_5 0x838
#define ODM_TXAGC_B_MCS0_MCS3 0x83c
#define ODM_TXAGC_B_MCS4_MCS7 0x848
#define ODM_TXAGC_B_MCS8_MCS11 0x84c
#define ODM_ANALOG_REGISTER 0x85c
#define ODM_RF_INTERFACE_OUTPUT 0x860
#define ODM_TXAGC_B_MCS12_MCS15 0x868
#define ODM_TXAGC_B_11_A_2_11 0x86c
#define ODM_AD_DA_LSB_MASK 0x874
#define ODM_ENABLE_3_WIRE 0x88c
#define ODM_PSD_REPORT 0x8b4
#define ODM_R_ANT_SELECT 0x90c
#define ODM_CCK_ANT_SELECT 0xa07
#define ODM_CCK_PD_THRESH 0xa0a
#define ODM_CCK_RF_REG1 0xa11
#define ODM_CCK_MATCH_FILTER 0xa20
#define ODM_CCK_RAKE_MAC 0xa2e
#define ODM_CCK_CNT_RESET 0xa2d
#define ODM_CCK_TX_DIVERSITY 0xa2f
#define ODM_CCK_FA_CNT_MSB 0xa5b
#define ODM_CCK_FA_CNT_LSB 0xa5c
#define ODM_CCK_NEW_FUNCTION 0xa75
#define ODM_OFDM_PHY0_PAGE_C 0xc00
#define ODM_OFDM_RX_ANT 0xc04
#define ODM_R_A_RXIQI 0xc14
#define ODM_R_A_AGC_CORE1 0xc50
#define ODM_R_A_AGC_CORE2 0xc54
#define ODM_R_B_AGC_CORE1 0xc58
#define ODM_R_AGC_PAR 0xc70
#define ODM_R_HTSTF_AGC_PAR 0xc7c
#define ODM_TX_PWR_TRAINING_A 0xc90
#define ODM_TX_PWR_TRAINING_B 0xc98
#define ODM_OFDM_FA_CNT1 0xcf0
#define ODM_OFDM_PHY0_PAGE_D 0xd00
#define ODM_OFDM_FA_CNT2 0xda0
#define ODM_OFDM_FA_CNT3 0xda4
#define ODM_OFDM_FA_CNT4 0xda8
#define ODM_TXAGC_A_6_18 0xe00
#define ODM_TXAGC_A_24_54 0xe04
#define ODM_TXAGC_A_1_MCS32 0xe08
#define ODM_TXAGC_A_MCS0_MCS3 0xe10
#define ODM_TXAGC_A_MCS4_MCS7 0xe14
#define ODM_TXAGC_A_MCS8_MCS11 0xe18
#define ODM_TXAGC_A_MCS12_MCS15 0xe1c
/* RF REG */
#define ODM_GAIN_SETTING 0x00
#define ODM_CHANNEL 0x18
#define ODM_RF_T_METER 0x24
#define ODM_RF_T_METER_92D 0x42
#define ODM_RF_T_METER_88E 0x42
#define ODM_RF_T_METER_92E 0x42
#define ODM_RF_T_METER_8812 0x42
#define REG_RF_TX_GAIN_OFFSET 0x55
/* ant Detect Reg */
#define ODM_DPDT 0x300
/* PSD Init */
#define ODM_PSDREG 0x808
/* 92D path Div */
#define PATHDIV_REG 0xB30
#define PATHDIV_TRI 0xBA0
/*
* Bitmap Definition
*/
#define BIT_FA_RESET BIT(0)
#define REG_OFDM_0_XA_TX_IQ_IMBALANCE 0xC80
#define REG_OFDM_0_ECCA_THRESHOLD 0xC4C
#define REG_FPGA0_XB_LSSI_READ_BACK 0x8A4
#define REG_FPGA0_TX_GAIN_STAGE 0x80C
#define REG_OFDM_0_XA_AGC_CORE1 0xC50
#define REG_OFDM_0_XB_AGC_CORE1 0xC58
#define REG_A_TX_SCALE_JAGUAR 0xC1C
#define REG_B_TX_SCALE_JAGUAR 0xE1C
#define REG_AFE_XTAL_CTRL 0x0024
#define REG_AFE_PLL_CTRL 0x0028
#define REG_MAC_PHY_CTRL 0x002C
#define RF_CHNLBW 0x18
#endif

View File

@ -0,0 +1,94 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODM_REGDEFINE11AC_H__
#define __ODM_REGDEFINE11AC_H__
/* 2 RF REG LIST */
/* 2 BB REG LIST */
/* PAGE 8 */
#define ODM_REG_CCK_RPT_FORMAT_11AC 0x804
#define ODM_REG_BB_RX_PATH_11AC 0x808
#define ODM_REG_BB_TX_PATH_11AC 0x80c
#define ODM_REG_BB_ATC_11AC 0x860
#define ODM_REG_EDCCA_POWER_CAL 0x8dc
#define ODM_REG_DBG_RPT_11AC 0x8fc
/* PAGE 9 */
#define ODM_REG_EDCCA_DOWN_OPT 0x900
#define ODM_REG_ACBB_EDCCA_ENHANCE 0x944
#define odm_adc_trigger_jaguar2 0x95C /*ADC sample mode*/
#define ODM_REG_OFDM_FA_RST_11AC 0x9A4
#define ODM_REG_CCX_PERIOD_11AC 0x990
#define ODM_REG_NHM_TH9_TH10_11AC 0x994
#define ODM_REG_CLM_11AC 0x994
#define ODM_REG_NHM_TH3_TO_TH0_11AC 0x998
#define ODM_REG_NHM_TH7_TO_TH4_11AC 0x99c
#define ODM_REG_NHM_TH8_11AC 0x9a0
#define ODM_REG_NHM_9E8_11AC 0x9e8
#define ODM_REG_CSI_CONTENT_VALUE 0x9b4
/* PAGE A */
#define ODM_REG_CCK_CCA_11AC 0xA0A
#define ODM_REG_CCK_FA_RST_11AC 0xA2C
#define ODM_REG_CCK_FA_11AC 0xA5C
/* PAGE B */
#define ODM_REG_RST_RPT_11AC 0xB58
/* PAGE C */
#define ODM_REG_TRMUX_11AC 0xC08
#define ODM_REG_IGI_A_11AC 0xC50
/* PAGE E */
#define ODM_REG_IGI_B_11AC 0xE50
#define ODM_REG_TRMUX_11AC_B 0xE08
/* PAGE F */
#define ODM_REG_CCK_CRC32_CNT_11AC 0xF04
#define ODM_REG_CCK_CCA_CNT_11AC 0xF08
#define ODM_REG_VHT_CRC32_CNT_11AC 0xF0c
#define ODM_REG_HT_CRC32_CNT_11AC 0xF10
#define ODM_REG_OFDM_CRC32_CNT_11AC 0xF14
#define ODM_REG_OFDM_FA_11AC 0xF48
#define ODM_REG_RPT_11AC 0xfa0
#define ODM_REG_CLM_RESULT_11AC 0xfa4
#define ODM_REG_NHM_CNT_11AC 0xfa8
#define ODM_REG_NHM_DUR_READY_11AC 0xfb4
#define ODM_REG_NHM_CNT7_TO_CNT4_11AC 0xfac
#define ODM_REG_NHM_CNT11_TO_CNT8_11AC 0xfb0
#define ODM_REG_OFDM_FA_TYPE2_11AC 0xFD0
/* PAGE 18 */
#define ODM_REG_IGI_C_11AC 0x1850
/* PAGE 1A */
#define ODM_REG_IGI_D_11AC 0x1A50
/* 2 MAC REG LIST */
#define ODM_REG_RESP_TX_11AC 0x6D8
/* DIG Related */
#define ODM_BIT_IGI_11AC 0xFFFFFFFF
#define ODM_BIT_CCK_RPT_FORMAT_11AC BIT(16)
#define ODM_BIT_BB_RX_PATH_11AC 0xF
#define ODM_BIT_BB_TX_PATH_11AC 0xF
#define ODM_BIT_BB_ATC_11AC BIT(14)
#endif

View File

@ -0,0 +1,213 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODM_REGDEFINE11N_H__
#define __ODM_REGDEFINE11N_H__
/* 2 RF REG LIST */
#define ODM_REG_RF_MODE_11N 0x00
#define ODM_REG_RF_0B_11N 0x0B
#define ODM_REG_CHNBW_11N 0x18
#define ODM_REG_T_METER_11N 0x24
#define ODM_REG_RF_25_11N 0x25
#define ODM_REG_RF_26_11N 0x26
#define ODM_REG_RF_27_11N 0x27
#define ODM_REG_RF_2B_11N 0x2B
#define ODM_REG_RF_2C_11N 0x2C
#define ODM_REG_RXRF_A3_11N 0x3C
#define ODM_REG_T_METER_92D_11N 0x42
#define ODM_REG_T_METER_88E_11N 0x42
/* 2 BB REG LIST */
/* PAGE 8 */
#define ODM_REG_BB_CTRL_11N 0x800
#define ODM_REG_RF_PIN_11N 0x804
#define ODM_REG_PSD_CTRL_11N 0x808
#define ODM_REG_TX_ANT_CTRL_11N 0x80C
#define ODM_REG_BB_PWR_SAV5_11N 0x818
#define ODM_REG_CCK_RPT_FORMAT_11N 0x824
#define ODM_REG_CCK_RPT_FORMAT_11N_B 0x82C
#define ODM_REG_RX_DEFAULT_A_11N 0x858
#define ODM_REG_RX_DEFAULT_B_11N 0x85A
#define ODM_REG_BB_PWR_SAV3_11N 0x85C
#define ODM_REG_ANTSEL_CTRL_11N 0x860
#define ODM_REG_RX_ANT_CTRL_11N 0x864
#define ODM_REG_PIN_CTRL_11N 0x870
#define ODM_REG_BB_PWR_SAV1_11N 0x874
#define ODM_REG_ANTSEL_PATH_11N 0x878
#define ODM_REG_BB_3WIRE_11N 0x88C
#define ODM_REG_SC_CNT_11N 0x8C4
#define ODM_REG_PSD_DATA_11N 0x8B4
#define ODM_REG_CCX_PERIOD_11N 0x894
#define ODM_REG_NHM_TH9_TH10_11N 0x890
#define ODM_REG_CLM_11N 0x890
#define ODM_REG_NHM_TH3_TO_TH0_11N 0x898
#define ODM_REG_NHM_TH7_TO_TH4_11N 0x89c
#define ODM_REG_NHM_TH8_11N 0xe28
#define ODM_REG_CLM_READY_11N 0x8b4
#define ODM_REG_CLM_RESULT_11N 0x8d0
#define ODM_REG_NHM_CNT_11N 0x8d8
/* For struct acs_info, Jeffery, 2014-12-26 */
#define ODM_REG_NHM_CNT7_TO_CNT4_11N 0x8dc
#define ODM_REG_NHM_CNT9_TO_CNT8_11N 0x8d0
#define ODM_REG_NHM_CNT10_TO_CNT11_11N 0x8d4
/* PAGE 9 */
#define ODM_REG_BB_CTRL_PAGE9_11N 0x900
#define ODM_REG_DBG_RPT_11N 0x908
#define ODM_REG_BB_TX_PATH_11N 0x90c
#define ODM_REG_ANT_MAPPING1_11N 0x914
#define ODM_REG_ANT_MAPPING2_11N 0x918
#define ODM_REG_EDCCA_DOWN_OPT_11N 0x948
#define ODM_REG_RX_DFIR_MOD_97F 0x948
/* PAGE A */
#define ODM_REG_CCK_ANTDIV_PARA1_11N 0xA00
#define ODM_REG_CCK_ANT_SEL_11N 0xA04
#define ODM_REG_CCK_CCA_11N 0xA0A
#define ODM_REG_CCK_ANTDIV_PARA2_11N 0xA0C
#define ODM_REG_CCK_ANTDIV_PARA3_11N 0xA10
#define ODM_REG_CCK_ANTDIV_PARA4_11N 0xA14
#define ODM_REG_CCK_FILTER_PARA1_11N 0xA22
#define ODM_REG_CCK_FILTER_PARA2_11N 0xA23
#define ODM_REG_CCK_FILTER_PARA3_11N 0xA24
#define ODM_REG_CCK_FILTER_PARA4_11N 0xA25
#define ODM_REG_CCK_FILTER_PARA5_11N 0xA26
#define ODM_REG_CCK_FILTER_PARA6_11N 0xA27
#define ODM_REG_CCK_FILTER_PARA7_11N 0xA28
#define ODM_REG_CCK_FILTER_PARA8_11N 0xA29
#define ODM_REG_CCK_FA_RST_11N 0xA2C
#define ODM_REG_CCK_FA_MSB_11N 0xA58
#define ODM_REG_CCK_FA_LSB_11N 0xA5C
#define ODM_REG_CCK_CCA_CNT_11N 0xA60
#define ODM_REG_BB_PWR_SAV4_11N 0xA74
/* PAGE B */
#define ODM_REG_LNA_SWITCH_11N 0xB2C
#define ODM_REG_PATH_SWITCH_11N 0xB30
#define ODM_REG_RSSI_CTRL_11N 0xB38
#define ODM_REG_CONFIG_ANTA_11N 0xB68
#define ODM_REG_RSSI_BT_11N 0xB9C
#define ODM_REG_RXCK_RFMOD 0xBB0
#define ODM_REG_EDCCA_DCNF_97F 0xBC0
/* PAGE C */
#define ODM_REG_OFDM_FA_HOLDC_11N 0xC00
#define ODM_REG_BB_RX_PATH_11N 0xC04
#define ODM_REG_TRMUX_11N 0xC08
#define ODM_REG_OFDM_FA_RSTC_11N 0xC0C
#define ODM_REG_DOWNSAM_FACTOR_11N 0xC10
#define ODM_REG_RXIQI_MATRIX_11N 0xC14
#define ODM_REG_TXIQK_MATRIX_LSB1_11N 0xC4C
#define ODM_REG_IGI_A_11N 0xC50
#define ODM_REG_ANTDIV_PARA2_11N 0xC54
#define ODM_REG_IGI_B_11N 0xC58
#define ODM_REG_ANTDIV_PARA3_11N 0xC5C
#define ODM_REG_L1SBD_PD_CH_11N 0XC6C
#define ODM_REG_BB_PWR_SAV2_11N 0xC70
#define ODM_REG_BB_AGC_SET_2_11N 0xc74
#define ODM_REG_RX_OFF_11N 0xC7C
#define ODM_REG_TXIQK_MATRIXA_11N 0xC80
#define ODM_REG_TXIQK_MATRIXB_11N 0xC88
#define ODM_REG_TXIQK_MATRIXA_LSB2_11N 0xC94
#define ODM_REG_TXIQK_MATRIXB_LSB2_11N 0xC9C
#define ODM_REG_RXIQK_MATRIX_LSB_11N 0xCA0
#define ODM_REG_ANTDIV_PARA1_11N 0xCA4
#define ODM_REG_SMALL_BANDWIDTH_11N 0xCE4
#define ODM_REG_OFDM_FA_TYPE1_11N 0xCF0
/* PAGE D */
#define ODM_REG_OFDM_FA_RSTD_11N 0xD00
#define ODM_REG_BB_RX_ANT_11N 0xD04
#define ODM_REG_BB_ATC_11N 0xD2C
#define ODM_REG_OFDM_FA_TYPE2_11N 0xDA0
#define ODM_REG_OFDM_FA_TYPE3_11N 0xDA4
#define ODM_REG_OFDM_FA_TYPE4_11N 0xDA8
#define ODM_REG_RPT_11N 0xDF4
/* PAGE E */
#define ODM_REG_TXAGC_A_6_18_11N 0xE00
#define ODM_REG_TXAGC_A_24_54_11N 0xE04
#define ODM_REG_TXAGC_A_1_MCS32_11N 0xE08
#define ODM_REG_TXAGC_A_MCS0_3_11N 0xE10
#define ODM_REG_TXAGC_A_MCS4_7_11N 0xE14
#define ODM_REG_TXAGC_A_MCS8_11_11N 0xE18
#define ODM_REG_TXAGC_A_MCS12_15_11N 0xE1C
#define ODM_REG_EDCCA_DCNF_11N 0xE24
#define ODM_REG_TAP_UPD_97F 0xE24
#define ODM_REG_FPGA0_IQK_11N 0xE28
#define ODM_REG_PAGE_B1_97F 0xE28
#define ODM_REG_TXIQK_TONE_A_11N 0xE30
#define ODM_REG_RXIQK_TONE_A_11N 0xE34
#define ODM_REG_TXIQK_PI_A_11N 0xE38
#define ODM_REG_RXIQK_PI_A_11N 0xE3C
#define ODM_REG_TXIQK_11N 0xE40
#define ODM_REG_RXIQK_11N 0xE44
#define ODM_REG_IQK_AGC_PTS_11N 0xE48
#define ODM_REG_IQK_AGC_RSP_11N 0xE4C
#define ODM_REG_BLUETOOTH_11N 0xE6C
#define ODM_REG_RX_WAIT_CCA_11N 0xE70
#define ODM_REG_TX_CCK_RFON_11N 0xE74
#define ODM_REG_TX_CCK_BBON_11N 0xE78
#define ODM_REG_OFDM_RFON_11N 0xE7C
#define ODM_REG_OFDM_BBON_11N 0xE80
#define ODM_REG_TX2RX_11N 0xE84
#define ODM_REG_TX2TX_11N 0xE88
#define ODM_REG_RX_CCK_11N 0xE8C
#define ODM_REG_RX_OFDM_11N 0xED0
#define ODM_REG_RX_WAIT_RIFS_11N 0xED4
#define ODM_REG_RX2RX_11N 0xED8
#define ODM_REG_STANDBY_11N 0xEDC
#define ODM_REG_SLEEP_11N 0xEE0
#define ODM_REG_PMPD_ANAEN_11N 0xEEC
/* PAGE F */
#define ODM_REG_PAGE_F_RST_11N 0xF14
#define ODM_REG_IGI_C_11N 0xF84
#define ODM_REG_IGI_D_11N 0xF88
#define ODM_REG_CCK_CRC32_ERROR_CNT_11N 0xF84
#define ODM_REG_CCK_CRC32_OK_CNT_11N 0xF88
#define ODM_REG_HT_CRC32_CNT_11N 0xF90
#define ODM_REG_OFDM_CRC32_CNT_11N 0xF94
/* 2 MAC REG LIST */
#define ODM_REG_BB_RST_11N 0x02
#define ODM_REG_ANTSEL_PIN_11N 0x4C
#define ODM_REG_EARLY_MODE_11N 0x4D0
#define ODM_REG_RSSI_MONITOR_11N 0x4FE
#define ODM_REG_EDCA_VO_11N 0x500
#define ODM_REG_EDCA_VI_11N 0x504
#define ODM_REG_EDCA_BE_11N 0x508
#define ODM_REG_EDCA_BK_11N 0x50C
#define ODM_REG_TXPAUSE_11N 0x522
#define ODM_REG_RESP_TX_11N 0x6D8
#define ODM_REG_ANT_TRAIN_PARA1_11N 0x7b0
#define ODM_REG_ANT_TRAIN_PARA2_11N 0x7b4
/* DIG Related */
#define ODM_BIT_IGI_11N 0x0000007F
#define ODM_BIT_CCK_RPT_FORMAT_11N BIT(9)
#define ODM_BIT_BB_RX_PATH_11N 0xF
#define ODM_BIT_BB_TX_PATH_11N 0xF
#define ODM_BIT_BB_ATC_11N BIT(11)
#endif

View File

@ -0,0 +1,130 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODM_TYPES_H__
#define __ODM_TYPES_H__
/*Define Different SW team support*/
#define ODM_AP 0x01 /*BIT0*/
#define ODM_CE 0x04 /*BIT2*/
#define ODM_WIN 0x08 /*BIT3*/
#define ODM_ADSL 0x10 /*BIT4*/
#define ODM_IOT 0x20 /*BIT5*/
/*Deifne HW endian support*/
#define ODM_ENDIAN_BIG 0
#define ODM_ENDIAN_LITTLE 1
#define GET_PDM_ODM(__padapter) \
((struct phy_dm_struct *)(&(GET_HAL_DATA(__padapter))->odmpriv))
enum hal_status {
HAL_STATUS_SUCCESS,
HAL_STATUS_FAILURE,
};
/*
* Declare for ODM spin lock definition temporarily fro compile pass.
*/
enum rt_spinlock_type {
RT_TX_SPINLOCK = 1,
RT_RX_SPINLOCK = 2,
RT_RM_SPINLOCK = 3,
RT_CAM_SPINLOCK = 4,
RT_SCAN_SPINLOCK = 5,
RT_LOG_SPINLOCK = 7,
RT_BW_SPINLOCK = 8,
RT_CHNLOP_SPINLOCK = 9,
RT_RF_OPERATE_SPINLOCK = 10,
RT_INITIAL_SPINLOCK = 11,
RT_RF_STATE_SPINLOCK =
12, /* For RF state. Added by Bruce, 2007-10-30. */
/* Shall we define Ndis 6.2 SpinLock Here ? */
RT_PORT_SPINLOCK = 16,
RT_VNIC_SPINLOCK = 17,
RT_HVL_SPINLOCK = 18,
RT_H2C_SPINLOCK = 20, /* For H2C cmd. Added by tynli. 2009.11.09. */
rt_bt_data_spinlock = 25,
RT_WAPI_OPTION_SPINLOCK = 26,
RT_WAPI_RX_SPINLOCK = 27,
/* add for 92D CCK control issue */
RT_CCK_PAGEA_SPINLOCK = 28,
RT_BUFFER_SPINLOCK = 29,
RT_CHANNEL_AND_BANDWIDTH_SPINLOCK = 30,
RT_GEN_TEMP_BUF_SPINLOCK = 31,
RT_AWB_SPINLOCK = 32,
RT_FW_PS_SPINLOCK = 33,
RT_HW_TIMER_SPIN_LOCK = 34,
RT_MPT_WI_SPINLOCK = 35,
RT_P2P_SPIN_LOCK = 36, /* Protect P2P context */
RT_DBG_SPIN_LOCK = 37,
RT_IQK_SPINLOCK = 38,
RT_PENDED_OID_SPINLOCK = 39,
RT_CHNLLIST_SPINLOCK = 40,
RT_INDIC_SPINLOCK = 41, /* protect indication */
RT_RFD_SPINLOCK = 42,
RT_SYNC_IO_CNT_SPINLOCK = 43,
RT_LAST_SPINLOCK,
};
#include <asm/byteorder.h>
#if defined(__LITTLE_ENDIAN)
#define ODM_ENDIAN_TYPE ODM_ENDIAN_LITTLE
#elif defined(__BIG_ENDIAN)
#define ODM_ENDIAN_TYPE ODM_ENDIAN_BIG
#else
#error
#endif
#define COND_ELSE 2
#define COND_ENDIF 3
#define MASKBYTE0 0xff
#define MASKBYTE1 0xff00
#define MASKBYTE2 0xff0000
#define MASKBYTE3 0xff000000
#define MASKHWORD 0xffff0000
#define MASKLWORD 0x0000ffff
#define MASKDWORD 0xffffffff
#define MASK7BITS 0x7f
#define MASK12BITS 0xfff
#define MASKH4BITS 0xf0000000
#define MASK20BITS 0xfffff
#define MASKOFDM_D 0xffc00000
#define MASKCCK 0x3f3f3f3f
#define RFREGOFFSETMASK 0xfffff
#define MASKH3BYTES 0xffffff00
#define MASKL3BYTES 0x00ffffff
#define MASKBYTE2HIGHNIBBLE 0x00f00000
#define MASKBYTE3LOWNIBBLE 0x0f000000
#define MASKL3BYTES 0x00ffffff
#define RFREGOFFSETMASK 0xfffff
#include "phydm_features.h"
#endif /* __ODM_TYPES_H__ */

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,54 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*Image2HeaderVersion: 3.2*/
#ifndef __INC_MP_BB_HW_IMG_8822B_H
#define __INC_MP_BB_HW_IMG_8822B_H
/******************************************************************************
* agc_tab.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_agc_tab(/* tc: Test Chip, mp: mp Chip*/
struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_agc_tab(void);
/******************************************************************************
* phy_reg.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_phy_reg(/* tc: Test Chip, mp: mp Chip*/
struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_phy_reg(void);
/******************************************************************************
* phy_reg_pg.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_phy_reg_pg(/* tc: Test Chip, mp: mp Chip*/
struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_phy_reg_pg(void);
#endif

View File

@ -0,0 +1,222 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*Image2HeaderVersion: 3.2*/
#include "../mp_precomp.h"
#include "../phydm_precomp.h"
static bool check_positive(struct phy_dm_struct *dm, const u32 condition1,
const u32 condition2, const u32 condition3,
const u32 condition4)
{
u8 _board_type = ((dm->board_type & BIT(4)) >> 4) << 0 | /* _GLNA*/
((dm->board_type & BIT(3)) >> 3) << 1 | /* _GPA*/
((dm->board_type & BIT(7)) >> 7) << 2 | /* _ALNA*/
((dm->board_type & BIT(6)) >> 6) << 3 | /* _APA */
((dm->board_type & BIT(2)) >> 2) << 4; /* _BT*/
u32 cond1 = condition1, cond2 = condition2, cond3 = condition3,
cond4 = condition4;
u8 cut_version_for_para =
(dm->cut_version == ODM_CUT_A) ? 14 : dm->cut_version;
u8 pkg_type_for_para = (dm->package_type == 0) ? 14 : dm->package_type;
u32 driver1 = cut_version_for_para << 24 |
(dm->support_interface & 0xF0) << 16 |
dm->support_platform << 16 | pkg_type_for_para << 12 |
(dm->support_interface & 0x0F) << 8 | _board_type;
u32 driver2 = (dm->type_glna & 0xFF) << 0 | (dm->type_gpa & 0xFF) << 8 |
(dm->type_alna & 0xFF) << 16 |
(dm->type_apa & 0xFF) << 24;
u32 driver3 = 0;
u32 driver4 = (dm->type_glna & 0xFF00) >> 8 | (dm->type_gpa & 0xFF00) |
(dm->type_alna & 0xFF00) << 8 |
(dm->type_apa & 0xFF00) << 16;
ODM_RT_TRACE(
dm, ODM_COMP_INIT,
"===> %s (cond1, cond2, cond3, cond4) = (0x%X 0x%X 0x%X 0x%X)\n",
__func__, cond1, cond2, cond3, cond4);
ODM_RT_TRACE(
dm, ODM_COMP_INIT,
"===> %s (driver1, driver2, driver3, driver4) = (0x%X 0x%X 0x%X 0x%X)\n",
__func__, driver1, driver2, driver3, driver4);
ODM_RT_TRACE(dm, ODM_COMP_INIT,
" (Platform, Interface) = (0x%X, 0x%X)\n",
dm->support_platform, dm->support_interface);
ODM_RT_TRACE(dm, ODM_COMP_INIT,
" (Board, Package) = (0x%X, 0x%X)\n",
dm->board_type, dm->package_type);
/*============== value Defined Check ===============*/
/*QFN type [15:12] and cut version [27:24] need to do value check*/
if (((cond1 & 0x0000F000) != 0) &&
((cond1 & 0x0000F000) != (driver1 & 0x0000F000)))
return false;
if (((cond1 & 0x0F000000) != 0) &&
((cond1 & 0x0F000000) != (driver1 & 0x0F000000)))
return false;
/*=============== Bit Defined Check ================*/
/* We don't care [31:28] */
cond1 &= 0x00FF0FFF;
driver1 &= 0x00FF0FFF;
if ((cond1 & driver1) == cond1) {
u32 bit_mask = 0;
if ((cond1 & 0x0F) == 0) /* board_type is DONTCARE*/
return true;
if ((cond1 & BIT(0)) != 0) /*GLNA*/
bit_mask |= 0x000000FF;
if ((cond1 & BIT(1)) != 0) /*GPA*/
bit_mask |= 0x0000FF00;
if ((cond1 & BIT(2)) != 0) /*ALNA*/
bit_mask |= 0x00FF0000;
if ((cond1 & BIT(3)) != 0) /*APA*/
bit_mask |= 0xFF000000;
if (((cond2 & bit_mask) == (driver2 & bit_mask)) &&
((cond4 & bit_mask) ==
(driver4 &
bit_mask))) /* board_type of each RF path is matched*/
return true;
else
return false;
} else {
return false;
}
}
/******************************************************************************
* mac_reg.TXT
******************************************************************************/
static u32 array_mp_8822b_mac_reg[] = {
0x029, 0x000000F9, 0x420, 0x00000080, 0x421, 0x0000000F,
0x428, 0x0000000A, 0x429, 0x00000010, 0x430, 0x00000000,
0x431, 0x00000000, 0x432, 0x00000000, 0x433, 0x00000001,
0x434, 0x00000004, 0x435, 0x00000005, 0x436, 0x00000007,
0x437, 0x00000008, 0x43C, 0x00000004, 0x43D, 0x00000005,
0x43E, 0x00000007, 0x43F, 0x00000008, 0x440, 0x0000005D,
0x441, 0x00000001, 0x442, 0x00000000, 0x444, 0x00000010,
0x445, 0x000000F0, 0x446, 0x00000001, 0x447, 0x000000FE,
0x448, 0x00000000, 0x449, 0x00000000, 0x44A, 0x00000000,
0x44B, 0x00000040, 0x44C, 0x00000010, 0x44D, 0x000000F0,
0x44E, 0x0000003F, 0x44F, 0x00000000, 0x450, 0x00000000,
0x451, 0x00000000, 0x452, 0x00000000, 0x453, 0x00000040,
0x455, 0x00000070, 0x45E, 0x00000004, 0x49C, 0x00000010,
0x49D, 0x000000F0, 0x49E, 0x00000000, 0x49F, 0x00000006,
0x4A0, 0x000000E0, 0x4A1, 0x00000003, 0x4A2, 0x00000000,
0x4A3, 0x00000040, 0x4A4, 0x00000015, 0x4A5, 0x000000F0,
0x4A6, 0x00000000, 0x4A7, 0x00000006, 0x4A8, 0x000000E0,
0x4A9, 0x00000000, 0x4AA, 0x00000000, 0x4AB, 0x00000000,
0x7DA, 0x00000008, 0x1448, 0x00000006, 0x144A, 0x00000006,
0x144C, 0x00000006, 0x144E, 0x00000006, 0x4C8, 0x000000FF,
0x4C9, 0x00000008, 0x4CA, 0x00000020, 0x4CB, 0x00000020,
0x4CC, 0x000000FF, 0x4CD, 0x000000FF, 0x4CE, 0x00000001,
0x4CF, 0x00000008, 0x500, 0x00000026, 0x501, 0x000000A2,
0x502, 0x0000002F, 0x503, 0x00000000, 0x504, 0x00000028,
0x505, 0x000000A3, 0x506, 0x0000005E, 0x507, 0x00000000,
0x508, 0x0000002B, 0x509, 0x000000A4, 0x50A, 0x0000005E,
0x50B, 0x00000000, 0x50C, 0x0000004F, 0x50D, 0x000000A4,
0x50E, 0x00000000, 0x50F, 0x00000000, 0x512, 0x0000001C,
0x514, 0x0000000A, 0x516, 0x0000000A, 0x521, 0x0000002F,
0x525, 0x0000004F, 0x551, 0x00000010, 0x559, 0x00000002,
0x55C, 0x00000050, 0x55D, 0x000000FF, 0x577, 0x0000000B,
0x5BE, 0x00000064, 0x605, 0x00000030, 0x608, 0x0000000E,
0x609, 0x00000022, 0x60C, 0x00000018, 0x6A0, 0x000000FF,
0x6A1, 0x000000FF, 0x6A2, 0x000000FF, 0x6A3, 0x000000FF,
0x6A4, 0x000000FF, 0x6A5, 0x000000FF, 0x6DE, 0x00000084,
0x620, 0x000000FF, 0x621, 0x000000FF, 0x622, 0x000000FF,
0x623, 0x000000FF, 0x624, 0x000000FF, 0x625, 0x000000FF,
0x626, 0x000000FF, 0x627, 0x000000FF, 0x638, 0x00000050,
0x63C, 0x0000000A, 0x63D, 0x0000000A, 0x63E, 0x0000000E,
0x63F, 0x0000000E, 0x640, 0x00000040, 0x642, 0x00000040,
0x643, 0x00000000, 0x652, 0x000000C8, 0x66E, 0x00000005,
0x718, 0x00000040, 0x7D4, 0x00000098,
};
void odm_read_and_config_mp_8822b_mac_reg(struct phy_dm_struct *dm)
{
u32 i = 0;
u8 c_cond;
bool is_matched = true, is_skipped = false;
u32 array_len = sizeof(array_mp_8822b_mac_reg) / sizeof(u32);
u32 *array = array_mp_8822b_mac_reg;
u32 v1 = 0, v2 = 0, pre_v1 = 0, pre_v2 = 0;
ODM_RT_TRACE(dm, ODM_COMP_INIT,
"===> %s\n", __func__);
for (; (i + 1) < array_len; i = i + 2) {
v1 = array[i];
v2 = array[i + 1];
if (v1 & BIT(31)) { /* positive condition*/
c_cond = (u8)((v1 & (BIT(29) | BIT(28))) >> 28);
if (c_cond == COND_ENDIF) { /*end*/
is_matched = true;
is_skipped = false;
ODM_RT_TRACE(dm, ODM_COMP_INIT, "ENDIF\n");
} else if (c_cond == COND_ELSE) { /*else*/
is_matched = is_skipped ? false : true;
ODM_RT_TRACE(dm, ODM_COMP_INIT, "ELSE\n");
} else { /*if , else if*/
pre_v1 = v1;
pre_v2 = v2;
ODM_RT_TRACE(dm, ODM_COMP_INIT,
"IF or ELSE IF\n");
}
} else if (v1 & BIT(30)) { /*negative condition*/
if (is_skipped) {
is_matched = false;
continue;
}
if (check_positive(dm, pre_v1, pre_v2, v1, v2)) {
is_matched = true;
is_skipped = true;
} else {
is_matched = false;
is_skipped = false;
}
} else if (is_matched) {
odm_config_mac_8822b(dm, v1, (u8)v2);
}
}
}
u32 odm_get_version_mp_8822b_mac_reg(void) { return 67; }

View File

@ -0,0 +1,38 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*Image2HeaderVersion: 3.2*/
#ifndef __INC_MP_MAC_HW_IMG_8822B_H
#define __INC_MP_MAC_HW_IMG_8822B_H
/******************************************************************************
* mac_reg.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_mac_reg(/* tc: Test Chip, mp: mp Chip*/
struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_mac_reg(void);
#endif

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,129 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*Image2HeaderVersion: 3.2*/
#ifndef __INC_MP_RF_HW_IMG_8822B_H
#define __INC_MP_RF_HW_IMG_8822B_H
/******************************************************************************
* radioa.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_radioa(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_radioa(void);
/******************************************************************************
* radiob.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_radiob(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_radiob(void);
/******************************************************************************
* txpowertrack.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack(void);
/******************************************************************************
* txpowertrack_type0.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type0(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type0(void);
/******************************************************************************
* txpowertrack_type1.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type1(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type1(void);
/******************************************************************************
* txpowertrack_type2.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type2(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type2(void);
/******************************************************************************
* txpowertrack_type3_type5.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type3_type5(
struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type3_type5(void);
/******************************************************************************
* txpowertrack_type4.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type4(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type4(void);
/******************************************************************************
* txpowertrack_type6.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type6(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type6(void);
/******************************************************************************
* txpowertrack_type7.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type7(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type7(void);
/******************************************************************************
* txpowertrack_type8.TXT
*****************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type8(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type8(void);
/******************************************************************************
* txpowertrack_type9.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpowertrack_type9(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpowertrack_type9(void);
/******************************************************************************
* txpwr_lmt.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpwr_lmt(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpwr_lmt(void);
/******************************************************************************
* txpwr_lmt_type5.TXT
******************************************************************************/
void odm_read_and_config_mp_8822b_txpwr_lmt_type5(struct phy_dm_struct *dm);
u32 odm_get_version_mp_8822b_txpwr_lmt_type5(void);
#endif

View File

@ -0,0 +1,351 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "../mp_precomp.h"
#include "../phydm_precomp.h"
static bool
get_mix_mode_tx_agc_bb_swing_offset_8822b(void *dm_void,
enum pwrtrack_method method,
u8 rf_path, u8 tx_power_index_offest)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
u8 bb_swing_upper_bound = cali_info->default_ofdm_index + 10;
u8 bb_swing_lower_bound = 0;
s8 tx_agc_index = 0;
u8 tx_bb_swing_index = cali_info->default_ofdm_index;
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"Path_%d cali_info->absolute_ofdm_swing_idx[rf_path]=%d, tx_power_index_offest=%d\n",
rf_path, cali_info->absolute_ofdm_swing_idx[rf_path],
tx_power_index_offest);
if (tx_power_index_offest > 0XF)
tx_power_index_offest = 0XF;
if (cali_info->absolute_ofdm_swing_idx[rf_path] >= 0 &&
cali_info->absolute_ofdm_swing_idx[rf_path] <=
tx_power_index_offest) {
tx_agc_index = cali_info->absolute_ofdm_swing_idx[rf_path];
tx_bb_swing_index = cali_info->default_ofdm_index;
} else if (cali_info->absolute_ofdm_swing_idx[rf_path] >
tx_power_index_offest) {
tx_agc_index = tx_power_index_offest;
cali_info->remnant_ofdm_swing_idx[rf_path] =
cali_info->absolute_ofdm_swing_idx[rf_path] -
tx_power_index_offest;
tx_bb_swing_index = cali_info->default_ofdm_index +
cali_info->remnant_ofdm_swing_idx[rf_path];
if (tx_bb_swing_index > bb_swing_upper_bound)
tx_bb_swing_index = bb_swing_upper_bound;
} else {
tx_agc_index = 0;
if (cali_info->default_ofdm_index >
(cali_info->absolute_ofdm_swing_idx[rf_path] * (-1)))
tx_bb_swing_index =
cali_info->default_ofdm_index +
cali_info->absolute_ofdm_swing_idx[rf_path];
else
tx_bb_swing_index = bb_swing_lower_bound;
if (tx_bb_swing_index < bb_swing_lower_bound)
tx_bb_swing_index = bb_swing_lower_bound;
}
cali_info->absolute_ofdm_swing_idx[rf_path] = tx_agc_index;
cali_info->bb_swing_idx_ofdm[rf_path] = tx_bb_swing_index;
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"MixMode Offset Path_%d cali_info->absolute_ofdm_swing_idx[rf_path]=%d cali_info->bb_swing_idx_ofdm[rf_path]=%d tx_power_index_offest=%d\n",
rf_path, cali_info->absolute_ofdm_swing_idx[rf_path],
cali_info->bb_swing_idx_ofdm[rf_path], tx_power_index_offest);
return true;
}
void odm_tx_pwr_track_set_pwr8822b(void *dm_void, enum pwrtrack_method method,
u8 rf_path, u8 channel_mapped_index)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
u8 tx_power_index_offest = 0;
u8 tx_power_index = 0;
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
struct rtl_phy *rtlphy = &rtlpriv->phy;
u8 channel = rtlphy->current_channel;
u8 band_width = rtlphy->current_chan_bw;
u8 tx_rate = 0xFF;
if (!dm->mp_mode) {
u16 rate = *dm->forced_data_rate;
if (!rate) /*auto rate*/
tx_rate = dm->tx_rate;
else /*force rate*/
tx_rate = (u8)rate;
}
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK, "Call:%s tx_rate=0x%X\n",
__func__, tx_rate);
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"pRF->default_ofdm_index=%d pRF->default_cck_index=%d\n",
cali_info->default_ofdm_index,
cali_info->default_cck_index);
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"pRF->absolute_ofdm_swing_idx=%d pRF->remnant_ofdm_swing_idx=%d pRF->absolute_cck_swing_idx=%d pRF->remnant_cck_swing_idx=%d rf_path=%d\n",
cali_info->absolute_ofdm_swing_idx[rf_path],
cali_info->remnant_ofdm_swing_idx[rf_path],
cali_info->absolute_cck_swing_idx[rf_path],
cali_info->remnant_cck_swing_idx, rf_path);
if (dm->number_linked_client != 0)
tx_power_index = odm_get_tx_power_index(
dm, (enum odm_rf_radio_path)rf_path, tx_rate,
band_width, channel);
if (tx_power_index >= 63)
tx_power_index = 63;
tx_power_index_offest = 63 - tx_power_index;
ODM_RT_TRACE(dm, ODM_COMP_TX_PWR_TRACK,
"tx_power_index=%d tx_power_index_offest=%d rf_path=%d\n",
tx_power_index, tx_power_index_offest, rf_path);
if (method ==
BBSWING) { /*use for mp driver clean power tracking status*/
switch (rf_path) {
case ODM_RF_PATH_A:
odm_set_bb_reg(
dm, 0xC94, (BIT(29) | BIT(28) | BIT(27) |
BIT(26) | BIT(25)),
cali_info->absolute_ofdm_swing_idx[rf_path]);
odm_set_bb_reg(
dm, REG_A_TX_SCALE_JAGUAR, 0xFFE00000,
tx_scaling_table_jaguar
[cali_info
->bb_swing_idx_ofdm[rf_path]]);
break;
case ODM_RF_PATH_B:
odm_set_bb_reg(
dm, 0xE94, (BIT(29) | BIT(28) | BIT(27) |
BIT(26) | BIT(25)),
cali_info->absolute_ofdm_swing_idx[rf_path]);
odm_set_bb_reg(
dm, REG_B_TX_SCALE_JAGUAR, 0xFFE00000,
tx_scaling_table_jaguar
[cali_info
->bb_swing_idx_ofdm[rf_path]]);
break;
default:
break;
}
} else if (method == MIX_MODE) {
switch (rf_path) {
case ODM_RF_PATH_A:
get_mix_mode_tx_agc_bb_swing_offset_8822b(
dm, method, rf_path, tx_power_index_offest);
odm_set_bb_reg(
dm, 0xC94, (BIT(29) | BIT(28) | BIT(27) |
BIT(26) | BIT(25)),
cali_info->absolute_ofdm_swing_idx[rf_path]);
odm_set_bb_reg(
dm, REG_A_TX_SCALE_JAGUAR, 0xFFE00000,
tx_scaling_table_jaguar
[cali_info
->bb_swing_idx_ofdm[rf_path]]);
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"TXAGC(0xC94)=0x%x BBSwing(0xc1c)=0x%x BBSwingIndex=%d rf_path=%d\n",
odm_get_bb_reg(dm, 0xC94,
(BIT(29) | BIT(28) | BIT(27) |
BIT(26) | BIT(25))),
odm_get_bb_reg(dm, 0xc1c, 0xFFE00000),
cali_info->bb_swing_idx_ofdm[rf_path], rf_path);
break;
case ODM_RF_PATH_B:
get_mix_mode_tx_agc_bb_swing_offset_8822b(
dm, method, rf_path, tx_power_index_offest);
odm_set_bb_reg(
dm, 0xE94, (BIT(29) | BIT(28) | BIT(27) |
BIT(26) | BIT(25)),
cali_info->absolute_ofdm_swing_idx[rf_path]);
odm_set_bb_reg(
dm, REG_B_TX_SCALE_JAGUAR, 0xFFE00000,
tx_scaling_table_jaguar
[cali_info
->bb_swing_idx_ofdm[rf_path]]);
ODM_RT_TRACE(
dm, ODM_COMP_TX_PWR_TRACK,
"TXAGC(0xE94)=0x%x BBSwing(0xe1c)=0x%x BBSwingIndex=%d rf_path=%d\n",
odm_get_bb_reg(dm, 0xE94,
(BIT(29) | BIT(28) | BIT(27) |
BIT(26) | BIT(25))),
odm_get_bb_reg(dm, 0xe1c, 0xFFE00000),
cali_info->bb_swing_idx_ofdm[rf_path], rf_path);
break;
default:
break;
}
}
}
void get_delta_swing_table_8822b(void *dm_void, u8 **temperature_up_a,
u8 **temperature_down_a, u8 **temperature_up_b,
u8 **temperature_down_b)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
struct dm_rf_calibration_struct *cali_info = &dm->rf_calibrate_info;
struct rtl_priv *rtlpriv = (struct rtl_priv *)dm->adapter;
struct rtl_phy *rtlphy = &rtlpriv->phy;
u8 channel = rtlphy->current_channel;
*temperature_up_a = cali_info->delta_swing_table_idx_2ga_p;
*temperature_down_a = cali_info->delta_swing_table_idx_2ga_n;
*temperature_up_b = cali_info->delta_swing_table_idx_2gb_p;
*temperature_down_b = cali_info->delta_swing_table_idx_2gb_n;
if (channel >= 36 && channel <= 64) {
*temperature_up_a = cali_info->delta_swing_table_idx_5ga_p[0];
*temperature_down_a = cali_info->delta_swing_table_idx_5ga_n[0];
*temperature_up_b = cali_info->delta_swing_table_idx_5gb_p[0];
*temperature_down_b = cali_info->delta_swing_table_idx_5gb_n[0];
} else if (channel >= 100 && channel <= 144) {
*temperature_up_a = cali_info->delta_swing_table_idx_5ga_p[1];
*temperature_down_a = cali_info->delta_swing_table_idx_5ga_n[1];
*temperature_up_b = cali_info->delta_swing_table_idx_5gb_p[1];
*temperature_down_b = cali_info->delta_swing_table_idx_5gb_n[1];
} else if (channel >= 149 && channel <= 177) {
*temperature_up_a = cali_info->delta_swing_table_idx_5ga_p[2];
*temperature_down_a = cali_info->delta_swing_table_idx_5ga_n[2];
*temperature_up_b = cali_info->delta_swing_table_idx_5gb_p[2];
*temperature_down_b = cali_info->delta_swing_table_idx_5gb_n[2];
}
}
static void _phy_lc_calibrate_8822b(struct phy_dm_struct *dm)
{
u32 lc_cal = 0, cnt = 0;
/*backup RF0x18*/
lc_cal = odm_get_rf_reg(dm, ODM_RF_PATH_A, RF_CHNLBW, RFREGOFFSETMASK);
/*Start LCK*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, RF_CHNLBW, RFREGOFFSETMASK,
lc_cal | 0x08000);
ODM_delay_ms(100);
for (cnt = 0; cnt < 100; cnt++) {
if (odm_get_rf_reg(dm, ODM_RF_PATH_A, RF_CHNLBW, 0x8000) != 0x1)
break;
ODM_delay_ms(10);
}
/*Recover channel number*/
odm_set_rf_reg(dm, ODM_RF_PATH_A, RF_CHNLBW, RFREGOFFSETMASK, lc_cal);
}
void phy_lc_calibrate_8822b(void *dm_void)
{
struct phy_dm_struct *dm = (struct phy_dm_struct *)dm_void;
bool is_start_cont_tx = false, is_single_tone = false,
is_carrier_suppression = false;
u64 start_time;
u64 progressing_time;
if (is_start_cont_tx || is_single_tone || is_carrier_suppression) {
ODM_RT_TRACE(dm, ODM_COMP_CALIBRATION,
"[LCK]continues TX ing !!! LCK return\n");
return;
}
start_time = odm_get_current_time(dm);
_phy_lc_calibrate_8822b(dm);
progressing_time = odm_get_progressing_time(dm, start_time);
ODM_RT_TRACE(dm, ODM_COMP_CALIBRATION,
"[LCK]LCK progressing_time = %lld\n", progressing_time);
}
void configure_txpower_track_8822b(struct txpwrtrack_cfg *config)
{
config->swing_table_size_cck = TXSCALE_TABLE_SIZE;
config->swing_table_size_ofdm = TXSCALE_TABLE_SIZE;
config->threshold_iqk = IQK_THRESHOLD;
config->threshold_dpk = DPK_THRESHOLD;
config->average_thermal_num = AVG_THERMAL_NUM_8822B;
config->rf_path_count = MAX_PATH_NUM_8822B;
config->thermal_reg_addr = RF_T_METER_8822B;
config->odm_tx_pwr_track_set_pwr = odm_tx_pwr_track_set_pwr8822b;
config->do_iqk = do_iqk_8822b;
config->phy_lc_calibrate = phy_lc_calibrate_8822b;
config->get_delta_swing_table = get_delta_swing_table_8822b;
}
void phy_set_rf_path_switch_8822b(struct phy_dm_struct *dm, bool is_main)
{
/*BY SY Request */
odm_set_bb_reg(dm, 0x4C, (BIT(24) | BIT(23)), 0x2);
odm_set_bb_reg(dm, 0x974, 0xff, 0xff);
/*odm_set_bb_reg(dm, 0x1991, 0x3, 0x0);*/
odm_set_bb_reg(dm, 0x1990, (BIT(9) | BIT(8)), 0x0);
/*odm_set_bb_reg(dm, 0xCBE, 0x8, 0x0);*/
odm_set_bb_reg(dm, 0xCBC, BIT(19), 0x0);
odm_set_bb_reg(dm, 0xCB4, 0xff, 0x77);
odm_set_bb_reg(dm, 0x70, MASKBYTE3, 0x0e);
odm_set_bb_reg(dm, 0x1704, MASKDWORD, 0x0000ff00);
odm_set_bb_reg(dm, 0x1700, MASKDWORD, 0xc00f0038);
if (is_main) {
/*odm_set_bb_reg(dm, 0xCBD, 0x3, 0x2); WiFi */
odm_set_bb_reg(dm, 0xCBC, (BIT(9) | BIT(8)), 0x2); /*WiFi */
} else {
/*odm_set_bb_reg(dm, 0xCBD, 0x3, 0x1); BT*/
odm_set_bb_reg(dm, 0xCBC, (BIT(9) | BIT(8)), 0x1); /*BT*/
}
}

View File

@ -0,0 +1,45 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HAL_PHY_RF_8822B_H__
#define __HAL_PHY_RF_8822B_H__
#define AVG_THERMAL_NUM_8822B 4
#define RF_T_METER_8822B 0x42
void configure_txpower_track_8822b(struct txpwrtrack_cfg *config);
void odm_tx_pwr_track_set_pwr8822b(void *dm_void, enum pwrtrack_method method,
u8 rf_path, u8 channel_mapped_index);
void get_delta_swing_table_8822b(void *dm_void, u8 **temperature_up_a,
u8 **temperature_down_a, u8 **temperature_up_b,
u8 **temperature_down_b);
void phy_lc_calibrate_8822b(void *dm_void);
void phy_set_rf_path_switch_8822b(struct phy_dm_struct *dm, bool is_main);
#endif /* #ifndef __HAL_PHY_RF_8822B_H__ */

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,84 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __INC_PHYDM_API_H_8822B__
#define __INC_PHYDM_API_H_8822B__
/*2016.08.01 (HW user guide version: R27, SW user guide version: R05,
* Modification: R31)
*/
#define PHY_CONFIG_VERSION_8822B "27.5.31"
#define INVALID_RF_DATA 0xffffffff
#define INVALID_TXAGC_DATA 0xff
#define config_phydm_read_rf_check_8822b(data) (data != INVALID_RF_DATA)
#define config_phydm_read_txagc_check_8822b(data) (data != INVALID_TXAGC_DATA)
u32 config_phydm_read_rf_reg_8822b(struct phy_dm_struct *dm,
enum odm_rf_radio_path rf_path, u32 reg_addr,
u32 bit_mask);
bool config_phydm_write_rf_reg_8822b(struct phy_dm_struct *dm,
enum odm_rf_radio_path rf_path,
u32 reg_addr, u32 bit_mask, u32 data);
bool config_phydm_write_txagc_8822b(struct phy_dm_struct *dm, u32 power_index,
enum odm_rf_radio_path path, u8 hw_rate);
u8 config_phydm_read_txagc_8822b(struct phy_dm_struct *dm,
enum odm_rf_radio_path path, u8 hw_rate);
bool config_phydm_switch_band_8822b(struct phy_dm_struct *dm, u8 central_ch);
bool config_phydm_switch_channel_8822b(struct phy_dm_struct *dm, u8 central_ch);
bool config_phydm_switch_bandwidth_8822b(struct phy_dm_struct *dm,
u8 primary_ch_idx,
enum odm_bw bandwidth);
bool config_phydm_switch_channel_bw_8822b(struct phy_dm_struct *dm,
u8 central_ch, u8 primary_ch_idx,
enum odm_bw bandwidth);
bool config_phydm_trx_mode_8822b(struct phy_dm_struct *dm,
enum odm_rf_path tx_path,
enum odm_rf_path rx_path, bool is_tx2_path);
bool config_phydm_parameter_init(struct phy_dm_struct *dm,
enum odm_parameter_init type);
/* ======================================================================== */
/* These following functions can be used for PHY DM only*/
bool phydm_write_txagc_1byte_8822b(struct phy_dm_struct *dm, u32 power_index,
enum odm_rf_radio_path path, u8 hw_rate);
void phydm_init_hw_info_by_rfe_type_8822b(struct phy_dm_struct *dm);
s32 phydm_get_condition_number_8822B(struct phy_dm_struct *dm);
/* ======================================================================== */
#endif /* __INC_PHYDM_API_H_8822B__ */

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,48 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDM_IQK_8822B_H__
#define __PHYDM_IQK_8822B_H__
/*--------------------------Define Parameters-------------------------------*/
#define MAC_REG_NUM_8822B 2
#define BB_REG_NUM_8822B 13
#define RF_REG_NUM_8822B 5
#define LOK_delay_8822B 2
#define GS_delay_8822B 2
#define WBIQK_delay_8822B 2
#define TXIQK 0
#define RXIQK 1
#define SS_8822B 2
/*------------------------End Define Parameters-------------------------------*/
void do_iqk_8822b(void *dm_void, u8 delta_thermal_index, u8 thermal_value,
u8 threshold);
void phy_iq_calibrate_8822b(void *dm_void, bool clear);
#endif /* #ifndef __PHYDM_IQK_8822B_H__*/

View File

@ -0,0 +1,168 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "../mp_precomp.h"
#include "../phydm_precomp.h"
void odm_config_rf_reg_8822b(struct phy_dm_struct *dm, u32 addr, u32 data,
enum odm_rf_radio_path RF_PATH, u32 reg_addr)
{
if (addr == 0xffe) {
ODM_sleep_ms(50);
} else if (addr == 0xfe) {
ODM_delay_us(100);
} else {
odm_set_rf_reg(dm, RF_PATH, reg_addr, RFREGOFFSETMASK, data);
/* Add 1us delay between BB/RF register setting. */
ODM_delay_us(1);
}
}
void odm_config_rf_radio_a_8822b(struct phy_dm_struct *dm, u32 addr, u32 data)
{
u32 content = 0x1000; /* RF_Content: radioa_txt */
u32 maskfor_phy_set = (u32)(content & 0xE000);
odm_config_rf_reg_8822b(dm, addr, data, ODM_RF_PATH_A,
addr | maskfor_phy_set);
ODM_RT_TRACE(
dm, ODM_COMP_INIT,
"===> odm_config_rf_with_header_file: [RadioA] %08X %08X\n",
addr, data);
}
void odm_config_rf_radio_b_8822b(struct phy_dm_struct *dm, u32 addr, u32 data)
{
u32 content = 0x1001; /* RF_Content: radiob_txt */
u32 maskfor_phy_set = (u32)(content & 0xE000);
odm_config_rf_reg_8822b(dm, addr, data, ODM_RF_PATH_B,
addr | maskfor_phy_set);
ODM_RT_TRACE(
dm, ODM_COMP_INIT,
"===> odm_config_rf_with_header_file: [RadioB] %08X %08X\n",
addr, data);
}
void odm_config_mac_8822b(struct phy_dm_struct *dm, u32 addr, u8 data)
{
odm_write_1byte(dm, addr, data);
ODM_RT_TRACE(
dm, ODM_COMP_INIT,
"===> odm_config_mac_with_header_file: [MAC_REG] %08X %08X\n",
addr, data);
}
void odm_update_agc_big_jump_lmt_8822b(struct phy_dm_struct *dm, u32 addr,
u32 data)
{
struct dig_thres *dig_tab = &dm->dm_dig_table;
u8 rf_gain_idx = (u8)((data & 0xFF000000) >> 24);
u8 bb_gain_idx = (u8)((data & 0x00ff0000) >> 16);
u8 agc_table_idx = (u8)((data & 0x00000f00) >> 8);
static bool is_limit;
if (addr != 0x81c)
return;
if (bb_gain_idx > 0x3c) {
if ((rf_gain_idx == dig_tab->rf_gain_idx) && !is_limit) {
is_limit = true;
dig_tab->big_jump_lmt[agc_table_idx] = bb_gain_idx - 2;
ODM_RT_TRACE(
dm, ODM_COMP_DIG,
"===> [AGC_TAB] big_jump_lmt [%d] = 0x%x\n",
agc_table_idx,
dig_tab->big_jump_lmt[agc_table_idx]);
}
} else {
is_limit = false;
}
dig_tab->rf_gain_idx = rf_gain_idx;
}
void odm_config_bb_agc_8822b(struct phy_dm_struct *dm, u32 addr, u32 bitmask,
u32 data)
{
odm_update_agc_big_jump_lmt_8822b(dm, addr, data);
odm_set_bb_reg(dm, addr, bitmask, data);
/* Add 1us delay between BB/RF register setting. */
ODM_delay_us(1);
ODM_RT_TRACE(dm, ODM_COMP_INIT, "===> %s: [AGC_TAB] %08X %08X\n",
__func__, addr, data);
}
void odm_config_bb_phy_reg_pg_8822b(struct phy_dm_struct *dm, u32 band,
u32 rf_path, u32 tx_num, u32 addr,
u32 bitmask, u32 data)
{
if (addr == 0xfe || addr == 0xffe) {
ODM_sleep_ms(50);
} else {
phy_store_tx_power_by_rate(dm->adapter, band, rf_path, tx_num,
addr, bitmask, data);
}
ODM_RT_TRACE(dm, ODM_COMP_INIT, "===> %s: [PHY_REG] %08X %08X %08X\n",
__func__, addr, bitmask, data);
}
void odm_config_bb_phy_8822b(struct phy_dm_struct *dm, u32 addr, u32 bitmask,
u32 data)
{
if (addr == 0xfe)
ODM_sleep_ms(50);
else if (addr == 0xfd)
ODM_delay_ms(5);
else if (addr == 0xfc)
ODM_delay_ms(1);
else if (addr == 0xfb)
ODM_delay_us(50);
else if (addr == 0xfa)
ODM_delay_us(5);
else if (addr == 0xf9)
ODM_delay_us(1);
else
odm_set_bb_reg(dm, addr, bitmask, data);
/* Add 1us delay between BB/RF register setting. */
ODM_delay_us(1);
ODM_RT_TRACE(dm, ODM_COMP_INIT, "===> %s: [PHY_REG] %08X %08X\n",
__func__, addr, data);
}
void odm_config_bb_txpwr_lmt_8822b(struct phy_dm_struct *dm, u8 *regulation,
u8 *band, u8 *bandwidth, u8 *rate_section,
u8 *rf_path, u8 *channel, u8 *power_limit)
{
phy_set_tx_power_limit(dm, regulation, band, bandwidth, rate_section,
rf_path, channel, power_limit);
}

View File

@ -0,0 +1,54 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __INC_ODM_REGCONFIG_H_8822B
#define __INC_ODM_REGCONFIG_H_8822B
void odm_config_rf_reg_8822b(struct phy_dm_struct *dm, u32 addr, u32 data,
enum odm_rf_radio_path RF_PATH, u32 reg_addr);
void odm_config_rf_radio_a_8822b(struct phy_dm_struct *dm, u32 addr, u32 data);
void odm_config_rf_radio_b_8822b(struct phy_dm_struct *dm, u32 addr, u32 data);
void odm_config_mac_8822b(struct phy_dm_struct *dm, u32 addr, u8 data);
void odm_update_agc_big_jump_lmt_8822b(struct phy_dm_struct *dm, u32 addr,
u32 data);
void odm_config_bb_agc_8822b(struct phy_dm_struct *dm, u32 addr, u32 bitmask,
u32 data);
void odm_config_bb_phy_reg_pg_8822b(struct phy_dm_struct *dm, u32 band,
u32 rf_path, u32 tx_num, u32 addr,
u32 bitmask, u32 data);
void odm_config_bb_phy_8822b(struct phy_dm_struct *dm, u32 addr, u32 bitmask,
u32 data);
void odm_config_bb_txpwr_lmt_8822b(struct phy_dm_struct *dm, u8 *regulation,
u8 *band, u8 *bandwidth, u8 *rate_section,
u8 *rf_path, u8 *channel, u8 *power_limit);
#endif /* RTL8822B_SUPPORT == 1*/

View File

@ -0,0 +1,225 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "../mp_precomp.h"
#include "../phydm_precomp.h"
static void phydm_dynamic_switch_htstf_mumimo_8822b(struct phy_dm_struct *dm)
{
/*if rssi > 40dBm, enable HT-STF gain controller,
*otherwise, if rssi < 40dBm, disable the controller
*/
/*add by Chun-Hung Ho 20160711 */
if (dm->rssi_min >= 40)
odm_set_bb_reg(dm, 0x8d8, BIT(17), 0x1);
else if (dm->rssi_min < 35)
odm_set_bb_reg(dm, 0x8d8, BIT(17), 0x0);
ODM_RT_TRACE(dm, ODM_COMP_COMMON, "%s, rssi_min = %d\n", __func__,
dm->rssi_min);
}
static void _set_tx_a_cali_value(struct phy_dm_struct *dm, u8 rf_path,
u8 offset, u8 tx_a_bias_offset)
{
u32 modi_tx_a_value = 0;
u8 tmp1_byte = 0;
bool is_minus = false;
u8 comp_value = 0;
switch (offset) {
case 0x0:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X10124);
break;
case 0x1:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X10524);
break;
case 0x2:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X10924);
break;
case 0x3:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X10D24);
break;
case 0x4:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X30164);
break;
case 0x5:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X30564);
break;
case 0x6:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X30964);
break;
case 0x7:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X30D64);
break;
case 0x8:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X50195);
break;
case 0x9:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X50595);
break;
case 0xa:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X50995);
break;
case 0xb:
odm_set_rf_reg(dm, rf_path, 0x18, 0xFFFFF, 0X50D95);
break;
default:
ODM_RT_TRACE(dm, ODM_COMP_COMMON,
"Invalid TxA band offset...\n");
return;
}
/* Get TxA value */
modi_tx_a_value = odm_get_rf_reg(dm, rf_path, 0x61, 0xFFFFF);
tmp1_byte = (u8)modi_tx_a_value & (BIT(3) | BIT(2) | BIT(1) | BIT(0));
/* check how much need to calibration */
switch (tx_a_bias_offset) {
case 0xF6:
is_minus = true;
comp_value = 3;
break;
case 0xF4:
is_minus = true;
comp_value = 2;
break;
case 0xF2:
is_minus = true;
comp_value = 1;
break;
case 0xF3:
is_minus = false;
comp_value = 1;
break;
case 0xF5:
is_minus = false;
comp_value = 2;
break;
case 0xF7:
is_minus = false;
comp_value = 3;
break;
case 0xF9:
is_minus = false;
comp_value = 4;
break;
/* do nothing case */
case 0xF0:
default:
ODM_RT_TRACE(dm, ODM_COMP_COMMON,
"No need to do TxA bias current calibration\n");
return;
}
/* calc correct value to calibrate */
if (is_minus) {
if (tmp1_byte >= comp_value) {
tmp1_byte -= comp_value;
/*modi_tx_a_value += tmp1_byte;*/
} else {
tmp1_byte = 0;
}
} else {
tmp1_byte += comp_value;
if (tmp1_byte >= 7)
tmp1_byte = 7;
}
/* Write back to RF reg */
odm_set_rf_reg(dm, rf_path, 0x30, 0xFFFF,
(offset << 12 | (modi_tx_a_value & 0xFF0) | tmp1_byte));
}
static void _txa_bias_cali_4_each_path(struct phy_dm_struct *dm, u8 rf_path,
u8 efuse_value)
{
/* switch on set TxA bias */
odm_set_rf_reg(dm, rf_path, 0xEF, 0xFFFFF, 0x200);
/* Set 12 sets of TxA value */
_set_tx_a_cali_value(dm, rf_path, 0x0, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x1, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x2, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x3, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x4, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x5, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x6, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x7, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x8, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0x9, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0xa, efuse_value);
_set_tx_a_cali_value(dm, rf_path, 0xb, efuse_value);
/* switch off set TxA bias */
odm_set_rf_reg(dm, rf_path, 0xEF, 0xFFFFF, 0x0);
}
/*
* for 8822B PCIE D-cut patch only
* Normal driver and MP driver need this patch
*/
void phydm_txcurrentcalibration(struct phy_dm_struct *dm)
{
u8 efuse0x3D8, efuse0x3D7;
u32 orig_rf0x18_path_a = 0, orig_rf0x18_path_b = 0;
/* save original 0x18 value */
orig_rf0x18_path_a = odm_get_rf_reg(dm, ODM_RF_PATH_A, 0x18, 0xFFFFF);
orig_rf0x18_path_b = odm_get_rf_reg(dm, ODM_RF_PATH_B, 0x18, 0xFFFFF);
/* define efuse content */
efuse0x3D8 = dm->efuse0x3d8;
efuse0x3D7 = dm->efuse0x3d7;
/* check efuse content to judge whether need to calibration or not */
if (efuse0x3D7 == 0xFF) {
ODM_RT_TRACE(
dm, ODM_COMP_COMMON,
"efuse content 0x3D7 == 0xFF, No need to do TxA cali\n");
return;
}
/* write RF register for calibration */
_txa_bias_cali_4_each_path(dm, ODM_RF_PATH_A, efuse0x3D7);
_txa_bias_cali_4_each_path(dm, ODM_RF_PATH_B, efuse0x3D8);
/* restore original 0x18 value */
odm_set_rf_reg(dm, ODM_RF_PATH_A, 0x18, 0xFFFFF, orig_rf0x18_path_a);
odm_set_rf_reg(dm, ODM_RF_PATH_B, 0x18, 0xFFFFF, orig_rf0x18_path_b);
}
void phydm_hwsetting_8822b(struct phy_dm_struct *dm)
{
phydm_dynamic_switch_htstf_mumimo_8822b(dm);
}

View File

@ -0,0 +1,30 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __ODM_RTL8822B_H__
#define __ODM_RTL8822B_H__
void phydm_hwsetting_8822b(struct phy_dm_struct *dm);
#endif /* #define __ODM_RTL8822B_H__ */

View File

@ -0,0 +1,34 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
/*RTL8822B PHY Parameters*/
/*
* [Caution]
* Since 01/Aug/2015, the commit rules will be simplified.
* You do not need to fill up the version.h anymore,
* only the maintenance supervisor fills it before formal release.
*/
#define RELEASE_DATE_8822B 20161103
#define COMMIT_BY_8822B "BB_JOE"
#define RELEASE_VERSION_8822B 67

View File

@ -0,0 +1,874 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#include "mp_precomp.h"
#include "phydm_precomp.h"
#include <linux/module.h>
static int _rtl_phydm_init_com_info(struct rtl_priv *rtlpriv,
enum odm_ic_type ic_type,
struct rtl_phydm_params *params)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
struct rtl_phy *rtlphy = &rtlpriv->phy;
struct rtl_mac *mac = rtl_mac(rtlpriv);
struct rtl_ps_ctl *ppsc = rtl_psc(rtlpriv);
struct rtl_efuse *rtlefuse = rtl_efuse(rtlpriv);
u8 odm_board_type = ODM_BOARD_DEFAULT;
u32 support_ability;
int i;
dm->adapter = (void *)rtlpriv;
odm_cmn_info_init(dm, ODM_CMNINFO_PLATFORM, ODM_CE);
odm_cmn_info_init(dm, ODM_CMNINFO_IC_TYPE, ic_type);
odm_cmn_info_init(dm, ODM_CMNINFO_INTERFACE, ODM_ITRF_PCIE);
odm_cmn_info_init(dm, ODM_CMNINFO_MP_TEST_CHIP, params->mp_chip);
odm_cmn_info_init(dm, ODM_CMNINFO_PATCH_ID, rtlhal->oem_id);
odm_cmn_info_init(dm, ODM_CMNINFO_BWIFI_TEST, 1);
if (rtlphy->rf_type == RF_1T1R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_1T1R);
else if (rtlphy->rf_type == RF_1T2R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_1T2R);
else if (rtlphy->rf_type == RF_2T2R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_2T2R);
else if (rtlphy->rf_type == RF_2T2R_GREEN)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_2T2R_GREEN);
else if (rtlphy->rf_type == RF_2T3R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_2T3R);
else if (rtlphy->rf_type == RF_2T4R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_2T4R);
else if (rtlphy->rf_type == RF_3T3R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_3T3R);
else if (rtlphy->rf_type == RF_3T4R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_3T4R);
else if (rtlphy->rf_type == RF_4T4R)
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_4T4R);
else
odm_cmn_info_init(dm, ODM_CMNINFO_RF_TYPE, ODM_XTXR);
/* 1 ======= BoardType: ODM_CMNINFO_BOARD_TYPE ======= */
if (rtlhal->external_lna_2g != 0) {
odm_board_type |= ODM_BOARD_EXT_LNA;
odm_cmn_info_init(dm, ODM_CMNINFO_EXT_LNA, 1);
}
if (rtlhal->external_lna_5g != 0) {
odm_board_type |= ODM_BOARD_EXT_LNA_5G;
odm_cmn_info_init(dm, ODM_CMNINFO_5G_EXT_LNA, 1);
}
if (rtlhal->external_pa_2g != 0) {
odm_board_type |= ODM_BOARD_EXT_PA;
odm_cmn_info_init(dm, ODM_CMNINFO_EXT_PA, 1);
}
if (rtlhal->external_pa_5g != 0) {
odm_board_type |= ODM_BOARD_EXT_PA_5G;
odm_cmn_info_init(dm, ODM_CMNINFO_5G_EXT_PA, 1);
}
if (rtlpriv->cfg->ops->get_btc_status())
odm_board_type |= ODM_BOARD_BT;
odm_cmn_info_init(dm, ODM_CMNINFO_BOARD_TYPE, odm_board_type);
/* 1 ============== End of BoardType ============== */
odm_cmn_info_init(dm, ODM_CMNINFO_GPA, rtlhal->type_gpa);
odm_cmn_info_init(dm, ODM_CMNINFO_APA, rtlhal->type_apa);
odm_cmn_info_init(dm, ODM_CMNINFO_GLNA, rtlhal->type_glna);
odm_cmn_info_init(dm, ODM_CMNINFO_ALNA, rtlhal->type_alna);
odm_cmn_info_init(dm, ODM_CMNINFO_RFE_TYPE, rtlhal->rfe_type);
odm_cmn_info_init(dm, ODM_CMNINFO_EXT_TRSW, 0);
/*Add by YuChen for kfree init*/
odm_cmn_info_init(dm, ODM_CMNINFO_REGRFKFREEENABLE, 2);
odm_cmn_info_init(dm, ODM_CMNINFO_RFKFREEENABLE, 0);
/*Antenna diversity relative parameters*/
odm_cmn_info_hook(dm, ODM_CMNINFO_ANT_DIV,
&rtlefuse->antenna_div_cfg);
odm_cmn_info_init(dm, ODM_CMNINFO_RF_ANTENNA_TYPE,
rtlefuse->antenna_div_type);
odm_cmn_info_init(dm, ODM_CMNINFO_BE_FIX_TX_ANT, 0);
odm_cmn_info_init(dm, ODM_CMNINFO_WITH_EXT_ANTENNA_SWITCH, 0);
/* (8822B) efuse 0x3D7 & 0x3D8 for TX PA bias */
odm_cmn_info_init(dm, ODM_CMNINFO_EFUSE0X3D7, params->efuse0x3d7);
odm_cmn_info_init(dm, ODM_CMNINFO_EFUSE0X3D8, params->efuse0x3d8);
/*Add by YuChen for adaptivity init*/
odm_cmn_info_hook(dm, ODM_CMNINFO_ADAPTIVITY,
&rtlpriv->phydm.adaptivity_en);
phydm_adaptivity_info_init(dm, PHYDM_ADAPINFO_CARRIER_SENSE_ENABLE,
false);
phydm_adaptivity_info_init(dm, PHYDM_ADAPINFO_DCBACKOFF, 0);
phydm_adaptivity_info_init(dm, PHYDM_ADAPINFO_DYNAMICLINKADAPTIVITY,
false);
phydm_adaptivity_info_init(dm, PHYDM_ADAPINFO_TH_L2H_INI, 0);
phydm_adaptivity_info_init(dm, PHYDM_ADAPINFO_TH_EDCCA_HL_DIFF, 0);
odm_cmn_info_init(dm, ODM_CMNINFO_IQKFWOFFLOAD, 0);
/* Pointer reference */
odm_cmn_info_hook(dm, ODM_CMNINFO_TX_UNI,
&rtlpriv->stats.txbytesunicast);
odm_cmn_info_hook(dm, ODM_CMNINFO_RX_UNI,
&rtlpriv->stats.rxbytesunicast);
odm_cmn_info_hook(dm, ODM_CMNINFO_BAND, &rtlhal->current_bandtype);
odm_cmn_info_hook(dm, ODM_CMNINFO_FORCED_RATE,
&rtlpriv->phydm.forced_data_rate);
odm_cmn_info_hook(dm, ODM_CMNINFO_FORCED_IGI_LB,
&rtlpriv->phydm.forced_igi_lb);
odm_cmn_info_hook(dm, ODM_CMNINFO_SEC_CHNL_OFFSET,
&mac->cur_40_prime_sc);
odm_cmn_info_hook(dm, ODM_CMNINFO_BW, &rtlphy->current_chan_bw);
odm_cmn_info_hook(dm, ODM_CMNINFO_CHNL, &rtlphy->current_channel);
odm_cmn_info_hook(dm, ODM_CMNINFO_SCAN, &mac->act_scanning);
odm_cmn_info_hook(dm, ODM_CMNINFO_POWER_SAVING,
&ppsc->dot11_psmode); /* may add new boolean flag */
/*Add by Yuchen for phydm beamforming*/
odm_cmn_info_hook(dm, ODM_CMNINFO_TX_TP,
&rtlpriv->stats.txbytesunicast_inperiod_tp);
odm_cmn_info_hook(dm, ODM_CMNINFO_RX_TP,
&rtlpriv->stats.rxbytesunicast_inperiod_tp);
odm_cmn_info_hook(dm, ODM_CMNINFO_ANT_TEST,
&rtlpriv->phydm.antenna_test);
for (i = 0; i < ODM_ASSOCIATE_ENTRY_NUM; i++)
odm_cmn_info_ptr_array_hook(dm, ODM_CMNINFO_STA_STATUS, i,
NULL);
phydm_init_debug_setting(dm);
odm_cmn_info_init(dm, ODM_CMNINFO_FAB_VER, params->fab_ver);
odm_cmn_info_init(dm, ODM_CMNINFO_CUT_VER, params->cut_ver);
/* after ifup, ability is updated again */
support_ability = ODM_RF_CALIBRATION | ODM_RF_TX_PWR_TRACK;
odm_cmn_info_update(dm, ODM_CMNINFO_ABILITY, support_ability);
return 0;
}
static int rtl_phydm_init_priv(struct rtl_priv *rtlpriv,
struct rtl_phydm_params *params)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum odm_ic_type ic;
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
ic = ODM_RTL8822B;
else
return 0;
rtlpriv->phydm.internal =
kzalloc(sizeof(struct phy_dm_struct), GFP_KERNEL);
_rtl_phydm_init_com_info(rtlpriv, ic, params);
odm_init_all_timers(dm);
return 1;
}
static int rtl_phydm_deinit_priv(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
odm_cancel_all_timers(dm);
kfree(rtlpriv->phydm.internal);
rtlpriv->phydm.internal = NULL;
return 0;
}
static bool rtl_phydm_load_txpower_by_rate(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum hal_status status;
status = odm_config_bb_with_header_file(dm, CONFIG_BB_PHY_REG_PG);
if (status != HAL_STATUS_SUCCESS)
return false;
return true;
}
static bool rtl_phydm_load_txpower_limit(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum hal_status status;
if (IS_HARDWARE_TYPE_8822B(rtlpriv)) {
odm_read_and_config_mp_8822b_txpwr_lmt(dm);
} else {
status = odm_config_rf_with_header_file(dm, CONFIG_RF_TXPWR_LMT,
0);
if (status != HAL_STATUS_SUCCESS)
return false;
}
return true;
}
static int rtl_phydm_init_dm(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
u32 support_ability = 0;
/* clang-format off */
support_ability = 0
| ODM_BB_DIG
| ODM_BB_RA_MASK
| ODM_BB_DYNAMIC_TXPWR
| ODM_BB_FA_CNT
| ODM_BB_RSSI_MONITOR
| ODM_BB_CCK_PD
/* | ODM_BB_PWR_SAVE*/
| ODM_BB_CFO_TRACKING
| ODM_MAC_EDCA_TURBO
| ODM_RF_TX_PWR_TRACK
| ODM_RF_CALIBRATION
| ODM_BB_NHM_CNT
/* | ODM_BB_PWR_TRAIN*/
;
/* clang-format on */
odm_cmn_info_update(dm, ODM_CMNINFO_ABILITY, support_ability);
odm_dm_init(dm);
return 0;
}
static int rtl_phydm_deinit_dm(struct rtl_priv *rtlpriv)
{
return 0;
}
static int rtl_phydm_reset_dm(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
odm_dm_reset(dm);
return 0;
}
static bool rtl_phydm_parameter_init(struct rtl_priv *rtlpriv, bool post)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_parameter_init(dm, post ? ODM_POST_SETTING :
ODM_PRE_SETTING);
return false;
}
static bool rtl_phydm_phy_bb_config(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum hal_status status;
status = odm_config_bb_with_header_file(dm, CONFIG_BB_PHY_REG);
if (status != HAL_STATUS_SUCCESS)
return false;
status = odm_config_bb_with_header_file(dm, CONFIG_BB_AGC_TAB);
if (status != HAL_STATUS_SUCCESS)
return false;
return true;
}
static bool rtl_phydm_phy_rf_config(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
struct rtl_phy *rtlphy = &rtlpriv->phy;
enum hal_status status;
enum odm_rf_radio_path rfpath;
for (rfpath = 0; rfpath < rtlphy->num_total_rfpath; rfpath++) {
status = odm_config_rf_with_header_file(dm, CONFIG_RF_RADIO,
rfpath);
if (status != HAL_STATUS_SUCCESS)
return false;
}
status = odm_config_rf_with_tx_pwr_track_header_file(dm);
if (status != HAL_STATUS_SUCCESS)
return false;
return true;
}
static bool rtl_phydm_phy_mac_config(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum hal_status status;
status = odm_config_mac_with_header_file(dm);
if (status != HAL_STATUS_SUCCESS)
return false;
return true;
}
static bool rtl_phydm_trx_mode(struct rtl_priv *rtlpriv,
enum radio_mask tx_path, enum radio_mask rx_path,
bool is_tx2_path)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_trx_mode_8822b(dm,
(enum odm_rf_path)tx_path,
(enum odm_rf_path)rx_path,
is_tx2_path);
return false;
}
static bool rtl_phydm_watchdog(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
struct rtl_mac *mac = rtl_mac(rtlpriv);
struct rtl_ps_ctl *ppsc = rtl_psc(rtlpriv);
bool fw_current_inpsmode = false;
bool fw_ps_awake = true;
u8 is_linked = false;
u8 bsta_state = false;
u8 is_bt_enabled = false;
/* check whether do watchdog */
rtlpriv->cfg->ops->get_hw_reg(rtlpriv->hw, HW_VAR_FW_PSMODE_STATUS,
(u8 *)(&fw_current_inpsmode));
rtlpriv->cfg->ops->get_hw_reg(rtlpriv->hw, HW_VAR_FWLPS_RF_ON,
(u8 *)(&fw_ps_awake));
if (ppsc->p2p_ps_info.p2p_ps_mode)
fw_ps_awake = false;
if ((ppsc->rfpwr_state == ERFON) &&
((!fw_current_inpsmode) && fw_ps_awake) &&
(!ppsc->rfchange_inprogress))
;
else
return false;
/* update common info before doing watchdog */
if (mac->link_state >= MAC80211_LINKED) {
is_linked = true;
if (mac->vif && mac->vif->type == NL80211_IFTYPE_STATION)
bsta_state = true;
}
if (rtlpriv->cfg->ops->get_btc_status())
is_bt_enabled = !rtlpriv->btcoexist.btc_ops->btc_is_bt_disabled(
rtlpriv);
odm_cmn_info_update(dm, ODM_CMNINFO_LINK, is_linked);
odm_cmn_info_update(dm, ODM_CMNINFO_STATION_STATE, bsta_state);
odm_cmn_info_update(dm, ODM_CMNINFO_BT_ENABLED, is_bt_enabled);
/* do watchdog */
odm_dm_watchdog(dm);
return true;
}
static bool rtl_phydm_switch_band(struct rtl_priv *rtlpriv, u8 central_ch)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_switch_band_8822b(dm, central_ch);
return false;
}
static bool rtl_phydm_switch_channel(struct rtl_priv *rtlpriv, u8 central_ch)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_switch_channel_8822b(dm, central_ch);
return false;
}
static bool rtl_phydm_switch_bandwidth(struct rtl_priv *rtlpriv,
u8 primary_ch_idx,
enum ht_channel_width bandwidth)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum odm_bw odm_bw = (enum odm_bw)bandwidth;
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_switch_bandwidth_8822b(dm, primary_ch_idx,
odm_bw);
return false;
}
static bool rtl_phydm_iq_calibrate(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
phy_iq_calibrate_8822b(dm, false);
else
return false;
return true;
}
static bool rtl_phydm_clear_txpowertracking_state(struct rtl_priv *rtlpriv)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
odm_clear_txpowertracking_state(dm);
return true;
}
static bool rtl_phydm_pause_dig(struct rtl_priv *rtlpriv, bool pause)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
if (pause)
odm_pause_dig(dm, PHYDM_PAUSE, PHYDM_PAUSE_LEVEL_0, 0x1e);
else /* resume */
odm_pause_dig(dm, PHYDM_RESUME, PHYDM_PAUSE_LEVEL_0, 0xff);
return true;
}
static u32 rtl_phydm_read_rf_reg(struct rtl_priv *rtlpriv,
enum radio_path rfpath, u32 addr, u32 mask)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum odm_rf_radio_path odm_rfpath = (enum odm_rf_radio_path)rfpath;
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_read_rf_reg_8822b(dm, odm_rfpath, addr,
mask);
return -1;
}
static bool rtl_phydm_write_rf_reg(struct rtl_priv *rtlpriv,
enum radio_path rfpath, u32 addr, u32 mask,
u32 data)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum odm_rf_radio_path odm_rfpath = (enum odm_rf_radio_path)rfpath;
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_write_rf_reg_8822b(dm, odm_rfpath, addr,
mask, data);
return false;
}
static u8 rtl_phydm_read_txagc(struct rtl_priv *rtlpriv, enum radio_path rfpath,
u8 hw_rate)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum odm_rf_radio_path odm_rfpath = (enum odm_rf_radio_path)rfpath;
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_read_txagc_8822b(dm, odm_rfpath, hw_rate);
return -1;
}
static bool rtl_phydm_write_txagc(struct rtl_priv *rtlpriv, u32 power_index,
enum radio_path rfpath, u8 hw_rate)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
enum odm_rf_radio_path odm_rfpath = (enum odm_rf_radio_path)rfpath;
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
return config_phydm_write_txagc_8822b(dm, power_index,
odm_rfpath, hw_rate);
return false;
}
static bool rtl_phydm_c2h_content_parsing(struct rtl_priv *rtlpriv, u8 cmd_id,
u8 cmd_len, u8 *content)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
if (phydm_c2H_content_parsing(dm, cmd_id, cmd_len, content))
return true;
return false;
}
static bool rtl_phydm_query_phy_status(struct rtl_priv *rtlpriv, u8 *phystrpt,
struct ieee80211_hdr *hdr,
struct rtl_stats *pstatus)
{
/* NOTE: phystrpt may be NULL, and need to fill default value */
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
struct rtl_efuse *rtlefuse = rtl_efuse(rtlpriv);
struct rtl_mac *mac = rtl_mac(rtlpriv);
struct dm_per_pkt_info pktinfo; /* input of pydm */
struct dm_phy_status_info phy_info; /* output of phydm */
__le16 fc = hdr->frame_control;
/* fill driver pstatus */
ether_addr_copy(pstatus->psaddr, ieee80211_get_SA(hdr));
/* fill pktinfo */
memset(&pktinfo, 0, sizeof(pktinfo));
pktinfo.data_rate = pstatus->rate;
if (rtlpriv->mac80211.opmode == NL80211_IFTYPE_STATION) {
pktinfo.station_id = 0;
} else {
/* TODO: use rtl_find_sta() to find ID */
pktinfo.station_id = 0xFF;
}
pktinfo.is_packet_match_bssid =
(!ieee80211_is_ctl(fc) &&
(ether_addr_equal(mac->bssid,
ieee80211_has_tods(fc) ?
hdr->addr1 :
ieee80211_has_fromds(fc) ?
hdr->addr2 :
hdr->addr3)) &&
(!pstatus->hwerror) && (!pstatus->crc) && (!pstatus->icv));
pktinfo.is_packet_to_self =
pktinfo.is_packet_match_bssid &&
(ether_addr_equal(hdr->addr1, rtlefuse->dev_addr));
pktinfo.is_to_self = (!pstatus->icv) && (!pstatus->crc) &&
(ether_addr_equal(hdr->addr1, rtlefuse->dev_addr));
pktinfo.is_packet_beacon = (ieee80211_is_beacon(fc) ? true : false);
/* query phy status */
if (phystrpt)
odm_phy_status_query(dm, &phy_info, phystrpt, &pktinfo);
else
memset(&phy_info, 0, sizeof(phy_info));
/* copy phy_info from phydm to driver */
pstatus->rx_pwdb_all = phy_info.rx_pwdb_all;
pstatus->bt_rx_rssi_percentage = phy_info.bt_rx_rssi_percentage;
pstatus->recvsignalpower = phy_info.recv_signal_power;
pstatus->signalquality = phy_info.signal_quality;
pstatus->rx_mimo_signalquality[0] = phy_info.rx_mimo_signal_quality[0];
pstatus->rx_mimo_signalquality[1] = phy_info.rx_mimo_signal_quality[1];
pstatus->rx_packet_bw =
phy_info.band_width; /* HT_CHANNEL_WIDTH_20 <- ODM_BW20M */
/* fill driver pstatus */
pstatus->packet_matchbssid = pktinfo.is_packet_match_bssid;
pstatus->packet_toself = pktinfo.is_packet_to_self;
pstatus->packet_beacon = pktinfo.is_packet_beacon;
return true;
}
static u8 rtl_phydm_rate_id_mapping(struct rtl_priv *rtlpriv,
enum wireless_mode wireless_mode,
enum rf_type rf_type,
enum ht_channel_width bw)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
return phydm_rate_id_mapping(dm, wireless_mode, rf_type, bw);
}
static bool rtl_phydm_get_ra_bitmap(struct rtl_priv *rtlpriv,
enum wireless_mode wireless_mode,
enum rf_type rf_type,
enum ht_channel_width bw,
u8 tx_rate_level, /* 0~6 */
u32 *tx_bitmap_msb,
u32 *tx_bitmap_lsb)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
const u8 mimo_ps_enable = 0;
const u8 disable_cck_rate = 0;
phydm_update_hal_ra_mask(dm, wireless_mode, rf_type, bw, mimo_ps_enable,
disable_cck_rate, tx_bitmap_msb, tx_bitmap_lsb,
tx_rate_level);
return true;
}
static u8 _rtl_phydm_get_macid(struct rtl_priv *rtlpriv,
struct ieee80211_sta *sta)
{
struct rtl_mac *mac = rtl_mac(rtlpriv);
if (mac->opmode == NL80211_IFTYPE_STATION ||
mac->opmode == NL80211_IFTYPE_MESH_POINT) {
return 0;
} else if (mac->opmode == NL80211_IFTYPE_AP ||
mac->opmode == NL80211_IFTYPE_ADHOC)
return sta->aid + 1;
return 0;
}
static bool rtl_phydm_add_sta(struct rtl_priv *rtlpriv,
struct ieee80211_sta *sta)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
struct rtl_sta_info *sta_entry = (struct rtl_sta_info *)sta->drv_priv;
u8 mac_id = _rtl_phydm_get_macid(rtlpriv, sta);
odm_cmn_info_ptr_array_hook(dm, ODM_CMNINFO_STA_STATUS, mac_id,
sta_entry);
return true;
}
static bool rtl_phydm_del_sta(struct rtl_priv *rtlpriv,
struct ieee80211_sta *sta)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
u8 mac_id = _rtl_phydm_get_macid(rtlpriv, sta);
odm_cmn_info_ptr_array_hook(dm, ODM_CMNINFO_STA_STATUS, mac_id, NULL);
return true;
}
static u32 rtl_phydm_get_version(struct rtl_priv *rtlpriv)
{
u32 ver = 0;
if (IS_HARDWARE_TYPE_8822B(rtlpriv))
ver = RELEASE_VERSION_8822B;
return ver;
}
static bool rtl_phydm_modify_ra_pcr_threshold(struct rtl_priv *rtlpriv,
u8 ra_offset_direction,
u8 ra_threshold_offset)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
phydm_modify_RA_PCR_threshold(dm, ra_offset_direction,
ra_threshold_offset);
return true;
}
static u32 rtl_phydm_query_counter(struct rtl_priv *rtlpriv,
const char *info_type)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
static const struct query_entry {
const char *query_name;
enum phydm_info_query query_id;
} query_table[] = {
#define QUERY_ENTRY(name) {#name, name}
QUERY_ENTRY(PHYDM_INFO_FA_OFDM),
QUERY_ENTRY(PHYDM_INFO_FA_CCK),
QUERY_ENTRY(PHYDM_INFO_CCA_OFDM),
QUERY_ENTRY(PHYDM_INFO_CCA_CCK),
QUERY_ENTRY(PHYDM_INFO_CRC32_OK_CCK),
QUERY_ENTRY(PHYDM_INFO_CRC32_OK_LEGACY),
QUERY_ENTRY(PHYDM_INFO_CRC32_OK_HT),
QUERY_ENTRY(PHYDM_INFO_CRC32_OK_VHT),
QUERY_ENTRY(PHYDM_INFO_CRC32_ERROR_CCK),
QUERY_ENTRY(PHYDM_INFO_CRC32_ERROR_LEGACY),
QUERY_ENTRY(PHYDM_INFO_CRC32_ERROR_HT),
QUERY_ENTRY(PHYDM_INFO_CRC32_ERROR_VHT),
};
#define QUERY_TABLE_SIZE ARRAY_SIZE(query_table)
int i;
const struct query_entry *entry;
if (!strcmp(info_type, "IQK_TOTAL"))
return dm->n_iqk_cnt;
if (!strcmp(info_type, "IQK_OK"))
return dm->n_iqk_ok_cnt;
if (!strcmp(info_type, "IQK_FAIL"))
return dm->n_iqk_fail_cnt;
for (i = 0; i < QUERY_TABLE_SIZE; i++) {
entry = &query_table[i];
if (!strcmp(info_type, entry->query_name))
return phydm_cmn_info_query(dm, entry->query_id);
}
pr_err("Unrecognized info_type:%s!!!!:\n", info_type);
return 0xDEADDEAD;
}
static bool rtl_phydm_debug_cmd(struct rtl_priv *rtlpriv, char *in, u32 in_len,
char *out, u32 out_len)
{
struct phy_dm_struct *dm = rtlpriv_to_phydm(rtlpriv);
phydm_cmd(dm, in, in_len, 1, out, out_len);
return true;
}
static struct rtl_phydm_ops rtl_phydm_operation = {
/* init/deinit priv */
.phydm_init_priv = rtl_phydm_init_priv,
.phydm_deinit_priv = rtl_phydm_deinit_priv,
.phydm_load_txpower_by_rate = rtl_phydm_load_txpower_by_rate,
.phydm_load_txpower_limit = rtl_phydm_load_txpower_limit,
/* init hw */
.phydm_init_dm = rtl_phydm_init_dm,
.phydm_deinit_dm = rtl_phydm_deinit_dm,
.phydm_reset_dm = rtl_phydm_reset_dm,
.phydm_parameter_init = rtl_phydm_parameter_init,
.phydm_phy_bb_config = rtl_phydm_phy_bb_config,
.phydm_phy_rf_config = rtl_phydm_phy_rf_config,
.phydm_phy_mac_config = rtl_phydm_phy_mac_config,
.phydm_trx_mode = rtl_phydm_trx_mode,
/* watchdog */
.phydm_watchdog = rtl_phydm_watchdog,
/* channel */
.phydm_switch_band = rtl_phydm_switch_band,
.phydm_switch_channel = rtl_phydm_switch_channel,
.phydm_switch_bandwidth = rtl_phydm_switch_bandwidth,
.phydm_iq_calibrate = rtl_phydm_iq_calibrate,
.phydm_clear_txpowertracking_state =
rtl_phydm_clear_txpowertracking_state,
.phydm_pause_dig = rtl_phydm_pause_dig,
/* read/write reg */
.phydm_read_rf_reg = rtl_phydm_read_rf_reg,
.phydm_write_rf_reg = rtl_phydm_write_rf_reg,
.phydm_read_txagc = rtl_phydm_read_txagc,
.phydm_write_txagc = rtl_phydm_write_txagc,
/* RX */
.phydm_c2h_content_parsing = rtl_phydm_c2h_content_parsing,
.phydm_query_phy_status = rtl_phydm_query_phy_status,
/* TX */
.phydm_rate_id_mapping = rtl_phydm_rate_id_mapping,
.phydm_get_ra_bitmap = rtl_phydm_get_ra_bitmap,
/* STA */
.phydm_add_sta = rtl_phydm_add_sta,
.phydm_del_sta = rtl_phydm_del_sta,
/* BTC */
.phydm_get_version = rtl_phydm_get_version,
.phydm_modify_ra_pcr_threshold = rtl_phydm_modify_ra_pcr_threshold,
.phydm_query_counter = rtl_phydm_query_counter,
/* debug */
.phydm_debug_cmd = rtl_phydm_debug_cmd,
};
struct rtl_phydm_ops *rtl_phydm_get_ops_pointer(void)
{
return &rtl_phydm_operation;
}
EXPORT_SYMBOL(rtl_phydm_get_ops_pointer);
/* ********************************************************
* Define phydm callout function in below
* ********************************************************
*/
u8 phy_get_tx_power_index(void *adapter, u8 rf_path, u8 rate,
enum ht_channel_width bandwidth, u8 channel)
{
/* rate: DESC_RATE1M */
struct rtl_priv *rtlpriv = (struct rtl_priv *)adapter;
return rtlpriv->cfg->ops->get_txpower_index(rtlpriv->hw, rf_path, rate,
bandwidth, channel);
}
void phy_set_tx_power_index_by_rs(void *adapter, u8 ch, u8 path, u8 rs)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)adapter;
return rtlpriv->cfg->ops->set_tx_power_index_by_rs(rtlpriv->hw, ch,
path, rs);
}
void phy_store_tx_power_by_rate(void *adapter, u32 band, u32 rfpath, u32 txnum,
u32 regaddr, u32 bitmask, u32 data)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)adapter;
rtlpriv->cfg->ops->store_tx_power_by_rate(
rtlpriv->hw, band, rfpath, txnum, regaddr, bitmask, data);
}
void phy_set_tx_power_limit(void *dm, u8 *regulation, u8 *band, u8 *bandwidth,
u8 *rate_section, u8 *rf_path, u8 *channel,
u8 *power_limit)
{
struct rtl_priv *rtlpriv =
(struct rtl_priv *)((struct phy_dm_struct *)dm)->adapter;
rtlpriv->cfg->ops->phy_set_txpower_limit(rtlpriv->hw, regulation, band,
bandwidth, rate_section,
rf_path, channel, power_limit);
}
void rtl_hal_update_ra_mask(void *adapter, struct rtl_sta_info *psta,
u8 rssi_level)
{
struct rtl_priv *rtlpriv = (struct rtl_priv *)adapter;
struct ieee80211_sta *sta =
container_of((void *)psta, struct ieee80211_sta, drv_priv);
rtlpriv->cfg->ops->update_rate_tbl(rtlpriv->hw, sta, rssi_level, false);
}
MODULE_AUTHOR("Realtek WlanFAE <wlanfae@realtek.com>");
MODULE_AUTHOR("Larry Finger <Larry.FInger@lwfinger.net>");
MODULE_LICENSE("GPL");
MODULE_DESCRIPTION("Realtek 802.11n PCI wireless core");

View File

@ -0,0 +1,45 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __RTL_PHYDM_H__
#define __RTL_PHYDM_H__
struct rtl_phydm_ops *rtl_phydm_get_ops_pointer(void);
#define rtlpriv_to_phydm(priv) \
((struct phy_dm_struct *)((priv)->phydm.internal))
u8 phy_get_tx_power_index(void *adapter, u8 rf_path, u8 rate,
enum ht_channel_width bandwidth, u8 channel);
void phy_set_tx_power_index_by_rs(void *adapter, u8 ch, u8 path, u8 rs);
void phy_store_tx_power_by_rate(void *adapter, u32 band, u32 rfpath, u32 txnum,
u32 regaddr, u32 bitmask, u32 data);
void phy_set_tx_power_limit(void *dm, u8 *regulation, u8 *band, u8 *bandwidth,
u8 *rate_section, u8 *rf_path, u8 *channel,
u8 *power_limit);
void rtl_hal_update_ra_mask(void *adapter, struct rtl_sta_info *psta,
u8 rssi_level);
#endif

View File

@ -0,0 +1,67 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HAL_COM_TXBF_H__
#define __HAL_COM_TXBF_H__
enum txbf_set_type {
TXBF_SET_SOUNDING_ENTER,
TXBF_SET_SOUNDING_LEAVE,
TXBF_SET_SOUNDING_RATE,
TXBF_SET_SOUNDING_STATUS,
TXBF_SET_SOUNDING_FW_NDPA,
TXBF_SET_SOUNDING_CLK,
TXBF_SET_TX_PATH_RESET,
TXBF_SET_GET_TX_RATE
};
enum txbf_get_type {
TXBF_GET_EXPLICIT_BEAMFORMEE,
TXBF_GET_EXPLICIT_BEAMFORMER,
TXBF_GET_MU_MIMO_STA,
TXBF_GET_MU_MIMO_AP
};
/* 2 HAL TXBF related */
struct _HAL_TXBF_INFO {
u8 txbf_idx;
u8 ndpa_idx;
u8 BW;
u8 rate;
struct timer_list txbf_fw_ndpa_timer;
};
#define hal_com_txbf_beamform_init(dm_void) NULL
#define hal_com_txbf_config_gtab(dm_void) NULL
#define hal_com_txbf_enter_work_item_callback(_adapter) NULL
#define hal_com_txbf_leave_work_item_callback(_adapter) NULL
#define hal_com_txbf_fw_ndpa_work_item_callback(_adapter) NULL
#define hal_com_txbf_clk_work_item_callback(_adapter) NULL
#define hal_com_txbf_rate_work_item_callback(_adapter) NULL
#define hal_com_txbf_fw_ndpa_timer_callback(_adapter) NULL
#define hal_com_txbf_status_work_item_callback(_adapter) NULL
#define hal_com_txbf_get(_adapter, _get_type, _pout_buf)
#endif /* #ifndef __HAL_COM_TXBF_H__ */

View File

@ -0,0 +1,39 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HAL_TXBF_8822B_H__
#define __HAL_TXBF_8822B_H__
#define hal_txbf_8822b_enter(dm_void, idx)
#define hal_txbf_8822b_leave(dm_void, idx)
#define hal_txbf_8822b_status(dm_void, idx)
#define hal_txbf_8822b_fw_txbf(dm_void, idx)
#define hal_txbf_8822b_config_gtab(dm_void)
void phydm_8822btxbf_rfmode(void *dm_void, u8 su_bfee_cnt, u8 mu_bfee_cnt);
void phydm_8822b_sutxbfer_workaroud(void *dm_void, bool enable_su_bfer, u8 nc,
u8 nr, u8 ng, u8 CB, u8 BW, bool is_vht);
#endif

View File

@ -0,0 +1,38 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HAL_TXBF_INTERFACE_H__
#define __HAL_TXBF_INTERFACE_H__
#define beamforming_get_ndpa_frame(dm, _pdu_os)
#define beamforming_get_report_frame(adapter, precv_frame) RT_STATUS_FAILURE
#define send_fw_ht_ndpa_packet(dm_void, RA, BW)
#define send_sw_ht_ndpa_packet(dm_void, RA, BW)
#define send_fw_vht_ndpa_packet(dm_void, RA, AID, BW)
#define send_sw_vht_ndpa_packet(dm_void, RA, AID, BW)
#define send_sw_vht_gid_mgnt_frame(dm_void, RA, idx)
#define send_sw_vht_bf_report_poll(dm_void, RA, is_final_poll)
#define send_sw_vht_mu_ndpa_packet(dm_void, BW)
#endif

View File

@ -0,0 +1,36 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __HAL_TXBF_JAGUAR_H__
#define __HAL_TXBF_JAGUAR_H__
#define hal_txbf_8812a_set_ndpa_rate(dm_void, BW, rate)
#define hal_txbf_jaguar_enter(dm_void, idx)
#define hal_txbf_jaguar_leave(dm_void, idx)
#define hal_txbf_jaguar_status(dm_void, idx)
#define hal_txbf_jaguar_fw_txbf(dm_void, idx)
#define hal_txbf_jaguar_patch(dm_void, operation)
#define hal_txbf_jaguar_clk_8812a(dm_void)
#endif /* #ifndef __HAL_TXBF_JAGUAR_H__ */

View File

@ -0,0 +1,41 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2016 Realtek Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of version 2 of the GNU General Public License as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* The full GNU General Public License is included in this distribution in the
* file called LICENSE.
*
* Contact Information:
* wlanfae <wlanfae@realtek.com>
* Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
* Hsinchu 300, Taiwan.
*
* Larry Finger <Larry.Finger@lwfinger.net>
*
*****************************************************************************/
#ifndef __PHYDM_HAL_TXBF_API_H__
#define __PHYDM_HAL_TXBF_API_H__
#define tx_bf_nr(a, b) ((a > b) ? (b) : (a))
u8 beamforming_get_htndp_tx_rate(void *dm_void, u8 comp_steering_num_of_bfer);
u8 beamforming_get_vht_ndp_tx_rate(void *dm_void, u8 comp_steering_num_of_bfer);
u8 phydm_get_beamforming_sounding_info(void *dm_void, u16 *troughput,
u8 total_bfee_num, u8 *tx_rate);
u8 phydm_get_ndpa_rate(void *dm_void);
u8 phydm_get_mu_bfee_snding_decision(void *dm_void, u16 throughput);
#endif