XTAL SI is an indirect serial interface to access registers in another hardware domain. When BT driver initializes UART interface, firmware might rarely control XTAL SI at the same time causing access racing. Current is to adjust initialization flow to avoid the racing. To make the racing visible if it still presents, add a message to address this. USB adapters might be unplugged suddenly, causing flooding messages. Check RTW89_FLAG_UNPLUGGED flag to avoid them. Signed-off-by: Ping-Ke Shih --- v2: handle USB being unplugged case to avoid warnings. --- drivers/net/wireless/realtek/rtw89/mac.c | 31 +++++++++++++++++++-- drivers/net/wireless/realtek/rtw89/mac_be.c | 13 ++++++++- 2 files changed, 40 insertions(+), 4 deletions(-) diff --git a/drivers/net/wireless/realtek/rtw89/mac.c b/drivers/net/wireless/realtek/rtw89/mac.c index e5f2fa3b2b37..8987077bf756 100644 --- a/drivers/net/wireless/realtek/rtw89/mac.c +++ b/drivers/net/wireless/realtek/rtw89/mac.c @@ -1483,6 +1483,15 @@ static void rtw89_mac_power_switch_boot_mode(struct rtw89_dev *rtwdev) rtw89_write32_clr(rtwdev, R_AX_RSV_CTRL, B_AX_R_DIS_PRST); } +static int rtw89_mac_pwr_off_func_for_unplugged(struct rtw89_dev *rtwdev) +{ + /* + * Avoid accessing IO for unplugged power-off to prevent warnings, + * especially XTAL SI. + */ + return 0; +} + static int rtw89_mac_power_switch(struct rtw89_dev *rtwdev, bool on) { const struct rtw89_mac_gen_def *mac = rtwdev->chip->mac_def; @@ -1497,8 +1506,13 @@ static int rtw89_mac_power_switch(struct rtw89_dev *rtwdev, bool on) cfg_seq = chip->pwr_on_seq; cfg_func = chip->ops->pwr_on_func; } else { - cfg_seq = chip->pwr_off_seq; - cfg_func = chip->ops->pwr_off_func; + if (test_bit(RTW89_FLAG_UNPLUGGED, rtwdev->flags)) { + cfg_seq = NULL; + cfg_func = rtw89_mac_pwr_off_func_for_unplugged; + } else { + cfg_seq = chip->pwr_off_seq; + cfg_func = chip->ops->pwr_off_func; + } } if (test_bit(RTW89_FLAG_FW_RDY, rtwdev->flags)) @@ -7033,6 +7047,12 @@ int rtw89_mac_write_xtal_si_ax(struct rtw89_dev *rtwdev, u8 offset, u8 val, u8 m return ret; } + if (!test_bit(RTW89_FLAG_UNPLUGGED, rtwdev->flags) && + (u32_get_bits(val32, B_AX_WL_XTAL_SI_ADDR_MASK) != offset || + u32_get_bits(val32, B_AX_WL_XTAL_SI_DATA_MASK) != val)) + rtw89_warn(rtwdev, "xtal si write: offset=%x val=%x poll=%x\n", + offset, val, val32); + return 0; } @@ -7056,7 +7076,12 @@ int rtw89_mac_read_xtal_si_ax(struct rtw89_dev *rtwdev, u8 offset, u8 *val) return ret; } - *val = rtw89_read8(rtwdev, R_AX_WLAN_XTAL_SI_CTRL + 1); + if (!test_bit(RTW89_FLAG_UNPLUGGED, rtwdev->flags) && + u32_get_bits(val32, B_AX_WL_XTAL_SI_ADDR_MASK) != offset) + rtw89_warn(rtwdev, "xtal si read: offset=%x poll=%x\n", + offset, val32); + + *val = u32_get_bits(val32, B_AX_WL_XTAL_SI_DATA_MASK); return 0; } diff --git a/drivers/net/wireless/realtek/rtw89/mac_be.c b/drivers/net/wireless/realtek/rtw89/mac_be.c index 2bc329c13443..c0204e68c172 100644 --- a/drivers/net/wireless/realtek/rtw89/mac_be.c +++ b/drivers/net/wireless/realtek/rtw89/mac_be.c @@ -396,6 +396,12 @@ int rtw89_mac_write_xtal_si_be(struct rtw89_dev *rtwdev, u8 offset, u8 val, u8 m return ret; } + if (!test_bit(RTW89_FLAG_UNPLUGGED, rtwdev->flags) && + (u32_get_bits(val32, B_BE_WL_XTAL_SI_ADDR_MASK) != offset || + u32_get_bits(val32, B_BE_WL_XTAL_SI_DATA_MASK) != val)) + rtw89_warn(rtwdev, "xtal si write: offset=%x val=%x poll=%x\n", + offset, val, val32); + return 0; } @@ -420,7 +426,12 @@ int rtw89_mac_read_xtal_si_be(struct rtw89_dev *rtwdev, u8 offset, u8 *val) return ret; } - *val = rtw89_read8(rtwdev, R_BE_WLAN_XTAL_SI_CTRL + 1); + if (!test_bit(RTW89_FLAG_UNPLUGGED, rtwdev->flags) && + u32_get_bits(val32, B_BE_WL_XTAL_SI_ADDR_MASK) != offset) + rtw89_warn(rtwdev, "xtal si read: offset=%x poll=%x\n", + offset, val32); + + *val = u32_get_bits(val32, B_BE_WL_XTAL_SI_DATA_MASK); return 0; } -- 2.25.1