From: Ping-Ke Shih <pkshih@realtek.com>
To: <linux-wireless@vger.kernel.org>
Cc: <ku920601@realtek.com>
Subject: [PATCH rtw-next 01/11] wifi: rtw89: coex: Add Wi-Fi role info version 10
Date: Sun, 12 Jul 2026 11:04:56 +0800 [thread overview]
Message-ID: <20260712030506.43438-2-pkshih@realtek.com> (raw)
In-Reply-To: <20260712030506.43438-1-pkshih@realtek.com>
From: Ching-Te Ku <ku920601@realtek.com>
Because the new generation Bluetooth will able to work on 5/6GHz band,
it will suffer 5/6GHz Wi-Fi, the mechanism need to cover more scenario
with different Wi-Fi/Bluetooth combination.
Signed-off-by: Ching-Te Ku <ku920601@realtek.com>
Signed-off-by: Ping-Ke Shih <pkshih@realtek.com>
---
drivers/net/wireless/realtek/rtw89/coex.c | 2445 +++++++----------
drivers/net/wireless/realtek/rtw89/coex.h | 34 +
drivers/net/wireless/realtek/rtw89/core.h | 153 +-
drivers/net/wireless/realtek/rtw89/fw.c | 392 ++-
drivers/net/wireless/realtek/rtw89/fw.h | 48 +-
drivers/net/wireless/realtek/rtw89/rtw8851b.c | 1 +
drivers/net/wireless/realtek/rtw89/rtw8852a.c | 1 +
drivers/net/wireless/realtek/rtw89/rtw8852b.c | 1 +
.../net/wireless/realtek/rtw89/rtw8852bt.c | 1 +
drivers/net/wireless/realtek/rtw89/rtw8852c.c | 1 +
drivers/net/wireless/realtek/rtw89/rtw8922a.c | 1 +
drivers/net/wireless/realtek/rtw89/rtw8922d.c | 1 +
12 files changed, 1391 insertions(+), 1688 deletions(-)
diff --git a/drivers/net/wireless/realtek/rtw89/coex.c b/drivers/net/wireless/realtek/rtw89/coex.c
index 989344e93ab7..c02de0b4f7bf 100644
--- a/drivers/net/wireless/realtek/rtw89/coex.c
+++ b/drivers/net/wireless/realtek/rtw89/coex.c
@@ -436,11 +436,6 @@ union rtw89_fbtc_set_mon_reg {
struct rtw89_btc_btf_set_mon_reg_v7 v7;
} __packed;
-struct _wl_rinfo_now {
- u8 link_mode;
- u32 dbcc_2g_phy: 2;
-};
-
enum btc_btf_set_cx_policy {
CXPOLICY_TDMA = 0x0,
CXPOLICY_SLOT = 0x1,
@@ -570,9 +565,21 @@ enum btc_cx_poicy_type {
/* TDMA off + pri: WL > BT, Block-BT*/
BTC_CXP_OFF_WL2 = (BTC_CXP_OFF << 8) | 12,
- /* TDMA off+Bcn-Protect + pri: WL_Hi-Tx > BT_Hi_Rx, BT_Hi > WL > BT_Lo*/
+ /* TDMA off+Bcn-Protect + pri: BT_Hi > WL > BT_Lo */
BTC_CXP_OFFB_BWB0 = (BTC_CXP_OFFB << 8) | 0,
+ /* TDMA off+Bcn-Protect + pri: BT_Hi_Tx = WL_Hi-Tx > BT_Hi_Rx, BT_Hi > WL > BT_Lo */
+ BTC_CXP_OFFB_BWB1 = (BTC_CXP_OFFB << 8) | 1,
+
+ /* TDMA off+Bcn-Protect + pri: WL_Hi-Tx > BT, BT_Hi > other-WL > BT_Lo */
+ BTC_CXP_OFFB_BWB2 = (BTC_CXP_OFFB << 8) | 2,
+
+ /* TDMA off+Bcn-Protect + pri: WL_Hi-Tx = BT*/
+ BTC_CXP_OFFB_BWB3 = (BTC_CXP_OFFB << 8) | 3,
+
+ /* TDMA off+Bcn-Protect + pri: BT > WL*/
+ BTC_CXP_OFFB_BWB4 = (BTC_CXP_OFFB << 8) | 4,
+
/* TDMA off + Ext-Ctrl + pri: default */
BTC_CXP_OFFE_DEF = (BTC_CXP_OFFE << 8) | 0,
@@ -752,19 +759,31 @@ enum btc_w2b_scoreboard {
BTC_WSCB_ALL = GENMASK(23, 0),
};
-enum btc_wl_link_mode {
+enum btc_wl_link_mode_v0 {
+ BTC_WLINK_V0_NOLINK = 0x0,
+ BTC_WLINK_V0_2G_STA,
+ BTC_WLINK_V0_2G_AP,
+ BTC_WLINK_V0_2G_GO,
+ BTC_WLINK_V0_2G_GC,
+ BTC_WLINK_V0_2G_SCC,
+ BTC_WLINK_V0_2G_MCC,
+ BTC_WLINK_V0_25G_MCC,
+ BTC_WLINK_V0_25G_DBCC,
+ BTC_WLINK_V0_5G,
+ BTC_WLINK_V0_2G_NAN,
+ BTC_WLINK_V0_OTHER,
+ BTC_WLINK_V0_MAX
+};
+
+enum btc_wl_link_mode_v1 {
BTC_WLINK_NOLINK = 0x0,
- BTC_WLINK_2G_STA,
- BTC_WLINK_2G_AP,
- BTC_WLINK_2G_GO,
- BTC_WLINK_2G_GC,
- BTC_WLINK_2G_SCC,
- BTC_WLINK_2G_MCC,
- BTC_WLINK_25G_MCC,
- BTC_WLINK_25G_DBCC,
- BTC_WLINK_5G,
- BTC_WLINK_2G_NAN,
- BTC_WLINK_OTHER,
+ BTC_WLINK_STA,
+ BTC_WLINK_AP,
+ BTC_WLINK_GO,
+ BTC_WLINK_GC,
+ BTC_WLINK_SCC,
+ BTC_WLINK_SB_MCC,
+ BTC_WLINK_DB_MCC, /* 2+0/0+2 Dual-RF-band MCC */
BTC_WLINK_MAX
};
@@ -774,16 +793,13 @@ static const char *id_to_linkmode(u8 id)
{
switch (id) {
CASE_BTC_WL_LINK_MODE(NOLINK);
- CASE_BTC_WL_LINK_MODE(2G_STA);
- CASE_BTC_WL_LINK_MODE(2G_AP);
- CASE_BTC_WL_LINK_MODE(2G_GO);
- CASE_BTC_WL_LINK_MODE(2G_GC);
- CASE_BTC_WL_LINK_MODE(2G_SCC);
- CASE_BTC_WL_LINK_MODE(2G_MCC);
- CASE_BTC_WL_LINK_MODE(25G_MCC);
- CASE_BTC_WL_LINK_MODE(25G_DBCC);
- CASE_BTC_WL_LINK_MODE(5G);
- CASE_BTC_WL_LINK_MODE(OTHER);
+ CASE_BTC_WL_LINK_MODE(STA);
+ CASE_BTC_WL_LINK_MODE(AP);
+ CASE_BTC_WL_LINK_MODE(GO);
+ CASE_BTC_WL_LINK_MODE(GC);
+ CASE_BTC_WL_LINK_MODE(SCC);
+ CASE_BTC_WL_LINK_MODE(SB_MCC);
+ CASE_BTC_WL_LINK_MODE(DB_MCC);
default:
return "unknown";
}
@@ -969,7 +985,7 @@ static void _reset_btc_var(struct rtw89_dev *rtwdev, u8 type)
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
struct rtw89_btc_bt_link_info *bt_linfo = &bt->link_info;
struct rtw89_btc_wl_link_info *wl_linfo;
- u8 i;
+ u8 i, j;
rtw89_debug(rtwdev, RTW89_DBG_BTC, "[BTC], %s\n", __func__);
@@ -990,12 +1006,11 @@ static void _reset_btc_var(struct rtw89_dev *rtwdev, u8 type)
if (type & BTC_RESET_DM) {
memset(&btc->dm, 0, sizeof(btc->dm));
memset(bt_linfo->rssi_state, 0, sizeof(bt_linfo->rssi_state));
- for (i = 0; i < RTW89_PORT_NUM; i++) {
- if (btc->ver->fwlrole == 8)
- wl_linfo = &wl->rlink_info[i][0];
- else
- wl_linfo = &wl->link_info[i];
- memset(wl_linfo->rssi_state, 0, sizeof(wl_linfo->rssi_state));
+ for (j = RTW89_MAC_0; j <= RTW89_MAC_1; j++) {
+ for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) {
+ wl_linfo = &wl->rlink_info[i][j];
+ memset(wl_linfo->rssi_state, 0, sizeof(wl_linfo->rssi_state));
+ }
}
/* set the slot_now table to original */
@@ -2847,6 +2862,8 @@ static void _fw_set_drv_info(struct rtw89_dev *rtwdev, u8 index)
rtw89_fw_h2c_cxdrv_role_v7(rtwdev, index);
else if (ver->fwlrole == 8)
rtw89_fw_h2c_cxdrv_role_v8(rtwdev, index);
+ else if (ver->fwlrole == 10)
+ rtw89_fw_h2c_cxdrv_role_v10(rtwdev, index);
break;
case CXDRVINFO_CTRL:
if (ver->drvinfo_ver != 0)
@@ -3396,29 +3413,17 @@ static void _set_rf_trx_para(struct rtw89_dev *rtwdev)
const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_dm *dm = &btc->dm;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
+ struct rtw89_btc_wl_role_info *r = &wl->role_info;
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
struct rtw89_btc_bt_link_info *b = &bt->link_info;
struct rtw89_btc_wl_smap *wl_smap = &wl->status.map;
struct rtw89_btc_rf_trx_para_v9 para;
- u8 lv, link_mode = 0, i, dbcc_2g_phy = 0;
- u8 ul_para_num, dl_para_num;
- u8 rf_band = RTW89_BAND_2G;
- u8 bid = BTC_BT_1ST;
- u32 wl_stb_chg = 0;
-
- if (ver->fwlrole == 0) {
- link_mode = wl->role_info.link_mode;
- for (i = 0; i < RTW89_PHY_NUM; i++) {
- if (wl->dbcc_info.real_band[i] == RTW89_BAND_2G)
- dbcc_2g_phy = i;
- }
- } else if (ver->fwlrole == 1) {
- link_mode = wl->role_info_v1.link_mode;
- dbcc_2g_phy = wl->role_info_v1.dbcc_2g_phy;
- } else if (ver->fwlrole == 2) {
- link_mode = wl->role_info_v2.link_mode;
- dbcc_2g_phy = wl->role_info_v2.dbcc_2g_phy;
- }
+ u8 bmode = dm->tdd_bind.wl_link_mode;
+ u8 rf_band = dm->tdd_bind.rf_band;
+ u8 i, ul_para_num, dl_para_num;
+ u8 mode = BTC_WLINK_NOLINK;
+ u8 bid = BTC_BT_1ST, lv;
+ u32 wl_stb_chg;
if (ver->fcxtrx == 9 && chip->rf_para_ulink_v9) {
ul_para_num = chip->rf_para_ulink_num_v9;
@@ -3434,6 +3439,19 @@ static void _set_rf_trx_para(struct rtw89_dev *rtwdev)
goto next;
}
+ if (bmode == BTC_WLINK_NOLINK) {
+ return;
+ } else if (btc->ver->fwlrole == 10) {
+ if (rf_band == RTW89_BAND_5G) {
+ mode = BTC_WLINK_V0_5G;
+ } else if (rf_band == RTW89_BAND_2G &&
+ bmode == BTC_WLINK_STA) {
+ mode = BTC_WLINK_V0_2G_STA;
+ }
+ } else {
+ mode = r->link_mode_v0;
+ }
+
/* decide trx_para_level */
if (btc->ant_type == BTC_ANT_SHARED) {
/* fix LNA2 + TIA gain not change by GNT_BT */
@@ -3446,7 +3464,7 @@ static void _set_rf_trx_para(struct rtw89_dev *rtwdev)
dm->trx_para_level = 5;
/* modify trx_para if WK 2.4G-STA-DL + bt link */
if (b->link_cnt.now != 0 &&
- link_mode == BTC_WLINK_2G_STA &&
+ mode == BTC_WLINK_V0_2G_STA &&
wl->status.map.traffic_dir & BIT(RTW89_TFC_UL)) { /* uplink */
if (wl->rssi_level == 4 && bt->rssi_level > 2)
dm->trx_para_level = 6;
@@ -3504,10 +3522,8 @@ static void _set_rf_trx_para(struct rtw89_dev *rtwdev)
next:
if (!bt->enable.now || dm->wl_only || wl_smap->rf_off ||
- wl_smap->lps == BTC_LPS_RF_OFF ||
- link_mode == BTC_WLINK_5G ||
- link_mode == BTC_WLINK_NOLINK ||
- (rtwdev->dbcc_en && dbcc_2g_phy != RTW89_PHY_1))
+ wl_smap->lps == BTC_LPS_RF_OFF || mode == BTC_WLINK_V0_5G ||
+ (rtwdev->dbcc_en && r->dbcc_2g_phy != RTW89_PHY_1))
wl_stb_chg = 0;
else
wl_stb_chg = 1;
@@ -3544,282 +3560,372 @@ static void _update_btc_state_map(struct rtw89_dev *rtwdev)
}
}
-static void _set_bt_afh_info_v0(struct rtw89_dev *rtwdev)
+static u8 _get_wl_guard_bw(struct rtw89_dev *rtwdev, u8 index)
{
- const struct rtw89_chip_info *chip = rtwdev->chip;
- struct rtw89_btc *btc = &rtwdev->btc;
- const struct rtw89_btc_ver *ver = btc->ver;
- struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
- struct rtw89_btc_bt_link_info *b = &bt->link_info;
- struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo_v1 = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo_v8 = &wl->role_info_v8;
- struct rtw89_btc_wl_active_role *r;
- struct rtw89_btc_wl_active_role_v1 *r1;
- struct rtw89_btc_wl_active_role_v2 *r2;
- struct rtw89_btc_wl_active_role_v7 *r7;
- struct rtw89_btc_wl_rlink *rlink;
- u8 en = 0, i, ch = 0, bw = 0;
- u8 mode, connect_cnt;
-
- if (btc->manual_ctrl || wl->status.map.scan)
- return;
-
- if (ver->fwlrole == 0) {
- mode = wl_rinfo->link_mode;
- connect_cnt = wl_rinfo->connect_cnt;
- } else if (ver->fwlrole == 1) {
- mode = wl_rinfo_v1->link_mode;
- connect_cnt = wl_rinfo_v1->connect_cnt;
- } else if (ver->fwlrole == 2) {
- mode = wl_rinfo_v2->link_mode;
- connect_cnt = wl_rinfo_v2->connect_cnt;
- } else if (ver->fwlrole == 7) {
- mode = wl_rinfo_v7->link_mode;
- connect_cnt = wl_rinfo_v7->connect_cnt;
- } else if (ver->fwlrole == 8) {
- mode = wl_rinfo_v8->link_mode;
- connect_cnt = wl_rinfo_v8->connect_cnt;
- } else {
- return;
- }
-
- if (wl->status.map.rf_off || bt->whql_test ||
- mode == BTC_WLINK_NOLINK || mode == BTC_WLINK_5G ||
- connect_cnt > BTC_TDMA_WLROLE_MAX) {
- en = false;
- } else if (mode == BTC_WLINK_2G_MCC || mode == BTC_WLINK_2G_SCC) {
- en = true;
- /* get p2p channel */
- for (i = 0; i < RTW89_PORT_NUM; i++) {
- r = &wl_rinfo->active_role[i];
- r1 = &wl_rinfo_v1->active_role_v1[i];
- r2 = &wl_rinfo_v2->active_role_v2[i];
- r7 = &wl_rinfo_v7->active_role[i];
- rlink = &wl_rinfo_v8->rlink[i][0];
-
- if (ver->fwlrole == 0 &&
- (r->role == RTW89_WIFI_ROLE_P2P_GO ||
- r->role == RTW89_WIFI_ROLE_P2P_CLIENT)) {
- ch = r->ch;
- bw = r->bw;
- break;
- } else if (ver->fwlrole == 1 &&
- (r1->role == RTW89_WIFI_ROLE_P2P_GO ||
- r1->role == RTW89_WIFI_ROLE_P2P_CLIENT)) {
- ch = r1->ch;
- bw = r1->bw;
- break;
- } else if (ver->fwlrole == 2 &&
- (r2->role == RTW89_WIFI_ROLE_P2P_GO ||
- r2->role == RTW89_WIFI_ROLE_P2P_CLIENT)) {
- ch = r2->ch;
- bw = r2->bw;
- break;
- } else if (ver->fwlrole == 7 &&
- (r7->role == RTW89_WIFI_ROLE_P2P_GO ||
- r7->role == RTW89_WIFI_ROLE_P2P_CLIENT)) {
- ch = r7->ch;
- bw = r7->bw;
- break;
- } else if (ver->fwlrole == 8 &&
- (rlink->role == RTW89_WIFI_ROLE_P2P_GO ||
- rlink->role == RTW89_WIFI_ROLE_P2P_CLIENT)) {
- ch = rlink->ch;
- bw = rlink->bw;
- break;
- }
- }
- } else {
- en = true;
- /* get 2g channel */
- for (i = 0; i < RTW89_PORT_NUM; i++) {
- r = &wl_rinfo->active_role[i];
- r1 = &wl_rinfo_v1->active_role_v1[i];
- r2 = &wl_rinfo_v2->active_role_v2[i];
- r7 = &wl_rinfo_v7->active_role[i];
- rlink = &wl_rinfo_v8->rlink[i][0];
-
- if (ver->fwlrole == 0 &&
- r->connected && r->band == RTW89_BAND_2G) {
- ch = r->ch;
- bw = r->bw;
- break;
- } else if (ver->fwlrole == 1 &&
- r1->connected && r1->band == RTW89_BAND_2G) {
- ch = r1->ch;
- bw = r1->bw;
- break;
- } else if (ver->fwlrole == 2 &&
- r2->connected && r2->band == RTW89_BAND_2G) {
- ch = r2->ch;
- bw = r2->bw;
- break;
- } else if (ver->fwlrole == 7 &&
- r7->connected && r7->band == RTW89_BAND_2G) {
- ch = r7->ch;
- bw = r7->bw;
- break;
- } else if (ver->fwlrole == 8 &&
- rlink->connected && rlink->rf_band == RTW89_BAND_2G) {
- ch = rlink->ch;
- bw = rlink->bw;
- break;
- }
- }
- }
+ struct rtw89_btc_dm *dm = &rtwdev->btc.dm;
+ u8 guard_ch = rtwdev->chip->afh_guard_ch;
+ u8 bw = 0;
- switch (bw) {
+ /* default AFH channel sapn = center-ch +- 6MHz */
+ switch (index) {
case RTW89_CHANNEL_WIDTH_20:
- bw = 20 + chip->afh_guard_ch * 2;
+ if (dm->freerun || dm->fddt_train)
+ bw = 48;
+ else
+ bw = 20 + guard_ch * 2;
break;
case RTW89_CHANNEL_WIDTH_40:
- bw = 40 + chip->afh_guard_ch * 2;
+ bw = 40 + guard_ch * 2;
+ break;
+ case RTW89_CHANNEL_WIDTH_80:
+ bw = 80 + guard_ch * 2;
+ break;
+ case RTW89_CHANNEL_WIDTH_160:
+ case RTW89_CHANNEL_WIDTH_80_80:
+ bw = 160 + guard_ch * 2;
+ break;
+ case RTW89_CHANNEL_WIDTH_320:
+ bw = 320 + guard_ch * 2;
break;
case RTW89_CHANNEL_WIDTH_5:
- bw = 5 + chip->afh_guard_ch * 2;
+ bw = 5 + guard_ch * 2;
break;
case RTW89_CHANNEL_WIDTH_10:
- bw = 10 + chip->afh_guard_ch * 2;
+ bw = 10 + guard_ch * 2;
break;
default:
bw = 0;
- en = false; /* turn off AFH info if BW > 40 */
break;
}
- if (wl->afh_info.en == en &&
- wl->afh_info.ch == ch &&
- wl->afh_info.bw == bw &&
- b->link_cnt.last == b->link_cnt.now) {
- rtw89_debug(rtwdev, RTW89_DBG_BTC,
- "[BTC], %s(): return because no change!\n",
- __func__);
+ return bw;
+}
+
+static void _set_wl_ch_map(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_btc *btc = &rtwdev->btc;
+ struct rtw89_btc_wl_info *wl = &btc->cx.wl;
+ struct rtw89_btc_wl_afh_info *afh;
+ u16 ch_start, ch_end, i;
+ u8 b_group, b_pos; /* byte-group, bit-position */
+ u8 hwb;
+
+ if (wl->afh_info[RTW89_MAC_0][RTW89_BAND_2G].en &&
+ wl->afh_info[RTW89_MAC_1][RTW89_BAND_2G].en) {
+ /* select wilder bw if 1+1 */
+ if (wl->afh_info[RTW89_MAC_1][RTW89_BAND_2G].bw >
+ wl->afh_info[RTW89_MAC_0][RTW89_BAND_2G].bw)
+ hwb = RTW89_MAC_1;
+ else
+ hwb = RTW89_MAC_0;
+ } else if (wl->afh_info[RTW89_MAC_1][RTW89_BAND_2G].en) {
+ hwb = RTW89_MAC_1;
+ } else {
+ hwb = RTW89_MAC_0;
+ }
+
+ afh = &wl->afh_info[hwb][RTW89_BAND_2G];
+
+ /* focus on WL 2.4GHz link */
+ if (!afh->en || afh->band != RTW89_BAND_2G)
return;
+
+ memset(wl->ch_map, 0x0, sizeof(wl->ch_map));
+ memset(wl->ch_map_le, 0x0, sizeof(wl->ch_map_le));
+
+ ch_start = afh->ch * 5 + 2407 - afh->bw / 2;
+ ch_end = ch_start + afh->bw;
+
+ for (i = ch_start; i < ch_end; i++) {
+ if (i < 2402 || i > 2480)
+ continue;
+ b_group = (i - 2402) / 8;
+ b_pos = 7 - ((i - 2402) % 8);
+ wl->ch_map[b_group] |= BIT(b_pos);
+
+ if (i % 2) /* BLE ch = even-freq (ex:2402,2404) */
+ continue;
+
+ b_group = (i - 2402) / 16;
+ b_pos = 7 - (((i - 2402) / 2) % 8);
+ wl->ch_map_le[b_group] |= BIT(b_pos);
}
+}
- wl->afh_info.en = en;
- wl->afh_info.ch = ch;
- wl->afh_info.bw = bw;
+static u8 _get_w2b_fbd_ch(struct rtw89_dev *rtwdev,
+ u8 bt_fb_band, u32 wl_vco_freq,
+ u32 *ch_lo_bound, u32 *ch_up_bound)
+{
+ u32 ch_lo, ch_pup, ch_min, ch_max;
+ u8 out_of_range = 0;
+ s32 val_lo, val_up;
+ u32 vco_lo_in_KHz; /* VCO pulling lower bound */
+ u32 vco_up_in_KHz; /* VCO pulling Upper bound */
+ u32 freq_start;
- _send_fw_cmd(rtwdev, BTFC_SET, SET_BT_WL_CH_INFO, &wl->afh_info, 3);
+ vco_lo_in_KHz = wl_vco_freq - BTC_VCO_GUARD_W2B * 1000; /* KHz */
+ vco_up_in_KHz = wl_vco_freq + BTC_VCO_GUARD_W2B * 1000;
- rtw89_debug(rtwdev, RTW89_DBG_BTC,
- "[BTC], %s(): en=%d, ch=%d, bw=%d\n",
- __func__, en, ch, bw);
- wl->wcnt[BTC_WCNT_CH_UPDATE]++;
+ switch (bt_fb_band) {
+ default:
+ case BTC_BT_B2G: /* BT 2GHz forbiddened Channel */
+ val_lo = vco_lo_in_KHz * BTC_LO_2G_DNM / BTC_LO_2G_NMR;
+ val_up = vco_up_in_KHz * BTC_LO_2G_DNM / BTC_LO_2G_NMR;
+ freq_start = BTC_FREQ_B2G * 1000; /* KHz */
+ ch_min = BTC_CH_B2G_MIN;
+ ch_max = BTC_CH_B2G_MAX;
+ break;
+ case BTC_BT_B5G: /* BT 5/6GHz forbiddened Channel */
+ val_lo = vco_lo_in_KHz * BTC_LO_6G_DNM / BTC_LO_6G_NMR;
+ val_up = vco_up_in_KHz * BTC_LO_6G_DNM / BTC_LO_6G_NMR;
+ freq_start = BTC_FREQ_B6G * 1000; /* KHz */
+ ch_min = BTC_CH_B5G_MIN;
+ ch_max = BTC_CH_B5G_MAX;
+ break;
+ }
+
+ /* Search forbiddened Channel (un-process range)*/
+ ch_lo = (val_lo - freq_start) / 1000;
+ if ((val_lo - freq_start) % 1000 != 0) /* Round-UP */
+ ch_lo++;
+
+ ch_pup = (val_up - freq_start) / 1000; /* Round-down */
+
+ /* Search forbiddened Channel */
+ if (ch_lo > ch_max || ch_pup < ch_min) { /* out-of-range -> NA */
+ out_of_range = 1;
+ *ch_lo_bound = 0;
+ *ch_up_bound = 0;
+ }
+
+ if (ch_lo < ch_min)
+ *ch_lo_bound = ch_min;
+ else if (ch_lo <= ch_max)
+ *ch_lo_bound = ch_lo;
+
+ if (ch_pup > ch_max)
+ *ch_up_bound = ch_max;
+ else if (ch_pup >= ch_min)
+ *ch_up_bound = ch_pup;
+
+ if (bt_fb_band == BTC_BT_B5G) { /* BT ch is 8MHz-spacing for 5/6GHz */
+ *ch_lo_bound = *ch_lo_bound / 8; /* low-bound -> Round-down */
+
+ if (*ch_up_bound % 8 != 0) /* Up-bound -> cover wider range */
+ *ch_up_bound = *ch_up_bound / 8 + 1;
+ else
+ *ch_up_bound = *ch_up_bound / 8;
+ }
+
+ return out_of_range;
}
-static void _set_bt_afh_info_v1(struct rtw89_dev *rtwdev)
+static void _set_wl_ch_info(struct rtw89_dev *rtwdev)
+{
+ static const u8 path_hwb[BTC_RF_NUM] = {RTW89_PHY_0, RTW89_PHY_1};
+ struct rtw89_btc_dm *dm = &rtwdev->btc.dm;
+ struct rtw89_btc_cx *cx = &rtwdev->btc.cx;
+ struct rtw89_btc_wl_info *wl = &cx->wl;
+ u32 vco_freq, ch_lo = 0, ch_up = 0;
+ u16 rf_band, freq, f_diff;
+ u8 i, j, ch;
+
+ if (!(rtwdev->chip->para_ver & BTC_FEAT_MULTI_PTA)) /* only new-PTA require setup */
+ return;
+
+ for (i = RTW89_PHY_0; i <= RTW89_PHY_1; i++) {
+ if (wl->mlo_info.wmode[i] == RTW89_MR_WMODE_NONE) { /* no-connect */
+ dm->ost_info.rf_center_freq[i] = 0;
+ dm->ost_info.fbd_group_en[i][0] = 0;
+ dm->ost_info.fbd_group_en[i][1] = 0;
+ dm->ost_info.fbd_group_bound[i][0] = 0;
+ dm->ost_info.fbd_group_bound[i][1] = 0;
+ continue;
+ }
+
+ ch = wl->rf_ch_info[i].center_ch;
+ switch (wl->rf_ch_info[i].band) {
+ case RTW89_BAND_2G:
+ default:
+ rf_band = 0;
+ if (ch == 14)
+ freq = BTC_FREQ_W2G_CH14;
+ else
+ freq = BTC_FREQ_W2G + (ch - 1) * 5;
+ vco_freq = freq * 1000 * BTC_LO_2G_NMR / BTC_LO_2G_DNM;
+ break;
+ case RTW89_BAND_5G:
+ rf_band = BIT(15);
+ freq = BTC_FREQ_W5G + (ch - 1) * 5;
+ vco_freq = freq * 1000 * BTC_LO_5G_NMR / BTC_LO_5G_DNM;
+ break;
+ case RTW89_BAND_6G:
+ rf_band = BIT(15);
+ freq = BTC_FREQ_W6G + (ch - 1) * 5;
+ vco_freq = freq * 1000 * BTC_LO_6G_NMR / BTC_LO_6G_DNM;
+ break;
+ }
+
+ dm->ost_info.rf_center_freq[i] = rf_band + freq;
+
+ for (j = BTC_BT_B2G; j <= BTC_BT_B5G; j++) {
+ /* no WL->BT forbidden channel */
+ if (_get_w2b_fbd_ch(rtwdev, j, vco_freq, &ch_lo, &ch_up)) {
+ dm->ost_info.fbd_group_en[i][j] = j << 1;
+ dm->ost_info.fbd_group_bound[i][j] = 0;
+ continue;
+ }
+
+ dm->ost_info.fbd_group_en[i][j] = (j << 1) + 0x1;
+ dm->ost_info.fbd_group_bound[i][j] = (ch_up << 8) + ch_lo;
+ }
+ }
+
+ for (i = BTC_RF_S0; i <= BTC_RF_S1; i++) {
+ for (j = BTC_BT_1ST; j <= BTC_BT_EXT; j++) {
+ /*
+ * If WL & BT share same ANT/Path, set freq-diff > 2GHz,
+ * because TDD will always run in 5/6GHz band.
+ * Otherwise, the frq-diff thres is decided by the RF
+ * out-of-channel rejection capability.
+ */
+ if (dm->ant_xmap[i][j])
+ f_diff = 0x7ff; /* 2047MHz */
+ else
+ f_diff = rtwdev->chip->fdd_iso_freq;
+
+ dm->ost_info.freq_diff_thres[path_hwb[i]][j] = f_diff;
+ }
+ }
+}
+
+static void _set_bt_afh_info(struct rtw89_dev *rtwdev)
{
- const struct rtw89_chip_info *chip = rtwdev->chip;
struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo = &wl->role_info_v8;
- struct rtw89_btc_wl_afh_info *wl_afh = &wl->afh_info;
- struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
+ struct rtw89_btc_cx *cx = &btc->cx;
+ struct rtw89_btc_wl_info *wl = &cx->wl;
+ struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
struct rtw89_btc_wl_rlink *rlink;
- u8 en = 0, ch = 0, bw = 0, buf[3] = {};
- u8 i, j, link_mode;
+ u8 h2c_func, hwb, bt_link_chg;
+ u8 i, j, sz, bw;
+ u8 buf[4];
- if (btc->manual_ctrl || wl->status.map.scan)
+ if (btc->manual_ctrl || wl->status.map.rf_off ||
+ (wl->status.val & btc_scanning_map.val))
return;
- link_mode = wl_rinfo->link_mode;
+ memset(wl->afh_info, 0, sizeof(wl->afh_info));
- for (i = 0; i < btc->ver->max_role_num; i++) {
- for (j = RTW89_MAC_0; j < RTW89_MAC_NUM; j++) {
- if (wl->status.map.rf_off || bt->whql_test ||
- link_mode == BTC_WLINK_NOLINK ||
- link_mode == BTC_WLINK_5G)
- break;
+ for (j = RTW89_MAC_0; j < RTW89_MAC_NUM; j++) {
+ /* skip HW-Band if no fdd/fdd bind */
+ if ((!(btc->dm.tdd_bind.wl_hwb_sel & BIT(j))) &&
+ (!(btc->dm.fdd_bind.wl_hwb_sel & BIT(j))))
+ continue;
+ for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) {
rlink = &wl_rinfo->rlink[i][j];
- /* Don't care no-connected/non-2G-band role */
+ /* Skip no-active case */
if (!rlink->connected || !rlink->active ||
- rlink->rf_band != RTW89_BAND_2G)
+ rlink->rf_band >= RTW89_BAND_NUM)
continue;
- en = 1;
- ch = rlink->ch;
- bw = rlink->bw;
+ /* In addition to AP/P2P, skip if same-rf-band*/
+ if (wl->afh_info[j][rlink->rf_band].en &&
+ (rlink->role != RTW89_WIFI_ROLE_AP &&
+ rlink->role != RTW89_WIFI_ROLE_P2P_GO &&
+ rlink->role != RTW89_WIFI_ROLE_P2P_CLIENT))
+ continue;
- if (link_mode == BTC_WLINK_2G_MCC &&
- (rlink->role == RTW89_WIFI_ROLE_AP ||
- rlink->role == RTW89_WIFI_ROLE_P2P_GO ||
- rlink->role == RTW89_WIFI_ROLE_P2P_CLIENT)) {
- /* for 2.4G MCC, take role = ap/go/gc */
- break;
- } else if (link_mode != BTC_WLINK_2G_SCC ||
- rlink->bw == RTW89_CHANNEL_WIDTH_40) {
- /* for 2.4G scc, take bw = 40M */
- break;
- }
+ bw = _get_wl_guard_bw(rtwdev, rlink->bw);
+ wl->afh_info[j][rlink->rf_band].en = 1;
+ wl->afh_info[j][rlink->rf_band].ch = rlink->ch;
+ wl->afh_info[j][rlink->rf_band].bw = bw;
+ wl->afh_info[j][rlink->rf_band].band = rlink->rf_band;
}
}
- /* default AFH channel sapn = center-ch +- 6MHz */
- switch (bw) {
- case RTW89_CHANNEL_WIDTH_20:
- if (btc->dm.freerun || btc->dm.fddt_train)
- bw = 48;
- else
- bw = 20 + chip->afh_guard_ch * 2;
- break;
- case RTW89_CHANNEL_WIDTH_40:
- if (btc->dm.freerun)
- bw = 40 + chip->afh_guard_ch * 2;
- else
- bw = 40;
- break;
- case RTW89_CHANNEL_WIDTH_5:
- bw = 5 + chip->afh_guard_ch * 2;
- break;
- case RTW89_CHANNEL_WIDTH_10:
- bw = 10 + chip->afh_guard_ch * 2;
- break;
- default:
- en = false; /* turn off AFH info if invalid BW */
- bw = 0;
- ch = 0;
- break;
- }
+ for (j = RTW89_BAND_2G; j < RTW89_BAND_NUM; j++) {
+ /* skip non-2.4GHz if BT is 2.4GHz only*/
+ if (!(rtwdev->chip->para_ver & BTC_FEAT_BT_6G)) {
+ if (j != RTW89_BAND_2G)
+ continue;
+ sz = 3;
+ } else {
+ sz = 4;
+ }
- if (!en || ch > 14 || ch == 0) {
- en = false;
- bw = 0;
- ch = 0;
- }
+ if (wl->afh_info[RTW89_MAC_0][j].en &&
+ wl->afh_info[RTW89_MAC_1][j].en) {
+ /* select wilder bw if 1+1 */
+ if (wl->afh_info[RTW89_MAC_1][j].bw >
+ wl->afh_info[RTW89_MAC_0][j].bw)
+ hwb = RTW89_MAC_1;
+ else
+ hwb = RTW89_MAC_0;
+ } else if (wl->afh_info[RTW89_MAC_1][j].en) {
+ hwb = RTW89_MAC_1;
+ } else {
+ hwb = RTW89_MAC_0;
+ }
- if (wl_afh->en == en &&
- wl_afh->ch == ch &&
- wl_afh->bw == bw &&
- (!bt->enable.now || bt->enable.last))
- return;
+ if (j == RTW89_BAND_2G) {
+ if (cx->bt0.link_info.link_cnt.chg ||
+ cx->bt1.link_info.link_cnt.chg)
+ bt_link_chg = 1;
+ else
+ bt_link_chg = 0;
+ } else {
+ if (cx->bt0.link_info_56g.link_cnt.chg ||
+ cx->bt1.link_info_56g.link_cnt.chg)
+ bt_link_chg = 1;
+ else
+ bt_link_chg = 0;
+ }
+
+ /* return if no-afh-info-change/no wl-bt link change */
+ if (!memcmp(&wl->afh_info_last[hwb][j],
+ &wl->afh_info[hwb][j],
+ sizeof(struct rtw89_btc_wl_afh_info)) &&
+ !bt_link_chg &&
+ !wl->link_mode_chg)
+ continue;
+
+ memcpy(&wl->afh_info_last[hwb][j],
+ &wl->afh_info[hwb][j],
+ sizeof(struct rtw89_btc_wl_afh_info));
+
+ buf[0] = wl->afh_info[hwb][j].en;
+ buf[1] = wl->afh_info[hwb][j].ch;
+ buf[2] = wl->afh_info[hwb][j].bw;
+ buf[3] = wl->afh_info[hwb][j].band;
+
+ h2c_func = SET_BT_WL_CH_INFO;
+ if (cx->bt0.enable.now)
+ _send_fw_cmd(rtwdev, BTFC_SET, h2c_func, buf, sz);
- wl_afh->en = buf[0];
- wl_afh->ch = buf[1];
- wl_afh->bw = buf[2];
+ /* send mailbox to 2nd-BT if exist */
+ if (cx->bt1.enable.now) {
+ h2c_func |= BT_H2C_FUNC_BT2ND;
+ _send_fw_cmd(rtwdev, BTFC_SET, h2c_func, buf, sz);
+ }
- if (_send_fw_cmd(rtwdev, BTFC_SET, SET_BT_WL_CH_INFO, &wl->afh_info, 3)) {
rtw89_debug(rtwdev, RTW89_DBG_BTC,
- "[BTC], %s(): en=%d, ch=%d, bw=%d\n",
- __func__, en, ch, bw);
+ "[BTC], %s(): en=%d, ch=%d, bw=%d, rf_band=%d\n",
+ __func__, buf[0], buf[1], buf[2], buf[3]);
wl->wcnt[BTC_WCNT_CH_UPDATE]++;
+
+ /* ToDo: Remove if BT update new-define to support 6GHz */
+ if (j == RTW89_BAND_2G)
+ break;
}
-}
-static void _set_bt_afh_info(struct rtw89_dev *rtwdev)
-{
- if (rtwdev->chip->chip_id == RTL8922A)
- _set_bt_afh_info_v1(rtwdev);
- else
- _set_bt_afh_info_v0(rtwdev);
+ /* for AFH map display in coex log */
+ _set_wl_ch_map(rtwdev);
+
+ /* set HWB center-ch/forbidden group to ost_info for CR setup in FW */
+ _set_wl_ch_info(rtwdev);
}
static bool _check_freerun(struct rtw89_dev *rtwdev)
@@ -3828,39 +3934,24 @@ static bool _check_freerun(struct rtw89_dev *rtwdev)
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo_v1 = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo_v8 = &wl->role_info_v8;
struct rtw89_btc_bt_link_info *bt_linfo = &bt->link_info;
struct rtw89_btc_bt_hid_desc *hid = &bt_linfo->hid_desc;
union rtw89_btc_module_info *md = &btc->mdinfo;
const struct rtw89_btc_ver *ver = btc->ver;
- u8 isolation, connect_cnt = 0;
+ u8 isolation;
if (ver->fcxinit == 7)
isolation = md->md_v7.ant.isolation;
else
isolation = md->md.ant.isolation;
- if (ver->fwlrole == 0)
- connect_cnt = wl_rinfo->connect_cnt;
- else if (ver->fwlrole == 1)
- connect_cnt = wl_rinfo_v1->connect_cnt;
- else if (ver->fwlrole == 2)
- connect_cnt = wl_rinfo_v2->connect_cnt;
- else if (ver->fwlrole == 7)
- connect_cnt = wl_rinfo_v7->connect_cnt;
- else if (ver->fwlrole == 8)
- connect_cnt = wl_rinfo_v8->connect_cnt;
-
if (btc->ant_type == BTC_ANT_SHARED) {
btc->dm.trx_para_level = 0;
return false;
}
/* The below is dedicated antenna case */
- if (connect_cnt > BTC_TDMA_WLROLE_MAX) {
+ if (wl_rinfo->connect_cnt > BTC_TDMA_WLROLE_MAX) {
btc->dm.trx_para_level = 5;
return true;
}
@@ -4097,11 +4188,26 @@ void rtw89_btc_set_policy(struct rtw89_dev *rtwdev, u16 policy_type)
case BTC_CXP_OFFB: /* TDMA off + beacon protect */
tdma_on = false;
*t = t_def[CXTD_OFF_B2];
- s[CXST_OFF] = s_def[CXST_OFF];
+ _slot_set_le(btc, CXST_OFF, s_def[CXST_OFF].dur,
+ s_def[CXST_OFF].cxtbl, s_def[CXST_OFF].cxtype);
+ _slot_set(btc, CXST_B2, 10, cxtbl[1], SLOT_ISO);
+
switch (policy_type) {
case BTC_CXP_OFFB_BWB0:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[5]);
+ break;
+ case BTC_CXP_OFFB_BWB1:
_slot_set_tbl(btc, CXST_OFF, cxtbl[8]);
break;
+ case BTC_CXP_OFFB_BWB2:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[7]);
+ break;
+ case BTC_CXP_OFFB_BWB3:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[6]);
+ break;
+ case BTC_CXP_OFFB_BWB4:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[2]);
+ break;
}
break;
case BTC_CXP_OFFE: /* TDMA off + beacon protect + Ext_control */
@@ -4182,7 +4288,7 @@ void rtw89_btc_set_policy(struct rtw89_dev *rtwdev, u16 policy_type)
case BTC_CXP_PFIX: /* PS-TDMA Fix-Slot */
tdma_on = true;
*t = t_def[CXTD_PFIX];
- if (btc->cx.wl.role_info.role_map.role.ap)
+ if (btc->cx.wl.role_info.role_map & BIT(RTW89_WIFI_ROLE_AP))
_tdma_set_flctrl(btc, CXFLC_QOSNULL);
switch (policy_type) {
@@ -4461,12 +4567,23 @@ void rtw89_btc_set_policy_v1(struct rtw89_dev *rtwdev, u16 policy_type)
*t = t_def[CXTD_OFF_B2];
_slot_set_le(btc, CXST_OFF, s_def[CXST_OFF].dur,
s_def[CXST_OFF].cxtbl, s_def[CXST_OFF].cxtype);
+ _slot_set(btc, CXST_B2, 10, cxtbl[1], SLOT_ISO);
switch (policy_type) {
case BTC_CXP_OFFB_BWB0:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[5]);
+ break;
+ case BTC_CXP_OFFB_BWB1:
_slot_set_tbl(btc, CXST_OFF, cxtbl[8]);
break;
- default:
+ case BTC_CXP_OFFB_BWB2:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[7]);
+ break;
+ case BTC_CXP_OFFB_BWB3:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[6]);
+ break;
+ case BTC_CXP_OFFB_BWB4:
+ _slot_set_tbl(btc, CXST_OFF, cxtbl[2]);
break;
}
break;
@@ -4841,35 +4958,17 @@ static void _set_ant_v0(struct rtw89_dev *rtwdev, bool force_exec,
struct rtw89_btc_dm *dm = &btc->dm;
struct rtw89_btc_cx *cx = &btc->cx;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
+ struct rtw89_btc_wl_role_info *r = &btc->cx.wl.role_info;
struct rtw89_btc_bt_info *bt = &cx->bt0;
struct rtw89_btc_wl_dbcc_info *wl_dinfo = &wl->dbcc_info;
- u8 gwl, gwl0, gwl1, gbt, plt_ctrl, i, dbcc_2g_phy, b2g = 0;
- bool dbcc_chg = false, dbcc_en = false;
+ u8 gwl, gwl0, gwl1, gbt, plt_ctrl, i, b2g = 0;
u32 ant_path_type;
ant_path_type = ((phy_map << 8) + type);
- if (btc->ver->fwlrole == 1) {
- dbcc_chg = wl->role_info_v1.dbcc_chg;
- dbcc_en = wl->role_info_v1.dbcc_en;
- dbcc_2g_phy = wl->role_info_v1.dbcc_2g_phy;
- } else if (btc->ver->fwlrole == 2) {
- dbcc_chg = wl->role_info_v2.dbcc_chg;
- dbcc_en = wl->role_info_v2.dbcc_en;
- dbcc_2g_phy = wl->role_info_v2.dbcc_2g_phy;
- } else if (btc->ver->fwlrole == 7) {
- dbcc_chg = wl->role_info_v7.dbcc_chg;
- dbcc_en = wl->role_info_v7.dbcc_en;
- dbcc_2g_phy = wl->role_info_v7.dbcc_2g_phy;
- } else if (btc->ver->fwlrole == 8) {
- dbcc_chg = wl->role_info_v8.dbcc_chg;
- dbcc_en = wl->role_info_v8.dbcc_en;
- dbcc_2g_phy = wl->role_info_v8.dbcc_2g_phy;
- }
-
if (btc->dm.run_reason == BTC_RSN_NTFY_POWEROFF ||
btc->dm.run_reason == BTC_RSN_NTFY_RADIO_STATE ||
- btc->dm.run_reason == BTC_RSN_CMD_SET_COEX || dbcc_chg)
+ btc->dm.run_reason == BTC_RSN_CMD_SET_COEX || r->dbcc_chg)
force_exec = FC_EXEC;
if (!force_exec && ant_path_type == dm->set_ant_path) {
@@ -4967,12 +5066,12 @@ static void _set_ant_v0(struct rtw89_dev *rtwdev, bool force_exec,
default:
gbt = BTC_GNT_HW;
if ((rtwdev->chip->para_ver & BTC_FEAT_MULTI_PTA) ||
- !dbcc_en) {
+ !r->dbcc_en) {
gwl = BTC_GNT_HW;
_set_gnt(rtwdev, BTC_PHY_ALL, gwl, gbt);
} else {
/* for DBCC Only-1-PTA */
- if (dbcc_2g_phy == RTW89_PHY_0) {
+ if (r->dbcc_2g_phy == RTW89_PHY_0) {
gwl0 = BTC_GNT_HW;
gwl1 = BTC_GNT_SW_HI;
} else {
@@ -4994,7 +5093,7 @@ static void _set_ant_v1(struct rtw89_dev *rtwdev, bool force_exec,
struct rtw89_btc *btc = &rtwdev->btc;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo = &wl->role_info_v8;
+ struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
u32 ant_path_type = rtw89_get_antpath_type(phy_map, type);
struct rtw89_btc_wl_dbcc_info *wl_dinfo = &wl->dbcc_info;
struct rtw89_btc_dm *dm = &btc->dm;
@@ -5005,7 +5104,7 @@ static void _set_ant_v1(struct rtw89_dev *rtwdev, bool force_exec,
btc->dm.run_reason == BTC_RSN_CMD_SET_COEX || wl_rinfo->dbcc_chg)
force_exec = FC_EXEC;
- if (wl_rinfo->link_mode != BTC_WLINK_25G_MCC &&
+ if (wl_rinfo->link_mode != BTC_WLINK_DB_MCC &&
btc->dm.wl_btg_rx == 2)
force_exec = FC_EXEC;
@@ -5111,7 +5210,7 @@ static void _set_ant_v1(struct rtw89_dev *rtwdev, bool force_exec,
static void _set_ant(struct rtw89_dev *rtwdev, bool force_exec,
u8 phy_map, u8 type)
{
- if (rtwdev->chip->chip_id == RTL8922A)
+ if (rtwdev->chip->chip_id >= RTL8922A)
_set_ant_v1(rtwdev, force_exec, phy_map, type);
else
_set_ant_v0(rtwdev, force_exec, phy_map, type);
@@ -5134,29 +5233,24 @@ static void _action_wl_init(struct rtw89_dev *rtwdev)
static void _action_wl_off(struct rtw89_dev *rtwdev, u8 mode)
{
struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_info *wl = &btc->cx.wl;
+ struct rtw89_btc_dm *dm = &btc->dm;
+ struct rtw89_btc_cx *cx = &btc->cx;
+ struct rtw89_btc_wl_info *wl = &cx->wl;
rtw89_debug(rtwdev, RTW89_DBG_BTC, "[BTC], %s(): !!\n", __func__);
- if (wl->status.map.rf_off || btc->dm.bt_only) {
+ if (wl->status.map.rf_off || btc->dm.bt_only)
_set_ant(rtwdev, NM_EXEC, BTC_PHY_ALL, BTC_ANT_WOFF);
- } else if (wl->status.map.lps == BTC_LPS_RF_ON) {
- if (mode == BTC_WLINK_5G)
- _set_ant(rtwdev, FC_EXEC, BTC_PHY_ALL, BTC_ANT_W5G);
- else
- _set_ant(rtwdev, FC_EXEC, BTC_PHY_ALL, BTC_ANT_W2G);
- }
+ else if (wl->status.map.lps == BTC_LPS_RF_ON ||
+ cx->bt0.whql_test || cx->bt1.whql_test)
+ _set_ant(rtwdev, FC_EXEC, BTC_PHY_ALL, BTC_ANT_PTA);
- if (mode == BTC_WLINK_5G) {
+ if (dm->out_of_band)
_set_policy(rtwdev, BTC_CXP_OFF_EQ0, BTC_ACT_WL_OFF);
- } else if (wl->status.map.lps == BTC_LPS_RF_ON) {
- if (btc->cx.bt0.link_info.a2dp_desc.active)
- _set_policy(rtwdev, BTC_CXP_OFF_BT, BTC_ACT_WL_OFF);
- else
- _set_policy(rtwdev, BTC_CXP_OFF_BWB1, BTC_ACT_WL_OFF);
- } else {
+ else if (cx->bt0.whql_test || cx->bt1.whql_test)
+ _set_policy(rtwdev, BTC_CXP_OFFB_BWB4, BTC_ACT_WL_OFF);
+ else
_set_policy(rtwdev, BTC_CXP_OFF_BT, BTC_ACT_WL_OFF);
- }
}
static void _action_freerun(struct rtw89_dev *rtwdev)
@@ -5563,48 +5657,29 @@ static void _action_wl_rfk(struct rtw89_dev *rtwdev)
static void _set_btg_ctrl(struct rtw89_dev *rtwdev)
{
struct rtw89_btc *btc = &rtwdev->btc;
+ struct rtw89_btc_dm *dm = &btc->dm;
+ struct rtw89_btc_fbtc_outsrc_set_info *o_info = &dm->ost_info;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo_v1 = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo_v8 = &wl->role_info_v8;
- struct rtw89_btc_fbtc_outsrc_set_info *o_info = &btc->dm.ost_info;
- struct rtw89_btc_wl_role_info *wl_rinfo_v0 = &wl->role_info;
+ struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
const struct rtw89_chip_info *chip = rtwdev->chip;
- const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
- struct rtw89_btc_dm *dm = &btc->dm;
- struct _wl_rinfo_now wl_rinfo;
u32 is_btg = BTC_BTGCTRL_DISABLE;
if (btc->manual_ctrl)
return;
- if (ver->fwlrole == 0)
- wl_rinfo.link_mode = wl_rinfo_v0->link_mode;
- else if (ver->fwlrole == 1)
- wl_rinfo.link_mode = wl_rinfo_v1->link_mode;
- else if (ver->fwlrole == 2)
- wl_rinfo.link_mode = wl_rinfo_v2->link_mode;
- else if (ver->fwlrole == 7)
- wl_rinfo.link_mode = wl_rinfo_v7->link_mode;
- else if (ver->fwlrole == 8)
- wl_rinfo.link_mode = wl_rinfo_v8->link_mode;
- else
- return;
-
/* notify halbb ignore GNT_BT or not for WL BB Rx-AGC control */
if (btc->ant_type == BTC_ANT_SHARED) {
if (!(bt->run_patch_code && bt->enable.now))
is_btg = BTC_BTGCTRL_DISABLE;
- else if (wl_rinfo.link_mode != BTC_WLINK_5G)
+ else if (wl_rinfo->link_mode_v0 != BTC_WLINK_V0_5G)
is_btg = BTC_BTGCTRL_ENABLE;
else
is_btg = BTC_BTGCTRL_DISABLE;
/* bb call ctrl_btg() in WL FW by slot */
- if (!ver->fcxosi &&
- wl_rinfo.link_mode == BTC_WLINK_25G_MCC)
+ if (!btc->ver->fcxosi &&
+ wl_rinfo->link_mode_v0 == BTC_WLINK_V0_25G_MCC)
is_btg = BTC_BTGCTRL_BB_GNT_FWCTRL;
}
@@ -5614,7 +5689,7 @@ static void _set_btg_ctrl(struct rtw89_dev *rtwdev)
dm->wl_btg_rx = is_btg;
/* skip setup if btg_ctrl set by wl fw */
- if (!ver->fcxosi && is_btg > BTC_BTGCTRL_ENABLE)
+ if (!btc->ver->fcxosi && is_btg > BTC_BTGCTRL_ENABLE)
return;
/* Below flow is for BTC_FEAT_NEW_BBAPI_FLOW = 1 */
@@ -5633,7 +5708,7 @@ static void _set_btg_ctrl(struct rtw89_dev *rtwdev)
o_info->btg_rx[BTC_RF_S1] = is_btg;
}
- if (ver->fcxosi)
+ if (btc->ver->fcxosi)
return;
chip->ops->ctrl_btg_bt_rx(rtwdev, o_info->btg_rx[BTC_RF_S0],
@@ -5651,40 +5726,20 @@ static void _set_wl_preagc_ctrl(struct rtw89_dev *rtwdev)
struct rtw89_btc_fbtc_outsrc_set_info *o_info = &btc->dm.ost_info;
struct rtw89_btc_bt_link_info *bt_linfo = &btc->cx.bt0.link_info;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v2 *rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *rinfo_v8 = &wl->role_info_v8;
+ struct rtw89_btc_wl_role_info *rinfo = &wl->role_info;
const struct rtw89_chip_info *chip = rtwdev->chip;
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
struct rtw89_btc_dm *dm = &btc->dm;
- u8 is_preagc, val, link_mode, dbcc_2g_phy;
- u8 role_ver = rtwdev->btc.ver->fwlrole;
- bool dbcc_en;
+ u8 is_preagc, val;
if (btc->manual_ctrl)
return;
- if (role_ver == 2) {
- dbcc_en = rinfo_v2->dbcc_en;
- link_mode = rinfo_v2->link_mode;
- dbcc_2g_phy = rinfo_v2->dbcc_2g_phy;
- } else if (role_ver == 7) {
- dbcc_en = rinfo_v7->dbcc_en;
- link_mode = rinfo_v7->link_mode;
- dbcc_2g_phy = rinfo_v7->dbcc_2g_phy;
- } else if (role_ver == 8) {
- dbcc_en = rinfo_v8->dbcc_en;
- link_mode = rinfo_v8->link_mode;
- dbcc_2g_phy = rinfo_v7->dbcc_2g_phy;
- } else {
- return;
- }
-
if (!(bt->run_patch_code && bt->enable.now)) {
is_preagc = BTC_PREAGC_DISABLE;
- } else if (link_mode == BTC_WLINK_5G) {
+ } else if (dm->tdd_bind.rf_band == BIT(RTW89_BAND_5G)) {
is_preagc = BTC_PREAGC_DISABLE;
- } else if (link_mode == BTC_WLINK_NOLINK ||
+ } else if (rinfo->link_mode == BTC_WLINK_NOLINK ||
btc->cx.bt0.link_info.link_cnt.now == 0) {
is_preagc = BTC_PREAGC_DISABLE;
} else if (dm->tdma_now.type != CXTDMA_OFF &&
@@ -5692,7 +5747,7 @@ static void _set_wl_preagc_ctrl(struct rtw89_dev *rtwdev)
!bt_linfo->hid_desc.exist &&
dm->fddt_train == BTC_FDDT_DISABLE) {
is_preagc = BTC_PREAGC_DISABLE;
- } else if (dbcc_en && (dbcc_2g_phy != RTW89_PHY_1)) {
+ } else if (rinfo->dbcc_en && (rinfo->dbcc_2g_phy != RTW89_PHY_1)) {
is_preagc = BTC_PREAGC_DISABLE;
} else if (btc->ant_type == BTC_ANT_SHARED) {
is_preagc = BTC_PREAGC_DISABLE;
@@ -5700,7 +5755,7 @@ static void _set_wl_preagc_ctrl(struct rtw89_dev *rtwdev)
is_preagc = BTC_PREAGC_ENABLE;
}
- if (!btc->ver->fcxosi && link_mode == BTC_WLINK_25G_MCC)
+ if (!btc->ver->fcxosi && rinfo->link_mode == BTC_WLINK_DB_MCC)
is_preagc = BTC_PREAGC_BB_FWCTRL;
if (dm->wl_pre_agc_rb != dm->wl_pre_agc &&
@@ -5771,10 +5826,7 @@ static void __rtw89_tx_time_iter(struct rtw89_vif_link *rtwvif_link,
u16 enable = iter_data->enable;
bool reenable = iter_data->reenable;
- if (btc->ver->fwlrole == 8)
- plink = &wl->rlink_info[port][0];
- else
- plink = &wl->link_info[port];
+ plink = &wl->rlink_info[port][rtwsta_link->link_id];
rtw89_debug(rtwdev, RTW89_DBG_BTC,
"[BTC], %s(): port = %d\n", __func__, port);
@@ -5840,39 +5892,23 @@ static void _set_wl_tx_limit(struct rtw89_dev *rtwdev)
struct rtw89_btc_bt_hfp_desc *hfp = &b->hfp_desc;
struct rtw89_btc_bt_hid_desc *hid = &b->hid_desc;
struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo_v1 = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo_v8 = &wl->role_info_v8;
struct rtw89_txtime_data data = {.rtwdev = rtwdev};
- u8 mode, igno_bt, tx_retry;
+ bool reenable = false;
+ u8 igno_bt, tx_retry;
u32 tx_time;
u16 enable;
- bool reenable = false;
if (btc->manual_ctrl)
return;
- if (ver->fwlrole == 0)
- mode = wl_rinfo->link_mode;
- else if (ver->fwlrole == 1)
- mode = wl_rinfo_v1->link_mode;
- else if (ver->fwlrole == 2)
- mode = wl_rinfo_v2->link_mode;
- else if (ver->fwlrole == 7)
- mode = wl_rinfo_v7->link_mode;
- else if (ver->fwlrole == 8)
- mode = wl_rinfo_v8->link_mode;
- else
- return;
-
if (ver->fcxctrl == 7)
igno_bt = btc->ctrl.ctrl_v7.igno_bt;
else
igno_bt = btc->ctrl.ctrl.igno_bt;
if (btc->dm.freerun || igno_bt || b->link_cnt.now == 0 ||
- mode == BTC_WLINK_5G || mode == BTC_WLINK_NOLINK) {
+ dm->tdd_bind.rf_band == BIT(RTW89_BAND_5G) ||
+ wl_rinfo->link_mode == BTC_WLINK_NOLINK) {
enable = 0;
tx_time = BTC_MAX_TX_TIME_DEF;
tx_retry = BTC_MAX_TX_RETRY_DEF;
@@ -5915,31 +5951,12 @@ static void _set_wl_tx_limit(struct rtw89_dev *rtwdev)
static void _set_bt_rx_agc(struct rtw89_dev *rtwdev)
{
struct rtw89_btc *btc = &rtwdev->btc;
- const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo_v1 = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo_v8 = &wl->role_info_v8;
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
bool bt_hi_lna_rx = false;
- u8 mode;
- if (ver->fwlrole == 0)
- mode = wl_rinfo->link_mode;
- else if (ver->fwlrole == 1)
- mode = wl_rinfo_v1->link_mode;
- else if (ver->fwlrole == 2)
- mode = wl_rinfo_v2->link_mode;
- else if (ver->fwlrole == 7)
- mode = wl_rinfo_v7->link_mode;
- else if (ver->fwlrole == 8)
- mode = wl_rinfo_v8->link_mode;
- else
- return;
-
- if (mode != BTC_WLINK_NOLINK && btc->dm.wl_btg_rx)
+ if (wl_rinfo->link_mode != BTC_WLINK_NOLINK && btc->dm.wl_btg_rx)
bt_hi_lna_rx = true;
if (bt_hi_lna_rx == bt->hi_lna_rx)
@@ -5985,20 +6002,51 @@ static void _wl_req_mac(struct rtw89_dev *rtwdev, u8 mac)
rtw89_write32_set(rtwdev, add, B_AX_WL_SRC);
}
-static void _action_common(struct rtw89_dev *rtwdev)
+static void _update_zb_coex_tbl(struct rtw89_dev *rtwdev)
{
struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v8 *rinfo_v8 = &wl->role_info_v8;
- struct rtw89_btc_wl_smap *wl_smap = &wl->status.map;
- struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
- struct rtw89_btc_dm *dm = &btc->dm;
- u32 bt_rom_code_id, bt_fw_ver;
- u8 i;
-
- if (btc->ver->fwlrole == 8)
- _wl_req_mac(rtwdev, rinfo_v8->pta_req_band);
+ const struct rtw89_btc_ver *ver = btc->ver;
+ u32 zb_tbl0 = 0xda5a5a5a, zb_tbl1 = 0xda5a5a5a;
+ u8 link_mode_chg = btc->cx.wl.link_mode_chg;
+ u8 mode = btc->cx.wl.role_info.link_mode;
+ u8 wa_type;
+
+ if (btc->dm.run_reason != BTC_RSN_NTFY_INIT && !link_mode_chg)
+ return;
+
+ if (ver->fcxinit == 7)
+ wa_type = btc->mdinfo.md_v7.wa_type;
+ else
+ wa_type = btc->mdinfo.md.wa_type;
+ if (!(wa_type & BTC_WA_HFP_ZB))
+ return;
+
+ if (btc->dm.tdd_bind.rf_band == BIT(RTW89_BAND_5G) ||
+ rtwdev->btc.dm.freerun) {
+ zb_tbl0 = 0xffffffff;
+ zb_tbl1 = 0xffffffff;
+ } else if (mode == BTC_WLINK_DB_MCC) {
+ zb_tbl0 = 0xffffffff; /* for E5G slot */
+ zb_tbl1 = 0xda5a5a5a; /* for E2G slot */
+ }
+ rtw89_write32(rtwdev, R_BTC_ZB_COEX_TBL_0, zb_tbl0);
+ rtw89_write32(rtwdev, R_BTC_ZB_COEX_TBL_1, zb_tbl1);
+}
+
+static void _action_common(struct rtw89_dev *rtwdev)
+{
+ struct rtw89_btc *btc = &rtwdev->btc;
+ struct rtw89_btc_wl_info *wl = &btc->cx.wl;
+ struct rtw89_btc_wl_role_info *rinfo = &wl->role_info;
+ struct rtw89_btc_wl_smap *wl_smap = &wl->status.map;
+ struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
+ struct rtw89_btc_dm *dm = &btc->dm;
+ u32 bt_rom_code_id, bt_fw_ver;
+ u8 i;
+
+ _wl_req_mac(rtwdev, rinfo->pta_req_band);
+ _update_zb_coex_tbl(rtwdev);
_set_btg_ctrl(rtwdev);
_set_wl_preagc_ctrl(rtwdev);
_set_wl_tx_limit(rtwdev);
@@ -6041,7 +6089,10 @@ static void _action_common(struct rtw89_dev *rtwdev)
}
dm->tdma_instant_excute = 0;
dm->lps_ctrl_change = false;
+ wl->role_info.link_mode_chg = 0;
wl->pta_reg_mac_chg = false;
+ dm->pre_agc_chg = false;
+ wl->dbcc_chg = 0;
}
static void _action_by_bt(struct rtw89_dev *rtwdev)
@@ -6407,473 +6458,29 @@ void _update_dbcc_band(struct rtw89_dev *rtwdev, enum rtw89_phy_idx phy_idx)
btc->cx.wl.dbcc_info.op_band[phy_idx];
}
-static void _update_wl_info(struct rtw89_dev *rtwdev)
-{
- struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_link_info *wl_linfo = wl->link_info;
- struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
- struct rtw89_btc_wl_dbcc_info *wl_dinfo = &wl->dbcc_info;
- u8 i, cnt_connect = 0, cnt_connecting = 0, cnt_active = 0;
- u8 cnt_2g = 0, cnt_5g = 0, phy;
- u32 wl_2g_ch[2] = {0}, wl_5g_ch[2] = {0};
- bool b2g = false, b5g = false, client_joined = false;
-
- memset(wl_rinfo, 0, sizeof(*wl_rinfo));
-
- for (i = 0; i < RTW89_PORT_NUM; i++) {
- /* check if role active? */
- if (!wl_linfo[i].active)
- continue;
-
- cnt_active++;
- wl_rinfo->active_role[cnt_active - 1].role = wl_linfo[i].role;
- wl_rinfo->active_role[cnt_active - 1].pid = wl_linfo[i].pid;
- wl_rinfo->active_role[cnt_active - 1].phy = wl_linfo[i].phy;
- wl_rinfo->active_role[cnt_active - 1].band = wl_linfo[i].band;
- wl_rinfo->active_role[cnt_active - 1].noa = (u8)wl_linfo[i].noa;
- wl_rinfo->active_role[cnt_active - 1].connected = 0;
-
- wl->port_id[wl_linfo[i].role] = wl_linfo[i].pid;
-
- phy = wl_linfo[i].phy;
-
- /* check dbcc role */
- if (rtwdev->dbcc_en && phy < RTW89_PHY_NUM) {
- wl_dinfo->role[phy] = wl_linfo[i].role;
- wl_dinfo->op_band[phy] = wl_linfo[i].band;
- _update_dbcc_band(rtwdev, phy);
- _fw_set_drv_info(rtwdev, CXDRVINFO_DBCC);
- }
-
- if (wl_linfo[i].connected == MLME_NO_LINK) {
- continue;
- } else if (wl_linfo[i].connected == MLME_LINKING) {
- cnt_connecting++;
- } else {
- cnt_connect++;
- if ((wl_linfo[i].role == RTW89_WIFI_ROLE_P2P_GO ||
- wl_linfo[i].role == RTW89_WIFI_ROLE_AP) &&
- wl_linfo[i].client_cnt > 1)
- client_joined = true;
- }
-
- wl_rinfo->role_map.val |= BIT(wl_linfo[i].role);
- wl_rinfo->active_role[cnt_active - 1].ch = wl_linfo[i].ch;
- wl_rinfo->active_role[cnt_active - 1].bw = wl_linfo[i].bw;
- wl_rinfo->active_role[cnt_active - 1].connected = 1;
-
- /* only care 2 roles + BT coex */
- if (wl_linfo[i].band != RTW89_BAND_2G) {
- if (cnt_5g <= ARRAY_SIZE(wl_5g_ch) - 1)
- wl_5g_ch[cnt_5g] = wl_linfo[i].ch;
- cnt_5g++;
- b5g = true;
- } else {
- if (cnt_2g <= ARRAY_SIZE(wl_2g_ch) - 1)
- wl_2g_ch[cnt_2g] = wl_linfo[i].ch;
- cnt_2g++;
- b2g = true;
- }
- }
-
- wl_rinfo->connect_cnt = cnt_connect;
-
- /* Be careful to change the following sequence!! */
- if (cnt_connect == 0) {
- wl_rinfo->link_mode = BTC_WLINK_NOLINK;
- wl_rinfo->role_map.role.none = 1;
- } else if (!b2g && b5g) {
- wl_rinfo->link_mode = BTC_WLINK_5G;
- } else if (wl_rinfo->role_map.role.nan) {
- wl_rinfo->link_mode = BTC_WLINK_2G_NAN;
- } else if (cnt_connect > BTC_TDMA_WLROLE_MAX) {
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- } else if (b2g && b5g && cnt_connect == 2) {
- if (rtwdev->dbcc_en) {
- switch (wl_dinfo->role[RTW89_PHY_0]) {
- case RTW89_WIFI_ROLE_STATION:
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- break;
- case RTW89_WIFI_ROLE_P2P_GO:
- wl_rinfo->link_mode = BTC_WLINK_2G_GO;
- break;
- case RTW89_WIFI_ROLE_P2P_CLIENT:
- wl_rinfo->link_mode = BTC_WLINK_2G_GC;
- break;
- case RTW89_WIFI_ROLE_AP:
- wl_rinfo->link_mode = BTC_WLINK_2G_AP;
- break;
- default:
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- break;
- }
- } else {
- wl_rinfo->link_mode = BTC_WLINK_25G_MCC;
- }
- } else if (!b5g && cnt_connect == 2) {
- if (wl_rinfo->role_map.role.station &&
- (wl_rinfo->role_map.role.p2p_go ||
- wl_rinfo->role_map.role.p2p_gc ||
- wl_rinfo->role_map.role.ap)) {
- if (wl_2g_ch[0] == wl_2g_ch[1])
- wl_rinfo->link_mode = BTC_WLINK_2G_SCC;
- else
- wl_rinfo->link_mode = BTC_WLINK_2G_MCC;
- } else {
- wl_rinfo->link_mode = BTC_WLINK_2G_MCC;
- }
- } else if (!b5g && cnt_connect == 1) {
- if (wl_rinfo->role_map.role.station)
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- else if (wl_rinfo->role_map.role.ap)
- wl_rinfo->link_mode = BTC_WLINK_2G_AP;
- else if (wl_rinfo->role_map.role.p2p_go)
- wl_rinfo->link_mode = BTC_WLINK_2G_GO;
- else if (wl_rinfo->role_map.role.p2p_gc)
- wl_rinfo->link_mode = BTC_WLINK_2G_GC;
- else
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- }
-
- /* if no client_joined, don't care P2P-GO/AP role */
- if (wl_rinfo->role_map.role.p2p_go || wl_rinfo->role_map.role.ap) {
- if (!client_joined) {
- if (wl_rinfo->link_mode == BTC_WLINK_2G_SCC ||
- wl_rinfo->link_mode == BTC_WLINK_2G_MCC) {
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- wl_rinfo->connect_cnt = 1;
- } else if (wl_rinfo->link_mode == BTC_WLINK_2G_GO ||
- wl_rinfo->link_mode == BTC_WLINK_2G_AP) {
- wl_rinfo->link_mode = BTC_WLINK_NOLINK;
- wl_rinfo->connect_cnt = 0;
- }
- }
- }
-
- rtw89_debug(rtwdev, RTW89_DBG_BTC,
- "[BTC], cnt_connect = %d, connecting = %d, link_mode = %d\n",
- cnt_connect, cnt_connecting, wl_rinfo->link_mode);
-
- _fw_set_drv_info(rtwdev, CXDRVINFO_ROLE);
-}
-
-static void _update_wl_info_v1(struct rtw89_dev *rtwdev)
-{
- struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_link_info *wl_linfo = wl->link_info;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo = &wl->role_info_v1;
- struct rtw89_btc_wl_dbcc_info *wl_dinfo = &wl->dbcc_info;
- u8 cnt_connect = 0, cnt_connecting = 0, cnt_active = 0;
- u8 cnt_2g = 0, cnt_5g = 0, phy;
- u32 wl_2g_ch[2] = {}, wl_5g_ch[2] = {};
- bool b2g = false, b5g = false, client_joined = false;
- u8 i;
-
- memset(wl_rinfo, 0, sizeof(*wl_rinfo));
-
- for (i = 0; i < RTW89_PORT_NUM; i++) {
- if (!wl_linfo[i].active)
- continue;
-
- cnt_active++;
- wl_rinfo->active_role_v1[cnt_active - 1].role = wl_linfo[i].role;
- wl_rinfo->active_role_v1[cnt_active - 1].pid = wl_linfo[i].pid;
- wl_rinfo->active_role_v1[cnt_active - 1].phy = wl_linfo[i].phy;
- wl_rinfo->active_role_v1[cnt_active - 1].band = wl_linfo[i].band;
- wl_rinfo->active_role_v1[cnt_active - 1].noa = (u8)wl_linfo[i].noa;
- wl_rinfo->active_role_v1[cnt_active - 1].connected = 0;
-
- wl->port_id[wl_linfo[i].role] = wl_linfo[i].pid;
-
- phy = wl_linfo[i].phy;
-
- if (rtwdev->dbcc_en && phy < RTW89_PHY_NUM) {
- wl_dinfo->role[phy] = wl_linfo[i].role;
- wl_dinfo->op_band[phy] = wl_linfo[i].band;
- _update_dbcc_band(rtwdev, phy);
- _fw_set_drv_info(rtwdev, CXDRVINFO_DBCC);
- }
-
- if (wl_linfo[i].connected == MLME_NO_LINK) {
- continue;
- } else if (wl_linfo[i].connected == MLME_LINKING) {
- cnt_connecting++;
- } else {
- cnt_connect++;
- if ((wl_linfo[i].role == RTW89_WIFI_ROLE_P2P_GO ||
- wl_linfo[i].role == RTW89_WIFI_ROLE_AP) &&
- wl_linfo[i].client_cnt > 1)
- client_joined = true;
- }
-
- wl_rinfo->role_map.val |= BIT(wl_linfo[i].role);
- wl_rinfo->active_role_v1[cnt_active - 1].ch = wl_linfo[i].ch;
- wl_rinfo->active_role_v1[cnt_active - 1].bw = wl_linfo[i].bw;
- wl_rinfo->active_role_v1[cnt_active - 1].connected = 1;
-
- /* only care 2 roles + BT coex */
- if (wl_linfo[i].band != RTW89_BAND_2G) {
- if (cnt_5g <= ARRAY_SIZE(wl_5g_ch) - 1)
- wl_5g_ch[cnt_5g] = wl_linfo[i].ch;
- cnt_5g++;
- b5g = true;
- } else {
- if (cnt_2g <= ARRAY_SIZE(wl_2g_ch) - 1)
- wl_2g_ch[cnt_2g] = wl_linfo[i].ch;
- cnt_2g++;
- b2g = true;
- }
- }
-
- wl_rinfo->connect_cnt = cnt_connect;
-
- /* Be careful to change the following sequence!! */
- if (cnt_connect == 0) {
- wl_rinfo->link_mode = BTC_WLINK_NOLINK;
- wl_rinfo->role_map.role.none = 1;
- } else if (!b2g && b5g) {
- wl_rinfo->link_mode = BTC_WLINK_5G;
- } else if (wl_rinfo->role_map.role.nan) {
- wl_rinfo->link_mode = BTC_WLINK_2G_NAN;
- } else if (cnt_connect > BTC_TDMA_WLROLE_MAX) {
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- } else if (b2g && b5g && cnt_connect == 2) {
- if (rtwdev->dbcc_en) {
- switch (wl_dinfo->role[RTW89_PHY_0]) {
- case RTW89_WIFI_ROLE_STATION:
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- break;
- case RTW89_WIFI_ROLE_P2P_GO:
- wl_rinfo->link_mode = BTC_WLINK_2G_GO;
- break;
- case RTW89_WIFI_ROLE_P2P_CLIENT:
- wl_rinfo->link_mode = BTC_WLINK_2G_GC;
- break;
- case RTW89_WIFI_ROLE_AP:
- wl_rinfo->link_mode = BTC_WLINK_2G_AP;
- break;
- default:
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- break;
- }
- } else {
- wl_rinfo->link_mode = BTC_WLINK_25G_MCC;
- }
- } else if (!b5g && cnt_connect == 2) {
- if (wl_rinfo->role_map.role.station &&
- (wl_rinfo->role_map.role.p2p_go ||
- wl_rinfo->role_map.role.p2p_gc ||
- wl_rinfo->role_map.role.ap)) {
- if (wl_2g_ch[0] == wl_2g_ch[1])
- wl_rinfo->link_mode = BTC_WLINK_2G_SCC;
- else
- wl_rinfo->link_mode = BTC_WLINK_2G_MCC;
- } else {
- wl_rinfo->link_mode = BTC_WLINK_2G_MCC;
- }
- } else if (!b5g && cnt_connect == 1) {
- if (wl_rinfo->role_map.role.station)
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- else if (wl_rinfo->role_map.role.ap)
- wl_rinfo->link_mode = BTC_WLINK_2G_AP;
- else if (wl_rinfo->role_map.role.p2p_go)
- wl_rinfo->link_mode = BTC_WLINK_2G_GO;
- else if (wl_rinfo->role_map.role.p2p_gc)
- wl_rinfo->link_mode = BTC_WLINK_2G_GC;
- else
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- }
-
- /* if no client_joined, don't care P2P-GO/AP role */
- if (wl_rinfo->role_map.role.p2p_go || wl_rinfo->role_map.role.ap) {
- if (!client_joined) {
- if (wl_rinfo->link_mode == BTC_WLINK_2G_SCC ||
- wl_rinfo->link_mode == BTC_WLINK_2G_MCC) {
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- wl_rinfo->connect_cnt = 1;
- } else if (wl_rinfo->link_mode == BTC_WLINK_2G_GO ||
- wl_rinfo->link_mode == BTC_WLINK_2G_AP) {
- wl_rinfo->link_mode = BTC_WLINK_NOLINK;
- wl_rinfo->connect_cnt = 0;
- }
- }
- }
-
- rtw89_debug(rtwdev, RTW89_DBG_BTC,
- "[BTC], cnt_connect = %d, connecting = %d, link_mode = %d\n",
- cnt_connect, cnt_connecting, wl_rinfo->link_mode);
-
- _fw_set_drv_info(rtwdev, CXDRVINFO_ROLE);
-}
-
-static void _update_wl_info_v2(struct rtw89_dev *rtwdev)
-{
- struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_link_info *wl_linfo = wl->link_info;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo = &wl->role_info_v2;
- struct rtw89_btc_wl_dbcc_info *wl_dinfo = &wl->dbcc_info;
- u8 cnt_connect = 0, cnt_connecting = 0, cnt_active = 0;
- u8 cnt_2g = 0, cnt_5g = 0, phy;
- u32 wl_2g_ch[2] = {}, wl_5g_ch[2] = {};
- bool b2g = false, b5g = false, client_joined = false;
- u8 i;
-
- memset(wl_rinfo, 0, sizeof(*wl_rinfo));
-
- for (i = 0; i < RTW89_PORT_NUM; i++) {
- if (!wl_linfo[i].active)
- continue;
-
- cnt_active++;
- wl_rinfo->active_role_v2[cnt_active - 1].role = wl_linfo[i].role;
- wl_rinfo->active_role_v2[cnt_active - 1].pid = wl_linfo[i].pid;
- wl_rinfo->active_role_v2[cnt_active - 1].phy = wl_linfo[i].phy;
- wl_rinfo->active_role_v2[cnt_active - 1].band = wl_linfo[i].band;
- wl_rinfo->active_role_v2[cnt_active - 1].noa = (u8)wl_linfo[i].noa;
- wl_rinfo->active_role_v2[cnt_active - 1].connected = 0;
-
- wl->port_id[wl_linfo[i].role] = wl_linfo[i].pid;
-
- phy = wl_linfo[i].phy;
-
- if (rtwdev->dbcc_en && phy < RTW89_PHY_NUM) {
- wl_dinfo->role[phy] = wl_linfo[i].role;
- wl_dinfo->op_band[phy] = wl_linfo[i].band;
- _update_dbcc_band(rtwdev, phy);
- _fw_set_drv_info(rtwdev, CXDRVINFO_DBCC);
- }
-
- if (wl_linfo[i].connected == MLME_NO_LINK) {
- continue;
- } else if (wl_linfo[i].connected == MLME_LINKING) {
- cnt_connecting++;
- } else {
- cnt_connect++;
- if ((wl_linfo[i].role == RTW89_WIFI_ROLE_P2P_GO ||
- wl_linfo[i].role == RTW89_WIFI_ROLE_AP) &&
- wl_linfo[i].client_cnt > 1)
- client_joined = true;
- }
-
- wl_rinfo->role_map.val |= BIT(wl_linfo[i].role);
- wl_rinfo->active_role_v2[cnt_active - 1].ch = wl_linfo[i].ch;
- wl_rinfo->active_role_v2[cnt_active - 1].bw = wl_linfo[i].bw;
- wl_rinfo->active_role_v2[cnt_active - 1].connected = 1;
-
- /* only care 2 roles + BT coex */
- if (wl_linfo[i].band != RTW89_BAND_2G) {
- if (cnt_5g <= ARRAY_SIZE(wl_5g_ch) - 1)
- wl_5g_ch[cnt_5g] = wl_linfo[i].ch;
- cnt_5g++;
- b5g = true;
- } else {
- if (cnt_2g <= ARRAY_SIZE(wl_2g_ch) - 1)
- wl_2g_ch[cnt_2g] = wl_linfo[i].ch;
- cnt_2g++;
- b2g = true;
- }
- }
-
- wl_rinfo->connect_cnt = cnt_connect;
-
- /* Be careful to change the following sequence!! */
- if (cnt_connect == 0) {
- wl_rinfo->link_mode = BTC_WLINK_NOLINK;
- wl_rinfo->role_map.role.none = 1;
- } else if (!b2g && b5g) {
- wl_rinfo->link_mode = BTC_WLINK_5G;
- } else if (wl_rinfo->role_map.role.nan) {
- wl_rinfo->link_mode = BTC_WLINK_2G_NAN;
- } else if (cnt_connect > BTC_TDMA_WLROLE_MAX) {
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- } else if (b2g && b5g && cnt_connect == 2) {
- if (rtwdev->dbcc_en) {
- switch (wl_dinfo->role[RTW89_PHY_0]) {
- case RTW89_WIFI_ROLE_STATION:
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- break;
- case RTW89_WIFI_ROLE_P2P_GO:
- wl_rinfo->link_mode = BTC_WLINK_2G_GO;
- break;
- case RTW89_WIFI_ROLE_P2P_CLIENT:
- wl_rinfo->link_mode = BTC_WLINK_2G_GC;
- break;
- case RTW89_WIFI_ROLE_AP:
- wl_rinfo->link_mode = BTC_WLINK_2G_AP;
- break;
- default:
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- break;
- }
- } else {
- wl_rinfo->link_mode = BTC_WLINK_25G_MCC;
- }
- } else if (!b5g && cnt_connect == 2) {
- if (wl_rinfo->role_map.role.station &&
- (wl_rinfo->role_map.role.p2p_go ||
- wl_rinfo->role_map.role.p2p_gc ||
- wl_rinfo->role_map.role.ap)) {
- if (wl_2g_ch[0] == wl_2g_ch[1])
- wl_rinfo->link_mode = BTC_WLINK_2G_SCC;
- else
- wl_rinfo->link_mode = BTC_WLINK_2G_MCC;
- } else {
- wl_rinfo->link_mode = BTC_WLINK_2G_MCC;
- }
- } else if (!b5g && cnt_connect == 1) {
- if (wl_rinfo->role_map.role.station)
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- else if (wl_rinfo->role_map.role.ap)
- wl_rinfo->link_mode = BTC_WLINK_2G_AP;
- else if (wl_rinfo->role_map.role.p2p_go)
- wl_rinfo->link_mode = BTC_WLINK_2G_GO;
- else if (wl_rinfo->role_map.role.p2p_gc)
- wl_rinfo->link_mode = BTC_WLINK_2G_GC;
- else
- wl_rinfo->link_mode = BTC_WLINK_OTHER;
- }
-
- /* if no client_joined, don't care P2P-GO/AP role */
- if (wl_rinfo->role_map.role.p2p_go || wl_rinfo->role_map.role.ap) {
- if (!client_joined) {
- if (wl_rinfo->link_mode == BTC_WLINK_2G_SCC ||
- wl_rinfo->link_mode == BTC_WLINK_2G_MCC) {
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- wl_rinfo->connect_cnt = 1;
- } else if (wl_rinfo->link_mode == BTC_WLINK_2G_GO ||
- wl_rinfo->link_mode == BTC_WLINK_2G_AP) {
- wl_rinfo->link_mode = BTC_WLINK_NOLINK;
- wl_rinfo->connect_cnt = 0;
- }
- }
- }
-
- rtw89_debug(rtwdev, RTW89_DBG_BTC,
- "[BTC], cnt_connect = %d, connecting = %d, link_mode = %d\n",
- cnt_connect, cnt_connecting, wl_rinfo->link_mode);
-
- _fw_set_drv_info(rtwdev, CXDRVINFO_ROLE);
-}
-
#define BTC_CHK_HANG_MAX 3
#define BTC_SCB_INV_VALUE GENMASK(31, 0)
-static u8 _get_role_link_mode(u8 role)
+static u8 _get_role_link_mode(struct rtw89_btc_wl_role_info *r, u8 role, bool notv10)
{
switch (role) {
case RTW89_WIFI_ROLE_STATION:
- return BTC_WLINK_2G_STA;
+ default:
+ if (notv10)
+ r->link_mode_v0 = BTC_WLINK_V0_2G_STA;
+ return BTC_WLINK_STA;
case RTW89_WIFI_ROLE_P2P_GO:
- return BTC_WLINK_2G_GO;
+ if (notv10)
+ r->link_mode_v0 = BTC_WLINK_V0_2G_GO;
+ return BTC_WLINK_GO;
case RTW89_WIFI_ROLE_P2P_CLIENT:
- return BTC_WLINK_2G_GC;
+ if (notv10)
+ r->link_mode_v0 = BTC_WLINK_V0_2G_GC;
+ return BTC_WLINK_GC;
case RTW89_WIFI_ROLE_AP:
- return BTC_WLINK_2G_AP;
- default:
- return BTC_WLINK_OTHER;
+ if (notv10)
+ r->link_mode_v0 = BTC_WLINK_V0_2G_AP;
+ return BTC_WLINK_AP;
}
}
@@ -6891,13 +6498,13 @@ static bool _chk_role_ch_group(const struct rtw89_btc_chdef *r1,
}
static u8 _chk_dbcc(struct rtw89_dev *rtwdev, struct rtw89_btc_chdef *ch,
- u8 *phy, u8 *role, u8 link_cnt)
+ u8 *phy, u8 *role, u8 link_cnt, bool notv10)
{
struct rtw89_btc_wl_info *wl = &rtwdev->btc.cx.wl;
- struct rtw89_btc_wl_role_info_v7 *rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *rinfo_v8 = &wl->role_info_v8;
+ struct rtw89_btc_wl_role_info *rinfo = &wl->role_info;
bool is_2g_ch_exist = false, is_multi_role_in_2g_phy = false;
- u8 j, k, dbcc_2g_cid, dbcc_2g_cid2, dbcc_2g_phy, pta_req_band;
+ u8 j, k, dbcc_2g_cid = 0, dbcc_2g_cid2 = 0;
+ u8 mode;
/* find out the 2G-PHY by connect-id ->ch */
for (j = 0; j < link_cnt; j++) {
@@ -6908,34 +6515,31 @@ static u8 _chk_dbcc(struct rtw89_dev *rtwdev, struct rtw89_btc_chdef *ch,
}
/* If no any 2G-port exist, it's impossible because 5G-exclude */
- if (!is_2g_ch_exist)
- return BTC_WLINK_5G;
+ if (!is_2g_ch_exist) {
+ mode = BTC_WLINK_SB_MCC;
+ if (notv10)
+ rinfo->link_mode_v0 = BTC_WLINK_V0_5G;
+ return mode;
+ }
dbcc_2g_cid = j;
- dbcc_2g_phy = phy[dbcc_2g_cid];
+ rinfo->dbcc_2g_phy = phy[dbcc_2g_cid];
- if (dbcc_2g_phy == RTW89_PHY_1)
- pta_req_band = RTW89_PHY_1;
+ if (rinfo->dbcc_2g_phy == RTW89_PHY_1)
+ rinfo->pta_req_band = RTW89_PHY_1;
else
- pta_req_band = RTW89_PHY_0;
-
- if (rtwdev->btc.ver->fwlrole == 7) {
- rinfo_v7->dbcc_2g_phy = dbcc_2g_phy;
- } else if (rtwdev->btc.ver->fwlrole == 8) {
- rinfo_v8->dbcc_2g_phy = dbcc_2g_phy;
- rinfo_v8->pta_req_band = pta_req_band;
- }
+ rinfo->pta_req_band = RTW89_PHY_0;
/* connect_cnt <= 2 */
if (link_cnt < BTC_TDMA_WLROLE_MAX)
- return (_get_role_link_mode((role[dbcc_2g_cid])));
+ return _get_role_link_mode(rinfo, role[dbcc_2g_cid], notv10);
/* find the other-port in the 2G-PHY, ex: PHY-0:6G, PHY1: mcc/scc */
for (k = 0; k < link_cnt; k++) {
if (k == dbcc_2g_cid)
continue;
- if (phy[k] == dbcc_2g_phy) {
+ if (phy[k] == rinfo->dbcc_2g_phy) {
is_multi_role_in_2g_phy = true;
dbcc_2g_cid2 = k;
break;
@@ -6944,319 +6548,151 @@ static u8 _chk_dbcc(struct rtw89_dev *rtwdev, struct rtw89_btc_chdef *ch,
/* Single-role in 2G-PHY */
if (!is_multi_role_in_2g_phy)
- return (_get_role_link_mode(role[dbcc_2g_cid]));
+ return _get_role_link_mode(rinfo, role[dbcc_2g_cid], notv10);
/* 2-role in 2G-PHY */
- if (ch[dbcc_2g_cid2].center_ch > 14)
- return BTC_WLINK_25G_MCC;
- else if (_chk_role_ch_group(&ch[dbcc_2g_cid], &ch[dbcc_2g_cid2]))
- return BTC_WLINK_2G_SCC;
- else
- return BTC_WLINK_2G_MCC;
-}
-
-static void _update_role_link_mode(struct rtw89_dev *rtwdev,
- bool client_joined, u32 noa)
-{
- struct rtw89_btc_wl_role_info_v8 *rinfo_v8 = &rtwdev->btc.cx.wl.role_info_v8;
- struct rtw89_btc_wl_role_info_v7 *rinfo_v7 = &rtwdev->btc.cx.wl.role_info_v7;
- u8 role_ver = rtwdev->btc.ver->fwlrole;
- u32 type = BTC_WLMROLE_NONE, dur = 0;
- u8 link_mode, connect_cnt;
- u32 wl_role;
-
- if (role_ver == 7) {
- wl_role = rinfo_v7->role_map;
- link_mode = rinfo_v7->link_mode;
- connect_cnt = rinfo_v7->connect_cnt;
- } else if (role_ver == 8) {
- wl_role = rinfo_v8->role_map;
- link_mode = rinfo_v8->link_mode;
- connect_cnt = rinfo_v8->connect_cnt;
+ if (ch[dbcc_2g_cid2].center_ch > 14) {
+ if (notv10)
+ rinfo->link_mode_v0 = BTC_WLINK_V0_25G_MCC;
+ return BTC_WLINK_DB_MCC;
+ } else if (_chk_role_ch_group(&ch[dbcc_2g_cid], &ch[dbcc_2g_cid2])) {
+ if (notv10)
+ rinfo->link_mode_v0 = BTC_WLINK_V0_2G_SCC;
+ return BTC_WLINK_SCC;
} else {
- return;
- }
-
- /* if no client_joined, don't care P2P-GO/AP role */
- if (((wl_role & BIT(RTW89_WIFI_ROLE_P2P_GO)) ||
- (wl_role & BIT(RTW89_WIFI_ROLE_AP))) && !client_joined) {
- if (link_mode == BTC_WLINK_2G_SCC) {
- if (role_ver == 7) {
- rinfo_v7->link_mode = BTC_WLINK_2G_STA;
- rinfo_v7->connect_cnt--;
- } else if (role_ver == 8) {
- rinfo_v8->link_mode = BTC_WLINK_2G_STA;
- rinfo_v8->connect_cnt--;
- }
- } else if (link_mode == BTC_WLINK_2G_GO ||
- link_mode == BTC_WLINK_2G_AP) {
- if (role_ver == 7) {
- rinfo_v7->link_mode = BTC_WLINK_NOLINK;
- rinfo_v7->connect_cnt--;
- } else if (role_ver == 8) {
- rinfo_v8->link_mode = BTC_WLINK_NOLINK;
- rinfo_v8->connect_cnt--;
- }
- }
- }
-
- /* Identify 2-Role type */
- if (connect_cnt >= 2 &&
- (link_mode == BTC_WLINK_2G_SCC ||
- link_mode == BTC_WLINK_2G_MCC ||
- link_mode == BTC_WLINK_25G_MCC ||
- link_mode == BTC_WLINK_5G)) {
- if ((wl_role & BIT(RTW89_WIFI_ROLE_P2P_GO)) ||
- (wl_role & BIT(RTW89_WIFI_ROLE_AP)))
- type = noa ? BTC_WLMROLE_STA_GO_NOA : BTC_WLMROLE_STA_GO;
- else if (wl_role & BIT(RTW89_WIFI_ROLE_P2P_CLIENT))
- type = noa ? BTC_WLMROLE_STA_GC_NOA : BTC_WLMROLE_STA_GC;
- else
- type = BTC_WLMROLE_STA_STA;
-
- dur = noa;
- }
-
- if (role_ver == 7) {
- rinfo_v7->mrole_type = type;
- rinfo_v7->mrole_noa_duration = dur;
- } else if (role_ver == 8) {
- rinfo_v8->mrole_type = type;
- rinfo_v8->mrole_noa_duration = dur;
+ if (notv10)
+ rinfo->link_mode_v0 = BTC_WLINK_V0_2G_MCC;
+ return BTC_WLINK_SB_MCC;
}
}
-static void _update_wl_info_v7(struct rtw89_dev *rtwdev, u8 rid)
+static void _update_wl_link_mode(struct rtw89_dev *rtwdev, u8 hw_band, u8 type)
{
- struct rtw89_btc_chdef cid_ch[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER];
struct rtw89_btc *btc = &rtwdev->btc;
+ const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo = &wl->role_info_v7;
- struct rtw89_btc_wl_dbcc_info *wl_dinfo = &wl->dbcc_info;
- struct rtw89_btc_wl_link_info *wl_linfo = wl->link_info;
- struct rtw89_btc_wl_active_role_v7 *act_role = NULL;
- u8 i, mode, cnt = 0, cnt_2g = 0, cnt_5g = 0, phy_now = RTW89_PHY_NUM, phy_dbcc;
- bool b2g = false, b5g = false, client_joined = false, client_inc_2g = false;
- u8 client_cnt_last[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER] = {};
- u8 cid_role[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER] = {};
- u8 cid_phy[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER] = {};
- u8 mac = RTW89_MAC_0, dbcc_2g_phy = RTW89_PHY_0;
- u32 noa_duration = 0;
-
- memset(wl_rinfo, 0, sizeof(*wl_rinfo));
-
- for (i = 0; i < RTW89_PORT_NUM; i++) {
- if (!wl_linfo[i].active || wl_linfo[i].phy >= RTW89_PHY_NUM)
- continue;
-
- act_role = &wl_rinfo->active_role[i];
- act_role->role = wl_linfo[i].role;
-
- /* check if role connect? */
- if (wl_linfo[i].connected == MLME_NO_LINK) {
- act_role->connected = 0;
- continue;
- } else if (wl_linfo[i].connected == MLME_LINKING) {
- continue;
- }
-
- cnt++;
- act_role->connected = 1;
- act_role->pid = wl_linfo[i].pid;
- act_role->phy = wl_linfo[i].phy;
- act_role->band = wl_linfo[i].band;
- act_role->ch = wl_linfo[i].ch;
- act_role->bw = wl_linfo[i].bw;
- act_role->noa = wl_linfo[i].noa;
- act_role->noa_dur = wl_linfo[i].noa_duration;
- cid_ch[cnt - 1] = wl_linfo[i].chdef;
- cid_phy[cnt - 1] = wl_linfo[i].phy;
- cid_role[cnt - 1] = wl_linfo[i].role;
- wl_rinfo->role_map |= BIT(wl_linfo[i].role);
-
- if (rid == i)
- phy_now = act_role->phy;
-
- if (wl_linfo[i].role == RTW89_WIFI_ROLE_P2P_GO ||
- wl_linfo[i].role == RTW89_WIFI_ROLE_AP) {
- if (wl_linfo[i].client_cnt > 1)
- client_joined = true;
- if (client_cnt_last[i] < wl_linfo[i].client_cnt &&
- wl_linfo[i].chdef.band == RTW89_BAND_2G)
- client_inc_2g = true;
- act_role->client_cnt = wl_linfo[i].client_cnt;
- } else {
- act_role->client_cnt = 0;
- }
-
- if (act_role->noa && act_role->noa_dur > 0)
- noa_duration = act_role->noa_dur;
-
- if (rtwdev->dbcc_en) {
- phy_dbcc = wl_linfo[i].phy;
- wl_dinfo->role[phy_dbcc] |= BIT(wl_linfo[i].role);
- wl_dinfo->op_band[phy_dbcc] = wl_linfo[i].chdef.band;
- }
-
- if (wl_linfo[i].chdef.band != RTW89_BAND_2G) {
- cnt_5g++;
- b5g = true;
- } else {
- if (((wl_linfo[i].role == RTW89_WIFI_ROLE_P2P_GO ||
- wl_linfo[i].role == RTW89_WIFI_ROLE_AP) &&
- client_joined) ||
- wl_linfo[i].role == RTW89_WIFI_ROLE_P2P_CLIENT)
- wl_rinfo->p2p_2g = 1;
-
- if ((wl_linfo[i].mode & BIT(BTC_WL_MODE_11B)) ||
- (wl_linfo[i].mode & BIT(BTC_WL_MODE_11G)))
- wl->bg_mode = 1;
- else if (wl_linfo[i].mode & BIT(BTC_WL_MODE_HE))
- wl->he_mode = true;
-
- cnt_2g++;
- b2g = true;
- }
-
- if (act_role->band == RTW89_BAND_5G && act_role->ch >= 100)
- wl->is_5g_hi_channel = 1;
- else
- wl->is_5g_hi_channel = 0;
- }
-
- wl_rinfo->connect_cnt = cnt;
- wl->client_cnt_inc_2g = client_inc_2g;
-
- if (cnt == 0) {
- mode = BTC_WLINK_NOLINK;
- wl_rinfo->role_map = BIT(RTW89_WIFI_ROLE_NONE);
- } else if (!b2g && b5g) {
- mode = BTC_WLINK_5G;
- } else if (wl_rinfo->role_map & BIT(RTW89_WIFI_ROLE_NAN)) {
- mode = BTC_WLINK_2G_NAN;
- } else if (cnt > BTC_TDMA_WLROLE_MAX) {
- mode = BTC_WLINK_OTHER;
- } else if (rtwdev->dbcc_en) {
- mode = _chk_dbcc(rtwdev, cid_ch, cid_phy, cid_role, cnt);
-
- /* correct 2G-located PHY band for gnt ctrl */
- if (dbcc_2g_phy < RTW89_PHY_NUM)
- wl_dinfo->op_band[dbcc_2g_phy] = RTW89_BAND_2G;
- } else if (b2g && b5g && cnt == 2) {
- mode = BTC_WLINK_25G_MCC;
- } else if (!b5g && cnt == 2) { /* cnt_connect = 2 */
- if (_chk_role_ch_group(&cid_ch[0], &cid_ch[cnt - 1]))
- mode = BTC_WLINK_2G_SCC;
- else
- mode = BTC_WLINK_2G_MCC;
- } else if (!b5g && cnt == 1) { /* cnt_connect = 1 */
- mode = _get_role_link_mode(cid_role[0]);
- } else {
- mode = BTC_WLINK_NOLINK;
- }
-
- wl_rinfo->link_mode = mode;
- _update_role_link_mode(rtwdev, client_joined, noa_duration);
-
- /* todo DBCC related event */
- rtw89_debug(rtwdev, RTW89_DBG_BTC, "[BTC] wl_info phy_now=%d\n", phy_now);
- rtw89_debug(rtwdev, RTW89_DBG_BTC,
- "[BTC] rlink cnt_2g=%d cnt_5g=%d\n", cnt_2g, cnt_5g);
-
- if (wl_rinfo->dbcc_en != rtwdev->dbcc_en) {
- wl_rinfo->dbcc_chg = 1;
- wl_rinfo->dbcc_en = rtwdev->dbcc_en;
- wl->wcnt[BTC_WCNT_DBCC_CHG]++;
- }
-
- if (rtwdev->dbcc_en) {
- wl_rinfo->dbcc_2g_phy = dbcc_2g_phy;
-
- if (dbcc_2g_phy == RTW89_PHY_1)
- mac = RTW89_MAC_1;
-
- _update_dbcc_band(rtwdev, RTW89_PHY_0);
- _update_dbcc_band(rtwdev, RTW89_PHY_1);
- }
- _wl_req_mac(rtwdev, mac);
- _fw_set_drv_info(rtwdev, CXDRVINFO_ROLE);
-}
-
-static u8 _update_wl_link_mode(struct rtw89_dev *rtwdev, u8 hw_band, u8 type)
-{
- struct rtw89_btc_wl_info *wl = &rtwdev->btc.cx.wl;
struct rtw89_btc_wl_mlo_info *mlo_info = &wl->mlo_info;
- u8 mode = BTC_WLINK_NOLINK;
+ struct rtw89_btc_wl_role_info *r = &wl->role_info;
+ u8 p2p_exist = wl->role_info.p2p_exist;
+ if (hw_band == RTW89_PHY_1)
+ p2p_exist = wl->role_info.p2p_exist_hb1;
+
+ /* MLD: nLmR --> 2L1R: 2-Link by 1-RF, 2L2R: 2-link by 2-RF */
switch (type) {
case RTW89_MR_WTYPE_NONE: /* no-link */
- mode = BTC_WLINK_NOLINK;
+ r->link_mode = BTC_WLINK_NOLINK;
break;
case RTW89_MR_WTYPE_NONMLD: /* Non_MLO 1-role 2+0/0+2 */
case RTW89_MR_WTYPE_MLD1L1R: /* MLO only-1 link 2+0/0+2 */
+ if (mlo_info->wmode[hw_band] == RTW89_MR_WMODE_1AP) {
+ r->link_mode = BTC_WLINK_GO;
+ } else if (mlo_info->wmode[hw_band] == RTW89_MR_WMODE_1CLIENT &&
+ p2p_exist) {
+ r->link_mode = BTC_WLINK_GC;
+ } else {
+ r->link_mode = BTC_WLINK_STA;
+ }
+
+ if (ver->fwlrole >= 10)
+ break;
+
if (mlo_info->hwb_rf_band[hw_band] != RTW89_BAND_2G) {
- mode = BTC_WLINK_5G;
+ r->link_mode_v0 = BTC_WLINK_V0_5G;
} else if (mlo_info->wmode[hw_band] == RTW89_MR_WMODE_1AP) {
- mode = BTC_WLINK_2G_GO;
+ r->link_mode_v0 = BTC_WLINK_V0_2G_GO;
} else if (mlo_info->wmode[hw_band] == RTW89_MR_WMODE_1CLIENT) {
- if (wl->role_info_v8.p2p_2g)
- mode = BTC_WLINK_2G_GC;
+ if (wl->role_info.p2p_2g)
+ r->link_mode_v0 = BTC_WLINK_V0_2G_GC;
else
- mode = BTC_WLINK_2G_STA;
+ r->link_mode_v0 = BTC_WLINK_V0_2G_STA;
}
break;
case RTW89_MR_WTYPE_NONMLD_NONMLD: /* Non_MLO 2-role 2+0/0+2 */
case RTW89_MR_WTYPE_MLD1L1R_NONMLD: /* MLO only-1 link + P2P 2+0/0+2 */
+ if (mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_2GHZ_5GHZ ||
+ mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_2GHZ_6GHZ) {
+ r->link_mode = BTC_WLINK_DB_MCC;
+ } else if (mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_2GHZ ||
+ mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_5GHZ ||
+ mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_6GHZ ||
+ mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_5GHZ_6GHZ) {
+ r->link_mode = BTC_WLINK_SB_MCC;
+ } else {
+ r->link_mode = BTC_WLINK_SCC;
+ }
+
+ if (ver->fwlrole >= 10)
+ break;
+
if (mlo_info->hwb_rf_band[hw_band] != RTW89_BAND_2G) {
- mode = BTC_WLINK_5G;
+ r->link_mode_v0 = BTC_WLINK_V0_5G;
} else if (mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_2GHZ_5GHZ ||
mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_2GHZ_6GHZ) {
- mode = BTC_WLINK_25G_MCC;
+ r->link_mode_v0 = BTC_WLINK_V0_25G_MCC;
} else if (mlo_info->ch_type[hw_band] == RTW89_MR_CTX2_2GHZ) {
- mode = BTC_WLINK_2G_MCC;
+ r->link_mode_v0 = BTC_WLINK_V0_2G_MCC;
} else if (mlo_info->ch_type[hw_band] == RTW89_MR_CTX1_2GHZ) {
- mode = BTC_WLINK_2G_SCC;
+ r->link_mode_v0 = BTC_WLINK_V0_2G_SCC;
}
break;
case RTW89_MR_WTYPE_MLD2L1R: /* MLO_MLSR 2+0/0+2 */
+ if (p2p_exist) /* MLO_MLSR only support STA/GC */
+ r->link_mode = BTC_WLINK_GC;
+ else
+ r->link_mode = BTC_WLINK_STA;
+
+ if (ver->fwlrole >= 10)
+ break;
+
if (mlo_info->hwb_rf_band[hw_band] != RTW89_BAND_2G)
- mode = BTC_WLINK_5G;
- else if (wl->role_info_v8.p2p_2g)
- mode = BTC_WLINK_2G_GC;
+ r->link_mode_v0 = BTC_WLINK_V0_5G;
+ else if (wl->role_info.p2p_2g)
+ r->link_mode_v0 = BTC_WLINK_V0_2G_GC;
else
- mode = BTC_WLINK_2G_STA;
+ r->link_mode_v0 = BTC_WLINK_V0_2G_STA;
break;
case RTW89_MR_WTYPE_MLD2L1R_NONMLD: /* MLO_MLSR + P2P 2+0/0+2 */
- case RTW89_MR_WTYPE_MLD2L2R_NONMLD: /* MLO_MLMR + P2P 1+1/2+2 */
- /* driver may doze 1-link to
+ case RTW89_MR_WTYPE_MLD2L2R_NONMLD: /* MLO_MLMR + P2P 1+1/2+2*/
+ /* driver may doze 1-link (1+1) or 2+0->0+2->1+1
* 2G+5G -> TDMA slot switch by E2G/E5G
* 5G only -> TDMA slot switch by E5G
*/
- mode = BTC_WLINK_25G_MCC;
+ r->link_mode = BTC_WLINK_DB_MCC;
+
+ if (ver->fwlrole >= 10)
+ break;
+
+ r->link_mode_v0 = BTC_WLINK_V0_25G_MCC;
break;
case RTW89_MR_WTYPE_MLD2L2R: /* MLO_MLMR 1+1/2+2 */
+ /* MLMR only support STA now (2024) */
+ r->link_mode = BTC_WLINK_STA;
+
+ if (ver->fwlrole >= 10)
+ break;
+
if (mlo_info->hwb_rf_band[hw_band] != RTW89_BAND_2G) {
- mode = BTC_WLINK_5G;
+ r->link_mode_v0 = BTC_WLINK_V0_5G;
} else if (mlo_info->wmode[hw_band] == RTW89_MR_WMODE_1AP) {
- mode = BTC_WLINK_2G_GO;
+ r->link_mode_v0 = BTC_WLINK_V0_2G_GO;
} else if (mlo_info->wmode[hw_band] == RTW89_MR_WMODE_1CLIENT) {
- if (wl->role_info_v8.p2p_2g)
- mode = BTC_WLINK_2G_GC;
+ if (wl->role_info.p2p_2g)
+ r->link_mode_v0 = BTC_WLINK_V0_2G_GC;
else
- mode = BTC_WLINK_2G_STA;
+ r->link_mode_v0 = BTC_WLINK_V0_2G_STA;
}
break;
}
- return mode;
}
-static void _update_wl_mlo_info(struct rtw89_dev *rtwdev)
+static void _update_wl_mlo_info(struct rtw89_dev *rtwdev, u8 hw_band)
{
struct rtw89_btc_wl_info *wl = &rtwdev->btc.cx.wl;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo = &wl->role_info_v8;
+ struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
struct rtw89_btc_wl_mlo_info *mlo_info = &wl->mlo_info;
struct rtw89_mr_chanctx_info qinfo;
- u8 track_band = RTW89_PHY_0;
+ struct rtw89_chanctx *ch;
u8 rf_band = RTW89_BAND_2G;
u8 i, type;
@@ -7265,19 +6701,46 @@ static void _update_wl_mlo_info(struct rtw89_dev *rtwdev)
memset(&qinfo, 0, sizeof(qinfo));
rtw89_query_mr_chanctx_info(rtwdev, i, &qinfo);
+
+ switch (qinfo.ctxtype) {
+ default:
+ mlo_info->hwb_rf_band[i] = 0;
+ break;
+ case RTW89_MR_CTX1_2GHZ:
+ case RTW89_MR_CTX2_2GHZ:
+ mlo_info->hwb_rf_band[i] = BIT(RTW89_BAND_2G);
+ break;
+ case RTW89_MR_CTX1_5GHZ:
+ case RTW89_MR_CTX2_5GHZ:
+ mlo_info->hwb_rf_band[i] = BIT(RTW89_BAND_5G);
+ break;
+ case RTW89_MR_CTX1_6GHZ:
+ case RTW89_MR_CTX2_6GHZ:
+ mlo_info->hwb_rf_band[i] = BIT(RTW89_BAND_6G);
+ break;
+ case RTW89_MR_CTX2_2GHZ_5GHZ:
+ mlo_info->hwb_rf_band[i] = BIT(RTW89_BAND_2G) |
+ BIT(RTW89_BAND_5G);
+ break;
+ case RTW89_MR_CTX2_2GHZ_6GHZ:
+ mlo_info->hwb_rf_band[i] = BIT(RTW89_BAND_2G) |
+ BIT(RTW89_BAND_6G);
+ break;
+ case RTW89_MR_CTX2_5GHZ_6GHZ:
+ mlo_info->hwb_rf_band[i] = BIT(RTW89_BAND_5G) |
+ BIT(RTW89_BAND_6G);
+ break;
+ }
mlo_info->wmode[i] = qinfo.wmode;
mlo_info->ch_type[i] = qinfo.ctxtype;
mlo_info->wtype = qinfo.wtype;
-
- if (mlo_info->ch_type[i] == RTW89_MR_CTX1_5GHZ ||
- mlo_info->ch_type[i] == RTW89_MR_CTX2_5GHZ ||
- mlo_info->ch_type[i] == RTW89_MR_CTX2_5GHZ_6GHZ)
- mlo_info->hwb_rf_band[i] = RTW89_BAND_5G;
- else if (mlo_info->ch_type[i] == RTW89_MR_CTX1_6GHZ ||
- mlo_info->ch_type[i] == RTW89_MR_CTX2_6GHZ)
- mlo_info->hwb_rf_band[i] = RTW89_BAND_6G;
- else /* check if "2G-included" or unknown in each HW-band */
- mlo_info->hwb_rf_band[i] = RTW89_BAND_2G;
+ wl->rf_band_map[i] = mlo_info->hwb_rf_band[i];
+ ch = &rtwdev->hal.chanctx[i];
+ wl->rf_ch_info[i].center_ch = ch->chan.channel;
+ wl->rf_ch_info[i].band = ch->chan.band_type;
+ wl->rf_ch_info[i].chan = ch->chan.channel;
+ wl->rf_ch_info[i].offset = ch->chan.pri_ch_idx;
+ wl->rf_ch_info[i].bw = ch->chan.band_width;
}
mlo_info->link_status = rtwdev->mlo_dbcc_mode;
@@ -7312,71 +6775,64 @@ static void _update_wl_mlo_info(struct rtw89_dev *rtwdev)
default:
case MLO_2_PLUS_0_1RF: /* 2+0 */
case MLO_2_PLUS_0_2RF:
- mlo_info->rf_combination = BTC_MLO_RF_2_PLUS_0;
- track_band = RTW89_MAC_0;
- rf_band = mlo_info->hwb_rf_band[RTW89_MAC_0];
- mlo_info->path_rf_band[BTC_RF_S0] = rf_band;
- mlo_info->path_rf_band[BTC_RF_S1] = rf_band;
-
+ _update_wl_link_mode(rtwdev, RTW89_MAC_0, type);
+ wl_rinfo->link_mode_hb1 = wl_rinfo->link_mode;
wl_rinfo->pta_req_band = RTW89_MAC_0;
wl_rinfo->dbcc_2g_phy = RTW89_PHY_0;
wl_rinfo->dbcc_en = 0;
+
+ rf_band = wl->rf_band_map[RTW89_PHY_0];
+ mlo_info->path_rf_band[BTC_RF_S0] = rf_band;
+ mlo_info->path_rf_band[BTC_RF_S1] = rf_band;
break;
case MLO_0_PLUS_2_1RF: /* 0+2 */
case MLO_0_PLUS_2_2RF:
- mlo_info->rf_combination = BTC_MLO_RF_0_PLUS_2;
- track_band = RTW89_MAC_1;
- rf_band = mlo_info->hwb_rf_band[RTW89_MAC_1];
- mlo_info->path_rf_band[BTC_RF_S0] = rf_band;
- mlo_info->path_rf_band[BTC_RF_S1] = rf_band;
-
+ _update_wl_link_mode(rtwdev, RTW89_MAC_1, type);
+ wl_rinfo->link_mode_hb1 = wl_rinfo->link_mode;
wl_rinfo->pta_req_band = RTW89_MAC_1;
wl_rinfo->dbcc_2g_phy = RTW89_PHY_1;
wl_rinfo->dbcc_en = 0;
+
+ rf_band = wl->rf_band_map[RTW89_PHY_1];
+ mlo_info->path_rf_band[BTC_RF_S0] = rf_band;
+ mlo_info->path_rf_band[BTC_RF_S1] = rf_band;
break;
case MLO_1_PLUS_1_1RF: /* 1+1 */
case MLO_1_PLUS_1_2RF: /* 1+1 */
case MLO_2_PLUS_2_2RF: /* 2+2 */
case DBCC_LEGACY: /* DBCC 1+1 */
- if (mlo_info->link_status == MLO_2_PLUS_2_2RF)
- mlo_info->rf_combination = BTC_MLO_RF_2_PLUS_2;
- else
- mlo_info->rf_combination = BTC_MLO_RF_1_PLUS_1;
-
- if (mlo_info->hwb_rf_band[RTW89_MAC_0] == RTW89_BAND_2G)
- track_band = RTW89_MAC_0;
+ /* Check ch count from ch_type and modify type*/
+ if (mlo_info->ch_type[hw_band] == RTW89_MR_CTX1_2GHZ ||
+ mlo_info->ch_type[hw_band] == RTW89_MR_CTX1_5GHZ ||
+ mlo_info->ch_type[hw_band] == RTW89_MR_CTX1_6GHZ)
+ type = RTW89_MR_WTYPE_NONMLD; /* only 1-role */
else
- track_band = RTW89_MAC_1;
+ type = RTW89_MR_WTYPE_NONMLD_NONMLD;
- mlo_info->path_rf_band[BTC_RF_S0] =
- mlo_info->hwb_rf_band[RTW89_MAC_0];
- mlo_info->path_rf_band[BTC_RF_S1] =
- mlo_info->hwb_rf_band[RTW89_MAC_1];
+ rf_band = wl->rf_band_map[hw_band];
+ _update_wl_link_mode(rtwdev, hw_band, type);
- /* Check ch count from ch_type @ 2.4G HW-band, and modify type */
- if (mlo_info->ch_type[track_band] == RTW89_MR_CTX1_2GHZ)
- type = RTW89_MR_WTYPE_NONMLD; /* only 1-role at 2G */
- else
- type = RTW89_MR_WTYPE_NONMLD_NONMLD;
+ if (hw_band == RTW89_MAC_0) {
+ mlo_info->path_rf_band[BTC_RF_S0] = rf_band;
+ } else {
+ wl_rinfo->link_mode_hb1 = wl_rinfo->link_mode;
+ mlo_info->path_rf_band[BTC_RF_S1] = rf_band;
+ }
- if (mlo_info->hwb_rf_band[RTW89_MAC_0] == RTW89_BAND_2G) {
+ /* set pta_req_band for 1-PTA architecture */
+ if (wl->rf_band_map[RTW89_MAC_0] & BIT(RTW89_BAND_2G)) {
wl_rinfo->pta_req_band = RTW89_MAC_0;
wl_rinfo->dbcc_2g_phy = RTW89_PHY_0;
- } else {
+ } else if (wl->rf_band_map[RTW89_MAC_1] & BIT(RTW89_BAND_2G)) {
wl_rinfo->pta_req_band = RTW89_MAC_1;
wl_rinfo->dbcc_2g_phy = RTW89_PHY_1;
+ } else { /* Both HW-BAND are not on 2.4G*/
+ wl_rinfo->pta_req_band = RTW89_MAC_0;
+ wl_rinfo->dbcc_2g_phy = RTW89_PHY_0;
}
-
- if (mlo_info->wmode[RTW89_MAC_0] == RTW89_MR_WMODE_NONE &&
- mlo_info->wmode[RTW89_MAC_1] == RTW89_MR_WMODE_NONE)
- wl_rinfo->dbcc_en = 0;
- else
- wl_rinfo->dbcc_en = 1;
break;
}
- wl_rinfo->link_mode = _update_wl_link_mode(rtwdev, track_band, type);
-
rtw89_debug(rtwdev, RTW89_DBG_BTC, "[BTC], %s(), mode=%s, pta_band=%d",
__func__, id_to_linkmode(wl_rinfo->link_mode),
wl_rinfo->pta_req_band);
@@ -7386,16 +6842,19 @@ static void _update_wl_non_mlo_info(struct rtw89_dev *rtwdev)
{
struct rtw89_btc_wl_info *wl = &rtwdev->btc.cx.wl;
struct rtw89_btc_wl_rlink *rlink = NULL;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo = &wl->role_info_v8;
+ struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
struct rtw89_btc_chdef cid_ch[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER] = {};
u8 cid_role[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER] = {};
u8 cid_phy[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER] = {};
bool b2g = false, b5g = false, outloop = false;
+ bool notv10 = rtwdev->btc.ver->fwlrole != 10;
+ u8 mode_v0 = BTC_WLINK_V0_NOLINK;
u8 mode = BTC_WLINK_NOLINK;
u8 cnt_2g = 0, cnt_5g = 0;
u8 i, j, cnt = 0;
for (j = RTW89_PHY_0; j < RTW89_PHY_NUM; j++) {
+ wl->rf_band_map[j] = 0; /* j=link id, is the link use which band */
for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) {
rlink = &wl_rinfo->rlink[i][j];
@@ -7419,6 +6878,7 @@ static void _update_wl_non_mlo_info(struct rtw89_dev *rtwdev)
cnt_2g++;
b2g = true;
}
+ wl->rf_band_map[j] |= BIT(rlink->rf_band);
}
if (outloop)
break;
@@ -7427,56 +6887,73 @@ static void _update_wl_non_mlo_info(struct rtw89_dev *rtwdev)
rtw89_debug(rtwdev, RTW89_DBG_BTC,
"[BTC], %s(): cnt_2g=%d, cnt_5g=%d\n", __func__, cnt_2g, cnt_5g);
+ wl_rinfo->pta_req_band = RTW89_PHY_0; /* no 0+2 for non-MLO */
wl_rinfo->dbcc_en = rtwdev->dbcc_en;
+
/* Be careful to change the following sequence!! */
if (cnt == 0) {
mode = BTC_WLINK_NOLINK;
- } else if (!b2g && b5g) {
- mode = BTC_WLINK_5G;
+ mode_v0 = BTC_WLINK_V0_NOLINK;
} else if (wl_rinfo->dbcc_en) {
- mode = _chk_dbcc(rtwdev, cid_ch, cid_phy, cid_role, cnt);
+ /* update pta_req_band to 2.4GHz HW-BAND for DBCC = 1*/
+ mode = _chk_dbcc(rtwdev, cid_ch, cid_phy, cid_role, cnt, notv10);
+ mode_v0 = wl_rinfo->link_mode_v0;
+ } else if (!b2g && b5g && notv10) {
+ mode_v0 = BTC_WLINK_V0_5G;
} else if (b2g && b5g) {
- mode = BTC_WLINK_25G_MCC;
- } else if (!b5g && cnt >= 2) {
- if (_chk_role_ch_group(&cid_ch[0], &cid_ch[1]))
- mode = BTC_WLINK_2G_SCC;
- else
- mode = BTC_WLINK_2G_MCC;
- } else if (!b5g) { /* cnt_connect = 1 */
- mode = _get_role_link_mode(cid_role[0]);
+ mode = BTC_WLINK_DB_MCC;
+ mode_v0 = BTC_WLINK_V0_25G_MCC;
+ } else if (cnt >= 2) {
+ if (_chk_role_ch_group(&cid_ch[0], &cid_ch[1])) {
+ mode = BTC_WLINK_SCC;
+ mode_v0 = BTC_WLINK_V0_2G_SCC;
+ } else {
+ mode = BTC_WLINK_SB_MCC;
+ mode_v0 = BTC_WLINK_V0_2G_MCC;
+ }
+ } else {
+ mode = _get_role_link_mode(wl_rinfo, cid_role[0], notv10);
}
wl_rinfo->link_mode = mode;
+ wl_rinfo->link_mode_hb1 = mode;
+ wl_rinfo->link_mode_v0 = mode_v0;
}
-static void _modify_role_link_mode(struct rtw89_dev *rtwdev)
+static void _modify_role_link_mode(struct rtw89_dev *rtwdev, u8 hw_band)
{
- struct rtw89_btc_wl_info *wl = &rtwdev->btc.cx.wl;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo = &wl->role_info_v8;
+ struct rtw89_btc *btc = &rtwdev->btc;
+ struct rtw89_btc_wl_info *wl = &btc->cx.wl;
+ struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
u8 go_cleint_exist = wl->go_client_exist;
- u8 link_mode = wl_rinfo->link_mode;
+ u8 *link_mode = &wl_rinfo->link_mode;
u32 role_map = wl_rinfo->role_map;
u8 noa_exist = wl->noa_exist;
u32 mrole = BTC_WLMROLE_NONE;
+ if (hw_band == RTW89_PHY_1) {
+ *link_mode = wl_rinfo->link_mode_hb1;
+ role_map = wl_rinfo->role_map_hb1;
+ go_cleint_exist = wl->go_client_exist_hb1;
+ }
+
/* if no client_joined, don't care P2P-GO/AP role */
if (((role_map & BIT(RTW89_WIFI_ROLE_P2P_GO)) ||
- (role_map & BIT(RTW89_WIFI_ROLE_AP))) && !go_cleint_exist) {
- if (link_mode == BTC_WLINK_2G_SCC) {
- wl_rinfo->link_mode = BTC_WLINK_2G_STA;
- } else if (link_mode == BTC_WLINK_2G_GO ||
- link_mode == BTC_WLINK_2G_AP) {
- wl_rinfo->link_mode = BTC_WLINK_NOLINK;
+ (role_map & BIT(RTW89_WIFI_ROLE_AP))) && !go_cleint_exist) {
+ if (*link_mode == BTC_WLINK_SCC) {
+ *link_mode = BTC_WLINK_STA;
+ } else if (*link_mode == BTC_WLINK_GO ||
+ *link_mode == BTC_WLINK_AP) {
+ *link_mode = BTC_WLINK_NOLINK;
}
}
- /* Identify 2-Role type */
- if (link_mode == BTC_WLINK_2G_SCC ||
- link_mode == BTC_WLINK_2G_MCC ||
- link_mode == BTC_WLINK_25G_MCC ||
- link_mode == BTC_WLINK_5G) {
+ /* Identify 2-Role type */
+ if (*link_mode == BTC_WLINK_SCC ||
+ *link_mode == BTC_WLINK_SB_MCC ||
+ *link_mode == BTC_WLINK_DB_MCC) {
if ((role_map & BIT(RTW89_WIFI_ROLE_P2P_GO)) ||
- (role_map & BIT(RTW89_WIFI_ROLE_AP))) {
+ (role_map & BIT(RTW89_WIFI_ROLE_AP))) {
if (noa_exist)
mrole = BTC_WLMROLE_STA_GO_NOA;
else
@@ -7489,127 +6966,147 @@ static void _modify_role_link_mode(struct rtw89_dev *rtwdev)
} else {
mrole = BTC_WLMROLE_STA_STA;
}
- }
- wl_rinfo->mrole_type = mrole;
+ if (hw_band == RTW89_PHY_0) {
+ wl_rinfo->mrole_type &= GENMASK(31, 16); /* clear Low-Word */
+ wl_rinfo->mrole_type |= mrole;
+ } else {
+ wl_rinfo->mrole_type &= GENMASK(15, 0); /* clear high-Word */
+ wl_rinfo->mrole_type |= (mrole << 16);
+ }
+ } else {
+ wl_rinfo->mrole_type = BTC_WLMROLE_NONE;
+ }
rtw89_debug(rtwdev, RTW89_DBG_BTC,
"[BTC], %s(): link_mode=%s, mrole_type=%d\n", __func__,
id_to_linkmode(wl_rinfo->link_mode), wl_rinfo->mrole_type);
}
-static void _update_wl_info_v8(struct rtw89_dev *rtwdev, u8 role_id, u8 rlink_id,
- enum btc_role_state state)
+static void _update_wl_info(struct rtw89_dev *rtwdev, struct rtw89_btc_wl_link_info *wl_linfo)
{
- struct rtw89_btc_wl_rlink *rlink = NULL;
- struct rtw89_btc_wl_link_info *wl_linfo;
struct rtw89_btc *btc = &rtwdev->btc;
+ struct rtw89_btc_dm *dm = &btc->dm;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo = &wl->role_info_v8;
- bool client_joined = false, noa_exist = false, p2p_exist = false;
- bool is_5g_hi_channel = false, bg_mode = false, dbcc_en_ori;
- u8 i, j, link_mode_ori;
+ struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
+ struct rtw89_btc_wl_rlink *rlink = NULL;
+ u8 dbcc_en_ori, is_5g_hi_ch = 0, bg_mode = 0, p2p_exist = 0;
+ u8 go_client_exist = 0, noa_exist = 0;
+ u8 rlink_id = wl_linfo->phy;
+ u8 role_id = wl_linfo->pid;
+ u8 i, link_mode_ori;
u32 role_map = 0;
- if (role_id >= RTW89_BE_BTC_WL_MAX_ROLE_NUMBER || rlink_id >= RTW89_MAC_NUM)
+ if (role_id >= RTW89_BE_BTC_WL_MAX_ROLE_NUMBER || rlink_id >= RTW89_BAND_NUM)
return;
- /* Extract wl->link_info[role_id][rlink_id] to wl->role_info
+ /*
+ * Extract wl->link_info[role_id][rlink_id] to wl->role_info
* role_id: role index
* rlink_id: rlink index (= HW-band index)
* pid: port_index
*/
-
- wl_linfo = &wl->rlink_info[role_id][rlink_id];
rlink = &wl_rinfo->rlink[role_id][rlink_id];
rlink->role = wl_linfo->role;
rlink->active = wl_linfo->active; /* Doze or not */
rlink->pid = wl_linfo->pid;
+ rlink->mac_id = wl_linfo->mac_id;
rlink->phy = wl_linfo->phy;
- rlink->rf_band = wl_linfo->band;
- rlink->ch = wl_linfo->ch;
- rlink->bw = wl_linfo->bw;
+ rlink->rf_band = wl_linfo->chdef.band;
+ rlink->ch = wl_linfo->chdef.center_ch;
+ rlink->bw = wl_linfo->chdef.bw;
rlink->noa = wl_linfo->noa;
rlink->noa_dur = wl_linfo->noa_duration / 1000;
rlink->client_cnt = wl_linfo->client_cnt;
rlink->mode = wl_linfo->mode;
+ /* check if rlink connect? */
switch (wl_linfo->connected) {
case MLME_NO_LINK:
rlink->connected = 0;
break;
case MLME_LINKED:
rlink->connected = 1;
+
+ /* reset special-AP flag if station mode linked */
+ dm->leak_ap = 0;
break;
default:
return;
}
- for (j = RTW89_MAC_0; j <= RTW89_MAC_1; j++) {
- for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) {
- rlink = &wl_rinfo->rlink[i][j];
-
- if (!rlink->active || !rlink->connected)
- continue;
+ /* update by HW-Band */
+ for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) { /* i = role_id */
+ rlink = &wl_rinfo->rlink[i][rlink_id];
- role_map |= BIT(rlink->role);
+ if (!rlink->active || !rlink->connected)
+ continue;
- /* only one noa-role exist */
- if (rlink->noa && rlink->noa_dur > 0)
- noa_exist = true;
+ role_map |= BIT(rlink->role);
- /* for WL 5G-Rx interfered with BT issue */
- if (rlink->rf_band == RTW89_BAND_5G) {
- if (rlink->ch >= 100)
- is_5g_hi_channel = true;
+ /* Identify if P2P-Go (GO/GC/AP) exist at 2GHz band */
+ if (((rlink->role == RTW89_WIFI_ROLE_P2P_GO ||
+ rlink->role == RTW89_WIFI_ROLE_AP) &&
+ rlink->client_cnt > 1)) {
+ p2p_exist = 1;
+ go_client_exist = 1;
+ }
- continue;
- }
+ if (rlink->role == RTW89_WIFI_ROLE_P2P_CLIENT)
+ p2p_exist = 1;
- /* only if client connect for p2p-Go/AP */
- if ((rlink->role == RTW89_WIFI_ROLE_P2P_GO ||
- rlink->role == RTW89_WIFI_ROLE_AP) &&
- rlink->client_cnt > 1) {
- p2p_exist = true;
- client_joined = true;
- }
+ /* only one noa-role exist */
+ if (rlink->noa && rlink->noa_dur > 0)
+ noa_exist = 1;
- /* Identify if P2P-Go (GO/GC/AP) exist at 2G band */
- if (rlink->role == RTW89_WIFI_ROLE_P2P_CLIENT)
- p2p_exist = true;
+ /* for WL 5G-Rx interfered with BT issue */
+ if (rlink->rf_band == RTW89_BAND_5G && rlink->ch >= 100)
+ is_5g_hi_ch = 1;
- if ((rlink->mode & BIT(BTC_WL_MODE_11B)) ||
- (rlink->mode & BIT(BTC_WL_MODE_11G)))
- bg_mode = true;
- }
+ if ((rlink->mode & BIT(BTC_WL_MODE_11B)) ||
+ (rlink->mode & BIT(BTC_WL_MODE_11G)))
+ bg_mode = 1;
}
- link_mode_ori = wl_rinfo->link_mode;
- wl->is_5g_hi_channel = is_5g_hi_channel;
- wl->bg_mode = bg_mode;
- wl->go_client_exist = client_joined;
- wl->noa_exist = noa_exist;
- wl_rinfo->p2p_2g = p2p_exist;
- wl_rinfo->role_map = role_map;
+ if (rlink_id == RTW89_PHY_0) {
+ link_mode_ori = wl_rinfo->link_mode;
+ wl->is_5g_hi_ch = is_5g_hi_ch;
+ wl->bg_mode = bg_mode;
+ wl->go_client_exist = go_client_exist;
+ wl->noa_exist = noa_exist;
+ wl_rinfo->p2p_exist = p2p_exist;
+ wl_rinfo->role_map = role_map;
+ } else {
+ link_mode_ori = wl_rinfo->link_mode_hb1;
+ wl->is_5g_hi_ch_hb1 = is_5g_hi_ch;
+ wl->bg_mode_hb1 = bg_mode;
+ wl->go_client_exist_hb1 = go_client_exist;
+ wl->noa_exist_hb1 = noa_exist;
+ wl_rinfo->p2p_exist_hb1 = p2p_exist;
+ wl_rinfo->role_map_hb1 = role_map;
+ }
dbcc_en_ori = wl_rinfo->dbcc_en;
+ /* for MLO-supported, link-mode from driver directly */
if (rtwdev->chip->para_ver & BTC_FEAT_MLO_SUPPORT) {
- /* for MLO-supported, link-mode from driver directly */
- _update_wl_mlo_info(rtwdev);
- } else {
- /* for non-MLO-supported, link-mode by BTC */
+ _update_wl_mlo_info(rtwdev, rlink_id);
+ } else { /* for non-MLO-supported, link-mode by BTC */
_update_wl_non_mlo_info(rtwdev);
}
- _modify_role_link_mode(rtwdev);
+ _modify_role_link_mode(rtwdev, rlink_id);
- if (link_mode_ori != wl_rinfo->link_mode)
- wl->link_mode_chg = true;
+ if ((rlink_id == RTW89_PHY_0 && wl_rinfo->link_mode != link_mode_ori) ||
+ (rlink_id == RTW89_PHY_1 && wl_rinfo->link_mode_hb1 != link_mode_ori)) {
+ wl_rinfo->link_mode_chg = 1;
+ wl->link_mode_chg = 1;
+ }
if (wl_rinfo->dbcc_en != dbcc_en_ori) {
- wl->dbcc_chg = true;
+ wl->dbcc_chg = 1;
+ wl->role_info.dbcc_chg = 1;
wl->wcnt[BTC_WCNT_DBCC_CHG]++;
}
}
@@ -7685,25 +7182,21 @@ static void _update_bt_scbd(struct rtw89_dev *rtwdev, u8 bid)
struct rtw89_btc_dm *dm = &btc->dm;
struct rtw89_btc_bt_info *bt;
u32 val, any_bt_connect, any_bt_6g_connect = 0;
- u8 id, id_start, id_stop, mode;
+ u8 id, id_start, id_stop, mode = 0;
bool bt_link_change = false;
bool lps_ctrl = false;
if (!rtwdev->chip->scbd || bid > BTC_ALL_BT)
return;
- if (ver->fwlrole == 0)
- mode = wl->role_info.link_mode;
- else if (ver->fwlrole == 1)
- mode = wl->role_info_v1.link_mode;
- else if (ver->fwlrole == 2)
- mode = wl->role_info_v2.link_mode;
- else if (ver->fwlrole == 7)
- mode = wl->role_info_v7.link_mode;
- else if (ver->fwlrole == 8)
- mode = wl->role_info_v8.link_mode;
- else
- return;
+ if (ver->fwlrole == 10) {
+ if (wl->role_info.link_mode == BTC_WLINK_STA &&
+ (dm->tdd_en && wl->rf_band_map[RTW89_MAC_0] &
+ BIT(RTW89_BAND_2G)))
+ mode = BTC_WLINK_V0_2G_STA;
+ } else {
+ mode = wl->role_info.link_mode_v0;
+ }
if (bid == BTC_ALL_BT) {
id_start = BTC_BT_1ST;
@@ -7796,7 +7289,7 @@ static void _update_bt_scbd(struct rtw89_dev *rtwdev, u8 bid)
if (((bt->link_info.a2dp_desc.exist ||
bt->link_info.pan_desc.exist ||
bt->link_info.hfp_desc.exist) &&
- mode == BTC_WLINK_2G_STA) ||
+ mode == BTC_WLINK_V0_2G_STA) ||
bt->whql_test)
lps_ctrl = true;
@@ -7900,7 +7393,12 @@ static void _set_bind_info(struct rtw89_btc *btc, u8 type)
* HW-Band is decided by wl->mlo_info.mrcx_act_hwb_map
*/
if (wl->mlo_info.wtype == RTW89_MR_WTYPE_MLD2L1R_NONMLD) {
- /* TODO: Should patched WiFi mode & WiFi role patch */
+ if (wl->role_info.link_mode != BTC_WLINK_DB_MCC) { /* mode chg */
+ if (wl->mlo_info.mrcx_act_hwb_map == BIT(RTW89_MAC_1))
+ path_hwb[BTC_RF_S0] = RTW89_PHY_1; /* S0/1->HWB1 */
+ else
+ path_hwb[BTC_RF_S1] = RTW89_PHY_0; /* S0/1->HWB0 */
+ }
} else {
/*
* Dual-RF_band(HWB)TDMA if BT-profile is TDMA-type at both
@@ -7933,7 +7431,22 @@ static void _set_bind_info(struct rtw89_btc *btc, u8 type)
}
}
- /* TODO: Should patched WiFi mode & WiFi role patch */
+ if (wl->mlo_info.wtype == RTW89_MR_WTYPE_MLD2L2R &&
+ (bd->wl_hwb_sel == (BIT(RTW89_MAC_1) | BIT(RTW89_MAC_0)))) {
+ if (wl->role_info.link_mode == BTC_WLINK_AP ||
+ wl->role_info.link_mode_hb1 == BTC_WLINK_AP)
+ bd->wl_link_mode = BTC_WLINK_DB_MCC;
+ else
+ bd->wl_link_mode = BTC_WLINK_STA;
+ bd->wl_bg_mode = wl->bg_mode | wl->bg_mode_hb1;
+ } else if (bd->wl_hwb_sel == (BIT(RTW89_MAC_1))) {
+ bd->wl_link_mode = wl->role_info.link_mode_hb1;
+ bd->wl_bg_mode = wl->bg_mode_hb1;
+ } else {/* HW-BAND-0 or no-hw-band */
+ bd->wl_hwb_sel = BIT(RTW89_MAC_0);
+ bd->wl_link_mode = wl->role_info.link_mode;
+ bd->wl_bg_mode = wl->bg_mode;
+ }
/* update Bind-BT status map for BT0/BT1 */
for (i = BTC_BT_1ST; i < BTC_ALL_BT_EZL; i++) {
@@ -7966,9 +7479,9 @@ static void _set_bind_info(struct rtw89_btc *btc, u8 type)
bd->bt_smap.a2dp_sink |= b->a2dp_desc.sink;
bd->bt_smap.pan_active |= b->pan_desc.active;
bd->bt_smap.connect |= b->status.map.connect;
- bd->bt_smap.hid_cnt += (u8)b->hid_desc.pair_cnt;
+ bd->bt_smap.hid_cnt += b->hid_desc.pair_cnt;
bd->bt_smap.hid_type |= b->hid_desc.type;
- bd->bt_smap.cis_cnt += (u8)b->leaudio_desc.cis_cnt;
+ bd->bt_smap.cis_cnt += b->leaudio_desc.cis_cnt;
bd->bt_smap.link_cnt += b->link_cnt.now;
bd->bt_smap.inq_page |= b->status.map.inq_pag;
bd->bt_smap.page |= b->pag;
@@ -8028,7 +7541,7 @@ static void _set_coex_binding(struct rtw89_btc *btc)
* ==> 1: interference, 0: no-interference
*
* fdm_map(Frequency-Division-Multiplexing): WL/BT RF_Band overlap-map
- * 2bit-map: bit[1]:5GHz/6GHz, bit[0]:2.4GHz
+ * 2bit-map: bit[1]:5/6GHz, bit[0]:2.4GHz
*/
for (i = 0; i < RTW89_PHY_NUM; i++) {
if (wl->rf_band_map[i] & BIT(RTW89_BAND_2G))
@@ -8050,9 +7563,7 @@ static void _set_coex_binding(struct rtw89_btc *btc)
* In this case, BTC_RF_S0->HWB0, BTC_RF_S1->HWB1
*/
if (wl->mlo_info.wtype == RTW89_MR_WTYPE_MLD2L1R_NONMLD) {
- if (wl->role_info.link_mode != BTC_WLINK_2G_MCC &&
- wl->role_info.link_mode != BTC_WLINK_25G_MCC &&
- wl->role_info.link_mode != BTC_WLINK_25G_DBCC) {/* mode chg */
+ if (wl->role_info.link_mode != BTC_WLINK_DB_MCC) {/* mode chg */
if (wl->mlo_info.mrcx_act_hwb_map == BIT(RTW89_PHY_1))
path_hwb[BTC_RF_S0] = RTW89_PHY_1;/* S0/1->HWB1 */
else
@@ -8114,31 +7625,14 @@ void _run_coex(struct rtw89_dev *rtwdev, enum btc_reason_and_action reason)
struct rtw89_btc_cx *cx = &btc->cx;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
struct rtw89_btc_bt_info *bt = &btc->cx.bt0;
- struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo_v1 = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo_v8 = &wl->role_info_v8;
- u8 mode, igno_bt, always_freerun;
+ u8 mode = btc->dm.tdd_bind.wl_link_mode;
+ u8 mode_v0 = wl->role_info.link_mode_v0;
+ u8 igno_bt, always_freerun;
lockdep_assert_wiphy(rtwdev->hw->wiphy);
dm->run_reason = reason;
_update_dm_step(rtwdev, reason);
- _update_btc_state_map(rtwdev);
-
- if (ver->fwlrole == 0)
- mode = wl_rinfo->link_mode;
- else if (ver->fwlrole == 1)
- mode = wl_rinfo_v1->link_mode;
- else if (ver->fwlrole == 2)
- mode = wl_rinfo_v2->link_mode;
- else if (ver->fwlrole == 7)
- mode = wl_rinfo_v7->link_mode;
- else if (ver->fwlrole == 8)
- mode = wl_rinfo_v8->link_mode;
- else
- return;
if (ver->fcxctrl == 7) {
igno_bt = btc->ctrl.ctrl_v7.igno_bt;
@@ -8206,6 +7700,7 @@ void _run_coex(struct rtw89_dev *rtwdev, enum btc_reason_and_action reason)
igno_bt = false;
_set_coex_binding(btc);
+ _update_btc_state_map(rtwdev);
dm->freerun_chk = _check_freerun(rtwdev); /* check if meet freerun */
@@ -8253,43 +7748,76 @@ void _run_coex(struct rtw89_dev *rtwdev, enum btc_reason_and_action reason)
goto exit;
}
- switch (mode) {
+ if (mode == BTC_WLINK_NOLINK) {
+ mode_v0 = BTC_WLINK_V0_NOLINK;
+ } else if (btc->dm.tdd_bind.rf_band == BIT(RTW89_BAND_5G)) {
+ mode_v0 = BTC_WLINK_V0_5G;
+ } else if (btc->dm.tdd_bind.rf_band & BIT(RTW89_BAND_5G) &&
+ btc->dm.tdd_bind.rf_band & BIT(RTW89_BAND_2G)) {
+ mode_v0 = BTC_WLINK_V0_25G_MCC;
+ } else if (btc->dm.tdd_bind.rf_band == BIT(RTW89_BAND_2G)) {
+ switch (mode) {
+ case BTC_WLINK_STA:
+ mode_v0 = BTC_WLINK_V0_2G_STA;
+ break;
+ case BTC_WLINK_AP:
+ mode_v0 = BTC_WLINK_V0_2G_AP;
+ break;
+ case BTC_WLINK_GO:
+ mode_v0 = BTC_WLINK_V0_2G_GO;
+ break;
+ case BTC_WLINK_GC:
+ mode_v0 = BTC_WLINK_V0_2G_GC;
+ break;
+ case BTC_WLINK_SCC:
+ mode_v0 = BTC_WLINK_V0_2G_SCC;
+ break;
+ case BTC_WLINK_SB_MCC:
+ mode_v0 = BTC_WLINK_V0_2G_MCC;
+ break;
+ default:
+ mode_v0 = BTC_WLINK_V0_OTHER;
+ break;
+ }
+ }
+
+ switch (mode_v0) {
case BTC_WLINK_NOLINK:
_action_wl_nc(rtwdev);
break;
- case BTC_WLINK_2G_STA:
+ case BTC_WLINK_V0_2G_STA:
if (wl->status.map.traffic_dir & BIT(RTW89_TFC_DL))
bt->scan_rx_low_pri = true;
_action_wl_2g_sta(rtwdev);
break;
- case BTC_WLINK_2G_AP:
+ case BTC_WLINK_V0_2G_AP:
bt->scan_rx_low_pri = true;
_action_wl_2g_ap(rtwdev);
break;
- case BTC_WLINK_2G_GO:
+ case BTC_WLINK_V0_2G_GO:
bt->scan_rx_low_pri = true;
_action_wl_2g_go(rtwdev);
break;
- case BTC_WLINK_2G_GC:
+ case BTC_WLINK_V0_2G_GC:
bt->scan_rx_low_pri = true;
_action_wl_2g_gc(rtwdev);
break;
- case BTC_WLINK_2G_SCC:
+ case BTC_WLINK_V0_2G_SCC:
bt->scan_rx_low_pri = true;
_action_wl_2g_scc(rtwdev);
break;
- case BTC_WLINK_2G_MCC:
+ case BTC_WLINK_V0_2G_MCC:
bt->scan_rx_low_pri = true;
_action_wl_2g_mcc(rtwdev);
break;
- case BTC_WLINK_25G_MCC:
+ case BTC_WLINK_V0_25G_MCC:
bt->scan_rx_low_pri = true;
_action_wl_25g_mcc(rtwdev);
break;
- case BTC_WLINK_5G:
+ case BTC_WLINK_V0_5G:
_action_wl_5g(rtwdev);
break;
- case BTC_WLINK_2G_NAN:
+ case BTC_WLINK_V0_2G_NAN:
_action_wl_2g_nan(rtwdev);
break;
default:
@@ -8678,22 +8206,6 @@ static u8 _update_bt_rssi_level(struct rtw89_dev *rtwdev, u8 rssi)
return rssi_level;
}
-static void _update_zb_coex_tbl(struct rtw89_dev *rtwdev)
-{
- u8 mode = rtwdev->btc.cx.wl.role_info.link_mode;
- u32 zb_tbl0 = 0xda5a5a5a, zb_tbl1 = 0xda5a5a5a;
-
- if (mode == BTC_WLINK_5G || rtwdev->btc.dm.freerun) {
- zb_tbl0 = 0xffffffff;
- zb_tbl1 = 0xffffffff;
- } else if (mode == BTC_WLINK_25G_MCC) {
- zb_tbl0 = 0xffffffff; /* for E5G slot */
- zb_tbl1 = 0xda5a5a5a; /* for E2G slot */
- }
- rtw89_write32(rtwdev, R_BTC_ZB_COEX_TBL_0, zb_tbl0);
- rtw89_write32(rtwdev, R_BTC_ZB_COEX_TBL_1, zb_tbl1);
-}
-
#define BT_PROFILE_PROTOCOL_MASK GENMASK(7, 4)
static void _update_bt_info(struct rtw89_dev *rtwdev, u8 *buf, u32 len)
@@ -8842,11 +8354,10 @@ void rtw89_btc_ntfy_role_info(struct rtw89_dev *rtwdev,
struct ieee80211_bss_conf *bss_conf;
struct ieee80211_link_sta *link_sta;
struct rtw89_btc *btc = &rtwdev->btc;
- const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
struct rtw89_btc_wl_link_info r = {0};
struct rtw89_btc_wl_link_info *wlinfo = NULL;
- u8 mode = 0, rlink_id, link_mode_ori, pta_req_mac_ori, wa_type;
+ u8 mode = 0;
rcu_read_lock();
@@ -8894,66 +8405,32 @@ void rtw89_btc_ntfy_role_info(struct rtw89_dev *rtwdev,
rtw89_debug(rtwdev, RTW89_DBG_BTC,
"[BTC], wifi_role=%d\n", rtwvif_link->wifi_role);
- r.role = rtwvif_link->wifi_role;
- r.phy = rtwvif_link->phy_idx;
- r.pid = rtwvif_link->port;
- r.active = true;
- r.connected = MLME_LINKED;
- r.bcn_period = bss_conf->beacon_int;
- r.dtim_period = bss_conf->dtim_period;
- r.band = chan->band_type;
- r.ch = chan->channel;
- r.bw = chan->band_width;
- r.chdef.band = chan->band_type;
- r.chdef.center_ch = chan->channel;
- r.chdef.bw = chan->band_width;
- r.chdef.chan = chan->primary_channel;
+ wlinfo = &wl->rlink_info[rtwvif_link->port][rtwvif_link->phy_idx];
+
+ wlinfo->mode = mode;
+ wlinfo->role = rtwvif_link->wifi_role;
+ wlinfo->phy = rtwvif_link->phy_idx;
+ wlinfo->pid = rtwvif_link->port;
+ wlinfo->active = true;
+ wlinfo->connected = MLME_LINKED;
+ wlinfo->bcn_period = bss_conf->beacon_int;
+ wlinfo->dtim_period = bss_conf->dtim_period;
+ wlinfo->band = chan->band_type;
+ wlinfo->ch = chan->channel;
+ wlinfo->bw = chan->band_width;
+ wlinfo->chdef.band = chan->band_type;
+ wlinfo->chdef.center_ch = chan->channel;
+ wlinfo->chdef.bw = chan->band_width;
+ wlinfo->chdef.chan = chan->primary_channel;
ether_addr_copy(r.mac_addr, rtwvif_link->mac_addr);
rcu_read_unlock();
if (rtwsta_link && vif->type == NL80211_IFTYPE_STATION)
- r.mac_id = rtwsta_link->mac_id;
+ wlinfo->mac_id = rtwsta_link->mac_id;
btc->dm.cnt_notify[BTC_NCNT_ROLE_INFO]++;
- wlinfo = &wl->link_info[r.pid];
-
- if (ver->fwlrole == 0) {
- *wlinfo = r;
- _update_wl_info(rtwdev);
- } else if (ver->fwlrole == 1) {
- *wlinfo = r;
- _update_wl_info_v1(rtwdev);
- } else if (ver->fwlrole == 2) {
- *wlinfo = r;
- _update_wl_info_v2(rtwdev);
- } else if (ver->fwlrole == 7) {
- *wlinfo = r;
- _update_wl_info_v7(rtwdev, r.pid);
- } else if (ver->fwlrole == 8) {
- rlink_id = rtwvif_link->mac_idx;
- wlinfo = &wl->rlink_info[r.pid][rlink_id];
- *wlinfo = r;
- link_mode_ori = wl->role_info_v8.link_mode;
- pta_req_mac_ori = wl->pta_req_mac;
- _update_wl_info_v8(rtwdev, r.pid, rlink_id, state);
-
- if (wl->role_info_v8.link_mode != link_mode_ori) {
- wl->role_info_v8.link_mode_chg = 1;
- if (ver->fcxinit == 7)
- wa_type = btc->mdinfo.md_v7.wa_type;
- else
- wa_type = btc->mdinfo.md.wa_type;
-
- if (wa_type & BTC_WA_HFP_ZB)
- _update_zb_coex_tbl(rtwdev);
- }
-
- if (wl->pta_req_mac != pta_req_mac_ori)
- wl->pta_reg_mac_chg = 1;
- }
-
if (wlinfo->role == RTW89_WIFI_ROLE_STATION &&
wlinfo->connected == MLME_NO_LINK)
btc->dm.leak_ap = 0;
@@ -8967,6 +8444,8 @@ void rtw89_btc_ntfy_role_info(struct rtw89_dev *rtwdev,
state == BTC_ROLE_MSTS_STA_CONN_END)
wl->status.map._4way = false;
+ _update_wl_info(rtwdev, wlinfo);
+
_run_coex(rtwdev, BTC_RSN_NTFY_ROLE_INFO);
}
@@ -9150,15 +8629,14 @@ void __rtw89_btc_ntfy_wl_sta_iter(struct rtw89_vif_link *rtwvif_link,
struct rtw89_dev *rtwdev = iter_data->rtwdev;
struct rtw89_btc *btc = &rtwdev->btc;
struct rtw89_btc_dm *dm = &btc->dm;
- const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
struct rtw89_btc_wl_link_info *link_info = NULL;
struct rtw89_traffic_stats *link_info_t = NULL;
struct rtw89_traffic_stats *stats = &rtwvif->stats;
const struct rtw89_chip_info *chip = rtwdev->chip;
struct rtw89_btc_wl_role_info *r;
- struct rtw89_btc_wl_role_info_v1 *r1;
u32 last_tx_rate, last_rx_rate;
+ u8 link = rtwvif_link->phy_idx;
u16 last_tx_lvl, last_rx_lvl;
u8 port = rtwvif_link->port;
u8 rssi;
@@ -9171,10 +8649,7 @@ void __rtw89_btc_ntfy_wl_sta_iter(struct rtw89_vif_link *rtwvif_link,
rssi = ewma_rssi_read(&rtwsta_link->avg_rssi) >> RSSI_FACTOR;
rtw89_debug(rtwdev, RTW89_DBG_BTC, "[BTC], rssi=%d\n", rssi);
- if (btc->ver->fwlrole != 8)
- link_info = &wl->link_info[port];
- else
- link_info = &wl->rlink_info[port][rtwvif_link->mac_idx];
+ link_info = &wl->rlink_info[port][link];
link_info->stat.traffic = *stats;
link_info_t = &link_info->stat.traffic;
@@ -9214,7 +8689,6 @@ void __rtw89_btc_ntfy_wl_sta_iter(struct rtw89_vif_link *rtwvif_link,
else
dir = RTW89_TFC_DL;
- link_info = &wl->link_info[port];
if (link_info->busy != busy || link_info->dir != dir) {
is_sta_change = true;
link_info->busy = busy;
@@ -9244,19 +8718,11 @@ void __rtw89_btc_ntfy_wl_sta_iter(struct rtw89_vif_link *rtwvif_link,
dm->trx_info.rx_rate = link_info_t->rx_rate;
}
- if (ver->fwlrole == 0) {
- r = &wl->role_info;
- r->active_role[port].tx_lvl = stats->tx_tfc_lv;
- r->active_role[port].rx_lvl = stats->rx_tfc_lv;
- r->active_role[port].tx_rate = rtwsta_link->ra_report.hw_rate;
- r->active_role[port].rx_rate = rtwsta_link->rx_hw_rate;
- } else if (ver->fwlrole == 1) {
- r1 = &wl->role_info_v1;
- r1->active_role_v1[port].tx_lvl = stats->tx_tfc_lv;
- r1->active_role_v1[port].rx_lvl = stats->rx_tfc_lv;
- r1->active_role_v1[port].tx_rate = rtwsta_link->ra_report.hw_rate;
- r1->active_role_v1[port].rx_rate = rtwsta_link->rx_hw_rate;
- }
+ r = &wl->role_info;
+ r->rlink[port][link].tx_lvl = stats->tx_tfc_lv;
+ r->rlink[port][link].rx_lvl = stats->rx_tfc_lv;
+ r->rlink[port][link].tx_rate = rtwsta_link->ra_report.hw_rate;
+ r->rlink[port][link].rx_rate = rtwsta_link->rx_hw_rate;
dm->trx_info.tx_lvl = stats->tx_tfc_lv;
dm->trx_info.rx_lvl = stats->rx_tfc_lv;
@@ -9584,10 +9050,7 @@ static int _show_wl_role_info(struct rtw89_dev *rtwdev, char *buf, size_t bufsz)
for (i = 0; i < btc->ver->max_role_num; i++) {
for (j = 0; j < RTW89_MAC_NUM; j++) {
- if (btc->ver->fwlrole == 8)
- plink = &btc->cx.wl.rlink_info[i][j];
- else
- plink = &btc->cx.wl.link_info[i];
+ plink = &btc->cx.wl.rlink_info[i][j];
if (!plink->active)
continue;
@@ -9630,14 +9093,9 @@ static int _show_wl_role_info(struct rtw89_dev *rtwdev, char *buf, size_t bufsz)
static int _show_wl_info(struct rtw89_dev *rtwdev, char *buf, size_t bufsz)
{
struct rtw89_btc *btc = &rtwdev->btc;
- const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_cx *cx = &btc->cx;
struct rtw89_btc_wl_info *wl = &cx->wl;
struct rtw89_btc_wl_role_info *wl_rinfo = &wl->role_info;
- struct rtw89_btc_wl_role_info_v1 *wl_rinfo_v1 = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_v2 *wl_rinfo_v2 = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_v7 *wl_rinfo_v7 = &wl->role_info_v7;
- struct rtw89_btc_wl_role_info_v8 *wl_rinfo_v8 = &wl->role_info_v8;
char *p = buf, *end = buf + bufsz;
u8 mode;
@@ -9646,18 +9104,7 @@ static int _show_wl_info(struct rtw89_dev *rtwdev, char *buf, size_t bufsz)
p += scnprintf(p, end - p, "========== [WL Status] ==========\n");
- if (ver->fwlrole == 0)
- mode = wl_rinfo->link_mode;
- else if (ver->fwlrole == 1)
- mode = wl_rinfo_v1->link_mode;
- else if (ver->fwlrole == 2)
- mode = wl_rinfo_v2->link_mode;
- else if (ver->fwlrole == 7)
- mode = wl_rinfo_v7->link_mode;
- else if (ver->fwlrole == 8)
- mode = wl_rinfo_v8->link_mode;
- else
- goto out;
+ mode = wl_rinfo->link_mode;
p += scnprintf(p, end - p, " %-15s : link_mode:%s, ", "[status]",
id_to_linkmode(mode));
@@ -9677,7 +9124,6 @@ static int _show_wl_info(struct rtw89_dev *rtwdev, char *buf, size_t bufsz)
p += _show_wl_role_info(rtwdev, p, end - p);
-out:
return p - buf;
}
@@ -9755,6 +9201,8 @@ static int _show_bt_info(struct rtw89_dev *rtwdev, char *buf, size_t bufsz)
union rtw89_btc_module_info *md = &btc->mdinfo;
s8 br_dbm = bt->link_info.bt_txpwr_desc.br_dbm;
s8 le_dbm = bt->link_info.bt_txpwr_desc.le_dbm;
+ u8 hw_band = wl->role_info.pta_req_band;
+ struct rtw89_btc_wl_afh_info *wl_afh;
char *p = buf, *end = buf + bufsz;
u8 *afh = bt_linfo->afh_map;
u8 *afh_le = bt_linfo->afh_map_le;
@@ -9822,8 +9270,9 @@ static int _show_bt_info(struct rtw89_dev *rtwdev, char *buf, size_t bufsz)
afh_le[0], afh_le[1], afh_le[2],
afh_le[3], afh_le[4]);
- p += scnprintf(p, end - p, "wl_ch_map[en:%d/ch:%d/bw:%d]\n",
- wl->afh_info.en, wl->afh_info.ch, wl->afh_info.bw);
+ wl_afh = &wl->afh_info[hw_band][RTW89_BAND_2G];
+ p += scnprintf(p, end - p, "wl_ch_map[hwb:%d/en:%d/ch:%d/bw:%d/rf_band:%d]\n",
+ hw_band, wl_afh->en, wl_afh->ch, wl_afh->bw, wl_afh->band);
p += scnprintf(p, end - p,
" %-15s : retry:%d, relink:%d, rate_chg:%d, reinit:%d, reenable:%d, ",
diff --git a/drivers/net/wireless/realtek/rtw89/coex.h b/drivers/net/wireless/realtek/rtw89/coex.h
index 74027ca4eccc..c127bd80d31c 100644
--- a/drivers/net/wireless/realtek/rtw89/coex.h
+++ b/drivers/net/wireless/realtek/rtw89/coex.h
@@ -11,6 +11,40 @@
#define BTC_TLV_SLOT_ID_LEN_V7 1
#define BTC_SLOT_REQ_TH 2
+#define BTC_FREQ_W2G 2412
+#define BTC_FREQ_W5G 5005
+#define BTC_FREQ_W6G 5955
+
+#define BTC_FREQ_B2G 2402
+#define BTC_FREQ_B6G 5125
+
+#define BTC_FREQ_W2G_CH14 2484
+
+#define BTC_LO_2G_DNM 125 /* LO Coefficient Denominator */
+#define BTC_LO_5G_DNM 125
+#define BTC_LO_6G_DNM 150
+
+#define BTC_LO_2G_NMR 400 /* LO Coefficient Numerator */
+#define BTC_LO_5G_NMR 200
+#define BTC_LO_6G_NMR 200
+
+#define BTC_CH_W2G_MIN 1 /* start from 2412MHz */
+#define BTC_CH_W2G_MAX 14
+#define BTC_CH_W5G_MIN 1 /* start from 5005MHz */
+#define BTC_CH_W5G_MAX 165
+#define BTC_CH_W6G_MIN 1 /* start from 5955MHz */
+#define BTC_CH_W6G_MAX 233
+
+#define BTC_CH_B2G_MIN 0 /* start from 2402MHz */
+#define BTC_CH_B2G_MAX 78
+
+#define BTC_CH_B5G_MIN 600 /* start from 5725MHz */
+#define BTC_CH_B5G_MAX 1300
+
+#define BTC_VCO_GUARD_W2W 10 /* WiFi to WiFi VCO freq forbiddened range (MHZ) */
+#define BTC_VCO_GUARD_W2B 25 /* WiFi to WiFi VCO freq forbiddened range (MHZ) */
+#define BTC_VCO_GUARD_B2B 10 /* WiFi to WiFi VCO freq forbiddened range (MHZ) */
+
enum btc_mode {
BTC_MODE_NORMAL,
BTC_MODE_WL,
diff --git a/drivers/net/wireless/realtek/rtw89/core.h b/drivers/net/wireless/realtek/rtw89/core.h
index 174349c6bc58..ded788534651 100644
--- a/drivers/net/wireless/realtek/rtw89/core.h
+++ b/drivers/net/wireless/realtek/rtw89/core.h
@@ -1854,7 +1854,7 @@ union rtw89_btc_wl_role_info_map {
struct rtw89_btc_wl_role_info_bpos role;
};
-struct rtw89_btc_wl_role_info { /* struct size must be n*4 bytes */
+struct rtw89_btc_wl_role_info_v0 { /* struct size must be n*4 bytes */
u8 connect_cnt;
u8 link_mode;
union rtw89_btc_wl_role_info_map role_map;
@@ -1891,7 +1891,7 @@ struct rtw89_btc_wl_role_info_v2 { /* struct size must be n*4 bytes */
u32 rsvd: 27;
};
-struct rtw89_btc_wl_rlink { /* H2C info, struct size must be n*4 bytes */
+struct rtw89_btc_wl_rlink_v0 { /* H2C info, struct size must be n*4 bytes */
u8 connected;
u8 pid;
u8 phy;
@@ -1908,6 +1908,28 @@ struct rtw89_btc_wl_rlink { /* H2C info, struct size must be n*4 bytes */
u8 mode; /* wifi protocol */
} __packed;
+struct rtw89_btc_wl_rlink_v10 { /* H2C info, struct size must be n*4 bytes */
+ u8 connected;
+ u8 pid;
+ u8 phy;
+ u8 noa;
+
+ u8 rf_band; /* enum band_type RF band: 2.4G/5G/6G */
+ u8 active; /* 0:rlink is under doze */
+ u8 bw; /* enum channel_width */
+ u8 role; /*enum role_type */
+
+ u8 ch;
+ u8 noa_dur; /* ms */
+ u8 client_cnt; /* for Role = P2P-Go/AP */
+ u8 mode; /* wifi protocol */
+
+ u8 mac_id;
+ u8 rsvd0;
+ u8 rsvd1;
+ u8 rsvd2;
+} __packed;
+
#define RTW89_BE_BTC_WL_MAX_ROLE_NUMBER 6
struct rtw89_btc_wl_role_info_v7 { /* struct size must be n*4 bytes */
u8 connect_cnt;
@@ -1917,12 +1939,12 @@ struct rtw89_btc_wl_role_info_v7 { /* struct size must be n*4 bytes */
struct rtw89_btc_wl_active_role_v7 active_role[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER];
- u32 role_map;
- u32 mrole_type; /* btc_wl_mrole_type */
- u32 mrole_noa_duration; /* ms */
- u32 dbcc_en;
- u32 dbcc_chg;
- u32 dbcc_2g_phy; /* which phy operate in 2G, HW_PHY_0 or HW_PHY_1 */
+ __le32 role_map;
+ __le32 mrole_type; /* btc_wl_mrole_type */
+ __le32 mrole_noa_duration; /* ms */
+ __le32 dbcc_en;
+ __le32 dbcc_chg;
+ __le32 dbcc_2g_phy; /* which phy operate in 2G, HW_PHY_0 or HW_PHY_1 */
} __packed;
struct rtw89_btc_wl_role_info_v8 { /* H2C info, struct size must be n*4 bytes */
@@ -1936,12 +1958,90 @@ struct rtw89_btc_wl_role_info_v8 { /* H2C info, struct size must be n*4 bytes */
u8 dbcc_chg;
u8 dbcc_2g_phy; /* which phy operate in 2G, HW_PHY_0 or HW_PHY_1 */
+ struct rtw89_btc_wl_rlink_v0 rlink[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER][RTW89_MAC_NUM];
+
+ __le32 role_map;
+ __le32 mrole_type; /* btc_wl_mrole_type */
+ __le32 mrole_noa_duration; /* ms */
+} __packed;
+
+struct rtw89_btc_wl_role_info_v10 { /* H2C info, struct size must be n*4 bytes */
+ struct rtw89_btc_wl_rlink_v10 rlink[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER][RTW89_MAC_NUM];
+ u8 link_mode;
+ u8 link_mode_hb1;
+ u8 p2p_exist;
+ u8 p2p_exist_hb1;
+
+ u8 pta_req_band;
+ u8 dbcc_en; /* 1+1 and 2.4G-included */
+ u8 dbcc_2g_phy; /* which phy operate in 2G, HW_PHY_0 or HW_PHY_1 */
+ u8 rsvd;
+
+ __le32 role_map;
+ __le32 role_map_hb1;
+ __le32 mrole_type; /* btc_wl_mrole_type: [31:16]:band1, [15:0]:band0 */
+} __packed;
+
+struct rtw89_btc_wl_rlink { /* Logic dynamic using */
+ u8 connected;
+ u8 pid;
+ u8 phy;
+ u8 noa;
+
+ u8 rf_band; /* enum band_type RF band: 2.4G/5G/6G */
+ u8 active; /* 0:rlink is under doze */
+ u8 bw; /* enum channel_width */
+ u8 role; /*enum role_type */
+
+ u8 ch;
+ u8 noa_dur; /* ms */
+ u8 client_cnt; /* for Role = P2P-Go/AP */
+ u8 mode; /* wifi protocol */
+
+ /*v0 v1*/
+ u16 tx_lvl;
+ u16 rx_lvl;
+ u16 tx_rate;
+ u16 rx_rate;
+
+ /* v7 */
+ u8 client_ps; /*v7 v2 v1 v0*/
+
+ /* v10 */
+ u8 mac_id;
+ u8 rsvd0;
+ u8 rsvd1;
+ u8 rsvd2;
+};
+
+struct rtw89_btc_wl_role_info { /* Logic dynamic using */
struct rtw89_btc_wl_rlink rlink[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER][RTW89_MAC_NUM];
+ u8 link_mode;
+ u8 link_mode_hb1;
+ u8 p2p_exist;
+ u8 p2p_exist_hb1;
+
+ u8 pta_req_band;
+ u8 dbcc_en; /* 1+1 and 2.4G-included */
+ u8 dbcc_2g_phy; /* which phy operate in 2G, HW_PHY_0 or HW_PHY_1 */
+ u8 rsvd;
u32 role_map;
- u32 mrole_type; /* btc_wl_mrole_type */
- u32 mrole_noa_duration; /* ms */
-} __packed;
+ u32 role_map_hb1;
+ u32 mrole_type; /* btc_wl_mrole_type: [31:16]:band1, [15:0]:band0 */
+
+ /* Before v10 use this linkmode */
+ u8 link_mode_v0;
+
+ /* v7 */
+ u8 connect_cnt;
+ u32 dbcc_chg; /* v7 v2*/
+
+ /* v8 */
+ u8 link_mode_chg; /* v8, v7 v2*/
+ u8 p2p_2g; /* v8, v7 */
+ u32 mrole_noa_duration; /* v8, v7 v2*/
+};
struct rtw89_btc_wl_ver_info {
u32 fw_coex; /* match with which coex_ver */
@@ -1955,7 +2055,7 @@ struct rtw89_btc_wl_afh_info {
u8 en;
u8 ch;
u8 bw;
- u8 rsvd;
+ u8 band;
} __packed;
struct rtw89_btc_wl_rfk_info {
@@ -2167,16 +2267,13 @@ struct rtw89_btc_wl_nhm {
};
struct rtw89_btc_wl_info {
- struct rtw89_btc_wl_link_info link_info[RTW89_PORT_NUM];
struct rtw89_btc_wl_link_info rlink_info[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER][RTW89_MAC_NUM];
+ struct rtw89_btc_chdef rf_ch_info[RTW89_PHY_NUM];
struct rtw89_btc_wl_rfk_info rfk_info;
- struct rtw89_btc_wl_ver_info ver_info;
- struct rtw89_btc_wl_afh_info afh_info;
+ struct rtw89_btc_wl_ver_info ver_info;
+ struct rtw89_btc_wl_afh_info afh_info[RTW89_MAC_NUM][RTW89_BAND_NUM];
+ struct rtw89_btc_wl_afh_info afh_info_last[RTW89_MAC_NUM][RTW89_BAND_NUM];
struct rtw89_btc_wl_role_info role_info;
- struct rtw89_btc_wl_role_info_v1 role_info_v1;
- struct rtw89_btc_wl_role_info_v2 role_info_v2;
- struct rtw89_btc_wl_role_info_v7 role_info_v7;
- struct rtw89_btc_wl_role_info_v8 role_info_v8;
struct rtw89_btc_wl_scan_info scan_info;
struct rtw89_btc_wl_dbcc_info dbcc_info;
struct rtw89_btc_wl_mlo_info mlo_info;
@@ -2191,12 +2288,18 @@ struct rtw89_btc_wl_info {
u8 pta_req_mac;
u8 bt_polut_type[RTW89_PHY_NUM]; /* BT polluted WL-Tx type for phy0/1 */
u8 rf_band_map[RTW89_PHY_NUM]; /* rf_band bit-map */
+ u8 ch_map[12];
+ u8 ch_map_le[5];
- bool is_5g_hi_channel;
+ bool is_5g_hi_ch;
+ bool is_5g_hi_ch_hb1;
bool go_client_exist;
+ bool go_client_exist_hb1;
bool noa_exist;
+ bool noa_exist_hb1;
bool pta_reg_mac_chg;
bool bg_mode;
+ bool bg_mode_hb1;
bool he_mode;
bool scbd_chg[BTC_ALL_BT];
bool fw_ver_mismatch;
@@ -3280,6 +3383,14 @@ struct rtw89_btc_fbtc_outsrc_set_info {
u8 rf_gbt_source;
u8 bt_enable_state;
u8 wl_btg_standby_chg;
+ /* bit[15]-> 0:2G/1:5G,6G, bit[14:0]-> WL HWBx ch freq in MHz */
+ /* forbidden group-> bit[1]:fbd rf-band, bit[0]: fbd enable */
+ u8 fbd_group_en[RTW89_MAC_NUM][2]; /* HWB0/1 +.Group0/1 */
+ u16 rf_center_freq[RTW89_MAC_NUM]; /* HWB0/1 */
+ /* forbidden group boundary: [15:8]->UP, [7:0]->LO */
+ u16 fbd_group_bound[RTW89_MAC_NUM][2]; /* HWB0/1 +.Group0/1 */
+ /* 11-bit in MHz, freq diff threshold */
+ u16 freq_diff_thres[RTW89_MAC_NUM][BTC_ALL_BT_EZL]; /* HWB0/1 vs.BT0/1/2 */
} __packed;
union rtw89_btc_fbtc_slot_u {
@@ -3363,6 +3474,7 @@ struct rtw89_btc_dm {
u8 lps_ctrl_change: 1;
u8 scbd_write_instant;
bool scbd_b2w_update;
+ bool pre_agc_chg;
};
struct rtw89_btc_ctrl {
@@ -4961,6 +5073,7 @@ struct rtw89_chip_info {
u8 mailbox;
u8 afh_guard_ch;
+ u16 fdd_iso_freq;
const u8 *wl_rssi_thres;
const u8 *bt_rssi_thres;
u8 rssi_tol;
diff --git a/drivers/net/wireless/realtek/rtw89/fw.c b/drivers/net/wireless/realtek/rtw89/fw.c
index 0e7168605850..41c033d2ae7b 100644
--- a/drivers/net/wireless/realtek/rtw89/fw.c
+++ b/drivers/net/wireless/realtek/rtw89/fw.c
@@ -5922,14 +5922,14 @@ int rtw89_fw_h2c_cxdrv_init_v10(struct rtw89_dev *rtwdev, u8 type)
int rtw89_fw_h2c_cxdrv_role(struct rtw89_dev *rtwdev, u8 type)
{
struct rtw89_btc *btc = &rtwdev->btc;
- const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info *role_info = &wl->role_info;
- struct rtw89_btc_wl_role_info_bpos *bpos = &role_info->role_map.role;
- struct rtw89_btc_wl_active_role *active = role_info->active_role;
+ struct rtw89_btc_wl_role_info *r = &wl->role_info;
+ const struct rtw89_btc_ver *ver = btc->ver;
+ struct rtw89_btc_wl_rlink *rl;
struct sk_buff *skb;
- u32 len;
+ u32 rmap = r->role_map;
u8 offset = 0;
+ u32 len;
u8 *cmd;
int ret;
int i;
@@ -5947,36 +5947,37 @@ int rtw89_fw_h2c_cxdrv_role(struct rtw89_dev *rtwdev, u8 type)
RTW89_SET_FWCMD_CXHDR_TYPE(cmd, type);
RTW89_SET_FWCMD_CXHDR_LEN(cmd, len - H2C_LEN_CXDRVHDR);
- RTW89_SET_FWCMD_CXROLE_CONNECT_CNT(cmd, role_info->connect_cnt);
- RTW89_SET_FWCMD_CXROLE_LINK_MODE(cmd, role_info->link_mode);
-
- RTW89_SET_FWCMD_CXROLE_ROLE_NONE(cmd, bpos->none);
- RTW89_SET_FWCMD_CXROLE_ROLE_STA(cmd, bpos->station);
- RTW89_SET_FWCMD_CXROLE_ROLE_AP(cmd, bpos->ap);
- RTW89_SET_FWCMD_CXROLE_ROLE_VAP(cmd, bpos->vap);
- RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC(cmd, bpos->adhoc);
- RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC_MASTER(cmd, bpos->adhoc_master);
- RTW89_SET_FWCMD_CXROLE_ROLE_MESH(cmd, bpos->mesh);
- RTW89_SET_FWCMD_CXROLE_ROLE_MONITOR(cmd, bpos->moniter);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_DEV(cmd, bpos->p2p_device);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GC(cmd, bpos->p2p_gc);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GO(cmd, bpos->p2p_go);
- RTW89_SET_FWCMD_CXROLE_ROLE_NAN(cmd, bpos->nan);
-
- for (i = 0; i < RTW89_PORT_NUM; i++, active++) {
- RTW89_SET_FWCMD_CXROLE_ACT_CONNECTED(cmd, active->connected, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_PID(cmd, active->pid, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_PHY(cmd, active->phy, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_NOA(cmd, active->noa, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_BAND(cmd, active->band, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_CLIENT_PS(cmd, active->client_ps, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_BW(cmd, active->bw, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_ROLE(cmd, active->role, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_CH(cmd, active->ch, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_TX_LVL(cmd, active->tx_lvl, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_RX_LVL(cmd, active->rx_lvl, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_TX_RATE(cmd, active->tx_rate, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_RX_RATE(cmd, active->rx_rate, i, offset);
+ RTW89_SET_FWCMD_CXROLE_CONNECT_CNT(cmd, r->connect_cnt);
+ RTW89_SET_FWCMD_CXROLE_LINK_MODE(cmd, r->link_mode);
+
+ RTW89_SET_FWCMD_CXROLE_ROLE_NONE(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_NONE)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_STA(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_STATION)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_AP(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_AP)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_VAP(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_AP_VLAN)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_ADHOC)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC_MASTER(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_ADHOC_MASTER)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_MESH(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_MESH_POINT)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_MONITOR(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_MONITOR)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_DEV(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_DEVICE)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GC(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_CLIENT)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GO(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_GO)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_NAN(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_NAN)));
+
+ for (i = 0; i < RTW89_PORT_NUM; i++) {
+ rl = &r->rlink[i][RTW89_MAC_0];
+ RTW89_SET_FWCMD_CXROLE_ACT_CONNECTED(cmd, rl->connected, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_PID(cmd, rl->pid, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_PHY(cmd, rl->phy, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_NOA(cmd, rl->noa, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_BAND(cmd, rl->rf_band, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_CLIENT_PS(cmd, rl->client_ps, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_BW(cmd, rl->bw, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_ROLE(cmd, rl->role, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_CH(cmd, rl->ch, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_TX_LVL(cmd, rl->tx_lvl, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_RX_LVL(cmd, rl->rx_lvl, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_TX_RATE(cmd, rl->tx_rate, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_RX_RATE(cmd, rl->rx_rate, i, offset);
}
rtw89_h2c_pkt_set_hdr(rtwdev, skb, FWCMD_TYPE_H2C,
@@ -6005,12 +6006,12 @@ int rtw89_fw_h2c_cxdrv_role_v1(struct rtw89_dev *rtwdev, u8 type)
struct rtw89_btc *btc = &rtwdev->btc;
const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v1 *role_info = &wl->role_info_v1;
- struct rtw89_btc_wl_role_info_bpos *bpos = &role_info->role_map.role;
- struct rtw89_btc_wl_active_role_v1 *active = role_info->active_role_v1;
+ struct rtw89_btc_wl_role_info *r = &wl->role_info;
+ struct rtw89_btc_wl_rlink *rl;
struct sk_buff *skb;
- u32 len;
+ u32 rmap = r->role_map;
u8 *cmd, offset;
+ u32 len;
int ret;
int i;
@@ -6027,47 +6028,49 @@ int rtw89_fw_h2c_cxdrv_role_v1(struct rtw89_dev *rtwdev, u8 type)
RTW89_SET_FWCMD_CXHDR_TYPE(cmd, type);
RTW89_SET_FWCMD_CXHDR_LEN(cmd, len - H2C_LEN_CXDRVHDR);
- RTW89_SET_FWCMD_CXROLE_CONNECT_CNT(cmd, role_info->connect_cnt);
- RTW89_SET_FWCMD_CXROLE_LINK_MODE(cmd, role_info->link_mode);
-
- RTW89_SET_FWCMD_CXROLE_ROLE_NONE(cmd, bpos->none);
- RTW89_SET_FWCMD_CXROLE_ROLE_STA(cmd, bpos->station);
- RTW89_SET_FWCMD_CXROLE_ROLE_AP(cmd, bpos->ap);
- RTW89_SET_FWCMD_CXROLE_ROLE_VAP(cmd, bpos->vap);
- RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC(cmd, bpos->adhoc);
- RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC_MASTER(cmd, bpos->adhoc_master);
- RTW89_SET_FWCMD_CXROLE_ROLE_MESH(cmd, bpos->mesh);
- RTW89_SET_FWCMD_CXROLE_ROLE_MONITOR(cmd, bpos->moniter);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_DEV(cmd, bpos->p2p_device);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GC(cmd, bpos->p2p_gc);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GO(cmd, bpos->p2p_go);
- RTW89_SET_FWCMD_CXROLE_ROLE_NAN(cmd, bpos->nan);
+ RTW89_SET_FWCMD_CXROLE_CONNECT_CNT(cmd, r->connect_cnt);
+ RTW89_SET_FWCMD_CXROLE_LINK_MODE(cmd, r->link_mode);
+
+ RTW89_SET_FWCMD_CXROLE_ROLE_NONE(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_NONE)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_STA(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_STATION)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_AP(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_AP)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_VAP(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_AP_VLAN)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_ADHOC)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC_MASTER(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_ADHOC_MASTER)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_MESH(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_MESH_POINT)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_MONITOR(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_MONITOR)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_DEV(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_DEVICE)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GC(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_CLIENT)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GO(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_GO)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_NAN(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_NAN)));
offset = PORT_DATA_OFFSET;
- for (i = 0; i < RTW89_PORT_NUM; i++, active++) {
- RTW89_SET_FWCMD_CXROLE_ACT_CONNECTED(cmd, active->connected, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_PID(cmd, active->pid, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_PHY(cmd, active->phy, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_NOA(cmd, active->noa, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_BAND(cmd, active->band, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_CLIENT_PS(cmd, active->client_ps, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_BW(cmd, active->bw, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_ROLE(cmd, active->role, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_CH(cmd, active->ch, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_TX_LVL(cmd, active->tx_lvl, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_RX_LVL(cmd, active->rx_lvl, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_TX_RATE(cmd, active->tx_rate, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_RX_RATE(cmd, active->rx_rate, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_NOA_DUR(cmd, active->noa_duration, i, offset);
+
+ for (i = 0; i < RTW89_PORT_NUM; i++) {
+ rl = &r->rlink[i][RTW89_MAC_0];
+ RTW89_SET_FWCMD_CXROLE_ACT_CONNECTED(cmd, rl->connected, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_PID(cmd, rl->pid, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_PHY(cmd, rl->phy, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_NOA(cmd, rl->noa, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_BAND(cmd, rl->rf_band, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_CLIENT_PS(cmd, rl->client_ps, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_BW(cmd, rl->bw, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_ROLE(cmd, rl->role, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_CH(cmd, rl->ch, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_TX_LVL(cmd, rl->tx_lvl, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_RX_LVL(cmd, rl->rx_lvl, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_TX_RATE(cmd, rl->tx_rate, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_RX_RATE(cmd, rl->rx_rate, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_NOA_DUR(cmd, rl->noa_dur, i, offset);
}
offset = len - H2C_LEN_CXDRVINFO_ROLE_DBCC_LEN;
- RTW89_SET_FWCMD_CXROLE_MROLE_TYPE(cmd, role_info->mrole_type, offset);
- RTW89_SET_FWCMD_CXROLE_MROLE_NOA(cmd, role_info->mrole_noa_duration, offset);
- RTW89_SET_FWCMD_CXROLE_DBCC_EN(cmd, role_info->dbcc_en, offset);
- RTW89_SET_FWCMD_CXROLE_DBCC_CHG(cmd, role_info->dbcc_chg, offset);
- RTW89_SET_FWCMD_CXROLE_DBCC_2G_PHY(cmd, role_info->dbcc_2g_phy, offset);
- RTW89_SET_FWCMD_CXROLE_LINK_MODE_CHG(cmd, role_info->link_mode_chg, offset);
+ RTW89_SET_FWCMD_CXROLE_MROLE_TYPE(cmd, r->mrole_type, offset);
+ RTW89_SET_FWCMD_CXROLE_MROLE_NOA(cmd, r->mrole_noa_duration, offset);
+ RTW89_SET_FWCMD_CXROLE_DBCC_EN(cmd, r->dbcc_en, offset);
+ RTW89_SET_FWCMD_CXROLE_DBCC_CHG(cmd, r->dbcc_chg, offset);
+ RTW89_SET_FWCMD_CXROLE_DBCC_2G_PHY(cmd, r->dbcc_2g_phy, offset);
+ RTW89_SET_FWCMD_CXROLE_LINK_MODE_CHG(cmd, r->link_mode_chg, offset);
rtw89_h2c_pkt_set_hdr(rtwdev, skb, FWCMD_TYPE_H2C,
H2C_CAT_OUTSRC, BTFC_SET,
@@ -6095,10 +6098,10 @@ int rtw89_fw_h2c_cxdrv_role_v2(struct rtw89_dev *rtwdev, u8 type)
struct rtw89_btc *btc = &rtwdev->btc;
const struct rtw89_btc_ver *ver = btc->ver;
struct rtw89_btc_wl_info *wl = &btc->cx.wl;
- struct rtw89_btc_wl_role_info_v2 *role_info = &wl->role_info_v2;
- struct rtw89_btc_wl_role_info_bpos *bpos = &role_info->role_map.role;
- struct rtw89_btc_wl_active_role_v2 *active = role_info->active_role_v2;
+ struct rtw89_btc_wl_role_info *r = &wl->role_info;
+ struct rtw89_btc_wl_rlink *rl;
struct sk_buff *skb;
+ u32 rmap = r->role_map;
u32 len;
u8 *cmd, offset;
int ret;
@@ -6117,43 +6120,45 @@ int rtw89_fw_h2c_cxdrv_role_v2(struct rtw89_dev *rtwdev, u8 type)
RTW89_SET_FWCMD_CXHDR_TYPE(cmd, type);
RTW89_SET_FWCMD_CXHDR_LEN(cmd, len - H2C_LEN_CXDRVHDR);
- RTW89_SET_FWCMD_CXROLE_CONNECT_CNT(cmd, role_info->connect_cnt);
- RTW89_SET_FWCMD_CXROLE_LINK_MODE(cmd, role_info->link_mode);
-
- RTW89_SET_FWCMD_CXROLE_ROLE_NONE(cmd, bpos->none);
- RTW89_SET_FWCMD_CXROLE_ROLE_STA(cmd, bpos->station);
- RTW89_SET_FWCMD_CXROLE_ROLE_AP(cmd, bpos->ap);
- RTW89_SET_FWCMD_CXROLE_ROLE_VAP(cmd, bpos->vap);
- RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC(cmd, bpos->adhoc);
- RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC_MASTER(cmd, bpos->adhoc_master);
- RTW89_SET_FWCMD_CXROLE_ROLE_MESH(cmd, bpos->mesh);
- RTW89_SET_FWCMD_CXROLE_ROLE_MONITOR(cmd, bpos->moniter);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_DEV(cmd, bpos->p2p_device);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GC(cmd, bpos->p2p_gc);
- RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GO(cmd, bpos->p2p_go);
- RTW89_SET_FWCMD_CXROLE_ROLE_NAN(cmd, bpos->nan);
+ RTW89_SET_FWCMD_CXROLE_CONNECT_CNT(cmd, r->connect_cnt);
+ RTW89_SET_FWCMD_CXROLE_LINK_MODE(cmd, r->link_mode);
+
+ RTW89_SET_FWCMD_CXROLE_ROLE_NONE(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_NONE)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_STA(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_STATION)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_AP(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_AP)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_VAP(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_AP_VLAN)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_ADHOC)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_ADHOC_MASTER(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_ADHOC_MASTER)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_MESH(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_MESH_POINT)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_MONITOR(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_MONITOR)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_DEV(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_DEVICE)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GC(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_CLIENT)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_P2P_GO(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_P2P_GO)));
+ RTW89_SET_FWCMD_CXROLE_ROLE_NAN(cmd, !!(rmap & BIT(RTW89_WIFI_ROLE_NAN)));
offset = PORT_DATA_OFFSET;
- for (i = 0; i < RTW89_PORT_NUM; i++, active++) {
- RTW89_SET_FWCMD_CXROLE_ACT_CONNECTED_V2(cmd, active->connected, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_PID_V2(cmd, active->pid, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_PHY_V2(cmd, active->phy, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_NOA_V2(cmd, active->noa, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_BAND_V2(cmd, active->band, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_CLIENT_PS_V2(cmd, active->client_ps, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_BW_V2(cmd, active->bw, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_ROLE_V2(cmd, active->role, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_CH_V2(cmd, active->ch, i, offset);
- RTW89_SET_FWCMD_CXROLE_ACT_NOA_DUR_V2(cmd, active->noa_duration, i, offset);
+
+ for (i = 0; i < RTW89_PORT_NUM; i++) {
+ rl = &r->rlink[i][RTW89_MAC_0];
+ RTW89_SET_FWCMD_CXROLE_ACT_CONNECTED_V2(cmd, rl->connected, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_PID_V2(cmd, rl->pid, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_PHY_V2(cmd, rl->phy, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_NOA_V2(cmd, rl->noa, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_BAND_V2(cmd, rl->rf_band, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_CLIENT_PS_V2(cmd, rl->client_ps, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_BW_V2(cmd, rl->bw, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_ROLE_V2(cmd, rl->role, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_CH_V2(cmd, rl->ch, i, offset);
+ RTW89_SET_FWCMD_CXROLE_ACT_NOA_DUR_V2(cmd, rl->noa_dur, i, offset);
}
offset = len - H2C_LEN_CXDRVINFO_ROLE_DBCC_LEN;
- RTW89_SET_FWCMD_CXROLE_MROLE_TYPE(cmd, role_info->mrole_type, offset);
- RTW89_SET_FWCMD_CXROLE_MROLE_NOA(cmd, role_info->mrole_noa_duration, offset);
- RTW89_SET_FWCMD_CXROLE_DBCC_EN(cmd, role_info->dbcc_en, offset);
- RTW89_SET_FWCMD_CXROLE_DBCC_CHG(cmd, role_info->dbcc_chg, offset);
- RTW89_SET_FWCMD_CXROLE_DBCC_2G_PHY(cmd, role_info->dbcc_2g_phy, offset);
- RTW89_SET_FWCMD_CXROLE_LINK_MODE_CHG(cmd, role_info->link_mode_chg, offset);
+ RTW89_SET_FWCMD_CXROLE_MROLE_TYPE(cmd, r->mrole_type, offset);
+ RTW89_SET_FWCMD_CXROLE_MROLE_NOA(cmd, r->mrole_noa_duration, offset);
+ RTW89_SET_FWCMD_CXROLE_DBCC_EN(cmd, r->dbcc_en, offset);
+ RTW89_SET_FWCMD_CXROLE_DBCC_CHG(cmd, r->dbcc_chg, offset);
+ RTW89_SET_FWCMD_CXROLE_DBCC_2G_PHY(cmd, r->dbcc_2g_phy, offset);
+ RTW89_SET_FWCMD_CXROLE_LINK_MODE_CHG(cmd, r->link_mode_chg, offset);
rtw89_h2c_pkt_set_hdr(rtwdev, skb, FWCMD_TYPE_H2C,
H2C_CAT_OUTSRC, BTFC_SET,
@@ -6175,12 +6180,14 @@ int rtw89_fw_h2c_cxdrv_role_v2(struct rtw89_dev *rtwdev, u8 type)
int rtw89_fw_h2c_cxdrv_role_v7(struct rtw89_dev *rtwdev, u8 type)
{
- struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_role_info_v7 *role = &btc->cx.wl.role_info_v7;
+ struct rtw89_btc_wl_role_info *r = &rtwdev->btc.cx.wl.role_info;
struct rtw89_h2c_cxrole_v7 *h2c;
+ struct rtw89_btc_wl_rlink *rl;
u32 len = sizeof(*h2c);
struct sk_buff *skb;
+ __le32 rm;
int ret;
+ u8 i;
skb = rtw89_fw_h2c_alloc_skb_with_hdr(rtwdev, len);
if (!skb) {
@@ -6190,16 +6197,35 @@ int rtw89_fw_h2c_cxdrv_role_v7(struct rtw89_dev *rtwdev, u8 type)
skb_put(skb, len);
h2c = (struct rtw89_h2c_cxrole_v7 *)skb->data;
- h2c->hdr.type = type;
- h2c->hdr.ver = btc->ver->fwlrole;
- h2c->hdr.len = len - H2C_LEN_CXDRVHDR_V7;
- memcpy(&h2c->_u8, role, sizeof(h2c->_u8));
- h2c->_u32.role_map = cpu_to_le32(role->role_map);
- h2c->_u32.mrole_type = cpu_to_le32(role->mrole_type);
- h2c->_u32.mrole_noa_duration = cpu_to_le32(role->mrole_noa_duration);
- h2c->_u32.dbcc_en = cpu_to_le32(role->dbcc_en);
- h2c->_u32.dbcc_chg = cpu_to_le32(role->dbcc_chg);
- h2c->_u32.dbcc_2g_phy = cpu_to_le32(role->dbcc_2g_phy);
+ h2c->r.connect_cnt = r->connect_cnt;
+ h2c->r.link_mode = r->link_mode;
+ h2c->r.link_mode_chg = r->link_mode_chg;
+ h2c->r.p2p_2g = r->p2p_2g;
+
+ for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) {
+ rl = &r->rlink[i][RTW89_MAC_0];
+ h2c->r.active_role[i].connected = rl->connected;
+ h2c->r.active_role[i].pid = rl->pid;
+ h2c->r.active_role[i].phy = rl->phy;
+ h2c->r.active_role[i].noa = rl->noa;
+
+ h2c->r.active_role[i].band = rl->rf_band;
+ h2c->r.active_role[i].client_ps = rl->client_ps;
+ h2c->r.active_role[i].bw = rl->bw;
+ h2c->r.active_role[i].role = rl->role;
+
+ h2c->r.active_role[i].ch = rl->ch;
+ h2c->r.active_role[i].noa_dur = rl->noa_dur;
+ h2c->r.active_role[i].client_cnt = rl->client_cnt;
+ }
+
+ rm = cpu_to_le32(r->role_map);
+ memcpy(&h2c->r.role_map, &rm, sizeof(h2c->r.role_map));
+ h2c->r.mrole_type = cpu_to_le32(r->mrole_type);
+ h2c->r.mrole_noa_duration = cpu_to_le32(r->mrole_noa_duration);
+ h2c->r.dbcc_en = cpu_to_le32((u32)r->dbcc_en);
+ h2c->r.dbcc_chg = cpu_to_le32(r->dbcc_chg);
+ h2c->r.dbcc_2g_phy = cpu_to_le32(r->dbcc_2g_phy);
rtw89_h2c_pkt_set_hdr(rtwdev, skb, FWCMD_TYPE_H2C,
H2C_CAT_OUTSRC, BTFC_SET,
@@ -6221,12 +6247,14 @@ int rtw89_fw_h2c_cxdrv_role_v7(struct rtw89_dev *rtwdev, u8 type)
int rtw89_fw_h2c_cxdrv_role_v8(struct rtw89_dev *rtwdev, u8 type)
{
- struct rtw89_btc *btc = &rtwdev->btc;
- struct rtw89_btc_wl_role_info_v8 *role = &btc->cx.wl.role_info_v8;
+ struct rtw89_btc_wl_role_info *r = &rtwdev->btc.cx.wl.role_info;
struct rtw89_h2c_cxrole_v8 *h2c;
+ struct rtw89_btc_wl_rlink *rl;
u32 len = sizeof(*h2c);
struct sk_buff *skb;
+ __le32 rm;
int ret;
+ u8 i, j;
skb = rtw89_fw_h2c_alloc_skb_with_hdr(rtwdev, len);
if (!skb) {
@@ -6237,12 +6265,118 @@ int rtw89_fw_h2c_cxdrv_role_v8(struct rtw89_dev *rtwdev, u8 type)
h2c = (struct rtw89_h2c_cxrole_v8 *)skb->data;
h2c->hdr.type = type;
- h2c->hdr.ver = btc->ver->fwlrole;
+ h2c->hdr.ver = rtwdev->btc.ver->fwlrole;
+ h2c->hdr.len = len - H2C_LEN_CXDRVHDR_V7;
+ h2c->r.connect_cnt = r->connect_cnt;
+ h2c->r.link_mode = r->link_mode;
+ h2c->r.link_mode_chg = r->link_mode_chg;
+ h2c->r.p2p_2g = r->p2p_2g;
+ h2c->r.pta_req_band = r->pta_req_band;
+ h2c->r.dbcc_en = r->dbcc_en;
+ h2c->r.dbcc_chg = r->dbcc_chg;
+ h2c->r.dbcc_2g_phy = r->dbcc_2g_phy;
+
+ for (j = RTW89_MAC_0; j <= RTW89_MAC_1; j++) {
+ for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) {
+ rl = &r->rlink[i][j];
+ h2c->r.rlink[i][j].connected = rl->connected;
+ h2c->r.rlink[i][j].pid = rl->pid;
+ h2c->r.rlink[i][j].phy = rl->phy;
+ h2c->r.rlink[i][j].noa = rl->noa;
+
+ h2c->r.rlink[i][j].rf_band = rl->rf_band;
+ h2c->r.rlink[i][j].active = rl->active;
+ h2c->r.rlink[i][j].bw = rl->bw;
+ h2c->r.rlink[i][j].role = rl->role;
+
+ h2c->r.rlink[i][j].ch = rl->ch;
+ h2c->r.rlink[i][j].noa_dur = rl->noa_dur;
+ h2c->r.rlink[i][j].client_cnt = rl->client_cnt;
+ h2c->r.rlink[i][j].mode = rl->mode;
+ }
+ }
+
+ rm = cpu_to_le32(r->role_map);
+ memcpy(&h2c->r.role_map, &rm, sizeof(h2c->r.role_map));
+ h2c->r.mrole_type = cpu_to_le32(r->mrole_type);
+ h2c->r.mrole_noa_duration = cpu_to_le32(r->mrole_noa_duration);
+
+ rtw89_h2c_pkt_set_hdr(rtwdev, skb, FWCMD_TYPE_H2C,
+ H2C_CAT_OUTSRC, BTFC_SET,
+ SET_DRV_INFO, 0, 0,
+ len);
+
+ ret = rtw89_h2c_tx(rtwdev, skb, false);
+ if (ret) {
+ rtw89_err(rtwdev, "failed to send h2c\n");
+ goto fail;
+ }
+
+ return 0;
+fail:
+ dev_kfree_skb_any(skb);
+
+ return ret;
+}
+
+int rtw89_fw_h2c_cxdrv_role_v10(struct rtw89_dev *rtwdev, u8 type)
+{
+ struct rtw89_btc_wl_role_info *r = &rtwdev->btc.cx.wl.role_info;
+ struct rtw89_h2c_cxrole_v10 *h2c;
+ struct rtw89_btc_wl_rlink *rl;
+ u32 len = sizeof(*h2c);
+ struct sk_buff *skb;
+ __le32 rm;
+ int ret;
+ u8 i, j;
+
+ skb = rtw89_fw_h2c_alloc_skb_with_hdr(rtwdev, len);
+ if (!skb) {
+ rtw89_err(rtwdev, "failed to alloc skb for h2c cxdrv_role\n");
+ return -ENOMEM;
+ }
+ skb_put(skb, len);
+ h2c = (struct rtw89_h2c_cxrole_v10 *)skb->data;
+
+ h2c->hdr.type = type;
+ h2c->hdr.ver = rtwdev->btc.ver->fwlrole;
h2c->hdr.len = len - H2C_LEN_CXDRVHDR_V7;
- memcpy(&h2c->_u8, role, sizeof(h2c->_u8));
- h2c->_u32.role_map = cpu_to_le32(role->role_map);
- h2c->_u32.mrole_type = cpu_to_le32(role->mrole_type);
- h2c->_u32.mrole_noa_duration = cpu_to_le32(role->mrole_noa_duration);
+
+ for (j = RTW89_MAC_0; j <= RTW89_MAC_1; j++) {
+ for (i = 0; i < RTW89_BE_BTC_WL_MAX_ROLE_NUMBER; i++) {
+ rl = &r->rlink[i][j];
+ h2c->r.rlink[i][j].connected = rl->connected;
+ h2c->r.rlink[i][j].pid = rl->pid;
+ h2c->r.rlink[i][j].phy = rl->phy;
+ h2c->r.rlink[i][j].noa = rl->noa;
+
+ h2c->r.rlink[i][j].rf_band = rl->rf_band;
+ h2c->r.rlink[i][j].active = rl->active;
+ h2c->r.rlink[i][j].bw = rl->bw;
+ h2c->r.rlink[i][j].role = rl->role;
+
+ h2c->r.rlink[i][j].ch = rl->ch;
+ h2c->r.rlink[i][j].noa_dur = rl->noa_dur;
+ h2c->r.rlink[i][j].client_cnt = rl->client_cnt;
+ h2c->r.rlink[i][j].mode = rl->mode;
+ h2c->r.rlink[i][j].mac_id = rl->mac_id;
+ }
+ }
+
+ h2c->r.link_mode = r->link_mode;
+ h2c->r.link_mode_hb1 = r->link_mode_hb1;
+ h2c->r.p2p_exist = r->p2p_exist;
+ h2c->r.p2p_exist_hb1 = r->p2p_exist_hb1;
+
+ h2c->r.pta_req_band = r->pta_req_band;
+ h2c->r.dbcc_en = r->dbcc_en;
+ h2c->r.dbcc_2g_phy = r->dbcc_2g_phy;
+
+ rm = cpu_to_le32(r->role_map);
+ memcpy(&h2c->r.role_map, &rm, sizeof(h2c->r.role_map));
+ rm = cpu_to_le32(r->role_map_hb1);
+ memcpy(&h2c->r.role_map_hb1, &rm, sizeof(h2c->r.role_map_hb1));
+ h2c->r.mrole_type = cpu_to_le32(r->mrole_type);
rtw89_h2c_pkt_set_hdr(rtwdev, skb, FWCMD_TYPE_H2C,
H2C_CAT_OUTSRC, BTFC_SET,
diff --git a/drivers/net/wireless/realtek/rtw89/fw.h b/drivers/net/wireless/realtek/rtw89/fw.h
index af126d15a1fb..1e4267b22b36 100644
--- a/drivers/net/wireless/realtek/rtw89/fw.h
+++ b/drivers/net/wireless/realtek/rtw89/fw.h
@@ -2433,54 +2433,19 @@ struct rtw89_h2c_cxctrl_v7 {
#define H2C_LEN_CXDRVHDR sizeof(struct rtw89_h2c_cxhdr)
#define H2C_LEN_CXDRVHDR_V7 sizeof(struct rtw89_h2c_cxhdr_v7)
-struct rtw89_btc_wl_role_info_v7_u8 {
- u8 connect_cnt;
- u8 link_mode;
- u8 link_mode_chg;
- u8 p2p_2g;
-
- struct rtw89_btc_wl_active_role_v7 active_role[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER];
-} __packed;
-
-struct rtw89_btc_wl_role_info_v7_u32 {
- __le32 role_map;
- __le32 mrole_type;
- __le32 mrole_noa_duration;
- __le32 dbcc_en;
- __le32 dbcc_chg;
- __le32 dbcc_2g_phy;
-} __packed;
-
struct rtw89_h2c_cxrole_v7 {
struct rtw89_h2c_cxhdr_v7 hdr;
- struct rtw89_btc_wl_role_info_v7_u8 _u8;
- struct rtw89_btc_wl_role_info_v7_u32 _u32;
-} __packed;
-
-struct rtw89_btc_wl_role_info_v8_u8 {
- u8 connect_cnt;
- u8 link_mode;
- u8 link_mode_chg;
- u8 p2p_2g;
-
- u8 pta_req_band;
- u8 dbcc_en;
- u8 dbcc_chg;
- u8 dbcc_2g_phy;
-
- struct rtw89_btc_wl_rlink rlink[RTW89_BE_BTC_WL_MAX_ROLE_NUMBER][RTW89_MAC_NUM];
+ struct rtw89_btc_wl_role_info_v7 r;
} __packed;
-struct rtw89_btc_wl_role_info_v8_u32 {
- __le32 role_map;
- __le32 mrole_type;
- __le32 mrole_noa_duration;
+struct rtw89_h2c_cxrole_v8 {
+ struct rtw89_h2c_cxhdr_v7 hdr;
+ struct rtw89_btc_wl_role_info_v8 r;
} __packed;
-struct rtw89_h2c_cxrole_v8 {
+struct rtw89_h2c_cxrole_v10 {
struct rtw89_h2c_cxhdr_v7 hdr;
- struct rtw89_btc_wl_role_info_v8_u8 _u8;
- struct rtw89_btc_wl_role_info_v8_u32 _u32;
+ struct rtw89_btc_wl_role_info_v10 r;
} __packed;
struct rtw89_h2c_cxosi {
@@ -5413,6 +5378,7 @@ int rtw89_fw_h2c_cxdrv_role_v1(struct rtw89_dev *rtwdev, u8 type);
int rtw89_fw_h2c_cxdrv_role_v2(struct rtw89_dev *rtwdev, u8 type);
int rtw89_fw_h2c_cxdrv_role_v7(struct rtw89_dev *rtwdev, u8 type);
int rtw89_fw_h2c_cxdrv_role_v8(struct rtw89_dev *rtwdev, u8 type);
+int rtw89_fw_h2c_cxdrv_role_v10(struct rtw89_dev *rtwdev, u8 type);
int rtw89_fw_h2c_cxdrv_osi_info(struct rtw89_dev *rtwdev, u8 type);
int rtw89_fw_h2c_cxdrv_ctrl(struct rtw89_dev *rtwdev, u8 type);
int rtw89_fw_h2c_cxdrv_ctrl_v7(struct rtw89_dev *rtwdev, u8 type);
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8851b.c b/drivers/net/wireless/realtek/rtw89/rtw8851b.c
index 50480f72c96d..91d6cddc713e 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8851b.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8851b.c
@@ -2725,6 +2725,7 @@ const struct rtw89_chip_info rtw8851b_chip_info = {
.mailbox = 0x1,
.afh_guard_ch = 6,
+ .fdd_iso_freq = 1000,
.wl_rssi_thres = rtw89_btc_8851b_wl_rssi_thres,
.bt_rssi_thres = rtw89_btc_8851b_bt_rssi_thres,
.rssi_tol = 2,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852a.c b/drivers/net/wireless/realtek/rtw89/rtw8852a.c
index 0c7794742650..ed6dee63694f 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852a.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852a.c
@@ -2464,6 +2464,7 @@ const struct rtw89_chip_info rtw8852a_chip_info = {
.mailbox = 0x1,
.afh_guard_ch = 6,
+ .fdd_iso_freq = 1000,
.wl_rssi_thres = rtw89_btc_8852a_wl_rssi_thres,
.bt_rssi_thres = rtw89_btc_8852a_bt_rssi_thres,
.rssi_tol = 2,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852b.c b/drivers/net/wireless/realtek/rtw89/rtw8852b.c
index 5904127cc836..4f55a153d169 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852b.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852b.c
@@ -1060,6 +1060,7 @@ const struct rtw89_chip_info rtw8852b_chip_info = {
.mailbox = 0x1,
.afh_guard_ch = 6,
+ .fdd_iso_freq = 1000,
.wl_rssi_thres = rtw89_btc_8852b_wl_rssi_thres,
.bt_rssi_thres = rtw89_btc_8852b_bt_rssi_thres,
.rssi_tol = 2,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852bt.c b/drivers/net/wireless/realtek/rtw89/rtw8852bt.c
index e68f73827fa5..9e0c48fde2fa 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852bt.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852bt.c
@@ -898,6 +898,7 @@ const struct rtw89_chip_info rtw8852bt_chip_info = {
.mailbox = 0x1,
.afh_guard_ch = 6,
+ .fdd_iso_freq = 1000,
.wl_rssi_thres = rtw89_btc_8852bt_wl_rssi_thres,
.bt_rssi_thres = rtw89_btc_8852bt_bt_rssi_thres,
.rssi_tol = 2,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8852c.c b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
index 968666280c89..f21dd87e3846 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8852c.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8852c.c
@@ -3266,6 +3266,7 @@ const struct rtw89_chip_info rtw8852c_chip_info = {
.mailbox = 0x1,
.afh_guard_ch = 6,
+ .fdd_iso_freq = 1000,
.wl_rssi_thres = rtw89_btc_8852c_wl_rssi_thres,
.bt_rssi_thres = rtw89_btc_8852c_bt_rssi_thres,
.rssi_tol = 2,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8922a.c b/drivers/net/wireless/realtek/rtw89/rtw8922a.c
index fe87b4929ddc..cdcce091b922 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8922a.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8922a.c
@@ -3249,6 +3249,7 @@ const struct rtw89_chip_info rtw8922a_chip_info = {
.mailbox = 0x1,
.afh_guard_ch = 6,
+ .fdd_iso_freq = 1000,
.wl_rssi_thres = rtw89_btc_8922a_wl_rssi_thres,
.bt_rssi_thres = rtw89_btc_8922a_bt_rssi_thres,
.rssi_tol = 2,
diff --git a/drivers/net/wireless/realtek/rtw89/rtw8922d.c b/drivers/net/wireless/realtek/rtw89/rtw8922d.c
index 768434db14c6..aeade858ce95 100644
--- a/drivers/net/wireless/realtek/rtw89/rtw8922d.c
+++ b/drivers/net/wireless/realtek/rtw89/rtw8922d.c
@@ -3535,6 +3535,7 @@ const struct rtw89_chip_info rtw8922d_chip_info = {
.mailbox = 0x1,
.afh_guard_ch = 6,
+ .fdd_iso_freq = 1000,
.wl_rssi_thres = rtw89_btc_8922d_wl_rssi_thres,
.bt_rssi_thres = rtw89_btc_8922d_bt_rssi_thres,
.rssi_tol = 2,
--
2.25.1
next prev parent reply other threads:[~2026-07-12 3:06 UTC|newest]
Thread overview: 12+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-07-12 3:04 [PATCH rtw-next 00/11] wifi: rtw89: coex: implement coex for RTL8922D Ping-Ke Shih
2026-07-12 3:04 ` Ping-Ke Shih [this message]
2026-07-12 3:04 ` [PATCH rtw-next 02/11] wifi: rtw89: coex: Rearrange coexistence control structure Ping-Ke Shih
2026-07-12 3:04 ` [PATCH rtw-next 03/11] wifi: rtw89: coex: Update driver outsource info to firmware version 6 Ping-Ke Shih
2026-07-12 3:04 ` [PATCH rtw-next 04/11] wifi: rtw89: ceox: Update antenna & grant signal setting Ping-Ke Shih
2026-07-12 3:05 ` [PATCH rtw-next 05/11] wifi: rtw89: coex: Rearrange Bluetooth firmware report entry Ping-Ke Shih
2026-07-12 3:05 ` [PATCH rtw-next 06/11] wifi: rtw89: coex: Refine send firmware command function Ping-Ke Shih
2026-07-12 3:05 ` [PATCH rtw-next 07/11] wifi: rtw89: coex: Refine _reset_btc_var() Ping-Ke Shih
2026-07-12 3:05 ` [PATCH rtw-next 08/11] wifi: rtw89: coex: Correct SET_RFE settings Ping-Ke Shih
2026-07-12 3:05 ` [PATCH rtw-next 09/11] wifi: rtw89: coex: Add firmware report control report v11 Ping-Ke Shih
2026-07-12 3:05 ` [PATCH rtw-next 10/11] wifi: rtw89: coex: update external control length by case Ping-Ke Shih
2026-07-12 3:05 ` [PATCH rtw-next 11/11] wifi: rtw89: coex: Update coexistence version to 9.24.0 Ping-Ke Shih
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260712030506.43438-2-pkshih@realtek.com \
--to=pkshih@realtek.com \
--cc=ku920601@realtek.com \
--cc=linux-wireless@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox