wifi: rtw89: 8922a: add set_channel RF part

Configure RF registers according to band, channel, bandwidth. Since this
chip will support MLO, it needs check the operating mode to decide paths
we are going to configure.

Signed-off-by: Ping-Ke Shih <pkshih@realtek.com>
Signed-off-by: Kalle Valo <kvalo@kernel.org>
Link: https://msgid.link/20240215055741.14148-4-pkshih@realtek.com
This commit is contained in:
Ping-Ke Shih 2024-02-15 13:57:40 +08:00 committed by Kalle Valo
parent f59cb1a030
commit 2c681cbf6c
6 changed files with 208 additions and 0 deletions

View File

@ -6378,6 +6378,78 @@ void rtw89_phy_edcca_track(struct rtw89_dev *rtwdev)
rtw89_phy_edcca_log(rtwdev);
}
enum rtw89_rf_path_bit rtw89_phy_get_kpath(struct rtw89_dev *rtwdev,
enum rtw89_phy_idx phy_idx)
{
rtw89_debug(rtwdev, RTW89_DBG_RFK,
"[RFK] kpath dbcc_en: 0x%x, mode=0x%x, PHY%d\n",
rtwdev->dbcc_en, rtwdev->mlo_dbcc_mode, phy_idx);
switch (rtwdev->mlo_dbcc_mode) {
case MLO_1_PLUS_1_1RF:
if (phy_idx == RTW89_PHY_0)
return RF_A;
else
return RF_B;
case MLO_1_PLUS_1_2RF:
if (phy_idx == RTW89_PHY_0)
return RF_A;
else
return RF_D;
case MLO_0_PLUS_2_1RF:
case MLO_2_PLUS_0_1RF:
if (phy_idx == RTW89_PHY_0)
return RF_AB;
else
return RF_AB;
case MLO_0_PLUS_2_2RF:
case MLO_2_PLUS_0_2RF:
case MLO_2_PLUS_2_2RF:
default:
if (phy_idx == RTW89_PHY_0)
return RF_AB;
else
return RF_CD;
}
}
EXPORT_SYMBOL(rtw89_phy_get_kpath);
enum rtw89_rf_path rtw89_phy_get_syn_sel(struct rtw89_dev *rtwdev,
enum rtw89_phy_idx phy_idx)
{
rtw89_debug(rtwdev, RTW89_DBG_RFK,
"[RFK] kpath dbcc_en: 0x%x, mode=0x%x, PHY%d\n",
rtwdev->dbcc_en, rtwdev->mlo_dbcc_mode, phy_idx);
switch (rtwdev->mlo_dbcc_mode) {
case MLO_1_PLUS_1_1RF:
if (phy_idx == RTW89_PHY_0)
return RF_PATH_A;
else
return RF_PATH_B;
case MLO_1_PLUS_1_2RF:
if (phy_idx == RTW89_PHY_0)
return RF_PATH_A;
else
return RF_PATH_D;
case MLO_0_PLUS_2_1RF:
case MLO_2_PLUS_0_1RF:
if (phy_idx == RTW89_PHY_0)
return RF_PATH_A;
else
return RF_PATH_B;
case MLO_0_PLUS_2_2RF:
case MLO_2_PLUS_0_2RF:
case MLO_2_PLUS_2_2RF:
default:
if (phy_idx == RTW89_PHY_0)
return RF_PATH_A;
else
return RF_PATH_C;
}
}
EXPORT_SYMBOL(rtw89_phy_get_syn_sel);
static const struct rtw89_ccx_regs rtw89_ccx_regs_ax = {
.setting_addr = R_CCX,
.edcca_opt_mask = B_CCX_EDCCA_OPT_MSK,

View File

@ -945,5 +945,9 @@ void rtw89_decode_chan_idx(struct rtw89_dev *rtwdev, u8 chan_idx,
void rtw89_phy_config_edcca(struct rtw89_dev *rtwdev, bool scan);
void rtw89_phy_edcca_track(struct rtw89_dev *rtwdev);
void rtw89_phy_edcca_thre_calc(struct rtw89_dev *rtwdev);
enum rtw89_rf_path_bit rtw89_phy_get_kpath(struct rtw89_dev *rtwdev,
enum rtw89_phy_idx phy_idx);
enum rtw89_rf_path rtw89_phy_get_syn_sel(struct rtw89_dev *rtwdev,
enum rtw89_phy_idx phy_idx);
#endif

View File

@ -7497,6 +7497,12 @@
#define CFGCH_BAND0_2G 0
#define CFGCH_BAND0_5G 1
#define CFGCH_BAND0_6G 0
#define RR_CFGCH_BW_V2 GENMASK(12, 10)
#define CFGCH_BW_V2_20M 0
#define CFGCH_BW_V2_40M 1
#define CFGCH_BW_V2_80M 2
#define CFGCH_BW_V2_160M 3
#define CFGCH_BW_V2_320M 4
#define RR_CFGCH_BW GENMASK(11, 10)
#define RR_CFGCH_CH GENMASK(7, 0)
#define CFGCH_BW_20M 3
@ -7683,6 +7689,8 @@
#define RR_MMD 0xd5
#define RR_MMD_RST_EN BIT(8)
#define RR_MMD_RST_SYN BIT(6)
#define RR_SMD 0xd6
#define RR_VCO2 BIT(19)
#define RR_IQKPLL 0xdc
#define RR_IQKPLL_MOD GENMASK(9, 8)
#define RR_SYNLUT 0xdd

View File

@ -1781,6 +1781,7 @@ static void rtw8922a_set_channel(struct rtw89_dev *rtwdev,
{
rtw8922a_set_channel_mac(rtwdev, chan, mac_idx);
rtw8922a_set_channel_bb(rtwdev, chan, phy_idx);
rtw8922a_set_channel_rf(rtwdev, chan, phy_idx);
}
static void rtw8922a_dfs_en_idx(struct rtw89_dev *rtwdev,

View File

@ -34,6 +34,126 @@ void rtw8922a_tssi_cont_en_phyidx(struct rtw89_dev *rtwdev, bool en, u8 phy_idx)
}
}
static
void rtw8922a_ctl_band_ch_bw(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy,
u8 central_ch, enum rtw89_band band,
enum rtw89_bandwidth bw)
{
const u32 rf_addr[2] = {RR_CFGCH, RR_CFGCH_V1};
struct rtw89_hal *hal = &rtwdev->hal;
u32 rf_reg[RF_PATH_NUM_8922A][2];
u8 synpath;
u32 rf18;
u8 kpath;
u8 path;
u8 i;
rf_reg[RF_PATH_A][0] = rtw89_read_rf(rtwdev, RF_PATH_A, rf_addr[0], RFREG_MASK);
rf_reg[RF_PATH_A][1] = rtw89_read_rf(rtwdev, RF_PATH_A, rf_addr[1], RFREG_MASK);
rf_reg[RF_PATH_B][0] = rtw89_read_rf(rtwdev, RF_PATH_B, rf_addr[0], RFREG_MASK);
rf_reg[RF_PATH_B][1] = rtw89_read_rf(rtwdev, RF_PATH_B, rf_addr[1], RFREG_MASK);
kpath = rtw89_phy_get_kpath(rtwdev, phy);
synpath = rtw89_phy_get_syn_sel(rtwdev, phy);
rf18 = rtw89_read_rf(rtwdev, synpath, RR_CFGCH, RFREG_MASK);
if (rf18 == INV_RF_DATA) {
rtw89_warn(rtwdev, "[RFK] Invalid RF18 value\n");
return;
}
for (path = 0; path < RF_PATH_NUM_8922A; path++) {
if (!(kpath & BIT(path)))
continue;
for (i = 0; i < 2; i++) {
if (rf_reg[path][i] == INV_RF_DATA) {
rtw89_warn(rtwdev,
"[RFK] Invalid RF_0x18 for Path-%d\n", path);
return;
}
rf_reg[path][i] &= ~(RR_CFGCH_BAND1 | RR_CFGCH_BW |
RR_CFGCH_BAND0 | RR_CFGCH_CH);
rf_reg[path][i] |= u32_encode_bits(central_ch, RR_CFGCH_CH);
if (band == RTW89_BAND_2G)
rtw89_write_rf(rtwdev, path, RR_SMD, RR_VCO2, 0x0);
else
rtw89_write_rf(rtwdev, path, RR_SMD, RR_VCO2, 0x1);
switch (band) {
case RTW89_BAND_2G:
default:
break;
case RTW89_BAND_5G:
rf_reg[path][i] |=
u32_encode_bits(CFGCH_BAND1_5G, RR_CFGCH_BAND1) |
u32_encode_bits(CFGCH_BAND0_5G, RR_CFGCH_BAND0);
break;
case RTW89_BAND_6G:
rf_reg[path][i] |=
u32_encode_bits(CFGCH_BAND1_6G, RR_CFGCH_BAND1) |
u32_encode_bits(CFGCH_BAND0_6G, RR_CFGCH_BAND0);
break;
}
switch (bw) {
case RTW89_CHANNEL_WIDTH_5:
case RTW89_CHANNEL_WIDTH_10:
case RTW89_CHANNEL_WIDTH_20:
default:
break;
case RTW89_CHANNEL_WIDTH_40:
rf_reg[path][i] |=
u32_encode_bits(CFGCH_BW_V2_40M, RR_CFGCH_BW_V2);
break;
case RTW89_CHANNEL_WIDTH_80:
rf_reg[path][i] |=
u32_encode_bits(CFGCH_BW_V2_80M, RR_CFGCH_BW_V2);
break;
case RTW89_CHANNEL_WIDTH_160:
rf_reg[path][i] |=
u32_encode_bits(CFGCH_BW_V2_160M, RR_CFGCH_BW_V2);
break;
case RTW89_CHANNEL_WIDTH_320:
rf_reg[path][i] |=
u32_encode_bits(CFGCH_BW_V2_320M, RR_CFGCH_BW_V2);
break;
}
rtw89_write_rf(rtwdev, path, rf_addr[i],
RFREG_MASK, rf_reg[path][i]);
fsleep(100);
}
}
if (hal->cv != CHIP_CAV)
return;
if (band == RTW89_BAND_2G) {
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWE, RFREG_MASK, 0x80000);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWA, RFREG_MASK, 0x00003);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWD1, RFREG_MASK, 0x0c990);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWD0, RFREG_MASK, 0xebe38);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWE, RFREG_MASK, 0x00000);
} else {
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWE, RFREG_MASK, 0x80000);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWA, RFREG_MASK, 0x00003);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWD1, RFREG_MASK, 0x0c190);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWD0, RFREG_MASK, 0xebe38);
rtw89_write_rf(rtwdev, RF_PATH_A, RR_LUTWE, RFREG_MASK, 0x00000);
}
}
void rtw8922a_set_channel_rf(struct rtw89_dev *rtwdev,
const struct rtw89_chan *chan,
enum rtw89_phy_idx phy_idx)
{
rtw8922a_ctl_band_ch_bw(rtwdev, phy_idx, chan->channel, chan->band_type,
chan->band_width);
}
enum _rf_syn_pow {
RF_SYN_ON_OFF,
RF_SYN_OFF_ON,

View File

@ -8,6 +8,9 @@
#include "core.h"
void rtw8922a_tssi_cont_en_phyidx(struct rtw89_dev *rtwdev, bool en, u8 phy_idx);
void rtw8922a_set_channel_rf(struct rtw89_dev *rtwdev,
const struct rtw89_chan *chan,
enum rtw89_phy_idx phy_idx);
void rtw8922a_rfk_hw_init(struct rtw89_dev *rtwdev);
#endif