2022-05-03 01:27:37

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 0/8] rtw89: 8852c: add RF calibration

These RFK (RF calibration) can be called once interface is going up, or
when we are going to connect to AP in certain channel, or band is changed.
The general steps of calibration are to backup registers (optional) and
set a set of registers before doing calibration according to channels or
something else, and then trigger the calibration and poll if calibration
is complete. Then, check the result is positive or not to decide to
adjust parameters and re-trigger again. If the result is okay, set
registers accordingly, and restore registers we backup before (optional).

v3:
- shrink number of patches from 16 to 8
- add blank lines to make code more readable
- use upper case for macros name with proper prefix
- move const tables upward to top of .c file
v2: add patch 15 to fix clang warning

Ping-Ke Shih (8):
rtw89: 8852c: rfk: add RFK tables
rtw89: 8852c: rfk: add DACK
rtw89: 8852c: rfk: add LCK
rtw89: 8852c: rfk: add TSSI
rtw89: 8852c: rfk: add RCK
rtw89: 8852c: rfk: add RX DCK
rtw89: 8852c: rfk: add IQK
rtw89: 8852c: rfk: add DPK

drivers/net/wireless/realtek/rtw89/core.h | 19 +-
drivers/net/wireless/realtek/rtw89/reg.h | 211 +-
.../net/wireless/realtek/rtw89/rtw8852a_rfk.c | 8 +-
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 34 +
.../net/wireless/realtek/rtw89/rtw8852c_rfk.c | 3825 ++++++++++++++++-
.../net/wireless/realtek/rtw89/rtw8852c_rfk.h | 13 +
.../realtek/rtw89/rtw8852c_rfk_table.c | 781 ++++
.../realtek/rtw89/rtw8852c_rfk_table.h | 67 +
8 files changed, 4930 insertions(+), 28 deletions(-)
create mode 100644 drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.c
create mode 100644 drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.h

--
2.25.1


2022-05-03 01:27:39

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 6/8] rtw89: 8852c: rfk: add RX DCK

RX DCK is receiver DC calibration. Do this calibration when bringing up
interface and going to run on AP channel.

Signed-off-by: Ping-Ke Shih <[email protected]>
---
drivers/net/wireless/realtek/rtw89/reg.h | 9 ++-
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 2 +
.../net/wireless/realtek/rtw89/rtw8852c_rfk.c | 67 +++++++++++++++++++
.../net/wireless/realtek/rtw89/rtw8852c_rfk.h | 1 +
4 files changed, 78 insertions(+), 1 deletion(-)

diff --git a/drivers/net/wireless/realtek/rtw89/reg.h b/drivers/net/wireless/realtek/rtw89/reg.h
index 028c881308237..c65598a7af268 100644
--- a/drivers/net/wireless/realtek/rtw89/reg.h
+++ b/drivers/net/wireless/realtek/rtw89/reg.h
@@ -3312,17 +3312,24 @@
#define RR_RXIQGEN_ATTL GENMASK(12, 8)
#define RR_RXIQGEN_ATTH GENMASK(14, 13)
#define RR_RXBB2 0x8f
-#define RR_EN_TIA_IDA GENMASK(11, 10)
#define RR_RXBB2_DAC_EN BIT(13)
+#define RR_RXBB2_CKT BIT(12)
+#define RR_EN_TIA_IDA GENMASK(11, 10)
+#define RR_RXBB2_IDAC GENMASK(11, 9)
+#define RR_RXBB2_EBW GENMASK(6, 5)
#define RR_XALNA2 0x90
#define RR_XALNA2_SW GENMASK(1, 0)
#define RR_DCK 0x92
+#define RR_DCK_DONE GENMASK(7, 5)
#define RR_DCK_FINE BIT(1)
#define RR_DCK_LV BIT(0)
#define RR_DCK1 0x93
+#define RR_DCK1_CLR GENMASK(3, 0)
#define RR_DCK1_SEL BIT(3)
#define RR_DCK2 0x94
#define RR_DCK2_CYCLE GENMASK(7, 2)
+#define RR_DCKC 0x95
+#define RR_DCKC_CHK BIT(3)
#define RR_MIXER 0x9f
#define RR_MIXER_GN GENMASK(4, 3)
#define RR_XTALX2 0xb8
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c.c b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
index 6db61e6df1ff0..cbf69670eafe0 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
@@ -1779,12 +1779,14 @@ static void rtw8852c_rfk_init(struct rtw89_dev *rtwdev)

rtw8852c_rck(rtwdev);
rtw8852c_dack(rtwdev);
+ rtw8852c_rx_dck(rtwdev, RTW89_PHY_0, false);
}

static void rtw8852c_rfk_channel(struct rtw89_dev *rtwdev)
{
enum rtw89_phy_idx phy_idx = RTW89_PHY_0;

+ rtw8852c_rx_dck(rtwdev, phy_idx, false);
rtw8852c_tssi(rtwdev, phy_idx);
rtw89_fw_h2c_rf_ntfy_mcc(rtwdev);
}
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
index 4025245cd7e6b..197d177494dab 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
@@ -505,6 +505,42 @@ static void _rck(struct rtw89_dev *rtwdev, enum rtw89_rf_path path)
rtw89_read_rf(rtwdev, path, RR_RCKS, RFREG_MASK));
}

+static void _rx_dck_toggle(struct rtw89_dev *rtwdev, u8 path)
+{
+ int ret;
+ u32 val;
+
+ rtw89_write_rf(rtwdev, path, RR_DCK, RR_DCK_LV, 0x0);
+ rtw89_write_rf(rtwdev, path, RR_DCK, RR_DCK_LV, 0x1);
+
+ ret = read_poll_timeout_atomic(rtw89_read_rf, val, val,
+ 2, 1000, false, rtwdev, path, 0x93, BIT(5));
+ if (ret)
+ rtw89_warn(rtwdev, "[RX_DCK] S%d RXDCK timeout\n", path);
+ else
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[RX_DCK] S%d RXDCK finish\n", path);
+
+ rtw89_write_rf(rtwdev, path, RR_DCK, RR_DCK_LV, 0x0);
+}
+
+static void _set_rx_dck(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy, u8 path,
+ bool is_afe)
+{
+ u8 res;
+
+ rtw89_write_rf(rtwdev, path, RR_DCK1, RR_DCK1_CLR, 0x0);
+
+ _rx_dck_toggle(rtwdev, path);
+ if (rtw89_read_rf(rtwdev, path, RR_DCKC, RR_DCKC_CHK) == 0)
+ return;
+ res = rtw89_read_rf(rtwdev, path, RR_DCK, RR_DCK_DONE);
+ if (res > 1) {
+ rtw89_write_rf(rtwdev, path, RR_RXBB2, RR_RXBB2_IDAC, res);
+ _rx_dck_toggle(rtwdev, path);
+ rtw89_write_rf(rtwdev, path, RR_RXBB2, RR_RXBB2_IDAC, 0x1);
+ }
+}
+
static void _tssi_set_sys(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
enum rtw89_rf_path path)
{
@@ -1671,6 +1707,37 @@ void rtw8852c_dack(struct rtw89_dev *rtwdev)
rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_STOP);
}

+#define RXDCK_VER_8852C 0xe
+
+void rtw8852c_rx_dck(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy, bool is_afe)
+{
+ u8 path, kpath;
+ u32 rf_reg5;
+
+ kpath = _kpath(rtwdev, phy);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[RX_DCK] ****** RXDCK Start (Ver: 0x%x, Cv: %d) ******\n",
+ RXDCK_VER_8852C, rtwdev->hal.cv);
+
+ for (path = 0; path < 2; path++) {
+ rf_reg5 = rtw89_read_rf(rtwdev, path, RR_RSV1, RFREG_MASK);
+ if (!(kpath & BIT(path)))
+ continue;
+
+ if (rtwdev->is_tssi_mode[path])
+ rtw89_phy_write32_mask(rtwdev, R_P0_TSSI_TRK + (path << 13),
+ B_P0_TSSI_TRK_EN, 0x1);
+ rtw89_write_rf(rtwdev, path, RR_RSV1, RR_RSV1_RST, 0x0);
+ rtw89_write_rf(rtwdev, path, RR_MOD, RR_MOD_MASK, RR_MOD_V_RX);
+ _set_rx_dck(rtwdev, phy, path, is_afe);
+ rtw89_write_rf(rtwdev, path, RR_RSV1, RFREG_MASK, rf_reg5);
+
+ if (rtwdev->is_tssi_mode[path])
+ rtw89_phy_write32_mask(rtwdev, R_P0_TSSI_TRK + (path << 13),
+ B_P0_TSSI_TRK_EN, 0x0);
+ }
+}
+
void rtw8852c_tssi(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
{
u32 i, path = RF_PATH_A, path_max = RF_PATH_NUM_8852C;
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
index faacdf17a9286..fd07028a49640 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
@@ -9,6 +9,7 @@

void rtw8852c_rck(struct rtw89_dev *rtwdev);
void rtw8852c_dack(struct rtw89_dev *rtwdev);
+void rtw8852c_rx_dck(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx, bool is_afe);
void rtw8852c_tssi(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
void rtw8852c_tssi_scan(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
void rtw8852c_tssi_cont_en_phyidx(struct rtw89_dev *rtwdev, bool en, u8 phy_idx);
--
2.25.1

2022-05-03 01:27:41

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 5/8] rtw89: 8852c: rfk: add RCK

RCK is synchronize RC calibration. It needs to be triggered only once when
interface is going to up.

Signed-off-by: Ping-Ke Shih <[email protected]>
---
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 1 +
.../net/wireless/realtek/rtw89/rtw8852c_rfk.c | 43 +++++++++++++++++++
.../net/wireless/realtek/rtw89/rtw8852c_rfk.h | 1 +
3 files changed, 45 insertions(+)

diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c.c b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
index 36406488e60e4..6db61e6df1ff0 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
@@ -1777,6 +1777,7 @@ static void rtw8852c_rfk_init(struct rtw89_dev *rtwdev)
memset(mcc_info, 0, sizeof(*mcc_info));
rtw8852c_lck_init(rtwdev);

+ rtw8852c_rck(rtwdev);
rtw8852c_dack(rtwdev);
}

diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
index 974bb5794ad9f..4025245cd7e6b 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
@@ -470,6 +470,41 @@ static void _dac_cal(struct rtw89_dev *rtwdev, bool force)
rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]DACK finish!!!\n");
}

+static void _rck(struct rtw89_dev *rtwdev, enum rtw89_rf_path path)
+{
+ u32 rf_reg5, rck_val = 0;
+ u32 val;
+ int ret;
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[RCK] ====== S%d RCK ======\n", path);
+
+ rf_reg5 = rtw89_read_rf(rtwdev, path, RR_RSV1, RFREG_MASK);
+
+ rtw89_write_rf(rtwdev, path, RR_RSV1, RR_RSV1_RST, 0x0);
+ rtw89_write_rf(rtwdev, path, RR_MOD, RR_MOD_MASK, RR_MOD_V_RX);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[RCK] RF0x00 = 0x%x\n",
+ rtw89_read_rf(rtwdev, path, RR_MOD, RFREG_MASK));
+
+ /* RCK trigger */
+ rtw89_write_rf(rtwdev, path, RR_RCKC, RFREG_MASK, 0x00240);
+
+ ret = read_poll_timeout_atomic(rtw89_read_rf, val, val, 2, 20,
+ false, rtwdev, path, 0x1c, BIT(3));
+ if (ret)
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[RCK] RCK timeout\n");
+
+ rck_val = rtw89_read_rf(rtwdev, path, RR_RCKC, RR_RCKC_CA);
+ rtw89_write_rf(rtwdev, path, RR_RCKC, RFREG_MASK, rck_val);
+
+ rtw89_write_rf(rtwdev, path, RR_RSV1, RFREG_MASK, rf_reg5);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[RCK] RF 0x1b / 0x1c = 0x%x / 0x%x\n",
+ rtw89_read_rf(rtwdev, path, RR_RCKC, RFREG_MASK),
+ rtw89_read_rf(rtwdev, path, RR_RCKS, RFREG_MASK));
+}
+
static void _tssi_set_sys(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
enum rtw89_rf_path path)
{
@@ -1619,6 +1654,14 @@ void rtw8852c_set_channel_rf(struct rtw89_dev *rtwdev,
param->bandwidth);
}

+void rtw8852c_rck(struct rtw89_dev *rtwdev)
+{
+ u8 path;
+
+ for (path = 0; path < 2; path++)
+ _rck(rtwdev, path);
+}
+
void rtw8852c_dack(struct rtw89_dev *rtwdev)
{
u8 phy_map = rtw89_btc_phymap(rtwdev, RTW89_PHY_0, 0);
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
index a16ad9305ba42..faacdf17a9286 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
@@ -7,6 +7,7 @@

#include "core.h"

+void rtw8852c_rck(struct rtw89_dev *rtwdev);
void rtw8852c_dack(struct rtw89_dev *rtwdev);
void rtw8852c_tssi(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
void rtw8852c_tssi_scan(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
--
2.25.1

2022-05-03 01:27:44

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 8/8] rtw89: 8852c: rfk: add DPK

DPK is short for digital pre-distortion calibration. It can adjusts digital
waveform according to PA linear characteristics dynamically to enhance
TX EVM.

Do this calibration when we are going to run on AP channel. To prevent
power offset out of boundary, it monitors thermal and set proper boundary
to register.

8852c needs two backup buffers, so we enlarge the array. But, 8852a still
needs only one, so it only uses first element (index zero).

Signed-off-by: Ping-Ke Shih <[email protected]>
---
drivers/net/wireless/realtek/rtw89/core.h | 11 +-
drivers/net/wireless/realtek/rtw89/reg.h | 49 +
.../net/wireless/realtek/rtw89/rtw8852a_rfk.c | 8 +-
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 2 +
.../net/wireless/realtek/rtw89/rtw8852c_rfk.c | 1114 +++++++++++++++++
.../net/wireless/realtek/rtw89/rtw8852c_rfk.h | 2 +
6 files changed, 1178 insertions(+), 8 deletions(-)

diff --git a/drivers/net/wireless/realtek/rtw89/core.h b/drivers/net/wireless/realtek/rtw89/core.h
index 8fd719f93d6c7..2921814842ffa 100644
--- a/drivers/net/wireless/realtek/rtw89/core.h
+++ b/drivers/net/wireless/realtek/rtw89/core.h
@@ -2690,6 +2690,7 @@ struct rtw89_dpk_bkup_para {
enum rtw89_bandwidth bw;
u8 ch;
bool path_ok;
+ u8 mdpd_en;
u8 txagc_dpk;
u8 ther_dpk;
u8 gs;
@@ -2699,11 +2700,12 @@ struct rtw89_dpk_bkup_para {
struct rtw89_dpk_info {
bool is_dpk_enable;
bool is_dpk_reload_en;
- u16 dc_i[RTW89_DPK_RF_PATH];
- u16 dc_q[RTW89_DPK_RF_PATH];
- u8 corr_val[RTW89_DPK_RF_PATH];
- u8 corr_idx[RTW89_DPK_RF_PATH];
+ u16 dc_i[RTW89_DPK_RF_PATH][RTW89_DPK_BKUP_NUM];
+ u16 dc_q[RTW89_DPK_RF_PATH][RTW89_DPK_BKUP_NUM];
+ u8 corr_val[RTW89_DPK_RF_PATH][RTW89_DPK_BKUP_NUM];
+ u8 corr_idx[RTW89_DPK_RF_PATH][RTW89_DPK_BKUP_NUM];
u8 cur_idx[RTW89_DPK_RF_PATH];
+ u8 cur_k_set;
struct rtw89_dpk_bkup_para bp[RTW89_DPK_RF_PATH][RTW89_DPK_BKUP_NUM];
};

@@ -2712,6 +2714,7 @@ struct rtw89_fem_info {
bool elna_5g;
bool epa_2g;
bool epa_5g;
+ bool epa_6g;
};

struct rtw89_phy_ch_info {
diff --git a/drivers/net/wireless/realtek/rtw89/reg.h b/drivers/net/wireless/realtek/rtw89/reg.h
index 120fc13520fcc..6f5d1012c90c6 100644
--- a/drivers/net/wireless/realtek/rtw89/reg.h
+++ b/drivers/net/wireless/realtek/rtw89/reg.h
@@ -3191,6 +3191,7 @@
#define B_AX_GNT_BT_TX_SW_CTRL BIT(0)

#define RR_MOD 0x00
+#define RR_MOD_V1 0x10000
#define RR_MOD_IQK GENMASK(19, 4)
#define RR_MOD_DPK GENMASK(19, 5)
#define RR_MOD_MASK GENMASK(19, 16)
@@ -3357,8 +3358,16 @@
#define RR_DCK2_CYCLE GENMASK(7, 2)
#define RR_DCKC 0x95
#define RR_DCKC_CHK BIT(3)
+#define RR_IQGEN 0x97
+#define RR_IQGEN_BIAS GENMASK(11, 8)
+#define RR_TXIQK 0x98
+#define RR_TXIQK_ATT2 GENMASK(15, 12)
+#define RR_TIA 0x9e
+#define RR_TIA_N6 BIT(8)
#define RR_MIXER 0x9f
#define RR_MIXER_GN GENMASK(4, 3)
+#define RR_LOGEN 0xa3
+#define RR_LOGEN_RPT GENMASK(19, 16)
#define RR_XTALX2 0xb8
#define RR_MALSEL 0xbe
#define RR_LCK_TRG 0xd3
@@ -3370,6 +3379,7 @@
#define RR_RCKD_BW BIT(2)
#define RR_TXADBG 0xde
#define RR_LUTDBG 0xdf
+#define RR_LUTDBG_TIA BIT(12)
#define RR_LUTDBG_LOK BIT(2)
#define RR_LUTWE2 0xee
#define RR_LUTWE2_RTXBW BIT(2)
@@ -3580,6 +3590,8 @@
#define B_TXAGC_TP GENMASK(2, 0)
#define R_TSSI_THER 0x1C10
#define B_TSSI_THER GENMASK(29, 24)
+#define R_TXAGC_BTP 0x1CA0
+#define B_TXAGC_BTP GENMASK(31, 24)
#define R_TXAGC_BB 0x1C60
#define B_TXAGC_BB_OFT GENMASK(31, 16)
#define B_TXAGC_BB GENMASK(31, 24)
@@ -3866,10 +3878,15 @@
#define B_DPD_DIS BIT(14)
#define B_DPD_GDIS BIT(13)
#define B_IQK_RFC_ON BIT(1)
+#define R_TXPWRB 0x56CC
+#define B_TXPWRB_ON BIT(28)
+#define B_TXPWRB_VAL GENMASK(27, 19)
#define R_DPD_OFT_EN 0x5800
#define B_DPD_OFT_EN BIT(28)
#define R_DPD_OFT_ADDR 0x5804
#define B_DPD_OFT_ADDR GENMASK(31, 27)
+#define R_TXPWRB_H 0x580c
+#define B_TXPWRB_RDY BIT(15)
#define R_P0_TMETER 0x5810
#define B_P0_TMETER GENMASK(15, 10)
#define B_P0_TMETER_DIS BIT(16)
@@ -3981,16 +3998,23 @@
#define IQK_DF4_TXT_8_25MHZ 0x021
#define R_IQK_CFG 0x8034
#define B_IQK_CFG_SET GENMASK(5, 4)
+#define R_TPG_SEL 0x8068
#define R_TPG_MOD 0x806C
#define B_TPG_MOD_F GENMASK(2, 1)
#define R_MDPK_SYNC 0x8070
#define B_MDPK_SYNC_SEL BIT(31)
#define B_MDPK_SYNC_MAN GENMASK(31, 28)
#define R_MDPK_RX_DCK 0x8074
+#define B_MDPK_RX_DCK_EN BIT(31)
+#define R_KIP_MOD 0x8078
+#define B_KIP_MOD GENMASK(19, 0)
#define R_NCTL_RW 0x8080
#define R_KIP_SYSCFG 0x8088
#define R_KIP_CLK 0x808C
+#define R_DPK_IDL 0x809C
+#define B_DPK_IDL BIT(8)
#define R_LDL_NORM 0x80A0
+#define B_LDL_NORM_MA BIT(16)
#define B_LDL_NORM_PN GENMASK(12, 8)
#define B_LDL_NORM_OP GENMASK(1, 0)
#define R_DPK_CTL 0x80B0
@@ -4001,12 +4025,19 @@
#define B_DPK_CFG2_ST BIT(14)
#define R_DPK_CFG3 0x80C0
#define R_KPATH_CFG 0x80D0
+#define B_KPATH_CFG_ED GENMASK(21, 20)
#define R_KIP_RPT1 0x80D4
#define B_KIP_RPT1_SEL GENMASK(21, 16)
#define R_SRAM_IQRX 0x80D8
#define R_GAPK 0x80E0
#define B_GAPK_ADR BIT(0)
#define R_SRAM_IQRX2 0x80E8
+#define R_DPK_MPA 0x80EC
+#define B_DPK_MPA_T0 BIT(10)
+#define B_DPK_MPA_T1 BIT(9)
+#define B_DPK_MPA_T2 BIT(8)
+#define R_DPK_WR 0x80F4
+#define B_DPK_WR_ST BIT(29)
#define R_DPK_TRK 0x80f0
#define B_DPK_TRK_DIS BIT(31)
#define R_RPT_COM 0x80FC
@@ -4014,8 +4045,11 @@
#define B_PRT_COM_DCI GENMASK(27, 16)
#define B_PRT_COM_CORV GENMASK(15, 8)
#define B_PRT_COM_DCQ GENMASK(11, 0)
+#define B_PRT_COM_RXOV BIT(8)
#define B_PRT_COM_GL GENMASK(7, 4)
#define B_PRT_COM_CORI GENMASK(7, 0)
+#define B_PRT_COM_RXBB GENMASK(5, 0)
+#define B_PRT_COM_DONE BIT(0)
#define R_COEF_SEL 0x8104
#define B_COEF_SEL_IQC BIT(0)
#define B_COEF_SEL_MDPD BIT(8)
@@ -4045,14 +4079,22 @@
#define B_CFIR_LUT_G2 BIT(2)
#define B_CFIR_LUT_GP_V1 GENMASK(2, 0)
#define B_CFIR_LUT_GP GENMASK(1, 0)
+#define R_DPK_GN 0x819C
+#define B_DPK_GN_EN GENMASK(17, 16)
+#define B_DPK_GN_AG GENMASK(9, 0)
#define R_DPD_V1 0x81a0
+#define B_DPD_LBK BIT(7)
#define R_DPD_CH0 0x81AC
#define R_DPD_BND 0x81B4
#define R_DPD_CH0A 0x81BC
+#define B_DPD_MEN GENMASK(31, 28)
+#define B_DPD_ORDER GENMASK(26, 24)
+#define B_DPD_SEL GENMASK(13, 8)
#define R_TXAGC_RFK 0x81C4
#define B_TXAGC_RFK_CH0 GENMASK(5, 0)
#define R_DPD_COM 0x81C8
#define R_KIP_IQP 0x81CC
+#define B_KIP_IQP_SW GENMASK(13, 12)
#define B_KIP_IQP_IQSW GENMASK(5, 0)
#define R_KIP_RPT 0x81D4
#define B_KIP_RPT_SEL GENMASK(21, 16)
@@ -4060,8 +4102,15 @@
#define R_LOAD_COEF 0x81DC
#define B_LOAD_COEF_MDPD BIT(16)
#define B_LOAD_COEF_CFIR GENMASK(1, 0)
+#define B_LOAD_COEF_DI BIT(1)
#define B_LOAD_COEF_AUTO BIT(0)
+#define R_DPK_GL 0x81F0
+#define B_DPK_GL_A0 GENMASK(31, 28)
+#define B_DPK_GL_A1 GENMASK(17, 0)
#define R_RPT_PER 0x81FC
+#define B_RPT_PER_TSSI GENMASK(28, 16)
+#define B_RPT_PER_OF GENMASK(15, 8)
+#define B_RPT_PER_TH GENMASK(5, 0)
#define R_RXCFIR_P0C0 0x8D40
#define R_RXCFIR_P0C1 0x8D84
#define R_RXCFIR_P0C2 0x8DC8
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852a_rfk.c b/drivers/net/wireless/realtek/rtw89/rtw8852a_rfk.c
index aa782534e76be..e3c2fce326516 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852a_rfk.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852a_rfk.c
@@ -2189,8 +2189,8 @@ static bool _dpk_sync_check(struct rtw89_dev *rtwdev,
"[DPK] S%d Corr_idx / Corr_val = %d / %d\n", path, corr_idx,
corr_val);

- dpk->corr_idx[path] = corr_idx;
- dpk->corr_val[path] = corr_val;
+ dpk->corr_idx[path][0] = corr_idx;
+ dpk->corr_val[path][0] = corr_val;

rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0x9);

@@ -2203,8 +2203,8 @@ static bool _dpk_sync_check(struct rtw89_dev *rtwdev,
rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d DC I/Q, = %d / %d\n",
path, dc_i, dc_q);

- dpk->dc_i[path] = dc_i;
- dpk->dc_q[path] = dc_q;
+ dpk->dc_i[path][0] = dc_i;
+ dpk->dc_q[path][0] = dc_q;

if (dc_i > DPK_SYNC_TH_DC_I || dc_q > DPK_SYNC_TH_DC_Q ||
corr_val < DPK_SYNC_TH_CORR)
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c.c b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
index 0b722675aad42..4fb3de71d032f 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
@@ -1789,6 +1789,7 @@ static void rtw8852c_rfk_channel(struct rtw89_dev *rtwdev)
rtw8852c_rx_dck(rtwdev, phy_idx, false);
rtw8852c_iqk(rtwdev, phy_idx);
rtw8852c_tssi(rtwdev, phy_idx);
+ rtw8852c_dpk(rtwdev, phy_idx);
rtw89_fw_h2c_rf_ntfy_mcc(rtwdev);
}

@@ -1804,6 +1805,7 @@ static void rtw8852c_rfk_scan(struct rtw89_dev *rtwdev, bool start)

static void rtw8852c_rfk_track(struct rtw89_dev *rtwdev)
{
+ rtw8852c_dpk_track(rtwdev);
rtw8852c_lck_track(rtwdev);
}

diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
index 3108fa9cd5b20..ffc71ad249270 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
@@ -55,6 +55,11 @@ static const u32 _txk_g_track_range[TXK_GROUP_NR] = {0x5, 0x6, 0x6};
static const u32 _txk_g_gain_bb[TXK_GROUP_NR] = {0x0e, 0x0a, 0x0e};
static const u32 _txk_g_itqt[TXK_GROUP_NR] = { 0x12, 0x12, 0x12};

+static const u32 dpk_par_regs[RTW89_DPK_RF_PATH][4] = {
+ {0x8190, 0x8194, 0x8198, 0x81a4},
+ {0x81a8, 0x81c4, 0x81c8, 0x81e8},
+};
+
static u8 _kpath(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx)
{
rtw89_debug(rtwdev, RTW89_DBG_RFK, "[RFK]dbcc_en: %x, PHY%d\n",
@@ -1568,6 +1573,1093 @@ static void _set_rx_dck(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy, u8 pat
}
}

+#define RTW8852C_RF_REL_VERSION 34
+#define RTW8852C_DPK_VER 0x10
+#define RTW8852C_DPK_TH_AVG_NUM 4
+#define RTW8852C_DPK_RF_PATH 2
+#define RTW8852C_DPK_KIP_REG_NUM 5
+#define RTW8852C_DPK_RXSRAM_DBG 0
+
+enum rtw8852c_dpk_id {
+ LBK_RXIQK = 0x06,
+ SYNC = 0x10,
+ MDPK_IDL = 0x11,
+ MDPK_MPA = 0x12,
+ GAIN_LOSS = 0x13,
+ GAIN_CAL = 0x14,
+ DPK_RXAGC = 0x15,
+ KIP_PRESET = 0x16,
+ KIP_RESTORE = 0x17,
+ DPK_TXAGC = 0x19,
+ D_KIP_PRESET = 0x28,
+ D_TXAGC = 0x29,
+ D_RXAGC = 0x2a,
+ D_SYNC = 0x2b,
+ D_GAIN_LOSS = 0x2c,
+ D_MDPK_IDL = 0x2d,
+ D_GAIN_NORM = 0x2f,
+ D_KIP_THERMAL = 0x30,
+ D_KIP_RESTORE = 0x31
+};
+
+#define DPK_TXAGC_LOWER 0x2e
+#define DPK_TXAGC_UPPER 0x3f
+#define DPK_TXAGC_INVAL 0xff
+
+enum dpk_agc_step {
+ DPK_AGC_STEP_SYNC_DGAIN,
+ DPK_AGC_STEP_GAIN_LOSS_IDX,
+ DPK_AGC_STEP_GL_GT_CRITERION,
+ DPK_AGC_STEP_GL_LT_CRITERION,
+ DPK_AGC_STEP_SET_TX_GAIN,
+};
+
+static void _rf_direct_cntrl(struct rtw89_dev *rtwdev,
+ enum rtw89_rf_path path, bool is_bybb)
+{
+ if (is_bybb)
+ rtw89_write_rf(rtwdev, path, RR_RSV1, RR_RSV1_RST, 0x1);
+ else
+ rtw89_write_rf(rtwdev, path, RR_RSV1, RR_RSV1_RST, 0x0);
+}
+
+static void _dpk_onoff(struct rtw89_dev *rtwdev,
+ enum rtw89_rf_path path, bool off);
+
+static void _dpk_bkup_kip(struct rtw89_dev *rtwdev, const u32 reg[],
+ u32 reg_bkup[][RTW8852C_DPK_KIP_REG_NUM], u8 path)
+{
+ u8 i;
+
+ for (i = 0; i < RTW8852C_DPK_KIP_REG_NUM; i++) {
+ reg_bkup[path][i] =
+ rtw89_phy_read32_mask(rtwdev, reg[i] + (path << 8), MASKDWORD);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Backup 0x%x = %x\n",
+ reg[i] + (path << 8), reg_bkup[path][i]);
+ }
+}
+
+static void _dpk_reload_kip(struct rtw89_dev *rtwdev, const u32 reg[],
+ u32 reg_bkup[][RTW8852C_DPK_KIP_REG_NUM], u8 path)
+{
+ u8 i;
+
+ for (i = 0; i < RTW8852C_DPK_KIP_REG_NUM; i++) {
+ rtw89_phy_write32_mask(rtwdev, reg[i] + (path << 8),
+ MASKDWORD, reg_bkup[path][i]);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Reload 0x%x = %x\n",
+ reg[i] + (path << 8), reg_bkup[path][i]);
+ }
+}
+
+static u8 _dpk_one_shot(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, enum rtw8852c_dpk_id id)
+{
+ u16 dpk_cmd;
+ u32 val;
+ int ret;
+
+ dpk_cmd = (u16)((id << 8) | (0x19 + path * 0x12));
+
+ rtw89_phy_write32_mask(rtwdev, R_NCTL_CFG, MASKDWORD, dpk_cmd);
+
+ ret = read_poll_timeout_atomic(rtw89_phy_read32_mask, val, val == 0x55,
+ 10, 20000, false, rtwdev, 0xbff8, MASKBYTE0);
+ mdelay(10);
+ rtw89_phy_write32_clr(rtwdev, R_NCTL_N1, MASKBYTE0);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] one-shot for %s = 0x%x (ret=%d)\n",
+ id == 0x06 ? "LBK_RXIQK" :
+ id == 0x10 ? "SYNC" :
+ id == 0x11 ? "MDPK_IDL" :
+ id == 0x12 ? "MDPK_MPA" :
+ id == 0x13 ? "GAIN_LOSS" : "PWR_CAL",
+ dpk_cmd, ret);
+
+ if (ret) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] one-shot over 20ms!!!!\n");
+ return 1;
+ }
+
+ return 0;
+}
+
+static void _dpk_information(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ struct rtw89_hal *hal = &rtwdev->hal;
+
+ u8 kidx = dpk->cur_idx[path];
+
+ dpk->bp[path][kidx].band = hal->current_band_type;
+ dpk->bp[path][kidx].ch = hal->current_channel;
+ dpk->bp[path][kidx].bw = hal->current_band_width;
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] S%d[%d] (PHY%d): TSSI %s/ DBCC %s/ %s/ CH%d/ %s\n",
+ path, dpk->cur_idx[path], phy,
+ rtwdev->is_tssi_mode[path] ? "on" : "off",
+ rtwdev->dbcc_en ? "on" : "off",
+ dpk->bp[path][kidx].band == 0 ? "2G" :
+ dpk->bp[path][kidx].band == 1 ? "5G" : "6G",
+ dpk->bp[path][kidx].ch,
+ dpk->bp[path][kidx].bw == 0 ? "20M" :
+ dpk->bp[path][kidx].bw == 1 ? "40M" : "80M");
+}
+
+static void _dpk_bb_afe_setting(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kpath)
+{
+ /*1. Keep ADC_fifo reset*/
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A0 << path, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A1 << path, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A2 << path, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A3 << path, 0x0);
+
+ /*2. BB for IQK DBG mode*/
+ rtw89_phy_write32_mask(rtwdev, R_UPD_CLK + (path << 13), MASKDWORD, 0xd801dffd);
+
+ /*3.Set DAC clk*/
+ rtw8852c_txck_force(rtwdev, path, true, DAC_960M);
+
+ /*4. Set ADC clk*/
+ rtw8852c_rxck_force(rtwdev, path, true, ADC_1920M);
+ rtw89_phy_write32_mask(rtwdev, R_P0_CFCH_BW0 + (path << 8), B_P0_CFCH_BW0, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_P0_CFCH_BW1 + (path << 8), B_P0_CFCH_BW1, 0xb);
+ rtw89_phy_write32_mask(rtwdev, R_P0_NRBW + (path << 13),
+ B_P0_NRBW_DBG, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ANAPAR_PW15, MASKBYTE3, 0x1f);
+ rtw89_phy_write32_mask(rtwdev, R_ANAPAR_PW15, MASKBYTE3, 0x13);
+ rtw89_phy_write32_mask(rtwdev, R_ANAPAR, MASKHWORD, 0x0001);
+ rtw89_phy_write32_mask(rtwdev, R_ANAPAR, MASKHWORD, 0x0041);
+
+ /*5. ADDA fifo rst*/
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A1 << path, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A3 << path, 0x1);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d BB/AFE setting\n", path);
+}
+
+static void _dpk_bb_afe_restore(struct rtw89_dev *rtwdev, u8 path)
+{
+ rtw89_phy_write32_mask(rtwdev, R_P0_NRBW + (path << 13),
+ B_P0_NRBW_DBG, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A0 << path, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A1 << path, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A2 << path, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A3 << path, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_UPD_CLK + (path << 13), MASKDWORD, 0x00000000);
+ rtw89_phy_write32_mask(rtwdev, R_P0_RXCK + (path << 13), B_P0_TXCK_ALL, 0x00);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A0 << path, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_ADC_FIFO, B_ADC_FIFO_A2 << path, 0x0);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d BB/AFE restore\n", path);
+}
+
+static void _dpk_tssi_pause(struct rtw89_dev *rtwdev,
+ enum rtw89_rf_path path, bool is_pause)
+{
+ rtw89_phy_write32_mask(rtwdev, R_P0_TSSI_TRK + (path << 13),
+ B_P0_TSSI_TRK_EN, is_pause);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d TSSI %s\n", path,
+ is_pause ? "pause" : "resume");
+}
+
+static void _dpk_kip_control_rfc(struct rtw89_dev *rtwdev, u8 path, bool ctrl_by_kip)
+{
+ rtw89_phy_write32_mask(rtwdev, R_UPD_CLK + (path << 13), B_IQK_RFC_ON, ctrl_by_kip);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] RFC is controlled by %s\n",
+ ctrl_by_kip ? "KIP" : "BB");
+}
+
+static void _dpk_txpwr_bb_force(struct rtw89_dev *rtwdev, u8 path, bool force)
+{
+ rtw89_phy_write32_mask(rtwdev, R_TXPWRB + (path << 13), B_TXPWRB_ON, force);
+ rtw89_phy_write32_mask(rtwdev, R_TXPWRB_H + (path << 13), B_TXPWRB_RDY, force);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d txpwr_bb_force %s\n",
+ path, force ? "on" : "off");
+}
+
+static void _dpk_kip_restore(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ _dpk_one_shot(rtwdev, phy, path, D_KIP_RESTORE);
+ _dpk_kip_control_rfc(rtwdev, path, false);
+ _dpk_txpwr_bb_force(rtwdev, path, false);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d restore KIP\n", path);
+}
+
+static void _dpk_lbk_rxiqk(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+#define RX_TONE_IDX 0x00250025 /* Q.2 9.25MHz */
+ u8 cur_rxbb;
+ u32 rf_11, reg_81cc;
+
+ rtw89_phy_write32_mask(rtwdev, R_DPD_V1 + (path << 8), B_DPD_LBK, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_MDPK_RX_DCK, B_MDPK_RX_DCK_EN, 0x1);
+
+ _dpk_kip_control_rfc(rtwdev, path, false);
+
+ cur_rxbb = rtw89_read_rf(rtwdev, path, RR_MOD, RR_MOD_M_RXBB);
+ rf_11 = rtw89_read_rf(rtwdev, path, RR_TXIG, RFREG_MASK);
+ reg_81cc = rtw89_phy_read32_mask(rtwdev, R_KIP_IQP + (path << 8),
+ B_KIP_IQP_SW);
+
+ rtw89_write_rf(rtwdev, path, RR_TXIG, RR_TXIG_GR0, 0x0);
+ rtw89_write_rf(rtwdev, path, RR_TXIG, RR_TXIG_GR1, 0x3);
+ rtw89_write_rf(rtwdev, path, RR_TXIG, RR_TXIG_TG, 0xd);
+ rtw89_write_rf(rtwdev, path, RR_MOD, RR_MOD_M_RXBB, 0x1f);
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_IQP + (path << 8), B_KIP_IQP_IQSW, 0x12);
+ rtw89_phy_write32_mask(rtwdev, R_KIP_IQP + (path << 8), B_KIP_IQP_SW, 0x3);
+
+ _dpk_kip_control_rfc(rtwdev, path, true);
+
+ rtw89_phy_write32_mask(rtwdev, R_IQK_DIF4, MASKDWORD, RX_TONE_IDX);
+
+ _dpk_one_shot(rtwdev, phy, path, LBK_RXIQK);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d LBK RXIQC = 0x%x\n", path,
+ rtw89_phy_read32_mask(rtwdev, R_RXIQC + (path << 8), MASKDWORD));
+
+ _dpk_kip_control_rfc(rtwdev, path, false);
+
+ rtw89_write_rf(rtwdev, path, RR_TXIG, RFREG_MASK, rf_11);
+ rtw89_write_rf(rtwdev, path, RR_MOD, RR_MOD_M_RXBB, cur_rxbb);
+ rtw89_phy_write32_mask(rtwdev, R_KIP_IQP + (path << 8), B_KIP_IQP_SW, reg_81cc);
+
+ rtw89_phy_write32_mask(rtwdev, R_MDPK_RX_DCK, B_MDPK_RX_DCK_EN, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_KPATH_CFG, B_KPATH_CFG_ED, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_LOAD_COEF + (path << 8), B_LOAD_COEF_DI, 0x1);
+
+ _dpk_kip_control_rfc(rtwdev, path, true);
+}
+
+static void _dpk_rf_setting(struct rtw89_dev *rtwdev, u8 gain,
+ enum rtw89_rf_path path, u8 kidx)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+
+ if (dpk->bp[path][kidx].band == RTW89_BAND_2G) {
+ rtw89_write_rf(rtwdev, path, RR_MOD, RFREG_MASK,
+ 0x50121 | BIT(rtwdev->dbcc_en));
+ rtw89_write_rf(rtwdev, path, RR_MOD_V1, RR_MOD_MASK, RF_DPK);
+ rtw89_write_rf(rtwdev, path, RR_RXBB, RR_RXBB_ATTC, 0x2);
+ rtw89_write_rf(rtwdev, path, RR_RXBB, RR_RXBB_ATTR, 0x4);
+ rtw89_write_rf(rtwdev, path, RR_LUTDBG, RR_LUTDBG_TIA, 0x1);
+ rtw89_write_rf(rtwdev, path, RR_TIA, RR_TIA_N6, 0x1);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] RF 0x0/0x83/0x9e/0x1a/0xdf/0x1001a = 0x%x/ 0x%x/ 0x%x/ 0x%x/ 0x%x/ 0x%x\n",
+ rtw89_read_rf(rtwdev, path, RR_MOD, RFREG_MASK),
+ rtw89_read_rf(rtwdev, path, RR_RXBB, RFREG_MASK),
+ rtw89_read_rf(rtwdev, path, RR_TIA, RFREG_MASK),
+ rtw89_read_rf(rtwdev, path, RR_BTC, RFREG_MASK),
+ rtw89_read_rf(rtwdev, path, RR_LUTDBG, RFREG_MASK),
+ rtw89_read_rf(rtwdev, path, 0x1001a, RFREG_MASK));
+ } else {
+ rtw89_write_rf(rtwdev, path, RR_MOD, RFREG_MASK,
+ 0x50101 | BIT(rtwdev->dbcc_en));
+ rtw89_write_rf(rtwdev, path, RR_MOD_V1, RR_MOD_MASK, RF_DPK);
+
+ if (dpk->bp[path][kidx].band == RTW89_BAND_6G && dpk->bp[path][kidx].ch >= 161) {
+ rtw89_write_rf(rtwdev, path, RR_IQGEN, RR_IQGEN_BIAS, 0x8);
+ rtw89_write_rf(rtwdev, path, RR_LOGEN, RR_LOGEN_RPT, 0xd);
+ } else {
+ rtw89_write_rf(rtwdev, path, RR_LOGEN, RR_LOGEN_RPT, 0xd);
+ }
+
+ rtw89_write_rf(rtwdev, path, RR_RXA2, RR_RXA2_ATT, 0x0);
+ rtw89_write_rf(rtwdev, path, RR_TXIQK, RR_TXIQK_ATT2, 0x3);
+ rtw89_write_rf(rtwdev, path, RR_LUTDBG, RR_LUTDBG_TIA, 0x1);
+ rtw89_write_rf(rtwdev, path, RR_TIA, RR_TIA_N6, 0x1);
+
+ if (dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_160)
+ rtw89_write_rf(rtwdev, path, RR_RXBB2, RR_RXBB2_EBW, 0x0);
+ }
+}
+
+static void _dpk_tpg_sel(struct rtw89_dev *rtwdev, enum rtw89_rf_path path, u8 kidx)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+
+ if (dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_160) {
+ rtw89_phy_write32_mask(rtwdev, R_TPG_MOD, B_TPG_MOD_F, 0x3);
+ rtw89_phy_write32_mask(rtwdev, R_TPG_SEL, MASKDWORD, 0x0180ff30);
+ } else if (dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_80) {
+ rtw89_phy_write32_mask(rtwdev, R_TPG_MOD, B_TPG_MOD_F, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_TPG_SEL, MASKDWORD, 0xffe0fa00);
+ } else if (dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_40) {
+ rtw89_phy_write32_mask(rtwdev, R_TPG_MOD, B_TPG_MOD_F, 0x2);
+ rtw89_phy_write32_mask(rtwdev, R_TPG_SEL, MASKDWORD, 0xff4009e0);
+ } else {
+ rtw89_phy_write32_mask(rtwdev, R_TPG_MOD, B_TPG_MOD_F, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_TPG_SEL, MASKDWORD, 0xf9f007d0);
+ }
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] TPG_Select for %s\n",
+ dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_160 ? "160M" :
+ dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_80 ? "80M" :
+ dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_40 ? "40M" : "20M");
+}
+
+static bool _dpk_sync_check(struct rtw89_dev *rtwdev, enum rtw89_rf_path path, u8 kidx)
+{
+#define DPK_SYNC_TH_DC_I 200
+#define DPK_SYNC_TH_DC_Q 200
+#define DPK_SYNC_TH_CORR 170
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u16 dc_i, dc_q;
+ u8 corr_val, corr_idx, rxbb;
+ u8 rxbb_ov;
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0x0);
+
+ corr_idx = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_CORI);
+ corr_val = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_CORV);
+
+ dpk->corr_idx[path][kidx] = corr_idx;
+ dpk->corr_val[path][kidx] = corr_val;
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0x9);
+
+ dc_i = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_DCI);
+ dc_q = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_DCQ);
+
+ dc_i = abs(sign_extend32(dc_i, 11));
+ dc_q = abs(sign_extend32(dc_q, 11));
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] S%d Corr_idx/ Corr_val /DC I/Q, = %d / %d / %d / %d\n",
+ path, corr_idx, corr_val, dc_i, dc_q);
+
+ dpk->dc_i[path][kidx] = dc_i;
+ dpk->dc_q[path][kidx] = dc_q;
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0x8);
+ rxbb = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_RXBB);
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0x31);
+ rxbb_ov = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_RXOV);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] S%d RXBB/ RXAGC_done /RXBB_ovlmt = %d / %d / %d\n",
+ path, rxbb,
+ rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_DONE),
+ rxbb_ov);
+
+ if (dc_i > DPK_SYNC_TH_DC_I || dc_q > DPK_SYNC_TH_DC_Q ||
+ corr_val < DPK_SYNC_TH_CORR)
+ return true;
+ else
+ return false;
+}
+
+static u16 _dpk_dgain_read(struct rtw89_dev *rtwdev)
+{
+ u16 dgain = 0x0;
+
+ rtw89_phy_write32_clr(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL);
+
+ dgain = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_DCI);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] DGain = 0x%x (%d)\n", dgain, dgain);
+
+ return dgain;
+}
+
+static u8 _dpk_gainloss_read(struct rtw89_dev *rtwdev)
+{
+ u8 result;
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0x6);
+ rtw89_phy_write32_mask(rtwdev, R_DPK_CFG2, B_DPK_CFG2_ST, 0x1);
+
+ result = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_GL);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] tmp GL = %d\n", result);
+
+ return result;
+}
+
+static void _dpk_kset_query(struct rtw89_dev *rtwdev, enum rtw89_rf_path path)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT + (path << 8), B_KIP_RPT_SEL, 0x10);
+ dpk->cur_k_set =
+ rtw89_phy_read32_mask(rtwdev, R_RPT_PER + (path << 8), 0xE0000000) - 1;
+}
+
+static void _dpk_kip_set_txagc(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 dbm, bool set_from_bb)
+{
+ if (set_from_bb) {
+ dbm = clamp_t(u8, dbm, 7, 24);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] set S%d txagc to %ddBm\n", path, dbm);
+ rtw89_phy_write32_mask(rtwdev, R_TXPWRB + (path << 13), B_TXPWRB_VAL, dbm << 2);
+ }
+ _dpk_one_shot(rtwdev, phy, path, D_TXAGC);
+ _dpk_kset_query(rtwdev, path);
+}
+
+static u8 _dpk_gainloss(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kidx)
+{
+ _dpk_one_shot(rtwdev, phy, path, D_GAIN_LOSS);
+ _dpk_kip_set_txagc(rtwdev, phy, path, 0xff, false);
+
+ rtw89_phy_write32_mask(rtwdev, R_DPK_GL + (path << 8), B_DPK_GL_A1, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_DPK_GL + (path << 8), B_DPK_GL_A0, 0x0);
+
+ return _dpk_gainloss_read(rtwdev);
+}
+
+static bool _dpk_pas_read(struct rtw89_dev *rtwdev, bool is_check)
+{
+ u32 val1_i = 0, val1_q = 0, val2_i = 0, val2_q = 0;
+ u8 i;
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, MASKBYTE2, 0x06);
+ rtw89_phy_write32_mask(rtwdev, R_DPK_CFG2, B_DPK_CFG2_ST, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_DPK_CFG3, MASKBYTE2, 0x08);
+
+ if (is_check) {
+ rtw89_phy_write32_mask(rtwdev, R_DPK_CFG3, MASKBYTE3, 0x00);
+ val1_i = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, MASKHWORD);
+ val1_i = abs(sign_extend32(val1_i, 11));
+ val1_q = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, MASKLWORD);
+ val1_q = abs(sign_extend32(val1_q, 11));
+
+ rtw89_phy_write32_mask(rtwdev, R_DPK_CFG3, MASKBYTE3, 0x1f);
+ val2_i = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, MASKHWORD);
+ val2_i = abs(sign_extend32(val2_i, 11));
+ val2_q = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, MASKLWORD);
+ val2_q = abs(sign_extend32(val2_q, 11));
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] PAS_delta = 0x%x\n",
+ phy_div(val1_i * val1_i + val1_q * val1_q,
+ val2_i * val2_i + val2_q * val2_q));
+ } else {
+ for (i = 0; i < 32; i++) {
+ rtw89_phy_write32_mask(rtwdev, R_DPK_CFG3, MASKBYTE3, i);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] PAS_Read[%02d]= 0x%08x\n", i,
+ rtw89_phy_read32_mask(rtwdev, R_RPT_COM, MASKDWORD));
+ }
+ }
+
+ if (val1_i * val1_i + val1_q * val1_q >= (val2_i * val2_i + val2_q * val2_q) * 8 / 5)
+ return true;
+ else
+ return false;
+}
+
+static bool _dpk_kip_set_rxagc(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kidx)
+{
+ _dpk_one_shot(rtwdev, phy, path, D_RXAGC);
+
+ return _dpk_sync_check(rtwdev, path, kidx);
+}
+
+static void _dpk_read_rxsram(struct rtw89_dev *rtwdev)
+{
+ u32 addr;
+
+ rtw89_rfk_parser(rtwdev, &rtw8852c_read_rxsram_pre_defs_tbl);
+
+ for (addr = 0; addr < 0x200; addr++) {
+ rtw89_phy_write32_mask(rtwdev, R_SRAM_IQRX, MASKDWORD, 0x00010000 | addr);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] RXSRAM[%03d] = 0x%07x\n", addr,
+ rtw89_phy_read32_mask(rtwdev, R_RPT_COM, MASKDWORD));
+ }
+
+ rtw89_rfk_parser(rtwdev, &rtw8852c_read_rxsram_post_defs_tbl);
+}
+
+static void _dpk_bypass_rxiqc(struct rtw89_dev *rtwdev, enum rtw89_rf_path path)
+{
+ rtw89_phy_write32_mask(rtwdev, R_DPD_V1 + (path << 8), B_DPD_LBK, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_RXIQC + (path << 8), MASKDWORD, 0x40000002);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Bypass RXIQC\n");
+}
+
+static u8 _dpk_agc(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kidx, u8 init_xdbm, u8 loss_only)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u8 step = DPK_AGC_STEP_SYNC_DGAIN;
+ u8 tmp_dbm = init_xdbm, tmp_gl_idx = 0;
+ u8 tmp_rxbb;
+ u8 goout = 0, agc_cnt = 0;
+ u16 dgain = 0;
+ bool is_fail = false;
+ int limit = 200;
+
+ do {
+ switch (step) {
+ case DPK_AGC_STEP_SYNC_DGAIN:
+ is_fail = _dpk_kip_set_rxagc(rtwdev, phy, path, kidx);
+
+ if (RTW8852C_DPK_RXSRAM_DBG)
+ _dpk_read_rxsram(rtwdev);
+
+ if (is_fail) {
+ goout = 1;
+ break;
+ }
+
+ dgain = _dpk_dgain_read(rtwdev);
+
+ if (dgain > 0x5fc || dgain < 0x556) {
+ _dpk_one_shot(rtwdev, phy, path, D_SYNC);
+ dgain = _dpk_dgain_read(rtwdev);
+ }
+
+ if (agc_cnt == 0) {
+ if (dpk->bp[path][kidx].band == RTW89_BAND_2G)
+ _dpk_bypass_rxiqc(rtwdev, path);
+ else
+ _dpk_lbk_rxiqk(rtwdev, phy, path);
+ }
+ step = DPK_AGC_STEP_GAIN_LOSS_IDX;
+ break;
+
+ case DPK_AGC_STEP_GAIN_LOSS_IDX:
+ tmp_gl_idx = _dpk_gainloss(rtwdev, phy, path, kidx);
+
+ if ((tmp_gl_idx == 0 && _dpk_pas_read(rtwdev, true)) ||
+ tmp_gl_idx >= 7)
+ step = DPK_AGC_STEP_GL_GT_CRITERION;
+ else if (tmp_gl_idx == 0)
+ step = DPK_AGC_STEP_GL_LT_CRITERION;
+ else
+ step = DPK_AGC_STEP_SET_TX_GAIN;
+ break;
+
+ case DPK_AGC_STEP_GL_GT_CRITERION:
+ if (tmp_dbm <= 7) {
+ goout = 1;
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Txagc@lower bound!!\n");
+ } else {
+ tmp_dbm = max_t(u8, tmp_dbm - 3, 7);
+ _dpk_kip_set_txagc(rtwdev, phy, path, tmp_dbm, true);
+ }
+ step = DPK_AGC_STEP_SYNC_DGAIN;
+ agc_cnt++;
+ break;
+
+ case DPK_AGC_STEP_GL_LT_CRITERION:
+ if (tmp_dbm >= 24) {
+ goout = 1;
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Txagc@upper bound!!\n");
+ } else {
+ tmp_dbm = min_t(u8, tmp_dbm + 2, 24);
+ _dpk_kip_set_txagc(rtwdev, phy, path, tmp_dbm, true);
+ }
+ step = DPK_AGC_STEP_SYNC_DGAIN;
+ agc_cnt++;
+ break;
+
+ case DPK_AGC_STEP_SET_TX_GAIN:
+ _dpk_kip_control_rfc(rtwdev, path, false);
+ tmp_rxbb = rtw89_read_rf(rtwdev, path, RR_MOD, RR_MOD_M_RXBB);
+ if (tmp_rxbb + tmp_gl_idx > 0x1f)
+ tmp_rxbb = 0x1f;
+ else
+ tmp_rxbb = tmp_rxbb + tmp_gl_idx;
+
+ rtw89_write_rf(rtwdev, path, RR_MOD, RR_MOD_M_RXBB, tmp_rxbb);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Adjust RXBB (%+d) = 0x%x\n",
+ tmp_gl_idx, tmp_rxbb);
+ _dpk_kip_control_rfc(rtwdev, path, true);
+ goout = 1;
+ break;
+ default:
+ goout = 1;
+ break;
+ }
+ } while (!goout && agc_cnt < 6 && --limit > 0);
+
+ if (limit <= 0)
+ rtw89_warn(rtwdev, "[DPK] exceed loop limit\n");
+
+ return is_fail;
+}
+
+static void _dpk_set_mdpd_para(struct rtw89_dev *rtwdev, u8 order)
+{
+ static const struct rtw89_rfk_tbl *order_tbls[] = {
+ &rtw8852c_dpk_mdpd_order0_defs_tbl,
+ &rtw8852c_dpk_mdpd_order1_defs_tbl,
+ &rtw8852c_dpk_mdpd_order2_defs_tbl,
+ &rtw8852c_dpk_mdpd_order3_defs_tbl,
+ };
+
+ if (order >= ARRAY_SIZE(order_tbls)) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Wrong MDPD order!!(0x%x)\n", order);
+ return;
+ }
+
+ rtw89_rfk_parser(rtwdev, order_tbls[order]);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Set %s for IDL\n",
+ order == 0x0 ? "(5,3,1)" :
+ order == 0x1 ? "(5,3,0)" :
+ order == 0x2 ? "(5,0,0)" : "(7,3,1)");
+}
+
+static void _dpk_idl_mpa(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kidx)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u8 cnt;
+ u8 ov_flag;
+ u32 dpk_sync;
+
+ rtw89_phy_write32_mask(rtwdev, R_LDL_NORM, B_LDL_NORM_MA, 0x1);
+
+ if (rtw89_phy_read32_mask(rtwdev, R_DPK_MPA, B_DPK_MPA_T2) == 0x1)
+ _dpk_set_mdpd_para(rtwdev, 0x2);
+ else if (rtw89_phy_read32_mask(rtwdev, R_DPK_MPA, B_DPK_MPA_T1) == 0x1)
+ _dpk_set_mdpd_para(rtwdev, 0x1);
+ else if (rtw89_phy_read32_mask(rtwdev, R_DPK_MPA, B_DPK_MPA_T0) == 0x1)
+ _dpk_set_mdpd_para(rtwdev, 0x0);
+ else if (dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_5 ||
+ dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_10 ||
+ dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_20)
+ _dpk_set_mdpd_para(rtwdev, 0x2);
+ else if (dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_40 ||
+ dpk->bp[path][kidx].bw == RTW89_CHANNEL_WIDTH_80)
+ _dpk_set_mdpd_para(rtwdev, 0x1);
+ else
+ _dpk_set_mdpd_para(rtwdev, 0x0);
+
+ rtw89_phy_write32_mask(rtwdev, R_DPK_IDL, B_DPK_IDL, 0x0);
+ fsleep(1000);
+
+ _dpk_one_shot(rtwdev, phy, path, D_MDPK_IDL);
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0x0);
+ dpk_sync = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, MASKDWORD);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] dpk_sync = 0x%x\n", dpk_sync);
+
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0xf);
+ ov_flag = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_SYNERR);
+ for (cnt = 0; cnt < 5 && ov_flag == 0x1; cnt++) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] ReK due to MDPK ov!!!\n");
+ _dpk_one_shot(rtwdev, phy, path, D_MDPK_IDL);
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT1, B_KIP_RPT1_SEL, 0xf);
+ ov_flag = rtw89_phy_read32_mask(rtwdev, R_RPT_COM, B_PRT_COM_SYNERR);
+ }
+
+ if (ov_flag) {
+ _dpk_set_mdpd_para(rtwdev, 0x2);
+ _dpk_one_shot(rtwdev, phy, path, D_MDPK_IDL);
+ }
+}
+
+static bool _dpk_reload_check(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ bool is_reload = false;
+ u8 idx, cur_band, cur_ch;
+
+ cur_band = rtwdev->hal.current_band_type;
+ cur_ch = rtwdev->hal.current_channel;
+
+ for (idx = 0; idx < RTW89_DPK_BKUP_NUM; idx++) {
+ if (cur_band != dpk->bp[path][idx].band ||
+ cur_ch != dpk->bp[path][idx].ch)
+ continue;
+
+ rtw89_phy_write32_mask(rtwdev, R_COEF_SEL + (path << 8),
+ B_COEF_SEL_MDPD, idx);
+ dpk->cur_idx[path] = idx;
+ is_reload = true;
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] reload S%d[%d] success\n", path, idx);
+ }
+
+ return is_reload;
+}
+
+static void _dpk_kip_pwr_clk_onoff(struct rtw89_dev *rtwdev, bool turn_on)
+{
+ rtw89_rfk_parser(rtwdev, turn_on ? &rtw8852c_dpk_kip_pwr_clk_on_defs_tbl :
+ &rtw8852c_dpk_kip_pwr_clk_off_defs_tbl);
+}
+
+static void _dpk_kip_preset_8852c(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kidx)
+{
+ rtw89_phy_write32_mask(rtwdev, R_KIP_MOD, B_KIP_MOD,
+ rtw89_read_rf(rtwdev, path, RR_MOD, RFREG_MASK));
+
+ if (rtwdev->hal.cv == CHIP_CAV)
+ rtw89_phy_write32_mask(rtwdev,
+ R_DPD_CH0A + (path << 8) + (kidx << 2),
+ B_DPD_SEL, 0x01);
+ else
+ rtw89_phy_write32_mask(rtwdev,
+ R_DPD_CH0A + (path << 8) + (kidx << 2),
+ B_DPD_SEL, 0x0c);
+
+ _dpk_kip_control_rfc(rtwdev, path, true);
+ rtw89_phy_write32_mask(rtwdev, R_COEF_SEL + (path << 8), B_COEF_SEL_MDPD, kidx);
+
+ _dpk_one_shot(rtwdev, phy, path, D_KIP_PRESET);
+}
+
+static void _dpk_para_query(struct rtw89_dev *rtwdev, enum rtw89_rf_path path, u8 kidx)
+{
+#define _DPK_PARA_TXAGC GENMASK(15, 10)
+#define _DPK_PARA_THER GENMASK(31, 26)
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u32 para;
+
+ para = rtw89_phy_read32_mask(rtwdev, dpk_par_regs[kidx][dpk->cur_k_set] + (path << 8),
+ MASKDWORD);
+
+ dpk->bp[path][kidx].txagc_dpk = FIELD_GET(_DPK_PARA_TXAGC, para);
+ dpk->bp[path][kidx].ther_dpk = FIELD_GET(_DPK_PARA_THER, para);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] thermal/ txagc_RF (K%d) = 0x%x/ 0x%x\n",
+ dpk->cur_k_set, dpk->bp[path][kidx].ther_dpk, dpk->bp[path][kidx].txagc_dpk);
+}
+
+static void _dpk_gain_normalize_8852c(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kidx, bool is_execute)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+
+ if (is_execute) {
+ rtw89_phy_write32_mask(rtwdev, R_DPK_GN + (path << 8), B_DPK_GN_AG, 0x200);
+ rtw89_phy_write32_mask(rtwdev, R_DPK_GN + (path << 8), B_DPK_GN_EN, 0x3);
+
+ _dpk_one_shot(rtwdev, phy, path, D_GAIN_NORM);
+ } else {
+ rtw89_phy_write32_mask(rtwdev, dpk_par_regs[kidx][dpk->cur_k_set] + (path << 8),
+ 0x0000007F, 0x5b);
+ }
+ dpk->bp[path][kidx].gs =
+ rtw89_phy_read32_mask(rtwdev, dpk_par_regs[kidx][dpk->cur_k_set] + (path << 8),
+ 0x0000007F);
+}
+
+static u8 _dpk_order_convert(struct rtw89_dev *rtwdev)
+{
+ u32 val32 = rtw89_phy_read32_mask(rtwdev, R_LDL_NORM, B_LDL_NORM_OP);
+ u8 val;
+
+ switch (val32) {
+ case 0:
+ val = 0x6;
+ break;
+ case 1:
+ val = 0x2;
+ break;
+ case 2:
+ val = 0x0;
+ break;
+ case 3:
+ val = 0x7;
+ break;
+ default:
+ val = 0xff;
+ break;
+ }
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] convert MDPD order to 0x%x\n", val);
+
+ return val;
+}
+
+static void _dpk_on(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 kidx)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+
+ rtw89_phy_write32_mask(rtwdev, R_LOAD_COEF + (path << 8), B_LOAD_COEF_MDPD, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_LOAD_COEF + (path << 8), B_LOAD_COEF_MDPD, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_DPD_CH0A + (path << 8) + (kidx << 2),
+ B_DPD_ORDER, _dpk_order_convert(rtwdev));
+
+ dpk->bp[path][kidx].mdpd_en = BIT(dpk->cur_k_set);
+ dpk->bp[path][kidx].path_ok = true;
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d[%d] path_ok = 0x%x\n",
+ path, kidx, dpk->bp[path][kidx].mdpd_en);
+
+ rtw89_phy_write32_mask(rtwdev, R_DPD_CH0A + (path << 8) + (kidx << 2),
+ B_DPD_MEN, dpk->bp[path][kidx].mdpd_en);
+
+ _dpk_gain_normalize_8852c(rtwdev, phy, path, kidx, false);
+}
+
+static bool _dpk_main(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path, u8 gain)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u8 kidx = dpk->cur_idx[path];
+ u8 init_xdbm = 15;
+ bool is_fail;
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] ========= S%d[%d] DPK Start =========\n", path, kidx);
+ _dpk_kip_control_rfc(rtwdev, path, false);
+ _rf_direct_cntrl(rtwdev, path, false);
+ rtw89_write_rf(rtwdev, path, RR_BBDC, RFREG_MASK, 0x03ffd);
+ _dpk_rf_setting(rtwdev, gain, path, kidx);
+ _set_rx_dck(rtwdev, phy, path, false);
+ _dpk_kip_pwr_clk_onoff(rtwdev, true);
+ _dpk_kip_preset_8852c(rtwdev, phy, path, kidx);
+ _dpk_txpwr_bb_force(rtwdev, path, true);
+ _dpk_kip_set_txagc(rtwdev, phy, path, init_xdbm, true);
+ _dpk_tpg_sel(rtwdev, path, kidx);
+
+ is_fail = _dpk_agc(rtwdev, phy, path, kidx, init_xdbm, false);
+ if (is_fail)
+ goto _error;
+
+ _dpk_idl_mpa(rtwdev, phy, path, kidx);
+ _dpk_para_query(rtwdev, path, kidx);
+ _dpk_on(rtwdev, phy, path, kidx);
+
+_error:
+ _dpk_kip_control_rfc(rtwdev, path, false);
+ rtw89_write_rf(rtwdev, path, RR_MOD, RR_MOD_MASK, RF_RX);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d[%d]_K%d %s\n", path, kidx,
+ dpk->cur_k_set, is_fail ? "need Check" : "is Success");
+
+ return is_fail;
+}
+
+static void _dpk_init(struct rtw89_dev *rtwdev, u8 path)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u8 kidx = dpk->cur_idx[path];
+
+ dpk->bp[path][kidx].path_ok = false;
+}
+
+static void _dpk_drf_direct_cntrl(struct rtw89_dev *rtwdev, u8 path, bool is_bybb)
+{
+ if (is_bybb)
+ rtw89_write_rf(rtwdev, path, RR_BBDC, RR_BBDC_SEL, 0x1);
+ else
+ rtw89_write_rf(rtwdev, path, RR_BBDC, RR_BBDC_SEL, 0x0);
+}
+
+static void _dpk_cal_select(struct rtw89_dev *rtwdev, bool force,
+ enum rtw89_phy_idx phy, u8 kpath)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ static const u32 kip_reg[] = {0x813c, 0x8124, 0x8120, 0xc0d4, 0xc0d8};
+ u32 backup_rf_val[RTW8852C_DPK_RF_PATH][BACKUP_RF_REGS_NR];
+ u32 kip_bkup[RTW8852C_DPK_RF_PATH][RTW8852C_DPK_KIP_REG_NUM] = {};
+ u8 path;
+ bool is_fail = true, reloaded[RTW8852C_DPK_RF_PATH] = {false};
+
+ if (dpk->is_dpk_reload_en) {
+ for (path = 0; path < RTW8852C_DPK_RF_PATH; path++) {
+ if (!(kpath & BIT(path)))
+ continue;
+
+ reloaded[path] = _dpk_reload_check(rtwdev, phy, path);
+ if (!reloaded[path] && dpk->bp[path][0].ch != 0)
+ dpk->cur_idx[path] = !dpk->cur_idx[path];
+ else
+ _dpk_onoff(rtwdev, path, false);
+ }
+ } else {
+ for (path = 0; path < RTW8852C_DPK_RF_PATH; path++)
+ dpk->cur_idx[path] = 0;
+ }
+
+ for (path = 0; path < RTW8852C_DPK_RF_PATH; path++) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] ========= S%d[%d] DPK Init =========\n",
+ path, dpk->cur_idx[path]);
+ _dpk_bkup_kip(rtwdev, kip_reg, kip_bkup, path);
+ _rfk_backup_rf_reg(rtwdev, backup_rf_val[path], path);
+ _dpk_information(rtwdev, phy, path);
+ _dpk_init(rtwdev, path);
+ if (rtwdev->is_tssi_mode[path])
+ _dpk_tssi_pause(rtwdev, path, true);
+ }
+
+ for (path = 0; path < RTW8852C_DPK_RF_PATH; path++) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] ========= S%d[%d] DPK Start =========\n",
+ path, dpk->cur_idx[path]);
+ rtw8852c_disable_rxagc(rtwdev, path, 0x0);
+ _dpk_drf_direct_cntrl(rtwdev, path, false);
+ _dpk_bb_afe_setting(rtwdev, phy, path, kpath);
+ is_fail = _dpk_main(rtwdev, phy, path, 1);
+ _dpk_onoff(rtwdev, path, is_fail);
+ }
+
+ for (path = 0; path < RTW8852C_DPK_RF_PATH; path++) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] ========= S%d[%d] DPK Restore =========\n",
+ path, dpk->cur_idx[path]);
+ _dpk_kip_restore(rtwdev, phy, path);
+ _dpk_reload_kip(rtwdev, kip_reg, kip_bkup, path);
+ _rfk_restore_rf_reg(rtwdev, backup_rf_val[path], path);
+ _dpk_bb_afe_restore(rtwdev, path);
+ rtw8852c_disable_rxagc(rtwdev, path, 0x1);
+ if (rtwdev->is_tssi_mode[path])
+ _dpk_tssi_pause(rtwdev, path, false);
+ }
+
+ _dpk_kip_pwr_clk_onoff(rtwdev, false);
+}
+
+static bool _dpk_bypass_check(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
+{
+ struct rtw89_fem_info *fem = &rtwdev->fem;
+
+ if (rtwdev->hal.cv == CHIP_CAV && rtwdev->hal.current_band_type != RTW89_BAND_2G) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Skip DPK due to CAV & not 2G!!\n");
+ return true;
+ } else if (fem->epa_2g && rtwdev->hal.current_band_type == RTW89_BAND_2G) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Skip DPK due to 2G_ext_PA exist!!\n");
+ return true;
+ } else if (fem->epa_5g && rtwdev->hal.current_band_type == RTW89_BAND_5G) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Skip DPK due to 5G_ext_PA exist!!\n");
+ return true;
+ } else if (fem->epa_6g && rtwdev->hal.current_band_type == RTW89_BAND_6G) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] Skip DPK due to 6G_ext_PA exist!!\n");
+ return true;
+ }
+
+ return false;
+}
+
+static void _dpk_force_bypass(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
+{
+ u8 path, kpath;
+
+ kpath = _kpath(rtwdev, phy);
+
+ for (path = 0; path < RTW8852C_DPK_RF_PATH; path++) {
+ if (kpath & BIT(path))
+ _dpk_onoff(rtwdev, path, true);
+ }
+}
+
+static void _dpk(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy, bool force)
+{
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DPK] ****** DPK Start (Ver: 0x%x, Cv: %d, RF_para: %d) ******\n",
+ RTW8852C_DPK_VER, rtwdev->hal.cv,
+ RTW8852C_RF_REL_VERSION);
+
+ if (_dpk_bypass_check(rtwdev, phy))
+ _dpk_force_bypass(rtwdev, phy);
+ else
+ _dpk_cal_select(rtwdev, force, phy, _kpath(rtwdev, phy));
+
+ if (rtw89_read_rf(rtwdev, RF_PATH_A, RR_DCKC, RR_DCKC_CHK) == 0x1)
+ rtw8852c_rx_dck(rtwdev, phy, false);
+}
+
+static void _dpk_onoff(struct rtw89_dev *rtwdev,
+ enum rtw89_rf_path path, bool off)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u8 val, kidx = dpk->cur_idx[path];
+
+ val = dpk->is_dpk_enable && !off && dpk->bp[path][kidx].path_ok ?
+ dpk->bp[path][kidx].mdpd_en : 0;
+
+ rtw89_phy_write32_mask(rtwdev, R_DPD_CH0A + (path << 8) + (kidx << 2),
+ B_DPD_MEN, val);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DPK] S%d[%d] DPK %s !!!\n", path,
+ kidx, dpk->is_dpk_enable && !off ? "enable" : "disable");
+}
+
+static void _dpk_track(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dpk_info *dpk = &rtwdev->dpk;
+ u8 path, kidx;
+ u8 txagc_rf = 0;
+ s8 txagc_bb = 0, txagc_bb_tp = 0, txagc_ofst = 0;
+ u8 cur_ther;
+ s8 delta_ther = 0;
+ s16 pwsf_tssi_ofst;
+
+ for (path = 0; path < RTW8852C_DPK_RF_PATH; path++) {
+ kidx = dpk->cur_idx[path];
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[DPK_TRK] ================[S%d[%d] (CH %d)]================\n",
+ path, kidx, dpk->bp[path][kidx].ch);
+
+ txagc_rf =
+ rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB + (path << 13), 0x0000003f);
+ txagc_bb =
+ rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB + (path << 13), MASKBYTE2);
+ txagc_bb_tp =
+ rtw89_phy_read32_mask(rtwdev, R_TXAGC_BTP + (path << 13), B_TXAGC_BTP);
+
+ /* report from KIP */
+ rtw89_phy_write32_mask(rtwdev, R_KIP_RPT + (path << 8), B_KIP_RPT_SEL, 0xf);
+ cur_ther =
+ rtw89_phy_read32_mask(rtwdev, R_RPT_PER + (path << 8), B_RPT_PER_TH);
+ txagc_ofst =
+ rtw89_phy_read32_mask(rtwdev, R_RPT_PER + (path << 8), B_RPT_PER_OF);
+ pwsf_tssi_ofst =
+ rtw89_phy_read32_mask(rtwdev, R_RPT_PER + (path << 8), B_RPT_PER_TSSI);
+ pwsf_tssi_ofst = sign_extend32(pwsf_tssi_ofst, 12);
+
+ cur_ther = ewma_thermal_read(&rtwdev->phystat.avg_thermal[path]);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[DPK_TRK] thermal now = %d\n", cur_ther);
+
+ if (dpk->bp[path][kidx].ch != 0 && cur_ther != 0)
+ delta_ther = dpk->bp[path][kidx].ther_dpk - cur_ther;
+
+ delta_ther = delta_ther * 1 / 2;
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[DPK_TRK] extra delta_ther = %d (0x%x / 0x%x@k)\n",
+ delta_ther, cur_ther, dpk->bp[path][kidx].ther_dpk);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[DPK_TRK] delta_txagc = %d (0x%x / 0x%x@k)\n",
+ txagc_rf - dpk->bp[path][kidx].txagc_dpk, txagc_rf,
+ dpk->bp[path][kidx].txagc_dpk);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[DPK_TRK] txagc_offset / pwsf_tssi_ofst = 0x%x / %+d\n",
+ txagc_ofst, pwsf_tssi_ofst);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[DPK_TRK] txagc_bb_tp / txagc_bb = 0x%x / 0x%x\n",
+ txagc_bb_tp, txagc_bb);
+
+ if (rtw89_phy_read32_mask(rtwdev, R_DPK_WR, B_DPK_WR_ST) == 0x0 &&
+ txagc_rf != 0 && rtwdev->hal.cv == CHIP_CAV) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[DPK_TRK] New pwsf = 0x%x\n", 0x78 - delta_ther);
+
+ rtw89_phy_write32_mask(rtwdev, R_DPD_BND + (path << 8) + (kidx << 2),
+ 0x07FC0000, 0x78 - delta_ther);
+ }
+ }
+}
+
static void _tssi_set_sys(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
enum rtw89_rf_path path)
{
@@ -2781,6 +3873,28 @@ void rtw8852c_rx_dck(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy, bool is_a
}
}

+void rtw8852c_dpk(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx)
+{
+ u32 tx_en;
+ u8 phy_map = rtw89_btc_phymap(rtwdev, phy_idx, 0);
+
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DPK, BTC_WRFK_START);
+ rtw89_chip_stop_sch_tx(rtwdev, phy_idx, &tx_en, RTW89_SCH_TX_SEL_ALL);
+ _wait_rx_mode(rtwdev, _kpath(rtwdev, phy_idx));
+
+ rtwdev->dpk.is_dpk_enable = true;
+ rtwdev->dpk.is_dpk_reload_en = false;
+ _dpk(rtwdev, phy_idx, false);
+
+ rtw89_chip_resume_sch_tx(rtwdev, phy_idx, tx_en);
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DPK, BTC_WRFK_STOP);
+}
+
+void rtw8852c_dpk_track(struct rtw89_dev *rtwdev)
+{
+ _dpk_track(rtwdev);
+}
+
void rtw8852c_tssi(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
{
u32 i, path = RF_PATH_A, path_max = RF_PATH_NUM_8852C;
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
index 5c0623f6af208..e42fb1a4965ef 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
@@ -11,6 +11,8 @@ void rtw8852c_rck(struct rtw89_dev *rtwdev);
void rtw8852c_dack(struct rtw89_dev *rtwdev);
void rtw8852c_iqk(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx);
void rtw8852c_rx_dck(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx, bool is_afe);
+void rtw8852c_dpk(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
+void rtw8852c_dpk_track(struct rtw89_dev *rtwdev);
void rtw8852c_tssi(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
void rtw8852c_tssi_scan(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
void rtw8852c_tssi_cont_en_phyidx(struct rtw89_dev *rtwdev, bool en, u8 phy_idx);
--
2.25.1

2022-05-03 01:27:52

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 1/8] rtw89: 8852c: rfk: add RFK tables

These tables are used by RFK (RF calibration) to set parameters. These
parameters can trigger certain calibration, or configure/reset settings
before and after RF calibrations.

Signed-off-by: Ping-Ke Shih <[email protected]>
---
.../realtek/rtw89/rtw8852c_rfk_table.c | 781 ++++++++++++++++++
.../realtek/rtw89/rtw8852c_rfk_table.h | 67 ++
2 files changed, 848 insertions(+)
create mode 100644 drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.c
create mode 100644 drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.h

diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.c b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.c
new file mode 100644
index 0000000000000..d727d528b3651
--- /dev/null
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.c
@@ -0,0 +1,781 @@
+// SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause
+/* Copyright(c) 2019-2022 Realtek Corporation
+ */
+
+#include "rtw8852c_rfk_table.h"
+
+static const struct rtw89_reg5_def rtw8852c_dack_reload_defs[] = {
+ RTW89_DECL_RFK_WM(0xc004, BIT(17), 0x1),
+ RTW89_DECL_RFK_WM(0xc024, BIT(17), 0x1),
+ RTW89_DECL_RFK_WM(0xc104, BIT(17), 0x1),
+ RTW89_DECL_RFK_WM(0xc124, BIT(17), 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dack_reload_defs);
+
+static const struct rtw89_reg5_def rtw8852c_dack_reset_defs_a[] = {
+ RTW89_DECL_RFK_WM(0xc000, BIT(17), 0x0),
+ RTW89_DECL_RFK_WM(0xc000, BIT(17), 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dack_reset_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_dack_reset_defs_b[] = {
+ RTW89_DECL_RFK_WM(0xc100, BIT(17), 0x0),
+ RTW89_DECL_RFK_WM(0xc100, BIT(17), 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dack_reset_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_dack_defs_s0[] = {
+ RTW89_DECL_RFK_WM(0x12b8, BIT(30), 0x1),
+ RTW89_DECL_RFK_WM(0x030c, BIT(28), 0x1),
+ RTW89_DECL_RFK_WM(0x032c, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0xc004, 0xfff00000, 0x30),
+ RTW89_DECL_RFK_WM(0xc024, 0xfff00000, 0x30),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dack_defs_s0);
+
+static const struct rtw89_reg5_def rtw8852c_dack_defs_s1[] = {
+ RTW89_DECL_RFK_WM(0x32b8, BIT(30), 0x1),
+ RTW89_DECL_RFK_WM(0x030c, BIT(28), 0x1),
+ RTW89_DECL_RFK_WM(0x032c, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0xc104, 0xfff00000, 0x30),
+ RTW89_DECL_RFK_WM(0xc124, 0xfff00000, 0x30),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dack_defs_s1);
+
+static const struct rtw89_reg5_def rtw8852c_drck_defs[] = {
+ RTW89_DECL_RFK_WM(0xc0c4, BIT(6), 0x0),
+ RTW89_DECL_RFK_WM(0xc094, BIT(9), 0x1),
+ RTW89_DECL_RFK_DELAY(1),
+ RTW89_DECL_RFK_WM(0xc094, BIT(9), 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_drck_defs);
+
+static const struct rtw89_reg5_def rtw8852c_iqk_rxk_cfg_defs[] = {
+ RTW89_DECL_RFK_WM(0x030c, 0xff000000, 0x0f),
+ RTW89_DECL_RFK_WM(0x030c, 0xff000000, 0x03),
+ RTW89_DECL_RFK_WM(0x032c, 0xffff0000, 0x0001),
+ RTW89_DECL_RFK_WM(0x032c, 0xffff0000, 0x0041),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_iqk_rxk_cfg_defs);
+
+static const struct rtw89_reg5_def rtw8852c_iqk_afebb_restore_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x12b8, 0x40000000, 0x0),
+ RTW89_DECL_RFK_WM(0x20fc, 0x00010000, 0x1),
+ RTW89_DECL_RFK_WM(0x20fc, 0x00100000, 0x0),
+ RTW89_DECL_RFK_WM(0x20fc, 0x01000000, 0x1),
+ RTW89_DECL_RFK_WM(0x20fc, 0x10000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5670, MASKDWORD, 0x00000000),
+ RTW89_DECL_RFK_WM(0x12a0, 0x000ff000, 0x00),
+ RTW89_DECL_RFK_WM(0x20fc, 0x00010000, 0x0),
+ RTW89_DECL_RFK_WM(0x20fc, 0x01000000, 0x0),
+ RTW89_DECL_RFK_WRF(RF_PATH_A, 0x10005, 0x00001, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_iqk_afebb_restore_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_iqk_afebb_restore_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x32b8, 0x40000000, 0x0),
+ RTW89_DECL_RFK_WM(0x20fc, 0x00020000, 0x1),
+ RTW89_DECL_RFK_WM(0x20fc, 0x00200000, 0x0),
+ RTW89_DECL_RFK_WM(0x20fc, 0x02000000, 0x1),
+ RTW89_DECL_RFK_WM(0x20fc, 0x20000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7670, MASKDWORD, 0x00000000),
+ RTW89_DECL_RFK_WM(0x32a0, 0x000ff000, 0x00),
+ RTW89_DECL_RFK_WM(0x20fc, 0x00020000, 0x0),
+ RTW89_DECL_RFK_WM(0x20fc, 0x02000000, 0x0),
+ RTW89_DECL_RFK_WRF(RF_PATH_B, 0x10005, 0x00001, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_iqk_afebb_restore_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_read_rxsram_pre_defs[] = {
+ RTW89_DECL_RFK_WM(0x80e8, BIT(7), 0x1),
+ RTW89_DECL_RFK_WM(0x8074, BIT(31), 0x1),
+ RTW89_DECL_RFK_WM(0x80d4, MASKDWORD, 0x00020000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_read_rxsram_pre_defs);
+
+static const struct rtw89_reg5_def rtw8852c_read_rxsram_post_defs[] = {
+ RTW89_DECL_RFK_WM(0x80e8, BIT(7), 0x0),
+ RTW89_DECL_RFK_WM(0x8074, BIT(31), 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_read_rxsram_post_defs);
+
+static const struct rtw89_reg5_def rtw8852c_dpk_mdpd_order0_defs[] = {
+ RTW89_DECL_RFK_WM(0x80a0, BIT(1) | BIT(0), 0x0),
+ RTW89_DECL_RFK_WM(0x809c, BIT(10) | BIT(9), 0x2),
+ RTW89_DECL_RFK_WM(0x80a0, 0x00001F00, 0x4),
+ RTW89_DECL_RFK_WM(0x8070, 0x70000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dpk_mdpd_order0_defs);
+
+static const struct rtw89_reg5_def rtw8852c_dpk_mdpd_order1_defs[] = {
+ RTW89_DECL_RFK_WM(0x80a0, BIT(1) | BIT(0), 0x1),
+ RTW89_DECL_RFK_WM(0x809c, BIT(10) | BIT(9), 0x1),
+ RTW89_DECL_RFK_WM(0x80a0, 0x00001F00, 0x0),
+ RTW89_DECL_RFK_WM(0x8070, 0x70000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dpk_mdpd_order1_defs);
+
+static const struct rtw89_reg5_def rtw8852c_dpk_mdpd_order2_defs[] = {
+ RTW89_DECL_RFK_WM(0x80a0, BIT(1) | BIT(0), 0x2),
+ RTW89_DECL_RFK_WM(0x809c, BIT(10) | BIT(9), 0x0),
+ RTW89_DECL_RFK_WM(0x80a0, 0x00001F00, 0x0),
+ RTW89_DECL_RFK_WM(0x8070, 0x70000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dpk_mdpd_order2_defs);
+
+static const struct rtw89_reg5_def rtw8852c_dpk_mdpd_order3_defs[] = {
+ RTW89_DECL_RFK_WM(0x80a0, BIT(1) | BIT(0), 0x3),
+ RTW89_DECL_RFK_WM(0x809c, BIT(10) | BIT(9), 0x3),
+ RTW89_DECL_RFK_WM(0x80a0, 0x00001F00, 0x4),
+ RTW89_DECL_RFK_WM(0x8070, 0x70000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dpk_mdpd_order3_defs);
+
+static const struct rtw89_reg5_def rtw8852c_dpk_kip_pwr_clk_on_defs[] = {
+ RTW89_DECL_RFK_WM(0x8008, MASKDWORD, 0x00000080),
+ RTW89_DECL_RFK_WM(0x8088, MASKDWORD, 0x807f030a),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dpk_kip_pwr_clk_on_defs);
+
+static const struct rtw89_reg5_def rtw8852c_dpk_kip_pwr_clk_off_defs[] = {
+ RTW89_DECL_RFK_WM(0x8008, MASKDWORD, 0x00000000),
+ RTW89_DECL_RFK_WM(0x8088, MASKDWORD, 0x80000000),
+ RTW89_DECL_RFK_WM(0x80f4, BIT(18), 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_dpk_kip_pwr_clk_off_defs);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_sys_defs[] = {
+ RTW89_DECL_RFK_WM(0x12bc, 0x000ffff0, 0xb5b5),
+ RTW89_DECL_RFK_WM(0x32bc, 0x000ffff0, 0xb5b5),
+ RTW89_DECL_RFK_WM(0x0300, 0xff000000, 0x16),
+ RTW89_DECL_RFK_WM(0x0304, 0x0000ffff, 0x1f19),
+ RTW89_DECL_RFK_WM(0x0308, 0xff000000, 0x1c),
+ RTW89_DECL_RFK_WM(0x0314, 0xffff0000, 0x2041),
+ RTW89_DECL_RFK_WM(0x0318, 0xffffffff, 0x20012041),
+ RTW89_DECL_RFK_WM(0x0324, 0xffff0000, 0x2001),
+ RTW89_DECL_RFK_WM(0x0020, 0x00006000, 0x3),
+ RTW89_DECL_RFK_WM(0x0024, 0x00006000, 0x3),
+ RTW89_DECL_RFK_WM(0x0704, 0xffff0000, 0x601e),
+ RTW89_DECL_RFK_WM(0x2704, 0xffff0000, 0x601e),
+ RTW89_DECL_RFK_WM(0x0700, 0xf0000000, 0x4),
+ RTW89_DECL_RFK_WM(0x2700, 0xf0000000, 0x4),
+ RTW89_DECL_RFK_WM(0x0650, 0x3c000000, 0x0),
+ RTW89_DECL_RFK_WM(0x2650, 0x3c000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_sys_defs);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_sys_defs_2g_a[] = {
+ RTW89_DECL_RFK_WM(0x120c, 0x000000ff, 0x33),
+ RTW89_DECL_RFK_WM(0x12c0, 0x0ff00000, 0x33),
+ RTW89_DECL_RFK_WM(0x58f8, 0x40000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_sys_defs_2g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_sys_defs_2g_b[] = {
+ RTW89_DECL_RFK_WM(0x320c, 0x000000ff, 0x33),
+ RTW89_DECL_RFK_WM(0x32c0, 0x0ff00000, 0x33),
+ RTW89_DECL_RFK_WM(0x78f8, 0x40000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_sys_defs_2g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_sys_defs_5g_a[] = {
+ RTW89_DECL_RFK_WM(0x120c, 0x000000ff, 0x44),
+ RTW89_DECL_RFK_WM(0x12c0, 0x0ff00000, 0x44),
+ RTW89_DECL_RFK_WM(0x58f8, 0x40000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_sys_defs_5g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_sys_defs_5g_b[] = {
+ RTW89_DECL_RFK_WM(0x320c, 0x000000ff, 0x44),
+ RTW89_DECL_RFK_WM(0x32c0, 0x0ff00000, 0x44),
+ RTW89_DECL_RFK_WM(0x78f8, 0x40000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_sys_defs_5g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_txpwr_ctrl_bb_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x566c, 0x00001000, 0x0),
+ RTW89_DECL_RFK_WM(0x5800, 0xffffffff, 0x003f807f),
+ RTW89_DECL_RFK_WM(0x580c, 0x0000007f, 0x40),
+ RTW89_DECL_RFK_WM(0x580c, 0x0fffff00, 0x00040),
+ RTW89_DECL_RFK_WM(0x5810, 0xffffffff, 0x59010000),
+ RTW89_DECL_RFK_WM(0x5814, 0x01ffffff, 0x026d000),
+ RTW89_DECL_RFK_WM(0x5814, 0xf8000000, 0x00),
+ RTW89_DECL_RFK_WM(0x5818, 0xffffffff, 0x002c1800),
+ RTW89_DECL_RFK_WM(0x581c, 0x3fffffff, 0x3dc80280),
+ RTW89_DECL_RFK_WM(0x5820, 0xffffffff, 0x00000080),
+ RTW89_DECL_RFK_WM(0x58e8, 0x0000003f, 0x03),
+ RTW89_DECL_RFK_WM(0x580c, 0x10000000, 0x1),
+ RTW89_DECL_RFK_WM(0x580c, 0x40000000, 0x1),
+ RTW89_DECL_RFK_WM(0x5834, 0x3fffffff, 0x000115f2),
+ RTW89_DECL_RFK_WM(0x5838, 0x7fffffff, 0x0000121),
+ RTW89_DECL_RFK_WM(0x5854, 0x3fffffff, 0x000115f2),
+ RTW89_DECL_RFK_WM(0x5858, 0x7fffffff, 0x0000121),
+ RTW89_DECL_RFK_WM(0x5860, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5864, 0x07ffffff, 0x00801ff),
+ RTW89_DECL_RFK_WM(0x5898, 0xffffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x589c, 0xffffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x58a4, 0x000000ff, 0x16),
+ RTW89_DECL_RFK_WM(0x58b4, 0x7fffffff, 0x0a002000),
+ RTW89_DECL_RFK_WM(0x58b8, 0x7fffffff, 0x00007628),
+ RTW89_DECL_RFK_WM(0x58bc, 0x07ffffff, 0x7a7807f),
+ RTW89_DECL_RFK_WM(0x58c0, 0xfffe0000, 0x003f),
+ RTW89_DECL_RFK_WM(0x58c4, 0xffffffff, 0x0003ffff),
+ RTW89_DECL_RFK_WM(0x58c8, 0x00ffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x58c8, 0xf0000000, 0x0),
+ RTW89_DECL_RFK_WM(0x58cc, 0xffffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x58d0, 0x07ffffff, 0x2008101),
+ RTW89_DECL_RFK_WM(0x58d4, 0x000000ff, 0x00),
+ RTW89_DECL_RFK_WM(0x58d4, 0x0003fe00, 0x0ff),
+ RTW89_DECL_RFK_WM(0x58d4, 0x07fc0000, 0x100),
+ RTW89_DECL_RFK_WM(0x58d8, 0xffffffff, 0x8008016c),
+ RTW89_DECL_RFK_WM(0x58dc, 0x0001ffff, 0x0807f),
+ RTW89_DECL_RFK_WM(0x58dc, 0xfff00000, 0x800),
+ RTW89_DECL_RFK_WM(0x58f0, 0x0003ffff, 0x001ff),
+ RTW89_DECL_RFK_WM(0x58f4, 0x000fffff, 0x000),
+ RTW89_DECL_RFK_WM(0x58f8, 0x000fffff, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_txpwr_ctrl_bb_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_txpwr_ctrl_bb_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x566c, 0x00001000, 0x0),
+ RTW89_DECL_RFK_WM(0x7800, 0xffffffff, 0x003f807f),
+ RTW89_DECL_RFK_WM(0x780c, 0x0000007f, 0x40),
+ RTW89_DECL_RFK_WM(0x780c, 0x0fffff00, 0x00040),
+ RTW89_DECL_RFK_WM(0x7810, 0xffffffff, 0x59010000),
+ RTW89_DECL_RFK_WM(0x7814, 0x01ffffff, 0x026d000),
+ RTW89_DECL_RFK_WM(0x7814, 0xf8000000, 0x00),
+ RTW89_DECL_RFK_WM(0x7818, 0xffffffff, 0x002c1800),
+ RTW89_DECL_RFK_WM(0x781c, 0x3fffffff, 0x3dc80280),
+ RTW89_DECL_RFK_WM(0x7820, 0xffffffff, 0x00000080),
+ RTW89_DECL_RFK_WM(0x78e8, 0x0000003f, 0x03),
+ RTW89_DECL_RFK_WM(0x780c, 0x10000000, 0x1),
+ RTW89_DECL_RFK_WM(0x780c, 0x40000000, 0x1),
+ RTW89_DECL_RFK_WM(0x7834, 0x3fffffff, 0x000115f2),
+ RTW89_DECL_RFK_WM(0x7838, 0x7fffffff, 0x0000121),
+ RTW89_DECL_RFK_WM(0x7854, 0x3fffffff, 0x000115f2),
+ RTW89_DECL_RFK_WM(0x7858, 0x7fffffff, 0x0000121),
+ RTW89_DECL_RFK_WM(0x7860, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7864, 0x07ffffff, 0x00801ff),
+ RTW89_DECL_RFK_WM(0x7898, 0xffffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x789c, 0xffffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x78a4, 0x000000ff, 0x16),
+ RTW89_DECL_RFK_WM(0x78b4, 0x7fffffff, 0x0a002000),
+ RTW89_DECL_RFK_WM(0x78b8, 0x7fffffff, 0x00007628),
+ RTW89_DECL_RFK_WM(0x78bc, 0x07ffffff, 0x7a7807f),
+ RTW89_DECL_RFK_WM(0x78c0, 0xfffe0000, 0x003f),
+ RTW89_DECL_RFK_WM(0x78c4, 0xffffffff, 0x0003ffff),
+ RTW89_DECL_RFK_WM(0x78c8, 0x00ffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x78c8, 0xf0000000, 0x0),
+ RTW89_DECL_RFK_WM(0x78cc, 0xffffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x78d0, 0x07ffffff, 0x2008101),
+ RTW89_DECL_RFK_WM(0x78d4, 0x000000ff, 0x00),
+ RTW89_DECL_RFK_WM(0x78d4, 0x0003fe00, 0x0ff),
+ RTW89_DECL_RFK_WM(0x78d4, 0x07fc0000, 0x100),
+ RTW89_DECL_RFK_WM(0x78d8, 0xffffffff, 0x8008016c),
+ RTW89_DECL_RFK_WM(0x78dc, 0x0001ffff, 0x0807f),
+ RTW89_DECL_RFK_WM(0x78dc, 0xfff00000, 0x800),
+ RTW89_DECL_RFK_WM(0x78f0, 0x0003ffff, 0x001ff),
+ RTW89_DECL_RFK_WM(0x78f4, 0x000fffff, 0x000),
+ RTW89_DECL_RFK_WM(0x78f8, 0x000fffff, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_txpwr_ctrl_bb_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x58a0, 0xffffffff, 0x000000fe),
+ RTW89_DECL_RFK_WM(0x58e4, 0x0000007f, 0x1f),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x78a0, 0xffffffff, 0x000000fe),
+ RTW89_DECL_RFK_WM(0x78e4, 0x0000007f, 0x1f),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_dck_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x58c4, 0x3ffc0000, 0x0),
+ RTW89_DECL_RFK_WM(0x58c8, 0x00000fff, 0x0),
+ RTW89_DECL_RFK_WM(0x58c8, 0x00fff000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_dck_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_dck_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x78c4, 0x3ffc0000, 0x0),
+ RTW89_DECL_RFK_WM(0x78c8, 0x00000fff, 0x0),
+ RTW89_DECL_RFK_WM(0x78c8, 0x00fff000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_dck_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_dck_defs_2g_a[] = {
+ RTW89_DECL_RFK_WM(0x580c, 0x0fff0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5814, 0x003ff000, 0x1af),
+ RTW89_DECL_RFK_WM(0x5814, 0x18000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_dck_defs_2g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_dck_defs_2g_b[] = {
+ RTW89_DECL_RFK_WM(0x780c, 0x0fff0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7814, 0x003ff000, 0x1af),
+ RTW89_DECL_RFK_WM(0x7814, 0x18000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_dck_defs_2g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_dck_defs_5g_a[] = {
+ RTW89_DECL_RFK_WM(0x580c, 0x0fff0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5814, 0x00001000, 0x1),
+ RTW89_DECL_RFK_WM(0x5814, 0x0003c000, 0xb),
+ RTW89_DECL_RFK_WM(0x5814, 0x00002000, 0x1),
+ RTW89_DECL_RFK_WM(0x5814, 0x003c0000, 0x6),
+ RTW89_DECL_RFK_WM(0x5814, 0x18000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_dck_defs_5g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_dck_defs_5g_b[] = {
+ RTW89_DECL_RFK_WM(0x780c, 0x0fff0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7814, 0x00001000, 0x1),
+ RTW89_DECL_RFK_WM(0x7814, 0x0003c000, 0xb),
+ RTW89_DECL_RFK_WM(0x7814, 0x00002000, 0x1),
+ RTW89_DECL_RFK_WM(0x7814, 0x003c0000, 0x6),
+ RTW89_DECL_RFK_WM(0x7814, 0x18000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_dck_defs_5g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_bbgain_split_a[] = {
+ RTW89_DECL_RFK_WM(0x5818, 0x08000000, 0x1),
+ RTW89_DECL_RFK_WM(0x58d4, 0xf0000000, 0x7),
+ RTW89_DECL_RFK_WM(0x58f0, 0x000c0000, 0x1),
+ RTW89_DECL_RFK_WM(0x58f0, 0xfff00000, 0x400),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_bbgain_split_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_bbgain_split_b[] = {
+ RTW89_DECL_RFK_WM(0x7818, 0x08000000, 0x1),
+ RTW89_DECL_RFK_WM(0x78d4, 0xf0000000, 0x7),
+ RTW89_DECL_RFK_WM(0x78f0, 0x000c0000, 0x1),
+ RTW89_DECL_RFK_WM(0x78f0, 0xfff00000, 0x400),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_bbgain_split_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_slope_cal_org_defs_2g_a[] = {
+ RTW89_DECL_RFK_WM(0x5608, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x560c, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x5610, 0x07ffffff, 0x0201020),
+ RTW89_DECL_RFK_WM(0x5614, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x5618, 0x07ffffff, 0x0801008),
+ RTW89_DECL_RFK_WM(0x561c, 0x000001ff, 0x008),
+ RTW89_DECL_RFK_WM(0x561c, 0xffff0000, 0x0808),
+ RTW89_DECL_RFK_WM(0x5620, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x5624, 0xffffffff, 0x0808081e),
+ RTW89_DECL_RFK_WM(0x5628, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x562c, 0x0000ffff, 0x081d),
+ RTW89_DECL_RFK_WM(0x581c, 0x00100000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_slope_cal_org_defs_2g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_slope_cal_org_defs_2g_b[] = {
+ RTW89_DECL_RFK_WM(0x7608, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x760c, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x7610, 0x07ffffff, 0x0204020),
+ RTW89_DECL_RFK_WM(0x7614, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x7618, 0x07ffffff, 0x0801008),
+ RTW89_DECL_RFK_WM(0x761c, 0x000001ff, 0x020),
+ RTW89_DECL_RFK_WM(0x761c, 0xffff0000, 0x0808),
+ RTW89_DECL_RFK_WM(0x7620, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x7624, 0xffffffff, 0x08081e21),
+ RTW89_DECL_RFK_WM(0x7628, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x762c, 0x0000ffff, 0x1d23),
+ RTW89_DECL_RFK_WM(0x781c, 0x00100000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_slope_cal_org_defs_2g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_slope_cal_org_defs_5g_a[] = {
+ RTW89_DECL_RFK_WM(0x5608, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x560c, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x5610, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x5614, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x5618, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x561c, 0x000001ff, 0x008),
+ RTW89_DECL_RFK_WM(0x561c, 0xffff0000, 0x0808),
+ RTW89_DECL_RFK_WM(0x5620, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x5624, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x5628, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x562c, 0x0000ffff, 0x0808),
+ RTW89_DECL_RFK_WM(0x581c, 0x00100000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_slope_cal_org_defs_5g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_slope_cal_org_defs_5g_b[] = {
+ RTW89_DECL_RFK_WM(0x7608, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x760c, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x7610, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x7614, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x7618, 0x07ffffff, 0x0201008),
+ RTW89_DECL_RFK_WM(0x761c, 0x000001ff, 0x008),
+ RTW89_DECL_RFK_WM(0x761c, 0xffff0000, 0x0808),
+ RTW89_DECL_RFK_WM(0x7620, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x7624, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x7628, 0xffffffff, 0x08080808),
+ RTW89_DECL_RFK_WM(0x762c, 0x0000ffff, 0x0808),
+ RTW89_DECL_RFK_WM(0x781c, 0x00100000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_slope_cal_org_defs_5g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_aligk_default_defs_2g_a[] = {
+ RTW89_DECL_RFK_WM(0x5604, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WM(0x5600, 0x3fffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x5604, 0x003fffff, 0x2d2721),
+ RTW89_DECL_RFK_WM(0x5630, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x5634, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5634, 0x000ffc00, 0x3b8),
+ RTW89_DECL_RFK_WM(0x5634, 0x3ff00000, 0x3d2),
+ RTW89_DECL_RFK_WM(0x5638, 0x000003ff, 0x042),
+ RTW89_DECL_RFK_WM(0x5638, 0x000ffc00, 0x06b),
+ RTW89_DECL_RFK_WM(0x563c, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x5640, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5640, 0x000ffc00, 0x3bc),
+ RTW89_DECL_RFK_WM(0x5640, 0x3ff00000, 0x3d6),
+ RTW89_DECL_RFK_WM(0x5644, 0x000003ff, 0x03e),
+ RTW89_DECL_RFK_WM(0x5644, 0x000ffc00, 0x06b),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_aligk_default_defs_2g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_aligk_default_defs_2g_b[] = {
+ RTW89_DECL_RFK_WM(0x7604, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WM(0x7600, 0x3fffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x7604, 0x003fffff, 0x2d2721),
+ RTW89_DECL_RFK_WM(0x7630, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x7634, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7634, 0x000ffc00, 0x3c0),
+ RTW89_DECL_RFK_WM(0x7634, 0x3ff00000, 0x3da),
+ RTW89_DECL_RFK_WM(0x7638, 0x000003ff, 0x002),
+ RTW89_DECL_RFK_WM(0x7638, 0x000ffc00, 0x071),
+ RTW89_DECL_RFK_WM(0x763c, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x7640, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7640, 0x000ffc00, 0x3c8),
+ RTW89_DECL_RFK_WM(0x7640, 0x3ff00000, 0x3e2),
+ RTW89_DECL_RFK_WM(0x7644, 0x000003ff, 0x00c),
+ RTW89_DECL_RFK_WM(0x7644, 0x000ffc00, 0x071),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_aligk_default_defs_2g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_aligk_default_defs_5g_a[] = {
+ RTW89_DECL_RFK_WM(0x5604, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WM(0x5600, 0x3fffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x5604, 0x003fffff, 0x312600),
+ RTW89_DECL_RFK_WM(0x5630, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x5634, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5634, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x5634, 0x3ff00000, 0x3e9),
+ RTW89_DECL_RFK_WM(0x5638, 0x000003ff, 0x039),
+ RTW89_DECL_RFK_WM(0x5638, 0x000ffc00, 0x07d),
+ RTW89_DECL_RFK_WM(0x563c, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x5640, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5640, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x5640, 0x3ff00000, 0x000),
+ RTW89_DECL_RFK_WM(0x5644, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5644, 0x000ffc00, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_aligk_default_defs_5g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_aligk_default_defs_5g_b[] = {
+ RTW89_DECL_RFK_WM(0x7604, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WM(0x7600, 0x3fffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x7604, 0x003fffff, 0x312600),
+ RTW89_DECL_RFK_WM(0x7630, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x7634, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7634, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x7634, 0x3ff00000, 0x3e9),
+ RTW89_DECL_RFK_WM(0x7638, 0x000003ff, 0x039),
+ RTW89_DECL_RFK_WM(0x7638, 0x000ffc00, 0x07d),
+ RTW89_DECL_RFK_WM(0x763c, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x7640, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7640, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x7640, 0x3ff00000, 0x000),
+ RTW89_DECL_RFK_WM(0x7644, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7644, 0x000ffc00, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_aligk_default_defs_5g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_aligk_default_defs_6g_a[] = {
+ RTW89_DECL_RFK_WM(0x5604, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WM(0x5600, 0x3fffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x5604, 0x003fffff, 0x312600),
+ RTW89_DECL_RFK_WM(0x5630, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x5634, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5634, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x5634, 0x3ff00000, 0x3e9),
+ RTW89_DECL_RFK_WM(0x5638, 0x000003ff, 0x039),
+ RTW89_DECL_RFK_WM(0x5638, 0x000ffc00, 0x080),
+ RTW89_DECL_RFK_WM(0x563c, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x5640, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5640, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x5640, 0x3ff00000, 0x000),
+ RTW89_DECL_RFK_WM(0x5644, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x5644, 0x000ffc00, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_aligk_default_defs_6g_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_set_aligk_default_defs_6g_b[] = {
+ RTW89_DECL_RFK_WM(0x7604, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WM(0x7600, 0x3fffffff, 0x000000),
+ RTW89_DECL_RFK_WM(0x7604, 0x003fffff, 0x312600),
+ RTW89_DECL_RFK_WM(0x7630, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x7634, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7634, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x7634, 0x3ff00000, 0x3e9),
+ RTW89_DECL_RFK_WM(0x7638, 0x000003ff, 0x039),
+ RTW89_DECL_RFK_WM(0x7638, 0x000ffc00, 0x080),
+ RTW89_DECL_RFK_WM(0x763c, 0x3fffffff, 0x00000000),
+ RTW89_DECL_RFK_WM(0x7640, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7640, 0x000ffc00, 0x000),
+ RTW89_DECL_RFK_WM(0x7640, 0x3ff00000, 0x000),
+ RTW89_DECL_RFK_WM(0x7644, 0x000003ff, 0x000),
+ RTW89_DECL_RFK_WM(0x7644, 0x000ffc00, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_set_aligk_default_defs_6g_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_slope_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x5820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5818, 0x10000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5814, 0x00000800, 0x1),
+ RTW89_DECL_RFK_WM(0x581c, 0x20000000, 0x1),
+ RTW89_DECL_RFK_WM(0x58e8, 0x0000003f, 0x0f),
+ RTW89_DECL_RFK_WM(0x581c, 0x000003ff, 0x280),
+ RTW89_DECL_RFK_WM(0x581c, 0x000ffc00, 0x200),
+ RTW89_DECL_RFK_WM(0x58b8, 0x007f0000, 0x00),
+ RTW89_DECL_RFK_WM(0x58b8, 0x7f000000, 0x00),
+ RTW89_DECL_RFK_WM(0x58b4, 0x7f000000, 0x0a),
+ RTW89_DECL_RFK_WM(0x58b8, 0x0000007f, 0x28),
+ RTW89_DECL_RFK_WM(0x58b8, 0x00007f00, 0x76),
+ RTW89_DECL_RFK_WM(0x5810, 0x20000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5814, 0x20000000, 0x1),
+ RTW89_DECL_RFK_WM(0x580c, 0x10000000, 0x1),
+ RTW89_DECL_RFK_WM(0x580c, 0x40000000, 0x1),
+ RTW89_DECL_RFK_WM(0x5834, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x5834, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5838, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5838, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x5854, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x5854, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5858, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5858, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x5824, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x5824, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5828, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5828, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x582c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x582c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5830, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5830, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x583c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x583c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5840, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5840, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x5844, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x5844, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5848, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5848, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x584c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x584c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5850, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5850, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x585c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x585c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x5860, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x5860, 0x003ff000, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_slope_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_slope_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x7820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7818, 0x10000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7814, 0x00000800, 0x1),
+ RTW89_DECL_RFK_WM(0x781c, 0x20000000, 0x1),
+ RTW89_DECL_RFK_WM(0x78e8, 0x0000003f, 0x0f),
+ RTW89_DECL_RFK_WM(0x781c, 0x000003ff, 0x280),
+ RTW89_DECL_RFK_WM(0x781c, 0x000ffc00, 0x200),
+ RTW89_DECL_RFK_WM(0x78b8, 0x007f0000, 0x00),
+ RTW89_DECL_RFK_WM(0x78b8, 0x7f000000, 0x00),
+ RTW89_DECL_RFK_WM(0x78b4, 0x7f000000, 0x0a),
+ RTW89_DECL_RFK_WM(0x78b8, 0x0000007f, 0x28),
+ RTW89_DECL_RFK_WM(0x78b8, 0x00007f00, 0x76),
+ RTW89_DECL_RFK_WM(0x7810, 0x20000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7814, 0x20000000, 0x1),
+ RTW89_DECL_RFK_WM(0x780c, 0x10000000, 0x1),
+ RTW89_DECL_RFK_WM(0x780c, 0x40000000, 0x1),
+ RTW89_DECL_RFK_WM(0x7834, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x7834, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7838, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7838, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x7854, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x7854, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7858, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7858, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x7824, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x7824, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7828, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7828, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x782c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x782c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7830, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7830, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x783c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x783c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7840, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7840, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x7844, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x7844, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7848, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7848, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x784c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x784c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7850, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7850, 0x003ff000, 0x000),
+ RTW89_DECL_RFK_WM(0x785c, 0x0003ffff, 0x115f2),
+ RTW89_DECL_RFK_WM(0x785c, 0x3ffc0000, 0x000),
+ RTW89_DECL_RFK_WM(0x7860, 0x00000fff, 0x121),
+ RTW89_DECL_RFK_WM(0x7860, 0x003ff000, 0x000),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_slope_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_run_slope_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x5820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5820, 0x80000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_run_slope_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_run_slope_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x7820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7820, 0x80000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_run_slope_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_track_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x5820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5818, 0x10000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5814, 0x00000800, 0x0),
+ RTW89_DECL_RFK_WM(0x581c, 0x20000000, 0x1),
+ RTW89_DECL_RFK_WM(0x5864, 0x000003ff, 0x1ff),
+ RTW89_DECL_RFK_WM(0x5864, 0x000ffc00, 0x200),
+ RTW89_DECL_RFK_WM(0x5820, 0x00000fff, 0x080),
+ RTW89_DECL_RFK_WM(0x5814, 0x01000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_track_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_track_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x7820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7818, 0x10000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7814, 0x00000800, 0x0),
+ RTW89_DECL_RFK_WM(0x781c, 0x20000000, 0x1),
+ RTW89_DECL_RFK_WM(0x7864, 0x000003ff, 0x1ff),
+ RTW89_DECL_RFK_WM(0x7864, 0x000ffc00, 0x200),
+ RTW89_DECL_RFK_WM(0x7820, 0x00000fff, 0x080),
+ RTW89_DECL_RFK_WM(0x7814, 0x01000000, 0x0),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_track_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_txagc_ofst_mv_avg_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x58e4, 0x00003800, 0x1),
+ RTW89_DECL_RFK_WM(0x58e4, 0x00004000, 0x0),
+ RTW89_DECL_RFK_WM(0x58e4, 0x00008000, 0x1),
+ RTW89_DECL_RFK_WM(0x58e4, 0x000f0000, 0x0),
+ RTW89_DECL_RFK_WM(0x58e8, 0x0000003f, 0x03),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_txagc_ofst_mv_avg_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_txagc_ofst_mv_avg_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x78e4, 0x00003800, 0x1),
+ RTW89_DECL_RFK_WM(0x78e4, 0x00004000, 0x0),
+ RTW89_DECL_RFK_WM(0x78e4, 0x00008000, 0x1),
+ RTW89_DECL_RFK_WM(0x78e4, 0x000f0000, 0x0),
+ RTW89_DECL_RFK_WM(0x78e8, 0x0000003f, 0x03),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_txagc_ofst_mv_avg_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_enable_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x58e4, 0x00004000, 0x0),
+ RTW89_DECL_RFK_WM(0x5820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x5820, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WRF(0x0, 0x10055, 0x00080, 0x1),
+ RTW89_DECL_RFK_WM(0x5818, 0x10000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_enable_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_enable_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x78e4, 0x00004000, 0x0),
+ RTW89_DECL_RFK_WM(0x7820, 0x80000000, 0x0),
+ RTW89_DECL_RFK_WM(0x7820, 0x80000000, 0x1),
+ RTW89_DECL_RFK_WRF(0x1, 0x10055, 0x00080, 0x1),
+ RTW89_DECL_RFK_WM(0x7818, 0x10000000, 0x1),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_enable_defs_b);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_disable_defs_a[] = {
+ RTW89_DECL_RFK_WM(0x5820, 0x80000000, 0x00000000),
+ RTW89_DECL_RFK_WM(0x5818, 0x10000000, 0x00000000),
+ RTW89_DECL_RFK_WM(0x58e4, 0x00004000, 0x00000001),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_disable_defs_a);
+
+static const struct rtw89_reg5_def rtw8852c_tssi_disable_defs_b[] = {
+ RTW89_DECL_RFK_WM(0x7820, 0x80000000, 0x00000000),
+ RTW89_DECL_RFK_WM(0x7818, 0x10000000, 0x00000000),
+ RTW89_DECL_RFK_WM(0x78e4, 0x00004000, 0x00000001),
+};
+
+RTW89_DECLARE_RFK_TBL(rtw8852c_tssi_disable_defs_b);
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.h b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.h
new file mode 100644
index 0000000000000..953a960ef1e85
--- /dev/null
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk_table.h
@@ -0,0 +1,67 @@
+/* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */
+/* Copyright(c) 2019-2022 Realtek Corporation
+ */
+
+#ifndef __RTW89_8852C_RFK_TABLE_H__
+#define __RTW89_8852C_RFK_TABLE_H__
+
+#include "phy.h"
+
+extern const struct rtw89_rfk_tbl rtw8852c_dack_reload_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dack_reset_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dack_reset_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dack_defs_s0_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dack_defs_s1_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_drck_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_iqk_rxk_cfg_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_iqk_afebb_restore_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_iqk_afebb_restore_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_read_rxsram_pre_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_read_rxsram_post_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dpk_mdpd_order0_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dpk_mdpd_order1_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dpk_mdpd_order2_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dpk_mdpd_order3_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dpk_kip_pwr_clk_on_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_dpk_kip_pwr_clk_off_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_sys_defs_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_sys_defs_2g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_sys_defs_2g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_sys_defs_5g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_sys_defs_5g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_txpwr_ctrl_bb_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_txpwr_ctrl_bb_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_dck_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_dck_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_dck_defs_2g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_dck_defs_2g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_dck_defs_5g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_dck_defs_5g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_bbgain_split_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_bbgain_split_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_slope_cal_org_defs_2g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_slope_cal_org_defs_2g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_slope_cal_org_defs_5g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_slope_cal_org_defs_5g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_aligk_default_defs_2g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_aligk_default_defs_2g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_aligk_default_defs_5g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_aligk_default_defs_5g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_aligk_default_defs_6g_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_set_aligk_default_defs_6g_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_slope_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_slope_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_run_slope_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_run_slope_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_track_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_track_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_txagc_ofst_mv_avg_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_txagc_ofst_mv_avg_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_enable_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_enable_defs_b_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_disable_defs_a_tbl;
+extern const struct rtw89_rfk_tbl rtw8852c_tssi_disable_defs_b_tbl;
+
+#endif
--
2.25.1

2022-05-03 01:28:34

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 2/8] rtw89: 8852c: rfk: add DACK

DACK (digital-to-analog converters calibration) is used to calibrate DAC
to output analog signals as expected.

Signed-off-by: Ping-Ke Shih <[email protected]>
---
drivers/net/wireless/realtek/rtw89/reg.h | 96 +++-
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 2 +
.../net/wireless/realtek/rtw89/rtw8852c_rfk.c | 446 ++++++++++++++++++
.../net/wireless/realtek/rtw89/rtw8852c_rfk.h | 1 +
4 files changed, 538 insertions(+), 7 deletions(-)

diff --git a/drivers/net/wireless/realtek/rtw89/reg.h b/drivers/net/wireless/realtek/rtw89/reg.h
index 83cb509d2fbe9..ce472d3b1a665 100644
--- a/drivers/net/wireless/realtek/rtw89/reg.h
+++ b/drivers/net/wireless/realtek/rtw89/reg.h
@@ -3484,9 +3484,12 @@
#define R_S0_HW_SI_DIS 0x1200
#define B_S0_HW_SI_DIS_W_R_TRIG GENMASK(30, 28)
#define R_P0_RXCK 0x12A0
-#define B_P0_RXCK_VAL GENMASK(18, 16)
-#define B_P0_RXCK_ON BIT(19)
#define B_P0_RXCK_BW3 BIT(30)
+#define B_P0_TXCK_ALL GENMASK(19, 12)
+#define B_P0_RXCK_ON BIT(19)
+#define B_P0_RXCK_VAL GENMASK(18, 16)
+#define B_P0_TXCK_ON BIT(15)
+#define B_P0_TXCK_VAL GENMASK(14, 12)
#define R_P0_NRBW 0x12B8
#define B_P0_NRBW_DBG BIT(30)
#define R_S0_RXDC 0x12D4
@@ -4035,19 +4038,98 @@
#define R_IQKINF2 0x9FE8
#define B_IQKINF2_FCNT GENMASK(23, 16)
#define B_IQKINF2_KCNT GENMASK(15, 8)
-#define B_IQKINF2_NCTLV GENMAKS(7, 0)
+#define B_IQKINF2_NCTLV GENMASK(7, 0)
+#define R_DCOF0 0xC000
+#define B_DCOF0_V GENMASK(4, 1)
+#define R_DCOF1 0xC004
+#define B_DCOF1_S BIT(0)
+#define R_DCOF8 0xC020
+#define B_DCOF8_V GENMASK(4, 1)
+#define R_DACK_S0P0 0xC040
+#define B_DACK_S0P0_OK BIT(31)
+#define R_DACK_BIAS00 0xc048
+#define B_DACK_BIAS00 GENMASK(11, 2)
+#define R_DACK_S0P2 0xC05C
+#define B_DACK_S0M0 GENMASK(31, 24)
+#define B_DACK_S0P2_OK BIT(2)
+#define R_DACK_DADCK00 0xC060
+#define B_DACK_DADCK00 GENMASK(31, 24)
+#define R_DACK_S0P1 0xC064
+#define B_DACK_S0P1_OK BIT(31)
+#define R_DACK_BIAS01 0xC06C
+#define B_DACK_BIAS01 GENMASK(11, 2)
+#define R_DACK_S0P3 0xC080
+#define B_DACK_S0M1 GENMASK(31, 24)
+#define B_DACK_S0P3_OK BIT(2)
+#define R_DACK_DADCK01 0xC084
+#define B_DACK_DADCK01 GENMASK(31, 24)
+#define R_DRCK 0xC0C4
+#define B_DRCK_IDLE BIT(9)
+#define B_DRCK_EN BIT(6)
+#define B_DRCK_VAL GENMASK(4, 0)
+#define R_DRCK_RES 0xC0C8
+#define B_DRCK_RES GENMASK(19, 15)
+#define B_DRCK_POL BIT(3)
#define R_PATH0_SAMPL_DLY_T_V1 0xC0D4
#define B_PATH0_SAMPL_DLY_T_MSK_V1 GENMASK(27, 26)
+#define R_P0_CFCH_BW0 0xC0D4
+#define B_P0_CFCH_BW0 GENMASK(27, 26)
+#define R_P0_CFCH_BW1 0xC0D8
+#define B_P0_CFCH_BW1 GENMASK(8, 5)
+#define R_ADDCK0 0xC0F4
+#define B_ADDCK0 GENMASK(9, 8)
+#define B_ADDCK0_EN BIT(4)
+#define B_ADDCK0_RST BIT(2)
+#define R_ADDCK0_RL 0xC0F8
+#define B_ADDCK0_RLS GENMASK(29, 28)
+#define B_ADDCK0_RL1 GENMASK(27, 18)
+#define B_ADDCK0_RL0 GENMASK(17, 8)
+#define R_ADDCKR0 0xC0FC
+#define B_ADDCKR0_A0 GENMASK(19, 10)
+#define B_ADDCKR0_A1 GENMASK(9, 0)
+#define R_DACK10 0xC100
+#define B_DACK10 GENMASK(4, 1)
+#define R_DACK1_K 0xc104
+#define B_DACK1_EN BIT(0)
+#define R_DACK11 0xC120
+#define B_DACK11 GENMASK(4, 1)
+#define R_DACK_S1P0 0xC140
+#define B_DACK_S1P0_OK BIT(31)
+#define R_DACK_BIAS10 0xC148
+#define B_DACK_BIAS10 GENMASK(11, 2)
+#define R_DACK10S 0xC15C
+#define B_DACK10S GENMASK(31, 24)
+#define R_DACK_S1P2 0xC15C
+#define B_DACK_S1P2_OK BIT(2)
+#define R_DACK_DADCK10 0xC160
+#define B_DACK_DADCK10 GENMASK(31, 24)
+#define R_DACK_S1P1 0xC164
+#define B_DACK_S1P1_OK BIT(31)
+#define R_DACK_BIAS11 0xC16C
+#define B_DACK_BIAS11 GENMASK(11, 2)
+#define R_DACK11S 0xC180
+#define B_DACK11S GENMASK(31, 24)
+#define R_DACK_S1P3 0xC180
+#define B_DACK_S1P3_OK BIT(2)
+#define R_DACK_DADCK11 0xC184
+#define B_DACK_DADCK11 GENMASK(31, 24)
#define R_PATH1_SAMPL_DLY_T_V1 0xC1D4
#define B_PATH1_SAMPL_DLY_T_MSK_V1 GENMASK(27, 26)
#define R_PATH0_BW_SEL_V1 0xC0D8
#define B_PATH0_BW_SEL_MSK_V1 GENMASK(8, 5)
#define R_PATH1_BW_SEL_V1 0xC1D8
#define B_PATH1_BW_SEL_MSK_V1 GENMASK(8, 5)
-#define R_P0_CFCH_BW0 0xC0D4
-#define B_P0_CFCH_BW0 GENMASK(27, 26)
-#define R_P0_CFCH_BW1 0xC0D8
-#define B_P0_CFCH_BW1 GENMASK(8, 5)
+#define R_ADDCK1 0xC1F4
+#define B_ADDCK1 GENMASK(9, 8)
+#define B_ADDCK1_EN BIT(4)
+#define B_ADDCK1_RST BIT(2)
+#define R_ADDCK1_RL 0xC1F8
+#define B_ADDCK1_RLS GENMASK(29, 28)
+#define B_ADDCK1_RL1 GENMASK(27, 18)
+#define B_ADDCK1_RL0 GENMASK(17, 8)
+#define R_ADDCKR1 0xC1fC
+#define B_ADDCKR1_A0 GENMASK(19, 10)
+#define B_ADDCKR1_A1 GENMASK(9, 0)

/* WiFi CPU local domain */
#define R_AX_WDT_CTRL 0x0040
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c.c b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
index 2755684682126..502627d8141d4 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
@@ -1771,6 +1771,8 @@ static void rtw8852c_rfk_init(struct rtw89_dev *rtwdev)
struct rtw89_mcc_info *mcc_info = &rtwdev->mcc;

memset(mcc_info, 0, sizeof(*mcc_info));
+
+ rtw8852c_dack(rtwdev);
}

static void rtw8852c_rfk_channel(struct rtw89_dev *rtwdev)
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
index 56f0876c03fbd..4245a2c5f9d67 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
@@ -2,11 +2,13 @@
/* Copyright(c) 2019-2022 Realtek Corporation
*/

+#include "coex.h"
#include "debug.h"
#include "phy.h"
#include "reg.h"
#include "rtw8852c.h"
#include "rtw8852c_rfk.h"
+#include "rtw8852c_rfk_table.h"

static u8 _kpath(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx)
{
@@ -22,6 +24,441 @@ static u8 _kpath(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx)
return RF_B;
}

+static void _dack_dump(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ u8 i;
+ u8 t;
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DACK]S0 ADC_DCK ic = 0x%x, qc = 0x%x\n",
+ dack->addck_d[0][0], dack->addck_d[0][1]);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DACK]S1 ADC_DCK ic = 0x%x, qc = 0x%x\n",
+ dack->addck_d[1][0], dack->addck_d[1][1]);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DACK]S0 DAC_DCK ic = 0x%x, qc = 0x%x\n",
+ dack->dadck_d[0][0], dack->dadck_d[0][1]);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DACK]S1 DAC_DCK ic = 0x%x, qc = 0x%x\n",
+ dack->dadck_d[1][0], dack->dadck_d[1][1]);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DACK]S0 biask ic = 0x%x, qc = 0x%x\n",
+ dack->biask_d[0][0], dack->biask_d[0][1]);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK,
+ "[DACK]S1 biask ic = 0x%x, qc = 0x%x\n",
+ dack->biask_d[1][0], dack->biask_d[1][1]);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S0 MSBK ic:\n");
+ for (i = 0; i < RTW89_DACK_MSBK_NR; i++) {
+ t = dack->msbk_d[0][0][i];
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x\n", t);
+ }
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S0 MSBK qc:\n");
+ for (i = 0; i < RTW89_DACK_MSBK_NR; i++) {
+ t = dack->msbk_d[0][1][i];
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x\n", t);
+ }
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S1 MSBK ic:\n");
+ for (i = 0; i < RTW89_DACK_MSBK_NR; i++) {
+ t = dack->msbk_d[1][0][i];
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x\n", t);
+ }
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S1 MSBK qc:\n");
+ for (i = 0; i < RTW89_DACK_MSBK_NR; i++) {
+ t = dack->msbk_d[1][1][i];
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x\n", t);
+ }
+}
+
+static void _addck_backup(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0, B_ADDCK0, 0x0);
+ dack->addck_d[0][0] = rtw89_phy_read32_mask(rtwdev, R_ADDCKR0,
+ B_ADDCKR0_A0);
+ dack->addck_d[0][1] = rtw89_phy_read32_mask(rtwdev, R_ADDCKR0,
+ B_ADDCKR0_A1);
+
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1, B_ADDCK1, 0x0);
+ dack->addck_d[1][0] = rtw89_phy_read32_mask(rtwdev, R_ADDCKR1,
+ B_ADDCKR1_A0);
+ dack->addck_d[1][1] = rtw89_phy_read32_mask(rtwdev, R_ADDCKR1,
+ B_ADDCKR1_A1);
+}
+
+static void _addck_reload(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0_RL, B_ADDCK0_RL1,
+ dack->addck_d[0][0]);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0_RL, B_ADDCK0_RL0,
+ dack->addck_d[0][1]);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0_RL, B_ADDCK0_RLS, 0x3);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1_RL, B_ADDCK1_RL1,
+ dack->addck_d[1][0]);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1_RL, B_ADDCK1_RL0,
+ dack->addck_d[1][1]);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1_RL, B_ADDCK1_RLS, 0x3);
+}
+
+static void _dack_backup_s0(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ u8 i;
+
+ rtw89_phy_write32_mask(rtwdev, R_P0_NRBW, B_P0_NRBW_DBG, 0x1);
+ for (i = 0; i < RTW89_DACK_MSBK_NR; i++) {
+ rtw89_phy_write32_mask(rtwdev, R_DCOF0, B_DCOF0_V, i);
+ dack->msbk_d[0][0][i] = rtw89_phy_read32_mask(rtwdev,
+ R_DACK_S0P2,
+ B_DACK_S0M0);
+ rtw89_phy_write32_mask(rtwdev, R_DCOF8, B_DCOF8_V, i);
+ dack->msbk_d[0][1][i] = rtw89_phy_read32_mask(rtwdev,
+ R_DACK_S0P3,
+ B_DACK_S0M1);
+ }
+ dack->biask_d[0][0] = rtw89_phy_read32_mask(rtwdev, R_DACK_BIAS00,
+ B_DACK_BIAS00);
+ dack->biask_d[0][1] = rtw89_phy_read32_mask(rtwdev, R_DACK_BIAS01,
+ B_DACK_BIAS01);
+ dack->dadck_d[0][0] = rtw89_phy_read32_mask(rtwdev, R_DACK_DADCK00,
+ B_DACK_DADCK00);
+ dack->dadck_d[0][1] = rtw89_phy_read32_mask(rtwdev, R_DACK_DADCK01,
+ B_DACK_DADCK01);
+}
+
+static void _dack_backup_s1(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ u8 i;
+
+ rtw89_phy_write32_mask(rtwdev, R_P1_DBGMOD, B_P1_DBGMOD_ON, 0x1);
+ for (i = 0; i < RTW89_DACK_MSBK_NR; i++) {
+ rtw89_phy_write32_mask(rtwdev, R_DACK10, B_DACK10, i);
+ dack->msbk_d[1][0][i] = rtw89_phy_read32_mask(rtwdev,
+ R_DACK10S,
+ B_DACK10S);
+ rtw89_phy_write32_mask(rtwdev, R_DACK11, B_DACK11, i);
+ dack->msbk_d[1][1][i] = rtw89_phy_read32_mask(rtwdev,
+ R_DACK11S,
+ B_DACK11S);
+ }
+ dack->biask_d[1][0] = rtw89_phy_read32_mask(rtwdev, R_DACK_BIAS10,
+ B_DACK_BIAS10);
+ dack->biask_d[1][1] = rtw89_phy_read32_mask(rtwdev, R_DACK_BIAS11,
+ B_DACK_BIAS11);
+ dack->dadck_d[1][0] = rtw89_phy_read32_mask(rtwdev, R_DACK_DADCK10,
+ B_DACK_DADCK10);
+ dack->dadck_d[1][1] = rtw89_phy_read32_mask(rtwdev, R_DACK_DADCK11,
+ B_DACK_DADCK11);
+}
+
+static void _dack_reload_by_path(struct rtw89_dev *rtwdev,
+ enum rtw89_rf_path path, u8 index)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ u32 idx_offset, path_offset;
+ u32 val32, offset, addr;
+ u8 i;
+
+ idx_offset = (index == 0 ? 0 : 0x14);
+ path_offset = (path == RF_PATH_A ? 0 : 0x28);
+ offset = idx_offset + path_offset;
+
+ rtw89_rfk_parser(rtwdev, &rtw8852c_dack_reload_defs_tbl);
+
+ /* msbk_d: 15/14/13/12 */
+ val32 = 0x0;
+ for (i = 0; i < RTW89_DACK_MSBK_NR / 4; i++)
+ val32 |= dack->msbk_d[path][index][i + 12] << (i * 8);
+ addr = 0xc200 + offset;
+ rtw89_phy_write32(rtwdev, addr, val32);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x=0x%x\n", addr,
+ rtw89_phy_read32_mask(rtwdev, addr, MASKDWORD));
+
+ /* msbk_d: 11/10/9/8 */
+ val32 = 0x0;
+ for (i = 0; i < RTW89_DACK_MSBK_NR / 4; i++)
+ val32 |= dack->msbk_d[path][index][i + 8] << (i * 8);
+ addr = 0xc204 + offset;
+ rtw89_phy_write32(rtwdev, addr, val32);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x=0x%x\n", addr,
+ rtw89_phy_read32_mask(rtwdev, addr, MASKDWORD));
+
+ /* msbk_d: 7/6/5/4 */
+ val32 = 0x0;
+ for (i = 0; i < RTW89_DACK_MSBK_NR / 4; i++)
+ val32 |= dack->msbk_d[path][index][i + 4] << (i * 8);
+ addr = 0xc208 + offset;
+ rtw89_phy_write32(rtwdev, addr, val32);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x=0x%x\n", addr,
+ rtw89_phy_read32_mask(rtwdev, addr, MASKDWORD));
+
+ /* msbk_d: 3/2/1/0 */
+ val32 = 0x0;
+ for (i = 0; i < RTW89_DACK_MSBK_NR / 4; i++)
+ val32 |= dack->msbk_d[path][index][i] << (i * 8);
+ addr = 0xc20c + offset;
+ rtw89_phy_write32(rtwdev, addr, val32);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0x%x=0x%x\n", addr,
+ rtw89_phy_read32_mask(rtwdev, addr, MASKDWORD));
+
+ /* dadak_d/biask_d */
+ val32 = (dack->biask_d[path][index] << 22) |
+ (dack->dadck_d[path][index] << 14);
+ addr = 0xc210 + offset;
+ rtw89_phy_write32(rtwdev, addr, val32);
+ rtw89_phy_write32_set(rtwdev, addr, BIT(1));
+}
+
+static void _dack_reload(struct rtw89_dev *rtwdev, enum rtw89_rf_path path)
+{
+ u8 i;
+
+ for (i = 0; i < 2; i++)
+ _dack_reload_by_path(rtwdev, path, i);
+}
+
+static void _addck(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ u32 val;
+ int ret;
+
+ /* S0 */
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0, B_ADDCK0_RST, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0, B_ADDCK0_EN, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0, B_ADDCK0_EN, 0x0);
+ fsleep(1);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0, B_ADDCK0, 0x1);
+
+ ret = read_poll_timeout_atomic(rtw89_phy_read32_mask, val, val,
+ 1, 10000, false, rtwdev, 0xc0fc, BIT(0));
+ if (ret) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S0 ADDCK timeout\n");
+ dack->addck_timeout[0] = true;
+ }
+
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK0, B_ADDCK0_RST, 0x0);
+
+ /* S1 */
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1, B_ADDCK1_RST, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1, B_ADDCK1_EN, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1, B_ADDCK1_EN, 0x0);
+ udelay(1);
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1, B_ADDCK1, 0x1);
+
+ ret = read_poll_timeout_atomic(rtw89_phy_read32_mask, val, val,
+ 1, 10000, false, rtwdev, 0xc1fc, BIT(0));
+ if (ret) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S1 ADDCK timeout\n");
+ dack->addck_timeout[0] = true;
+ }
+ rtw89_phy_write32_mask(rtwdev, R_ADDCK1, B_ADDCK1_RST, 0x0);
+}
+
+static void _dack_reset(struct rtw89_dev *rtwdev, u8 path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_dack_reset_defs_a_tbl,
+ &rtw8852c_dack_reset_defs_b_tbl);
+}
+
+enum adc_ck {
+ ADC_NA = 0,
+ ADC_480M = 1,
+ ADC_960M = 2,
+ ADC_1920M = 3,
+};
+
+enum dac_ck {
+ DAC_40M = 0,
+ DAC_80M = 1,
+ DAC_120M = 2,
+ DAC_160M = 3,
+ DAC_240M = 4,
+ DAC_320M = 5,
+ DAC_480M = 6,
+ DAC_960M = 7,
+};
+
+enum rf_mode {
+ RF_SHUT_DOWN = 0x0,
+ RF_STANDBY = 0x1,
+ RF_TX = 0x2,
+ RF_RX = 0x3,
+ RF_TXIQK = 0x4,
+ RF_DPK = 0x5,
+ RF_RXK1 = 0x6,
+ RF_RXK2 = 0x7,
+};
+
+static void rtw8852c_txck_force(struct rtw89_dev *rtwdev, u8 path, bool force,
+ enum dac_ck ck)
+{
+ rtw89_phy_write32_mask(rtwdev, R_P0_RXCK | (path << 13), B_P0_TXCK_ON, 0x0);
+
+ if (!force)
+ return;
+
+ rtw89_phy_write32_mask(rtwdev, R_P0_RXCK | (path << 13), B_P0_TXCK_VAL, ck);
+ rtw89_phy_write32_mask(rtwdev, R_P0_RXCK | (path << 13), B_P0_TXCK_ON, 0x1);
+}
+
+static void rtw8852c_rxck_force(struct rtw89_dev *rtwdev, u8 path, bool force,
+ enum adc_ck ck)
+{
+ rtw89_phy_write32_mask(rtwdev, R_P0_RXCK | (path << 13), B_P0_RXCK_ON, 0x0);
+
+ if (!force)
+ return;
+
+ rtw89_phy_write32_mask(rtwdev, R_P0_RXCK | (path << 13), B_P0_RXCK_VAL, ck);
+ rtw89_phy_write32_mask(rtwdev, R_P0_RXCK | (path << 13), B_P0_RXCK_ON, 0x1);
+}
+
+static bool _check_dack_done(struct rtw89_dev *rtwdev, bool s0)
+{
+ if (s0) {
+ if (rtw89_phy_read32_mask(rtwdev, R_DACK_S0P0, B_DACK_S0P0_OK) == 0 ||
+ rtw89_phy_read32_mask(rtwdev, R_DACK_S0P1, B_DACK_S0P1_OK) == 0 ||
+ rtw89_phy_read32_mask(rtwdev, R_DACK_S0P2, B_DACK_S0P2_OK) == 0 ||
+ rtw89_phy_read32_mask(rtwdev, R_DACK_S0P3, B_DACK_S0P3_OK) == 0)
+ return false;
+ } else {
+ if (rtw89_phy_read32_mask(rtwdev, R_DACK_S1P0, B_DACK_S1P0_OK) == 0 ||
+ rtw89_phy_read32_mask(rtwdev, R_DACK_S1P1, B_DACK_S1P1_OK) == 0 ||
+ rtw89_phy_read32_mask(rtwdev, R_DACK_S1P2, B_DACK_S1P2_OK) == 0 ||
+ rtw89_phy_read32_mask(rtwdev, R_DACK_S1P3, B_DACK_S1P3_OK) == 0)
+ return false;
+ }
+
+ return true;
+}
+
+static void _dack_s0(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ bool done;
+ int ret;
+
+ rtw8852c_txck_force(rtwdev, RF_PATH_A, true, DAC_160M);
+ rtw89_rfk_parser(rtwdev, &rtw8852c_dack_defs_s0_tbl);
+
+ _dack_reset(rtwdev, RF_PATH_A);
+
+ rtw89_phy_write32_mask(rtwdev, R_DCOF1, B_DCOF1_S, 0x1);
+ ret = read_poll_timeout_atomic(_check_dack_done, done, done,
+ 1, 10000, false, rtwdev, true);
+ if (ret) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S0 DACK timeout\n");
+ dack->msbk_timeout[0] = true;
+ }
+ rtw89_phy_write32_mask(rtwdev, R_DCOF1, B_DCOF1_S, 0x0);
+ rtw8852c_txck_force(rtwdev, RF_PATH_A, false, DAC_960M);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]after S0 DADCK\n");
+
+ _dack_backup_s0(rtwdev);
+ _dack_reload(rtwdev, RF_PATH_A);
+ rtw89_phy_write32_mask(rtwdev, R_P0_NRBW, B_P0_NRBW_DBG, 0x0);
+}
+
+static void _dack_s1(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ bool done;
+ int ret;
+
+ rtw8852c_txck_force(rtwdev, RF_PATH_B, true, DAC_160M);
+ rtw89_rfk_parser(rtwdev, &rtw8852c_dack_defs_s1_tbl);
+
+ _dack_reset(rtwdev, RF_PATH_B);
+
+ rtw89_phy_write32_mask(rtwdev, R_DACK1_K, B_DACK1_EN, 0x1);
+ ret = read_poll_timeout_atomic(_check_dack_done, done, done,
+ 1, 10000, false, rtwdev, false);
+ if (ret) {
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]S1 DACK timeout\n");
+ dack->msbk_timeout[0] = true;
+ }
+ rtw89_phy_write32_mask(rtwdev, R_DACK1_K, B_DACK1_EN, 0x0);
+ rtw8852c_txck_force(rtwdev, RF_PATH_B, false, DAC_960M);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]after S1 DADCK\n");
+
+ _dack_backup_s1(rtwdev);
+ _dack_reload(rtwdev, RF_PATH_B);
+ rtw89_phy_write32_mask(rtwdev, R_P1_DBGMOD, B_P1_DBGMOD_ON, 0x0);
+}
+
+static void _dack(struct rtw89_dev *rtwdev)
+{
+ _dack_s0(rtwdev);
+ _dack_s1(rtwdev);
+}
+
+static void _drck(struct rtw89_dev *rtwdev)
+{
+ u32 val;
+ int ret;
+
+ rtw89_phy_write32_mask(rtwdev, R_DRCK, B_DRCK_EN, 0x1);
+ ret = read_poll_timeout_atomic(rtw89_phy_read32_mask, val, val,
+ 1, 10000, false, rtwdev, 0xc0c8, BIT(3));
+ if (ret)
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]DRCK timeout\n");
+
+ rtw89_rfk_parser(rtwdev, &rtw8852c_drck_defs_tbl);
+
+ val = rtw89_phy_read32_mask(rtwdev, R_DRCK_RES, B_DRCK_RES);
+ rtw89_phy_write32_mask(rtwdev, R_DRCK, B_DRCK_IDLE, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_DRCK, B_DRCK_VAL, val);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]0xc0c4 = 0x%x\n",
+ rtw89_phy_read32_mask(rtwdev, R_DRCK, MASKDWORD));
+}
+
+static void _dac_cal(struct rtw89_dev *rtwdev, bool force)
+{
+ struct rtw89_dack_info *dack = &rtwdev->dack;
+ u32 rf0_0, rf1_0;
+ u8 phy_map = rtw89_btc_phymap(rtwdev, RTW89_PHY_0, RF_AB);
+
+ dack->dack_done = false;
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]DACK b\n");
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]DACK start!!!\n");
+ rf0_0 = rtw89_read_rf(rtwdev, RF_PATH_A, RR_MOD, RFREG_MASK);
+ rf1_0 = rtw89_read_rf(rtwdev, RF_PATH_B, RR_MOD, RFREG_MASK);
+ _drck(rtwdev);
+
+ rtw89_write_rf(rtwdev, RF_PATH_A, RR_RSV1, RR_RSV1_RST, 0x0);
+ rtw89_write_rf(rtwdev, RF_PATH_B, RR_RSV1, RR_RSV1_RST, 0x0);
+ rtw89_write_rf(rtwdev, RF_PATH_A, RR_MOD, RFREG_MASK, 0x337e1);
+ rtw89_write_rf(rtwdev, RF_PATH_B, RR_MOD, RFREG_MASK, 0x337e1);
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_ONESHOT_START);
+ _addck(rtwdev);
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_ONESHOT_STOP);
+
+ _addck_backup(rtwdev);
+ _addck_reload(rtwdev);
+ rtw89_write_rf(rtwdev, RF_PATH_A, RR_MODOPT, RFREG_MASK, 0x0);
+ rtw89_write_rf(rtwdev, RF_PATH_B, RR_MODOPT, RFREG_MASK, 0x0);
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_ONESHOT_START);
+ _dack(rtwdev);
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_ONESHOT_STOP);
+
+ _dack_dump(rtwdev);
+ dack->dack_done = true;
+ rtw89_write_rf(rtwdev, RF_PATH_A, RR_MOD, RFREG_MASK, rf0_0);
+ rtw89_write_rf(rtwdev, RF_PATH_B, RR_MOD, RFREG_MASK, rf1_0);
+ rtw89_write_rf(rtwdev, RF_PATH_A, RR_RSV1, RR_RSV1_RST, 0x1);
+ rtw89_write_rf(rtwdev, RF_PATH_B, RR_RSV1, RR_RSV1_RST, 0x1);
+ dack->dack_cnt++;
+ rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]DACK finish!!!\n");
+}
+
static void _bw_setting(struct rtw89_dev *rtwdev, enum rtw89_rf_path path,
enum rtw89_bandwidth bw, bool is_dav)
{
@@ -212,3 +649,12 @@ void rtw8852c_set_channel_rf(struct rtw89_dev *rtwdev,
rtw8852c_ctrl_bw_ch(rtwdev, phy_idx, param->center_chan, param->band_type,
param->bandwidth);
}
+
+void rtw8852c_dack(struct rtw89_dev *rtwdev)
+{
+ u8 phy_map = rtw89_btc_phymap(rtwdev, RTW89_PHY_0, 0);
+
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_START);
+ _dac_cal(rtwdev, false);
+ rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_STOP);
+}
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
index 0e75555c1612d..7323183e74d41 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
@@ -7,6 +7,7 @@

#include "core.h"

+void rtw8852c_dack(struct rtw89_dev *rtwdev);
void rtw8852c_set_channel_rf(struct rtw89_dev *rtwdev,
struct rtw89_channel_params *param,
enum rtw89_phy_idx phy_idx);
--
2.25.1

2022-05-03 01:28:41

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 3/8] rtw89: 8852c: rfk: add LCK

LCK is short fro LC Tank calibration. Do this calibration once driver
loads RF parameters table. Since the characteristic can be changed by
temperature, we do this calibration again if difference of thermal value
is over a threshold.

Signed-off-by: Ping-Ke Shih <[email protected]>
---
drivers/net/wireless/realtek/rtw89/core.h | 5 ++
drivers/net/wireless/realtek/rtw89/reg.h | 2 +
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 7 +++
.../net/wireless/realtek/rtw89/rtw8852c_rfk.c | 63 +++++++++++++++++++
.../net/wireless/realtek/rtw89/rtw8852c_rfk.h | 2 +
5 files changed, 79 insertions(+)

diff --git a/drivers/net/wireless/realtek/rtw89/core.h b/drivers/net/wireless/realtek/rtw89/core.h
index d544cf29e588a..41d23711dc354 100644
--- a/drivers/net/wireless/realtek/rtw89/core.h
+++ b/drivers/net/wireless/realtek/rtw89/core.h
@@ -2642,6 +2642,10 @@ struct rtw89_mcc_info {
u8 table_idx;
};

+struct rtw89_lck_info {
+ u8 thermal[RF_PATH_MAX];
+};
+
struct rtw89_iqk_info {
bool lok_cor_fail[RTW89_IQK_CHS_NR][RTW89_IQK_PATH_NR];
bool lok_fin_fail[RTW89_IQK_CHS_NR][RTW89_IQK_PATH_NR];
@@ -3114,6 +3118,7 @@ struct rtw89_dev {
struct rtw89_iqk_info iqk;
struct rtw89_dpk_info dpk;
struct rtw89_mcc_info mcc;
+ struct rtw89_lck_info lck;
bool is_tssi_mode[RF_PATH_MAX];
bool is_bt_iqk_timeout;

diff --git a/drivers/net/wireless/realtek/rtw89/reg.h b/drivers/net/wireless/realtek/rtw89/reg.h
index ce472d3b1a665..028c881308237 100644
--- a/drivers/net/wireless/realtek/rtw89/reg.h
+++ b/drivers/net/wireless/realtek/rtw89/reg.h
@@ -3327,6 +3327,8 @@
#define RR_MIXER_GN GENMASK(4, 3)
#define RR_XTALX2 0xb8
#define RR_MALSEL 0xbe
+#define RR_LCK_TRG 0xd3
+#define RR_LCK_TRGSEL BIT(8)
#define RR_RCKD 0xde
#define RR_RCKD_POW GENMASK(19, 13)
#define RR_RCKD_BW BIT(2)
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c.c b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
index 502627d8141d4..14302ebed3d5e 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
@@ -1771,6 +1771,7 @@ static void rtw8852c_rfk_init(struct rtw89_dev *rtwdev)
struct rtw89_mcc_info *mcc_info = &rtwdev->mcc;

memset(mcc_info, 0, sizeof(*mcc_info));
+ rtw8852c_lck_init(rtwdev);

rtw8852c_dack(rtwdev);
}
@@ -1780,6 +1781,11 @@ static void rtw8852c_rfk_channel(struct rtw89_dev *rtwdev)
rtw89_fw_h2c_rf_ntfy_mcc(rtwdev);
}

+static void rtw8852c_rfk_track(struct rtw89_dev *rtwdev)
+{
+ rtw8852c_lck_track(rtwdev);
+}
+
static u32 rtw8852c_bb_cal_txpwr_ref(struct rtw89_dev *rtwdev,
enum rtw89_phy_idx phy_idx, s16 ref)
{
@@ -2708,6 +2714,7 @@ static const struct rtw89_chip_ops rtw8852c_chip_ops = {
.read_phycap = rtw8852c_read_phycap,
.rfk_init = rtw8852c_rfk_init,
.rfk_channel = rtw8852c_rfk_channel,
+ .rfk_track = rtw8852c_rfk_track,
.power_trim = rtw8852c_power_trim,
.set_txpwr = rtw8852c_set_txpwr,
.set_txpwr_ctrl = rtw8852c_set_txpwr_ctrl,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
index 4245a2c5f9d67..ce08b2dcf5459 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
@@ -632,6 +632,69 @@ static void _rxbb_bw(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
}
}

+static void _lck_keep_thermal(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_lck_info *lck = &rtwdev->lck;
+ int path;
+
+ for (path = 0; path < rtwdev->chip->rf_path_num; path++) {
+ lck->thermal[path] =
+ ewma_thermal_read(&rtwdev->phystat.avg_thermal[path]);
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[LCK] path=%d thermal=0x%x", path, lck->thermal[path]);
+ }
+}
+
+static void _lck(struct rtw89_dev *rtwdev)
+{
+ u32 tmp18[2];
+ int path = rtwdev->dbcc_en ? 2 : 1;
+ int i;
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK, "[LCK] DO LCK\n");
+
+ tmp18[0] = rtw89_read_rf(rtwdev, RF_PATH_A, RR_CFGCH, RFREG_MASK);
+ tmp18[1] = rtw89_read_rf(rtwdev, RF_PATH_B, RR_CFGCH, RFREG_MASK);
+
+ for (i = 0; i < path; i++) {
+ rtw89_write_rf(rtwdev, i, RR_LCK_TRG, RR_LCK_TRGSEL, 0x1);
+ rtw89_write_rf(rtwdev, i, RR_CFGCH, RFREG_MASK, tmp18[i]);
+ rtw89_write_rf(rtwdev, i, RR_LCK_TRG, RR_LCK_TRGSEL, 0x0);
+ }
+
+ _lck_keep_thermal(rtwdev);
+}
+
+#define RTW8852C_LCK_TH 8
+
+void rtw8852c_lck_track(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_lck_info *lck = &rtwdev->lck;
+ u8 cur_thermal;
+ int delta;
+ int path;
+
+ for (path = 0; path < rtwdev->chip->rf_path_num; path++) {
+ cur_thermal =
+ ewma_thermal_read(&rtwdev->phystat.avg_thermal[path]);
+ delta = abs((int)cur_thermal - lck->thermal[path]);
+
+ rtw89_debug(rtwdev, RTW89_DBG_RFK_TRACK,
+ "[LCK] path=%d current thermal=0x%x delta=0x%x\n",
+ path, cur_thermal, delta);
+
+ if (delta >= RTW8852C_LCK_TH) {
+ _lck(rtwdev);
+ return;
+ }
+ }
+}
+
+void rtw8852c_lck_init(struct rtw89_dev *rtwdev)
+{
+ _lck_keep_thermal(rtwdev);
+}
+
static
void rtw8852c_ctrl_bw_ch(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
u8 central_ch, enum rtw89_band band,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
index 7323183e74d41..4ce76ef4c5e60 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
@@ -11,5 +11,7 @@ void rtw8852c_dack(struct rtw89_dev *rtwdev);
void rtw8852c_set_channel_rf(struct rtw89_dev *rtwdev,
struct rtw89_channel_params *param,
enum rtw89_phy_idx phy_idx);
+void rtw8852c_lck_init(struct rtw89_dev *rtwdev);
+void rtw8852c_lck_track(struct rtw89_dev *rtwdev);

#endif
--
2.25.1

2022-05-03 01:29:28

by Ping-Ke Shih

[permalink] [raw]
Subject: [PATCH v3 4/8] rtw89: 8852c: rfk: add TSSI

TSSI is transmitter signal strength indication, which is a close-loop
hardware circuit to feedback actual transmitting power as a reference for
next transmission.

When we setup channel to connect an AP, it does full calibration. When
switching bands or channels, it needs to reset hardware status to prevent
use wrong feedback of previous transmission.

To do TX power compensation reflecting current temperature, it loads tables
of compensation values into registers according to channel and band group.

Signed-off-by: Ping-Ke Shih <[email protected]>
---
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 19 +
.../net/wireless/realtek/rtw89/rtw8852c_rfk.c | 1033 +++++++++++++++++
.../net/wireless/realtek/rtw89/rtw8852c_rfk.h | 5 +
3 files changed, 1057 insertions(+)

diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c.c b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
index 14302ebed3d5e..36406488e60e4 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
@@ -1754,6 +1754,7 @@ static void rtw8852c_set_channel_help(struct rtw89_dev *rtwdev, bool enter,
rtw89_chip_stop_sch_tx(rtwdev, RTW89_MAC_0, &p->tx_en, RTW89_SCH_TX_SEL_ALL);
rtw89_mac_cfg_ppdu_status(rtwdev, RTW89_MAC_0, false);
rtw8852c_dfs_en(rtwdev, false);
+ rtw8852c_tssi_cont_en_phyidx(rtwdev, false, RTW89_PHY_0);
rtw8852c_adc_en(rtwdev, false);
fsleep(40);
rtw8852c_bb_reset_en(rtwdev, phy_idx, false);
@@ -1761,6 +1762,7 @@ static void rtw8852c_set_channel_help(struct rtw89_dev *rtwdev, bool enter,
rtw89_mac_cfg_ppdu_status(rtwdev, RTW89_MAC_0, true);
rtw8852c_adc_en(rtwdev, true);
rtw8852c_dfs_en(rtwdev, true);
+ rtw8852c_tssi_cont_en_phyidx(rtwdev, true, RTW89_PHY_0);
rtw8852c_bb_reset_en(rtwdev, phy_idx, true);
rtw89_chip_resume_sch_tx(rtwdev, RTW89_MAC_0, p->tx_en);
}
@@ -1770,6 +1772,8 @@ static void rtw8852c_rfk_init(struct rtw89_dev *rtwdev)
{
struct rtw89_mcc_info *mcc_info = &rtwdev->mcc;

+ rtwdev->is_tssi_mode[RF_PATH_A] = false;
+ rtwdev->is_tssi_mode[RF_PATH_B] = false;
memset(mcc_info, 0, sizeof(*mcc_info));
rtw8852c_lck_init(rtwdev);

@@ -1778,9 +1782,22 @@ static void rtw8852c_rfk_init(struct rtw89_dev *rtwdev)

static void rtw8852c_rfk_channel(struct rtw89_dev *rtwdev)
{
+ enum rtw89_phy_idx phy_idx = RTW89_PHY_0;
+
+ rtw8852c_tssi(rtwdev, phy_idx);
rtw89_fw_h2c_rf_ntfy_mcc(rtwdev);
}

+static void rtw8852c_rfk_band_changed(struct rtw89_dev *rtwdev)
+{
+ rtw8852c_tssi_scan(rtwdev, RTW89_PHY_0);
+}
+
+static void rtw8852c_rfk_scan(struct rtw89_dev *rtwdev, bool start)
+{
+ rtw8852c_wifi_scan_notify(rtwdev, start, RTW89_PHY_0);
+}
+
static void rtw8852c_rfk_track(struct rtw89_dev *rtwdev)
{
rtw8852c_lck_track(rtwdev);
@@ -2714,6 +2731,8 @@ static const struct rtw89_chip_ops rtw8852c_chip_ops = {
.read_phycap = rtw8852c_read_phycap,
.rfk_init = rtw8852c_rfk_init,
.rfk_channel = rtw8852c_rfk_channel,
+ .rfk_band_changed = rtw8852c_rfk_band_changed,
+ .rfk_scan = rtw8852c_rfk_scan,
.rfk_track = rtw8852c_rfk_track,
.power_trim = rtw8852c_power_trim,
.set_txpwr = rtw8852c_set_txpwr,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
index ce08b2dcf5459..974bb5794ad9f 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.c
@@ -9,6 +9,17 @@
#include "rtw8852c.h"
#include "rtw8852c_rfk.h"
#include "rtw8852c_rfk_table.h"
+#include "rtw8852c_table.h"
+
+#define _TSSI_DE_MASK GENMASK(21, 12)
+static const u32 _tssi_de_cck_long[RF_PATH_NUM_8852C] = {0x5858, 0x7858};
+static const u32 _tssi_de_cck_short[RF_PATH_NUM_8852C] = {0x5860, 0x7860};
+static const u32 _tssi_de_mcs_20m[RF_PATH_NUM_8852C] = {0x5838, 0x7838};
+static const u32 _tssi_de_mcs_40m[RF_PATH_NUM_8852C] = {0x5840, 0x7840};
+static const u32 _tssi_de_mcs_80m[RF_PATH_NUM_8852C] = {0x5848, 0x7848};
+static const u32 _tssi_de_mcs_80m_80m[RF_PATH_NUM_8852C] = {0x5850, 0x7850};
+static const u32 _tssi_de_mcs_5m[RF_PATH_NUM_8852C] = {0x5828, 0x7828};
+static const u32 _tssi_de_mcs_10m[RF_PATH_NUM_8852C] = {0x5830, 0x7830};

static u8 _kpath(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx)
{
@@ -459,6 +470,901 @@ static void _dac_cal(struct rtw89_dev *rtwdev, bool force)
rtw89_debug(rtwdev, RTW89_DBG_RFK, "[DACK]DACK finish!!!\n");
}

+static void _tssi_set_sys(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ enum rtw89_band band = rtwdev->hal.current_band_type;
+
+ rtw89_rfk_parser(rtwdev, &rtw8852c_tssi_sys_defs_tbl);
+
+ if (path == RF_PATH_A)
+ rtw89_rfk_parser_by_cond(rtwdev, band == RTW89_BAND_2G,
+ &rtw8852c_tssi_sys_defs_2g_a_tbl,
+ &rtw8852c_tssi_sys_defs_5g_a_tbl);
+ else
+ rtw89_rfk_parser_by_cond(rtwdev, band == RTW89_BAND_2G,
+ &rtw8852c_tssi_sys_defs_2g_b_tbl,
+ &rtw8852c_tssi_sys_defs_5g_b_tbl);
+}
+
+static void _tssi_ini_txpwr_ctrl_bb(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_tssi_txpwr_ctrl_bb_defs_a_tbl,
+ &rtw8852c_tssi_txpwr_ctrl_bb_defs_b_tbl);
+}
+
+static void _tssi_ini_txpwr_ctrl_bb_he_tb(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_a_tbl,
+ &rtw8852c_tssi_txpwr_ctrl_bb_he_tb_defs_b_tbl);
+}
+
+static void _tssi_set_dck(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ enum rtw89_band band = rtwdev->hal.current_band_type;
+
+ if (path == RF_PATH_A) {
+ rtw89_rfk_parser(rtwdev, &rtw8852c_tssi_dck_defs_a_tbl);
+ rtw89_rfk_parser_by_cond(rtwdev, band == RTW89_BAND_2G,
+ &rtw8852c_tssi_dck_defs_2g_a_tbl,
+ &rtw8852c_tssi_dck_defs_5g_a_tbl);
+ } else {
+ rtw89_rfk_parser(rtwdev, &rtw8852c_tssi_dck_defs_b_tbl);
+ rtw89_rfk_parser_by_cond(rtwdev, band == RTW89_BAND_2G,
+ &rtw8852c_tssi_dck_defs_2g_b_tbl,
+ &rtw8852c_tssi_dck_defs_5g_b_tbl);
+ }
+}
+
+static void _tssi_set_bbgain_split(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_tssi_set_bbgain_split_a_tbl,
+ &rtw8852c_tssi_set_bbgain_split_b_tbl);
+}
+
+static void _tssi_set_tmeter_tbl(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+#define RTW8852C_TSSI_GET_VAL(ptr, idx) \
+({ \
+ s8 *__ptr = (ptr); \
+ u8 __idx = (idx), __i, __v; \
+ u32 __val = 0; \
+ for (__i = 0; __i < 4; __i++) { \
+ __v = (__ptr[__idx + __i]); \
+ __val |= (__v << (8 * __i)); \
+ } \
+ __val; \
+})
+ struct rtw89_tssi_info *tssi_info = &rtwdev->tssi;
+ u8 ch = rtwdev->hal.current_channel;
+ u8 subband = rtwdev->hal.current_subband;
+ const s8 *thm_up_a = NULL;
+ const s8 *thm_down_a = NULL;
+ const s8 *thm_up_b = NULL;
+ const s8 *thm_down_b = NULL;
+ u8 thermal = 0xff;
+ s8 thm_ofst[64] = {0};
+ u32 tmp = 0;
+ u8 i, j;
+
+ switch (subband) {
+ default:
+ case RTW89_CH_2G:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_2ga_p;
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_2ga_n;
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_2gb_p;
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_2gb_n;
+ break;
+ case RTW89_CH_5G_BAND_1:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_5ga_p[0];
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_5ga_n[0];
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_5gb_p[0];
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_5gb_n[0];
+ break;
+ case RTW89_CH_5G_BAND_3:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_5ga_p[1];
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_5ga_n[1];
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_5gb_p[1];
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_5gb_n[1];
+ break;
+ case RTW89_CH_5G_BAND_4:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_5ga_p[2];
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_5ga_n[2];
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_5gb_p[2];
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_5gb_n[2];
+ break;
+ case RTW89_CH_6G_BAND_IDX0:
+ case RTW89_CH_6G_BAND_IDX1:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_p[0];
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_n[0];
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_p[0];
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_n[0];
+ break;
+ case RTW89_CH_6G_BAND_IDX2:
+ case RTW89_CH_6G_BAND_IDX3:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_p[1];
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_n[1];
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_p[1];
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_n[1];
+ break;
+ case RTW89_CH_6G_BAND_IDX4:
+ case RTW89_CH_6G_BAND_IDX5:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_p[2];
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_n[2];
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_p[2];
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_n[2];
+ break;
+ case RTW89_CH_6G_BAND_IDX6:
+ case RTW89_CH_6G_BAND_IDX7:
+ thm_up_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_p[3];
+ thm_down_a = rtw89_8852c_trk_cfg.delta_swingidx_6ga_n[3];
+ thm_up_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_p[3];
+ thm_down_b = rtw89_8852c_trk_cfg.delta_swingidx_6gb_n[3];
+ break;
+ }
+
+ if (path == RF_PATH_A) {
+ thermal = tssi_info->thermal[RF_PATH_A];
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] ch=%d thermal_pathA=0x%x\n", ch, thermal);
+
+ rtw89_phy_write32_mask(rtwdev, R_P0_TMETER, B_P0_TMETER_DIS, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_P0_TMETER, B_P0_TMETER_TRK, 0x1);
+
+ if (thermal == 0xff) {
+ rtw89_phy_write32_mask(rtwdev, R_P0_TMETER, B_P0_TMETER, 32);
+ rtw89_phy_write32_mask(rtwdev, R_P0_RFCTM, B_P0_RFCTM_VAL, 32);
+
+ for (i = 0; i < 64; i += 4) {
+ rtw89_phy_write32(rtwdev, R_P0_TSSI_BASE + i, 0x0);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] write 0x%x val=0x%08x\n",
+ 0x5c00 + i, 0x0);
+ }
+
+ } else {
+ rtw89_phy_write32_mask(rtwdev, R_P0_TMETER, B_P0_TMETER, thermal);
+ rtw89_phy_write32_mask(rtwdev, R_P0_RFCTM, B_P0_RFCTM_VAL,
+ thermal);
+
+ i = 0;
+ for (j = 0; j < 32; j++)
+ thm_ofst[j] = i < DELTA_SWINGIDX_SIZE ?
+ -thm_down_a[i++] :
+ -thm_down_a[DELTA_SWINGIDX_SIZE - 1];
+
+ i = 1;
+ for (j = 63; j >= 32; j--)
+ thm_ofst[j] = i < DELTA_SWINGIDX_SIZE ?
+ thm_up_a[i++] :
+ thm_up_a[DELTA_SWINGIDX_SIZE - 1];
+
+ for (i = 0; i < 64; i += 4) {
+ tmp = RTW8852C_TSSI_GET_VAL(thm_ofst, i);
+ rtw89_phy_write32(rtwdev, R_P0_TSSI_BASE + i, tmp);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] write 0x%x val=0x%08x\n",
+ 0x5c00 + i, tmp);
+ }
+ }
+ rtw89_phy_write32_mask(rtwdev, R_P0_RFCTM, R_P0_RFCTM_RDY, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_P0_RFCTM, R_P0_RFCTM_RDY, 0x0);
+
+ } else {
+ thermal = tssi_info->thermal[RF_PATH_B];
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] ch=%d thermal_pathB=0x%x\n", ch, thermal);
+
+ rtw89_phy_write32_mask(rtwdev, R_P1_TMETER, B_P1_TMETER_DIS, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_P1_TMETER, B_P1_TMETER_TRK, 0x1);
+
+ if (thermal == 0xff) {
+ rtw89_phy_write32_mask(rtwdev, R_P1_TMETER, B_P1_TMETER, 32);
+ rtw89_phy_write32_mask(rtwdev, R_P1_RFCTM, B_P1_RFCTM_VAL, 32);
+
+ for (i = 0; i < 64; i += 4) {
+ rtw89_phy_write32(rtwdev, R_TSSI_THOF + i, 0x0);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] write 0x%x val=0x%08x\n",
+ 0x7c00 + i, 0x0);
+ }
+
+ } else {
+ rtw89_phy_write32_mask(rtwdev, R_P1_TMETER, B_P1_TMETER, thermal);
+ rtw89_phy_write32_mask(rtwdev, R_P1_RFCTM, B_P1_RFCTM_VAL,
+ thermal);
+
+ i = 0;
+ for (j = 0; j < 32; j++)
+ thm_ofst[j] = i < DELTA_SWINGIDX_SIZE ?
+ -thm_down_b[i++] :
+ -thm_down_b[DELTA_SWINGIDX_SIZE - 1];
+
+ i = 1;
+ for (j = 63; j >= 32; j--)
+ thm_ofst[j] = i < DELTA_SWINGIDX_SIZE ?
+ thm_up_b[i++] :
+ thm_up_b[DELTA_SWINGIDX_SIZE - 1];
+
+ for (i = 0; i < 64; i += 4) {
+ tmp = RTW8852C_TSSI_GET_VAL(thm_ofst, i);
+ rtw89_phy_write32(rtwdev, R_TSSI_THOF + i, tmp);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] write 0x%x val=0x%08x\n",
+ 0x7c00 + i, tmp);
+ }
+ }
+ rtw89_phy_write32_mask(rtwdev, R_P1_RFCTM, R_P1_RFCTM_RDY, 0x1);
+ rtw89_phy_write32_mask(rtwdev, R_P1_RFCTM, R_P1_RFCTM_RDY, 0x0);
+ }
+#undef RTW8852C_TSSI_GET_VAL
+}
+
+static void _tssi_slope_cal_org(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ enum rtw89_band band = rtwdev->hal.current_band_type;
+
+ if (path == RF_PATH_A) {
+ rtw89_rfk_parser_by_cond(rtwdev, band == RTW89_BAND_2G,
+ &rtw8852c_tssi_slope_cal_org_defs_2g_a_tbl,
+ &rtw8852c_tssi_slope_cal_org_defs_5g_a_tbl);
+ } else {
+ rtw89_rfk_parser_by_cond(rtwdev, band == RTW89_BAND_2G,
+ &rtw8852c_tssi_slope_cal_org_defs_2g_b_tbl,
+ &rtw8852c_tssi_slope_cal_org_defs_5g_b_tbl);
+ }
+}
+
+static void _tssi_set_aligk_default(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ enum rtw89_band band = rtwdev->hal.current_band_type;
+ const struct rtw89_rfk_tbl *tbl;
+
+ if (path == RF_PATH_A) {
+ if (band == RTW89_BAND_2G)
+ tbl = &rtw8852c_tssi_set_aligk_default_defs_2g_a_tbl;
+ else if (band == RTW89_BAND_6G)
+ tbl = &rtw8852c_tssi_set_aligk_default_defs_6g_a_tbl;
+ else
+ tbl = &rtw8852c_tssi_set_aligk_default_defs_5g_a_tbl;
+ } else {
+ if (band == RTW89_BAND_2G)
+ tbl = &rtw8852c_tssi_set_aligk_default_defs_2g_b_tbl;
+ else if (band == RTW89_BAND_6G)
+ tbl = &rtw8852c_tssi_set_aligk_default_defs_6g_b_tbl;
+ else
+ tbl = &rtw8852c_tssi_set_aligk_default_defs_5g_b_tbl;
+ }
+
+ rtw89_rfk_parser(rtwdev, tbl);
+}
+
+static void _tssi_set_slope(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_tssi_slope_defs_a_tbl,
+ &rtw8852c_tssi_slope_defs_b_tbl);
+}
+
+static void _tssi_run_slope(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_tssi_run_slope_defs_a_tbl,
+ &rtw8852c_tssi_run_slope_defs_b_tbl);
+}
+
+static void _tssi_set_track(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_tssi_track_defs_a_tbl,
+ &rtw8852c_tssi_track_defs_b_tbl);
+}
+
+static void _tssi_set_txagc_offset_mv_avg(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ rtw89_rfk_parser_by_cond(rtwdev, path == RF_PATH_A,
+ &rtw8852c_tssi_txagc_ofst_mv_avg_defs_a_tbl,
+ &rtw8852c_tssi_txagc_ofst_mv_avg_defs_b_tbl);
+}
+
+static void _tssi_enable(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
+{
+ struct rtw89_tssi_info *tssi_info = &rtwdev->tssi;
+ u32 i, path = RF_PATH_A, path_max = RF_PATH_NUM_8852C;
+
+ if (rtwdev->dbcc_en) {
+ if (phy == RTW89_PHY_0) {
+ path = RF_PATH_A;
+ path_max = RF_PATH_B;
+ } else if (phy == RTW89_PHY_1) {
+ path = RF_PATH_B;
+ path_max = RF_PATH_NUM_8852C;
+ }
+ }
+
+ for (i = path; i < path_max; i++) {
+ _tssi_set_track(rtwdev, phy, i);
+ _tssi_set_txagc_offset_mv_avg(rtwdev, phy, i);
+
+ rtw89_rfk_parser_by_cond(rtwdev, i == RF_PATH_A,
+ &rtw8852c_tssi_enable_defs_a_tbl,
+ &rtw8852c_tssi_enable_defs_b_tbl);
+
+ tssi_info->base_thermal[i] =
+ ewma_thermal_read(&rtwdev->phystat.avg_thermal[i]);
+ rtwdev->is_tssi_mode[i] = true;
+ }
+}
+
+static void _tssi_disable(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
+{
+ u32 i, path = RF_PATH_A, path_max = RF_PATH_NUM_8852C;
+
+ if (rtwdev->dbcc_en) {
+ if (phy == RTW89_PHY_0) {
+ path = RF_PATH_A;
+ path_max = RF_PATH_B;
+ } else if (phy == RTW89_PHY_1) {
+ path = RF_PATH_B;
+ path_max = RF_PATH_NUM_8852C;
+ }
+ }
+
+ for (i = path; i < path_max; i++) {
+ if (i == RF_PATH_A) {
+ rtw89_rfk_parser(rtwdev, &rtw8852c_tssi_disable_defs_a_tbl);
+ rtwdev->is_tssi_mode[RF_PATH_A] = false;
+ } else if (i == RF_PATH_B) {
+ rtw89_rfk_parser(rtwdev, &rtw8852c_tssi_disable_defs_b_tbl);
+ rtwdev->is_tssi_mode[RF_PATH_B] = false;
+ }
+ }
+}
+
+static u32 _tssi_get_cck_group(struct rtw89_dev *rtwdev, u8 ch)
+{
+ switch (ch) {
+ case 1 ... 2:
+ return 0;
+ case 3 ... 5:
+ return 1;
+ case 6 ... 8:
+ return 2;
+ case 9 ... 11:
+ return 3;
+ case 12 ... 13:
+ return 4;
+ case 14:
+ return 5;
+ }
+
+ return 0;
+}
+
+#define TSSI_EXTRA_GROUP_BIT (BIT(31))
+#define TSSI_EXTRA_GROUP(idx) (TSSI_EXTRA_GROUP_BIT | (idx))
+#define IS_TSSI_EXTRA_GROUP(group) ((group) & TSSI_EXTRA_GROUP_BIT)
+#define TSSI_EXTRA_GET_GROUP_IDX1(group) ((group) & ~TSSI_EXTRA_GROUP_BIT)
+#define TSSI_EXTRA_GET_GROUP_IDX2(group) (TSSI_EXTRA_GET_GROUP_IDX1(group) + 1)
+
+static u32 _tssi_get_ofdm_group(struct rtw89_dev *rtwdev, u8 ch)
+{
+ switch (ch) {
+ case 1 ... 2:
+ return 0;
+ case 3 ... 5:
+ return 1;
+ case 6 ... 8:
+ return 2;
+ case 9 ... 11:
+ return 3;
+ case 12 ... 14:
+ return 4;
+ case 36 ... 40:
+ return 5;
+ case 41 ... 43:
+ return TSSI_EXTRA_GROUP(5);
+ case 44 ... 48:
+ return 6;
+ case 49 ... 51:
+ return TSSI_EXTRA_GROUP(6);
+ case 52 ... 56:
+ return 7;
+ case 57 ... 59:
+ return TSSI_EXTRA_GROUP(7);
+ case 60 ... 64:
+ return 8;
+ case 100 ... 104:
+ return 9;
+ case 105 ... 107:
+ return TSSI_EXTRA_GROUP(9);
+ case 108 ... 112:
+ return 10;
+ case 113 ... 115:
+ return TSSI_EXTRA_GROUP(10);
+ case 116 ... 120:
+ return 11;
+ case 121 ... 123:
+ return TSSI_EXTRA_GROUP(11);
+ case 124 ... 128:
+ return 12;
+ case 129 ... 131:
+ return TSSI_EXTRA_GROUP(12);
+ case 132 ... 136:
+ return 13;
+ case 137 ... 139:
+ return TSSI_EXTRA_GROUP(13);
+ case 140 ... 144:
+ return 14;
+ case 149 ... 153:
+ return 15;
+ case 154 ... 156:
+ return TSSI_EXTRA_GROUP(15);
+ case 157 ... 161:
+ return 16;
+ case 162 ... 164:
+ return TSSI_EXTRA_GROUP(16);
+ case 165 ... 169:
+ return 17;
+ case 170 ... 172:
+ return TSSI_EXTRA_GROUP(17);
+ case 173 ... 177:
+ return 18;
+ }
+
+ return 0;
+}
+
+static u32 _tssi_get_6g_ofdm_group(struct rtw89_dev *rtwdev, u8 ch)
+{
+ switch (ch) {
+ case 1 ... 5:
+ return 0;
+ case 6 ... 8:
+ return TSSI_EXTRA_GROUP(0);
+ case 9 ... 13:
+ return 1;
+ case 14 ... 16:
+ return TSSI_EXTRA_GROUP(1);
+ case 17 ... 21:
+ return 2;
+ case 22 ... 24:
+ return TSSI_EXTRA_GROUP(2);
+ case 25 ... 29:
+ return 3;
+ case 33 ... 37:
+ return 4;
+ case 38 ... 40:
+ return TSSI_EXTRA_GROUP(4);
+ case 41 ... 45:
+ return 5;
+ case 46 ... 48:
+ return TSSI_EXTRA_GROUP(5);
+ case 49 ... 53:
+ return 6;
+ case 54 ... 56:
+ return TSSI_EXTRA_GROUP(6);
+ case 57 ... 61:
+ return 7;
+ case 65 ... 69:
+ return 8;
+ case 70 ... 72:
+ return TSSI_EXTRA_GROUP(8);
+ case 73 ... 77:
+ return 9;
+ case 78 ... 80:
+ return TSSI_EXTRA_GROUP(9);
+ case 81 ... 85:
+ return 10;
+ case 86 ... 88:
+ return TSSI_EXTRA_GROUP(10);
+ case 89 ... 93:
+ return 11;
+ case 97 ... 101:
+ return 12;
+ case 102 ... 104:
+ return TSSI_EXTRA_GROUP(12);
+ case 105 ... 109:
+ return 13;
+ case 110 ... 112:
+ return TSSI_EXTRA_GROUP(13);
+ case 113 ... 117:
+ return 14;
+ case 118 ... 120:
+ return TSSI_EXTRA_GROUP(14);
+ case 121 ... 125:
+ return 15;
+ case 129 ... 133:
+ return 16;
+ case 134 ... 136:
+ return TSSI_EXTRA_GROUP(16);
+ case 137 ... 141:
+ return 17;
+ case 142 ... 144:
+ return TSSI_EXTRA_GROUP(17);
+ case 145 ... 149:
+ return 18;
+ case 150 ... 152:
+ return TSSI_EXTRA_GROUP(18);
+ case 153 ... 157:
+ return 19;
+ case 161 ... 165:
+ return 20;
+ case 166 ... 168:
+ return TSSI_EXTRA_GROUP(20);
+ case 169 ... 173:
+ return 21;
+ case 174 ... 176:
+ return TSSI_EXTRA_GROUP(21);
+ case 177 ... 181:
+ return 22;
+ case 182 ... 184:
+ return TSSI_EXTRA_GROUP(22);
+ case 185 ... 189:
+ return 23;
+ case 193 ... 197:
+ return 24;
+ case 198 ... 200:
+ return TSSI_EXTRA_GROUP(24);
+ case 201 ... 205:
+ return 25;
+ case 206 ... 208:
+ return TSSI_EXTRA_GROUP(25);
+ case 209 ... 213:
+ return 26;
+ case 214 ... 216:
+ return TSSI_EXTRA_GROUP(26);
+ case 217 ... 221:
+ return 27;
+ case 225 ... 229:
+ return 28;
+ case 230 ... 232:
+ return TSSI_EXTRA_GROUP(28);
+ case 233 ... 237:
+ return 29;
+ case 238 ... 240:
+ return TSSI_EXTRA_GROUP(29);
+ case 241 ... 245:
+ return 30;
+ case 246 ... 248:
+ return TSSI_EXTRA_GROUP(30);
+ case 249 ... 253:
+ return 31;
+ }
+
+ return 0;
+}
+
+static u32 _tssi_get_trim_group(struct rtw89_dev *rtwdev, u8 ch)
+{
+ switch (ch) {
+ case 1 ... 8:
+ return 0;
+ case 9 ... 14:
+ return 1;
+ case 36 ... 48:
+ return 2;
+ case 49 ... 51:
+ return TSSI_EXTRA_GROUP(2);
+ case 52 ... 64:
+ return 3;
+ case 100 ... 112:
+ return 4;
+ case 113 ... 115:
+ return TSSI_EXTRA_GROUP(4);
+ case 116 ... 128:
+ return 5;
+ case 132 ... 144:
+ return 6;
+ case 149 ... 177:
+ return 7;
+ }
+
+ return 0;
+}
+
+static u32 _tssi_get_6g_trim_group(struct rtw89_dev *rtwdev, u8 ch)
+{
+ switch (ch) {
+ case 1 ... 13:
+ return 0;
+ case 14 ... 16:
+ return TSSI_EXTRA_GROUP(0);
+ case 17 ... 29:
+ return 1;
+ case 33 ... 45:
+ return 2;
+ case 46 ... 48:
+ return TSSI_EXTRA_GROUP(2);
+ case 49 ... 61:
+ return 3;
+ case 65 ... 77:
+ return 4;
+ case 78 ... 80:
+ return TSSI_EXTRA_GROUP(4);
+ case 81 ... 93:
+ return 5;
+ case 97 ... 109:
+ return 6;
+ case 110 ... 112:
+ return TSSI_EXTRA_GROUP(6);
+ case 113 ... 125:
+ return 7;
+ case 129 ... 141:
+ return 8;
+ case 142 ... 144:
+ return TSSI_EXTRA_GROUP(8);
+ case 145 ... 157:
+ return 9;
+ case 161 ... 173:
+ return 10;
+ case 174 ... 176:
+ return TSSI_EXTRA_GROUP(10);
+ case 177 ... 189:
+ return 11;
+ case 193 ... 205:
+ return 12;
+ case 206 ... 208:
+ return TSSI_EXTRA_GROUP(12);
+ case 209 ... 221:
+ return 13;
+ case 225 ... 237:
+ return 14;
+ case 238 ... 240:
+ return TSSI_EXTRA_GROUP(14);
+ case 241 ... 253:
+ return 15;
+ }
+
+ return 0;
+}
+
+static s8 _tssi_get_ofdm_de(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ struct rtw89_tssi_info *tssi_info = &rtwdev->tssi;
+ enum rtw89_band band = rtwdev->hal.current_band_type;
+ u8 ch = rtwdev->hal.current_channel;
+ u32 gidx, gidx_1st, gidx_2nd;
+ s8 de_1st;
+ s8 de_2nd;
+ s8 val;
+
+ if (band == RTW89_BAND_2G || band == RTW89_BAND_5G) {
+ gidx = _tssi_get_ofdm_group(rtwdev, ch);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs group_idx=0x%x\n",
+ path, gidx);
+
+ if (IS_TSSI_EXTRA_GROUP(gidx)) {
+ gidx_1st = TSSI_EXTRA_GET_GROUP_IDX1(gidx);
+ gidx_2nd = TSSI_EXTRA_GET_GROUP_IDX2(gidx);
+ de_1st = tssi_info->tssi_mcs[path][gidx_1st];
+ de_2nd = tssi_info->tssi_mcs[path][gidx_2nd];
+ val = (de_1st + de_2nd) / 2;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs de=%d 1st=%d 2nd=%d\n",
+ path, val, de_1st, de_2nd);
+ } else {
+ val = tssi_info->tssi_mcs[path][gidx];
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs de=%d\n", path, val);
+ }
+ } else {
+ gidx = _tssi_get_6g_ofdm_group(rtwdev, ch);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs group_idx=0x%x\n",
+ path, gidx);
+
+ if (IS_TSSI_EXTRA_GROUP(gidx)) {
+ gidx_1st = TSSI_EXTRA_GET_GROUP_IDX1(gidx);
+ gidx_2nd = TSSI_EXTRA_GET_GROUP_IDX2(gidx);
+ de_1st = tssi_info->tssi_6g_mcs[path][gidx_1st];
+ de_2nd = tssi_info->tssi_6g_mcs[path][gidx_2nd];
+ val = (de_1st + de_2nd) / 2;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs de=%d 1st=%d 2nd=%d\n",
+ path, val, de_1st, de_2nd);
+ } else {
+ val = tssi_info->tssi_6g_mcs[path][gidx];
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs de=%d\n", path, val);
+ }
+ }
+
+ return val;
+}
+
+static s8 _tssi_get_ofdm_trim_de(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy,
+ enum rtw89_rf_path path)
+{
+ struct rtw89_tssi_info *tssi_info = &rtwdev->tssi;
+ enum rtw89_band band = rtwdev->hal.current_band_type;
+ u8 ch = rtwdev->hal.current_channel;
+ u32 tgidx, tgidx_1st, tgidx_2nd;
+ s8 tde_1st = 0;
+ s8 tde_2nd = 0;
+ s8 val;
+
+ if (band == RTW89_BAND_2G || band == RTW89_BAND_5G) {
+ tgidx = _tssi_get_trim_group(rtwdev, ch);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs trim_group_idx=0x%x\n",
+ path, tgidx);
+
+ if (IS_TSSI_EXTRA_GROUP(tgidx)) {
+ tgidx_1st = TSSI_EXTRA_GET_GROUP_IDX1(tgidx);
+ tgidx_2nd = TSSI_EXTRA_GET_GROUP_IDX2(tgidx);
+ tde_1st = tssi_info->tssi_trim[path][tgidx_1st];
+ tde_2nd = tssi_info->tssi_trim[path][tgidx_2nd];
+ val = (tde_1st + tde_2nd) / 2;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs trim_de=%d 1st=%d 2nd=%d\n",
+ path, val, tde_1st, tde_2nd);
+ } else {
+ val = tssi_info->tssi_trim[path][tgidx];
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs trim_de=%d\n",
+ path, val);
+ }
+ } else {
+ tgidx = _tssi_get_6g_trim_group(rtwdev, ch);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs trim_group_idx=0x%x\n",
+ path, tgidx);
+
+ if (IS_TSSI_EXTRA_GROUP(tgidx)) {
+ tgidx_1st = TSSI_EXTRA_GET_GROUP_IDX1(tgidx);
+ tgidx_2nd = TSSI_EXTRA_GET_GROUP_IDX2(tgidx);
+ tde_1st = tssi_info->tssi_trim_6g[path][tgidx_1st];
+ tde_2nd = tssi_info->tssi_trim_6g[path][tgidx_2nd];
+ val = (tde_1st + tde_2nd) / 2;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs trim_de=%d 1st=%d 2nd=%d\n",
+ path, val, tde_1st, tde_2nd);
+ } else {
+ val = tssi_info->tssi_trim_6g[path][tgidx];
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs trim_de=%d\n",
+ path, val);
+ }
+ }
+
+ return val;
+}
+
+static void _tssi_set_efuse_to_de(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy)
+{
+ struct rtw89_tssi_info *tssi_info = &rtwdev->tssi;
+ u8 ch = rtwdev->hal.current_channel;
+ u8 gidx;
+ s8 ofdm_de;
+ s8 trim_de;
+ s32 val;
+ u32 i, path = RF_PATH_A, path_max = RF_PATH_NUM_8852C;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI, "[TSSI][TRIM]: phy=%d ch=%d\n",
+ phy, ch);
+
+ if (rtwdev->dbcc_en) {
+ if (phy == RTW89_PHY_0) {
+ path = RF_PATH_A;
+ path_max = RF_PATH_B;
+ } else if (phy == RTW89_PHY_1) {
+ path = RF_PATH_B;
+ path_max = RF_PATH_NUM_8852C;
+ }
+ }
+
+ for (i = path; i < path_max; i++) {
+ gidx = _tssi_get_cck_group(rtwdev, ch);
+ trim_de = _tssi_get_ofdm_trim_de(rtwdev, phy, i);
+ val = tssi_info->tssi_cck[i][gidx] + trim_de;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d cck[%d]=0x%x trim=0x%x\n",
+ i, gidx, tssi_info->tssi_cck[i][gidx], trim_de);
+
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_cck_long[i], _TSSI_DE_MASK, val);
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_cck_short[i], _TSSI_DE_MASK, val);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] Set TSSI CCK DE 0x%x[21:12]=0x%x\n",
+ _tssi_de_cck_long[i],
+ rtw89_phy_read32_mask(rtwdev, _tssi_de_cck_long[i],
+ _TSSI_DE_MASK));
+
+ ofdm_de = _tssi_get_ofdm_de(rtwdev, phy, i);
+ trim_de = _tssi_get_ofdm_trim_de(rtwdev, phy, i);
+ val = ofdm_de + trim_de;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI][TRIM]: path=%d mcs=0x%x trim=0x%x\n",
+ i, ofdm_de, trim_de);
+
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_mcs_20m[i], _TSSI_DE_MASK, val);
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_mcs_40m[i], _TSSI_DE_MASK, val);
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_mcs_80m[i], _TSSI_DE_MASK, val);
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_mcs_80m_80m[i], _TSSI_DE_MASK, val);
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_mcs_5m[i], _TSSI_DE_MASK, val);
+ rtw89_phy_write32_mask(rtwdev, _tssi_de_mcs_10m[i], _TSSI_DE_MASK, val);
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI,
+ "[TSSI] Set TSSI MCS DE 0x%x[21:12]=0x%x\n",
+ _tssi_de_mcs_20m[i],
+ rtw89_phy_read32_mask(rtwdev, _tssi_de_mcs_20m[i],
+ _TSSI_DE_MASK));
+ }
+}
+
+static void rtw8852c_tssi_cont_en(struct rtw89_dev *rtwdev, bool en,
+ enum rtw89_rf_path path)
+{
+ static const u32 tssi_trk[2] = {0x5818, 0x7818};
+ static const u32 tssi_en[2] = {0x5820, 0x7820};
+
+ if (en) {
+ rtw89_phy_write32_mask(rtwdev, tssi_trk[path], BIT(30), 0x0);
+ rtw89_phy_write32_mask(rtwdev, tssi_en[path], BIT(31), 0x0);
+ if (rtwdev->dbcc_en && path == RF_PATH_B)
+ _tssi_set_efuse_to_de(rtwdev, RTW89_PHY_1);
+ else
+ _tssi_set_efuse_to_de(rtwdev, RTW89_PHY_0);
+ } else {
+ rtw89_phy_write32_mask(rtwdev, tssi_trk[path], BIT(30), 0x1);
+ rtw89_phy_write32_mask(rtwdev, tssi_en[path], BIT(31), 0x1);
+ }
+}
+
+void rtw8852c_tssi_cont_en_phyidx(struct rtw89_dev *rtwdev, bool en, u8 phy_idx)
+{
+ if (!rtwdev->dbcc_en) {
+ rtw8852c_tssi_cont_en(rtwdev, en, RF_PATH_A);
+ rtw8852c_tssi_cont_en(rtwdev, en, RF_PATH_B);
+ } else {
+ if (phy_idx == RTW89_PHY_0)
+ rtw8852c_tssi_cont_en(rtwdev, en, RF_PATH_A);
+ else
+ rtw8852c_tssi_cont_en(rtwdev, en, RF_PATH_B);
+ }
+}
+
static void _bw_setting(struct rtw89_dev *rtwdev, enum rtw89_rf_path path,
enum rtw89_bandwidth bw, bool is_dav)
{
@@ -721,3 +1627,130 @@ void rtw8852c_dack(struct rtw89_dev *rtwdev)
_dac_cal(rtwdev, false);
rtw89_btc_ntfy_wl_rfk(rtwdev, phy_map, BTC_WRFKT_DACK, BTC_WRFK_STOP);
}
+
+void rtw8852c_tssi(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
+{
+ u32 i, path = RF_PATH_A, path_max = RF_PATH_NUM_8852C;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI, "[TSSI] %s: phy=%d\n", __func__, phy);
+
+ if (rtwdev->dbcc_en) {
+ if (phy == RTW89_PHY_0) {
+ path = RF_PATH_A;
+ path_max = RF_PATH_B;
+ } else if (phy == RTW89_PHY_1) {
+ path = RF_PATH_B;
+ path_max = RF_PATH_NUM_8852C;
+ }
+ }
+
+ _tssi_disable(rtwdev, phy);
+
+ for (i = path; i < path_max; i++) {
+ _tssi_set_sys(rtwdev, phy, i);
+ _tssi_ini_txpwr_ctrl_bb(rtwdev, phy, i);
+ _tssi_ini_txpwr_ctrl_bb_he_tb(rtwdev, phy, i);
+ _tssi_set_dck(rtwdev, phy, i);
+ _tssi_set_bbgain_split(rtwdev, phy, i);
+ _tssi_set_tmeter_tbl(rtwdev, phy, i);
+ _tssi_slope_cal_org(rtwdev, phy, i);
+ _tssi_set_aligk_default(rtwdev, phy, i);
+ _tssi_set_slope(rtwdev, phy, i);
+ _tssi_run_slope(rtwdev, phy, i);
+ }
+
+ _tssi_enable(rtwdev, phy);
+ _tssi_set_efuse_to_de(rtwdev, phy);
+}
+
+void rtw8852c_tssi_scan(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy)
+{
+ u32 i, path = RF_PATH_A, path_max = RF_PATH_NUM_8852C;
+
+ rtw89_debug(rtwdev, RTW89_DBG_TSSI, "[TSSI] %s: phy=%d\n",
+ __func__, phy);
+
+ if (!rtwdev->is_tssi_mode[RF_PATH_A])
+ return;
+ if (!rtwdev->is_tssi_mode[RF_PATH_B])
+ return;
+
+ if (rtwdev->dbcc_en) {
+ if (phy == RTW89_PHY_0) {
+ path = RF_PATH_A;
+ path_max = RF_PATH_B;
+ } else if (phy == RTW89_PHY_1) {
+ path = RF_PATH_B;
+ path_max = RF_PATH_NUM_8852C;
+ }
+ }
+
+ _tssi_disable(rtwdev, phy);
+
+ for (i = path; i < path_max; i++) {
+ _tssi_set_sys(rtwdev, phy, i);
+ _tssi_set_dck(rtwdev, phy, i);
+ _tssi_set_tmeter_tbl(rtwdev, phy, i);
+ _tssi_slope_cal_org(rtwdev, phy, i);
+ _tssi_set_aligk_default(rtwdev, phy, i);
+ }
+
+ _tssi_enable(rtwdev, phy);
+ _tssi_set_efuse_to_de(rtwdev, phy);
+}
+
+static void rtw8852c_tssi_default_txagc(struct rtw89_dev *rtwdev,
+ enum rtw89_phy_idx phy, bool enable)
+{
+ struct rtw89_tssi_info *tssi_info = &rtwdev->tssi;
+ u8 i;
+
+ if (!rtwdev->is_tssi_mode[RF_PATH_A] && !rtwdev->is_tssi_mode[RF_PATH_B])
+ return;
+
+ if (enable) {
+ /* SCAN_START */
+ if (rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB, B_TXAGC_BB_OFT) != 0xc000 &&
+ rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB, B_TXAGC_BB_OFT) != 0x0) {
+ for (i = 0; i < 6; i++) {
+ tssi_info->default_txagc_offset[RF_PATH_A] =
+ rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB,
+ B_TXAGC_BB);
+ if (tssi_info->default_txagc_offset[RF_PATH_A])
+ break;
+ }
+ }
+
+ if (rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB_S1, B_TXAGC_BB_S1_OFT) != 0xc000 &&
+ rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB_S1, B_TXAGC_BB_S1_OFT) != 0x0) {
+ for (i = 0; i < 6; i++) {
+ tssi_info->default_txagc_offset[RF_PATH_B] =
+ rtw89_phy_read32_mask(rtwdev, R_TXAGC_BB_S1,
+ B_TXAGC_BB_S1);
+ if (tssi_info->default_txagc_offset[RF_PATH_B])
+ break;
+ }
+ }
+ } else {
+ /* SCAN_END */
+ rtw89_phy_write32_mask(rtwdev, R_P0_TSSI_TRK, B_P0_TSSI_OFT,
+ tssi_info->default_txagc_offset[RF_PATH_A]);
+ rtw89_phy_write32_mask(rtwdev, R_P1_TSSI_TRK, B_P1_TSSI_OFT,
+ tssi_info->default_txagc_offset[RF_PATH_B]);
+
+ rtw89_phy_write32_mask(rtwdev, R_P0_TSSI_TRK, B_P0_TSSI_OFT_EN, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_P0_TSSI_TRK, B_P0_TSSI_OFT_EN, 0x1);
+
+ rtw89_phy_write32_mask(rtwdev, R_P1_TSSI_TRK, B_P1_TSSI_OFT_EN, 0x0);
+ rtw89_phy_write32_mask(rtwdev, R_P1_TSSI_TRK, B_P1_TSSI_OFT_EN, 0x1);
+ }
+}
+
+void rtw8852c_wifi_scan_notify(struct rtw89_dev *rtwdev,
+ bool scan_start, enum rtw89_phy_idx phy_idx)
+{
+ if (scan_start)
+ rtw8852c_tssi_default_txagc(rtwdev, phy_idx, true);
+ else
+ rtw8852c_tssi_default_txagc(rtwdev, phy_idx, false);
+}
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
index 4ce76ef4c5e60..a16ad9305ba42 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c_rfk.h
@@ -8,6 +8,11 @@
#include "core.h"

void rtw8852c_dack(struct rtw89_dev *rtwdev);
+void rtw8852c_tssi(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
+void rtw8852c_tssi_scan(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy);
+void rtw8852c_tssi_cont_en_phyidx(struct rtw89_dev *rtwdev, bool en, u8 phy_idx);
+void rtw8852c_wifi_scan_notify(struct rtw89_dev *rtwdev, bool scan_start,
+ enum rtw89_phy_idx phy_idx);
void rtw8852c_set_channel_rf(struct rtw89_dev *rtwdev,
struct rtw89_channel_params *param,
enum rtw89_phy_idx phy_idx);
--
2.25.1

2022-05-03 05:32:33

by Kalle Valo

[permalink] [raw]
Subject: Re: [PATCH v3 1/8] rtw89: 8852c: rfk: add RFK tables

Ping-Ke Shih <[email protected]> wrote:

> These tables are used by RFK (RF calibration) to set parameters. These
> parameters can trigger certain calibration, or configure/reset settings
> before and after RF calibrations.
>
> Signed-off-by: Ping-Ke Shih <[email protected]>

8 patches applied to wireless-next.git, thanks.

ec424639d41b rtw89: 8852c: rfk: add RFK tables
76599a8d0b7d rtw89: 8852c: rfk: add DACK
fb8177d729f2 rtw89: 8852c: rfk: add LCK
e5efc4d55c20 rtw89: 8852c: rfk: add TSSI
30052c5a1c99 rtw89: 8852c: rfk: add RCK
ac91be975616 rtw89: 8852c: rfk: add RX DCK
2da8109d9885 rtw89: 8852c: rfk: add IQK
da4cea16cb13 rtw89: 8852c: rfk: add DPK

--
https://patchwork.kernel.org/project/linux-wireless/patch/[email protected]/

https://wireless.wiki.kernel.org/en/developers/documentation/submittingpatches