diff options
Diffstat (limited to 'drivers/net/wireless/realtek/rtw89/phy.c')
-rw-r--r-- | drivers/net/wireless/realtek/rtw89/phy.c | 476 |
1 files changed, 440 insertions, 36 deletions
diff --git a/drivers/net/wireless/realtek/rtw89/phy.c b/drivers/net/wireless/realtek/rtw89/phy.c index d607577b353c..ba7feadd7582 100644 --- a/drivers/net/wireless/realtek/rtw89/phy.c +++ b/drivers/net/wireless/realtek/rtw89/phy.c @@ -1702,6 +1702,91 @@ void rtw89_phy_init_bb_reg(struct rtw89_dev *rtwdev) rtw89_phy_bb_reset(rtwdev); } +void rtw89_phy_init_bb_afe(struct rtw89_dev *rtwdev) +{ + struct rtw89_fw_elm_info *elm_info = &rtwdev->fw.elm_info; + const struct rtw89_fw_element_hdr *afe_elm = elm_info->afe; + const struct rtw89_phy_afe_info *info; + u32 action, cat, class; + u32 addr, mask, val; + u32 poll, rpt; + u32 n, i; + + if (!afe_elm) + return; + + n = le32_to_cpu(afe_elm->size) / sizeof(*info); + + for (i = 0; i < n; i++) { + info = &afe_elm->u.afe.infos[i]; + + class = le32_to_cpu(info->class); + switch (class) { + case RTW89_FW_AFE_CLASS_P0: + case RTW89_FW_AFE_CLASS_P1: + case RTW89_FW_AFE_CLASS_CMN: + /* Currently support two paths */ + break; + case RTW89_FW_AFE_CLASS_P2: + case RTW89_FW_AFE_CLASS_P3: + case RTW89_FW_AFE_CLASS_P4: + default: + rtw89_warn(rtwdev, "unexpected AFE class %u\n", class); + continue; + } + + addr = le32_to_cpu(info->addr); + mask = le32_to_cpu(info->mask); + val = le32_to_cpu(info->val); + cat = le32_to_cpu(info->cat); + action = le32_to_cpu(info->action); + + switch (action) { + case RTW89_FW_AFE_ACTION_WRITE: + switch (cat) { + case RTW89_FW_AFE_CAT_MAC: + case RTW89_FW_AFE_CAT_MAC1: + rtw89_write32_mask(rtwdev, addr, mask, val); + break; + case RTW89_FW_AFE_CAT_AFEDIG: + case RTW89_FW_AFE_CAT_AFEDIG1: + rtw89_write32_mask(rtwdev, addr, mask, val); + break; + case RTW89_FW_AFE_CAT_BB: + rtw89_phy_write32_idx(rtwdev, addr, mask, val, RTW89_PHY_0); + break; + case RTW89_FW_AFE_CAT_BB1: + rtw89_phy_write32_idx(rtwdev, addr, mask, val, RTW89_PHY_1); + break; + default: + rtw89_warn(rtwdev, + "unexpected AFE writing action %u\n", action); + break; + } + break; + case RTW89_FW_AFE_ACTION_POLL: + for (poll = 0; poll <= 10; poll++) { + /* + * For CAT_BB, AFE reads register with mcu_offset 0, + * so both CAT_MAC and CAT_BB use the same method. + */ + rpt = rtw89_read32_mask(rtwdev, addr, mask); + if (rpt == val) + goto poll_done; + + fsleep(1); + } + rtw89_warn(rtwdev, "failed to poll AFE cat=%u addr=0x%x mask=0x%x\n", + cat, addr, mask); +poll_done: + break; + case RTW89_FW_AFE_ACTION_DELAY: + fsleep(addr); + break; + } + } +} + static u32 rtw89_phy_nctl_poll(struct rtw89_dev *rtwdev) { rtw89_phy_write32(rtwdev, 0x8080, 0x4); @@ -2943,7 +3028,7 @@ static void __rtw89_phy_c2h_ra_rpt_iter(struct rtw89_sta_link *rtwsta_link, } if (mode == RTW89_RA_RPT_MODE_LEGACY) { - valid = rtw89_ra_report_to_bitrate(rtwdev, rate, &legacy_bitrate); + valid = rtw89_legacy_rate_to_bitrate(rtwdev, rate, &legacy_bitrate); if (!valid) return; } @@ -3087,6 +3172,34 @@ void (* const rtw89_phy_c2h_dm_handler[])(struct rtw89_dev *rtwdev, [RTW89_PHY_C2H_DM_FUNC_FW_SCAN] = rtw89_phy_c2h_fw_scan_rpt, }; +static +void rtw89_phy_c2h_rfk_tas_pwr(struct rtw89_dev *rtwdev, + const struct rtw89_c2h_rf_tas_rpt_log *content) +{ + const enum rtw89_sar_sources src = rtwdev->sar.src; + struct rtw89_tas_info *tas = &rtwdev->tas; + u64 linear = 0; + u32 i, cur_idx; + s16 txpwr; + + if (!tas->enable || src == RTW89_SAR_SOURCE_NONE) + return; + + cur_idx = le32_to_cpu(content->cur_idx); + for (i = 0; i < cur_idx; i++) { + txpwr = le16_to_cpu(content->txpwr_history[i]); + linear += rtw89_db_quarter_to_linear(txpwr); + + rtw89_debug(rtwdev, RTW89_DBG_SAR, + "tas: index: %u, txpwr: %d\n", i, txpwr); + } + + if (cur_idx == 0) + tas->instant_txpwr = rtw89_db_to_linear(0); + else + tas->instant_txpwr = DIV_ROUND_DOWN_ULL(linear, cur_idx); +} + static void rtw89_phy_c2h_rfk_rpt_log(struct rtw89_dev *rtwdev, enum rtw89_phy_c2h_rfk_log_func func, void *content, u16 len) @@ -3338,6 +3451,13 @@ static void rtw89_phy_c2h_rfk_rpt_log(struct rtw89_dev *rtwdev, rtw89_debug(rtwdev, RTW89_DBG_RFK, "[TXGAPK]rpt power_d[1] = %*ph\n", (int)sizeof(txgapk->power_d[1]), txgapk->power_d[1]); return; + case RTW89_PHY_C2H_RFK_LOG_FUNC_TAS_PWR: + if (len != sizeof(struct rtw89_c2h_rf_tas_rpt_log)) + goto out; + + rtw89_phy_c2h_rfk_tas_pwr(rtwdev, content); + + return; default: break; } @@ -3390,9 +3510,6 @@ static void rtw89_phy_c2h_rfk_log(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u16 chunk_len; bool handled; - if (!rtw89_debug_is_enabled(rtwdev, RTW89_DBG_RFK)) - return; - log_ptr += sizeof(*c2h_hdr); len -= sizeof(*c2h_hdr); @@ -3469,6 +3586,13 @@ rtw89_phy_c2h_rfk_log_txgapk(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u32 RTW89_PHY_C2H_RFK_LOG_FUNC_TXGAPK, "TXGAPK"); } +static void +rtw89_phy_c2h_rfk_log_tas_pwr(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u32 len) +{ + rtw89_phy_c2h_rfk_log(rtwdev, c2h, len, + RTW89_PHY_C2H_RFK_LOG_FUNC_TAS_PWR, "TAS"); +} + static void (* const rtw89_phy_c2h_rfk_log_handler[])(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u32 len) = { @@ -3478,6 +3602,7 @@ void (* const rtw89_phy_c2h_rfk_log_handler[])(struct rtw89_dev *rtwdev, [RTW89_PHY_C2H_RFK_LOG_FUNC_RXDCK] = rtw89_phy_c2h_rfk_log_rxdck, [RTW89_PHY_C2H_RFK_LOG_FUNC_TSSI] = rtw89_phy_c2h_rfk_log_tssi, [RTW89_PHY_C2H_RFK_LOG_FUNC_TXGAPK] = rtw89_phy_c2h_rfk_log_txgapk, + [RTW89_PHY_C2H_RFK_LOG_FUNC_TAS_PWR] = rtw89_phy_c2h_rfk_log_tas_pwr, }; static @@ -3540,39 +3665,19 @@ rtw89_phy_c2h_rfk_report_state(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u3 } static void -rtw89_phy_c2h_rfk_log_tas_pwr(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u32 len) +rtw89_phy_c2h_rfk_report_tas_pwr(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u32 len) { - const struct rtw89_c2h_rf_tas_info *rf_tas = + const struct rtw89_c2h_rf_tas_info *report = (const struct rtw89_c2h_rf_tas_info *)c2h->data; - const enum rtw89_sar_sources src = rtwdev->sar.src; - struct rtw89_tas_info *tas = &rtwdev->tas; - u64 linear = 0; - u32 i, cur_idx; - s16 txpwr; - - if (!tas->enable || src == RTW89_SAR_SOURCE_NONE) - return; - - cur_idx = le32_to_cpu(rf_tas->cur_idx); - for (i = 0; i < cur_idx; i++) { - txpwr = (s16)le16_to_cpu(rf_tas->txpwr_history[i]); - linear += rtw89_db_quarter_to_linear(txpwr); - - rtw89_debug(rtwdev, RTW89_DBG_SAR, - "tas: index: %u, txpwr: %d\n", i, txpwr); - } - if (cur_idx == 0) - tas->instant_txpwr = rtw89_db_to_linear(0); - else - tas->instant_txpwr = DIV_ROUND_DOWN_ULL(linear, cur_idx); + rtw89_phy_c2h_rfk_tas_pwr(rtwdev, &report->content); } static void (* const rtw89_phy_c2h_rfk_report_handler[])(struct rtw89_dev *rtwdev, struct sk_buff *c2h, u32 len) = { [RTW89_PHY_C2H_RFK_REPORT_FUNC_STATE] = rtw89_phy_c2h_rfk_report_state, - [RTW89_PHY_C2H_RFK_LOG_TAS_PWR] = rtw89_phy_c2h_rfk_log_tas_pwr, + [RTW89_PHY_C2H_RFK_REPORT_FUNC_TAS_PWR] = rtw89_phy_c2h_rfk_report_tas_pwr, }; bool rtw89_phy_c2h_chk_atomic(struct rtw89_dev *rtwdev, u8 class, u8 func) @@ -3626,12 +3731,11 @@ void rtw89_phy_c2h_handle(struct rtw89_dev *rtwdev, struct sk_buff *skb, handler = rtw89_phy_c2h_dm_handler[func]; break; default: - rtw89_info(rtwdev, "PHY c2h class %d not support\n", class); - return; + break; } if (!handler) { - rtw89_info(rtwdev, "PHY c2h class %d func %d not support\n", class, - func); + rtw89_info_once(rtwdev, "PHY c2h class %d func %d not support\n", + class, func); return; } handler(rtwdev, skb, len); @@ -5497,6 +5601,34 @@ static void rtw89_phy_ifs_clm_set_th_reg(struct rtw89_dev *rtwdev, i + 1, env->ifs_clm_th_l[i], env->ifs_clm_th_h[i]); } +static void __rtw89_phy_nhm_setting_init(struct rtw89_dev *rtwdev, + struct rtw89_bb_ctx *bb) +{ + const struct rtw89_phy_gen_def *phy = rtwdev->chip->phy_def; + struct rtw89_env_monitor_info *env = &bb->env_monitor; + const struct rtw89_ccx_regs *ccx = phy->ccx; + + env->nhm_include_cca = false; + env->nhm_mntr_time = 0; + env->nhm_sum = 0; + + rtw89_phy_write32_idx_set(rtwdev, ccx->nhm_config, ccx->nhm_en_mask, bb->phy_idx); + rtw89_phy_write32_idx_set(rtwdev, ccx->nhm_method, ccx->nhm_pwr_method_msk, + bb->phy_idx); +} + +void rtw89_phy_nhm_setting_init(struct rtw89_dev *rtwdev) +{ + const struct rtw89_chip_info *chip = rtwdev->chip; + struct rtw89_bb_ctx *bb; + + if (!chip->support_noise) + return; + + rtw89_for_each_active_bb(rtwdev, bb) + __rtw89_phy_nhm_setting_init(rtwdev, bb); +} + static void rtw89_phy_ifs_clm_setting_init(struct rtw89_dev *rtwdev, struct rtw89_bb_ctx *bb) { @@ -5558,7 +5690,7 @@ static int rtw89_phy_ccx_racing_ctrl(struct rtw89_dev *rtwdev, } static void rtw89_phy_ccx_trigger(struct rtw89_dev *rtwdev, - struct rtw89_bb_ctx *bb) + struct rtw89_bb_ctx *bb, u8 sel) { const struct rtw89_phy_gen_def *phy = rtwdev->chip->phy_def; struct rtw89_env_monitor_info *env = &bb->env_monitor; @@ -5568,10 +5700,17 @@ static void rtw89_phy_ccx_trigger(struct rtw89_dev *rtwdev, bb->phy_idx); rtw89_phy_write32_idx(rtwdev, ccx->setting_addr, ccx->measurement_trig_mask, 0, bb->phy_idx); + if (sel & RTW89_PHY_ENV_MON_NHM) + rtw89_phy_write32_idx_clr(rtwdev, ccx->nhm_config, + ccx->nhm_en_mask, bb->phy_idx); + rtw89_phy_write32_idx(rtwdev, ccx->ifs_cnt_addr, ccx->ifs_clm_cnt_clear_mask, 1, bb->phy_idx); rtw89_phy_write32_idx(rtwdev, ccx->setting_addr, ccx->measurement_trig_mask, 1, bb->phy_idx); + if (sel & RTW89_PHY_ENV_MON_NHM) + rtw89_phy_write32_idx_set(rtwdev, ccx->nhm_config, + ccx->nhm_en_mask, bb->phy_idx); env->ccx_ongoing = true; } @@ -5642,6 +5781,125 @@ static void rtw89_phy_ifs_clm_get_utility(struct rtw89_dev *rtwdev, env->ifs_clm_cca_avg[i]); } +static u8 rtw89_nhm_weighted_avg(struct rtw89_dev *rtwdev, struct rtw89_bb_ctx *bb) +{ + struct rtw89_env_monitor_info *env = &bb->env_monitor; + u8 nhm_weight[RTW89_NHM_RPT_NUM]; + u32 nhm_weighted_sum = 0; + u8 weight_zero; + u8 i; + + if (env->nhm_sum == 0) + return 0; + + weight_zero = clamp_t(u16, env->nhm_th[0] - RTW89_NHM_WEIGHT_OFFSET, 0, U8_MAX); + + for (i = 0; i < RTW89_NHM_RPT_NUM; i++) { + if (i == 0) + nhm_weight[i] = weight_zero; + else if (i == (RTW89_NHM_RPT_NUM - 1)) + nhm_weight[i] = env->nhm_th[i - 1] + RTW89_NHM_WEIGHT_OFFSET; + else + nhm_weight[i] = (env->nhm_th[i - 1] + env->nhm_th[i]) / 2; + } + + if (rtwdev->chip->chip_id == RTL8852A || rtwdev->chip->chip_id == RTL8852B || + rtwdev->chip->chip_id == RTL8852C) { + if (env->nhm_th[RTW89_NHM_TH_NUM - 1] == RTW89_NHM_WA_TH) { + nhm_weight[RTW89_NHM_RPT_NUM - 1] = + env->nhm_th[RTW89_NHM_TH_NUM - 2] + + RTW89_NHM_WEIGHT_OFFSET; + nhm_weight[RTW89_NHM_RPT_NUM - 2] = + nhm_weight[RTW89_NHM_RPT_NUM - 1]; + } + + env->nhm_result[0] += env->nhm_result[RTW89_NHM_RPT_NUM - 1]; + env->nhm_result[RTW89_NHM_RPT_NUM - 1] = 0; + } + + for (i = 0; i < RTW89_NHM_RPT_NUM; i++) + nhm_weighted_sum += env->nhm_result[i] * nhm_weight[i]; + + return (nhm_weighted_sum / env->nhm_sum) >> RTW89_NHM_TH_FACTOR; +} + +static void __rtw89_phy_nhm_get_result(struct rtw89_dev *rtwdev, + struct rtw89_bb_ctx *bb, enum rtw89_band hw_band, + u16 ch_hw_value) +{ + const struct rtw89_phy_gen_def *phy = rtwdev->chip->phy_def; + struct rtw89_env_monitor_info *env = &bb->env_monitor; + const struct rtw89_chip_info *chip = rtwdev->chip; + const struct rtw89_ccx_regs *ccx = phy->ccx; + struct ieee80211_supported_band *sband; + const struct rtw89_reg_def *nhm_rpt; + enum nl80211_band band; + u32 sum = 0; + u8 chan_idx; + u8 nhm_pwr; + u8 i; + + if (!rtw89_phy_read32_idx(rtwdev, ccx->nhm, ccx->nhm_ready, bb->phy_idx)) { + rtw89_debug(rtwdev, RTW89_DBG_PHY_TRACK, "[NHM] Get NHM report Fail\n"); + return; + } + + for (i = 0; i < RTW89_NHM_RPT_NUM; i++) { + nhm_rpt = &(*chip->nhm_report)[i]; + + env->nhm_result[i] = + rtw89_phy_read32_idx(rtwdev, nhm_rpt->addr, + nhm_rpt->mask, bb->phy_idx); + sum += env->nhm_result[i]; + } + env->nhm_sum = sum; + nhm_pwr = rtw89_nhm_weighted_avg(rtwdev, bb); + + if (!ch_hw_value) + return; + + band = rtw89_hw_to_nl80211_band(hw_band); + sband = rtwdev->hw->wiphy->bands[band]; + if (!sband) + return; + + for (chan_idx = 0; chan_idx < sband->n_channels; chan_idx++) { + struct ieee80211_channel *channel; + struct rtw89_nhm_report *rpt; + struct list_head *nhm_list; + + channel = &sband->channels[chan_idx]; + if (channel->hw_value != ch_hw_value) + continue; + + rpt = &env->nhm_his[hw_band][chan_idx]; + nhm_list = &env->nhm_rpt_list; + + rpt->channel = channel; + rpt->noise = nhm_pwr; + + if (list_empty(&rpt->list)) + list_add_tail(&rpt->list, nhm_list); + + return; + } + + rtw89_debug(rtwdev, RTW89_DBG_PHY_TRACK, "[NHM] channel not found\n"); +} + +void rtw89_phy_nhm_get_result(struct rtw89_dev *rtwdev, enum rtw89_band hw_band, + u16 ch_hw_value) +{ + const struct rtw89_chip_info *chip = rtwdev->chip; + struct rtw89_bb_ctx *bb; + + if (!chip->support_noise) + return; + + rtw89_for_each_active_bb(rtwdev, bb) + __rtw89_phy_nhm_get_result(rtwdev, bb, hw_band, ch_hw_value); +} + static bool rtw89_phy_ifs_clm_get_result(struct rtw89_dev *rtwdev, struct rtw89_bb_ctx *bb) { @@ -5742,6 +6000,107 @@ static bool rtw89_phy_ifs_clm_get_result(struct rtw89_dev *rtwdev, return true; } +static void rtw89_phy_nhm_th_update(struct rtw89_dev *rtwdev, + struct rtw89_bb_ctx *bb) +{ + struct rtw89_env_monitor_info *env = &bb->env_monitor; + static const u8 nhm_th_11k[RTW89_NHM_RPT_NUM] = { + 18, 21, 24, 27, 30, 35, 40, 45, 50, 55, 60, 0 + }; + const struct rtw89_chip_info *chip = rtwdev->chip; + const struct rtw89_reg_def *nhm_th; + u8 i; + + for (i = 0; i < RTW89_NHM_RPT_NUM; i++) + env->nhm_th[i] = nhm_th_11k[i] << RTW89_NHM_TH_FACTOR; + + if (chip->chip_id == RTL8852A || chip->chip_id == RTL8852B || + chip->chip_id == RTL8852C) + env->nhm_th[RTW89_NHM_TH_NUM - 1] = RTW89_NHM_WA_TH; + + for (i = 0; i < RTW89_NHM_TH_NUM; i++) { + nhm_th = &(*chip->nhm_th)[i]; + + rtw89_phy_write32_idx(rtwdev, nhm_th->addr, nhm_th->mask, + env->nhm_th[i], bb->phy_idx); + } +} + +static int rtw89_phy_nhm_set(struct rtw89_dev *rtwdev, + struct rtw89_bb_ctx *bb, + struct rtw89_ccx_para_info *para) +{ + const struct rtw89_phy_gen_def *phy = rtwdev->chip->phy_def; + struct rtw89_env_monitor_info *env = &bb->env_monitor; + const struct rtw89_ccx_regs *ccx = phy->ccx; + u32 unit_idx = 0; + u32 period = 0; + + if (para->mntr_time == 0) { + rtw89_debug(rtwdev, RTW89_DBG_PHY_TRACK, + "[NHM] MNTR_TIME is 0\n"); + return -EINVAL; + } + + if (rtw89_phy_ccx_racing_ctrl(rtwdev, bb, para->rac_lv)) + return -EINVAL; + + rtw89_debug(rtwdev, RTW89_DBG_PHY_TRACK, + "[NHM]nhm_incld_cca=%d, mntr_time=%d ms\n", + para->nhm_incld_cca, para->mntr_time); + + if (para->mntr_time != env->nhm_mntr_time) { + rtw89_phy_ccx_ms_to_period_unit(rtwdev, para->mntr_time, + &period, &unit_idx); + rtw89_phy_write32_idx(rtwdev, ccx->nhm_config, + ccx->nhm_period_mask, period, bb->phy_idx); + rtw89_phy_write32_idx(rtwdev, ccx->nhm_config, + ccx->nhm_unit_mask, period, bb->phy_idx); + + env->nhm_mntr_time = para->mntr_time; + env->ccx_period = period; + env->ccx_unit_idx = unit_idx; + } + + if (para->nhm_incld_cca != env->nhm_include_cca) { + rtw89_phy_write32_idx(rtwdev, ccx->nhm_config, + ccx->nhm_include_cca_mask, para->nhm_incld_cca, + bb->phy_idx); + + env->nhm_include_cca = para->nhm_incld_cca; + } + + rtw89_phy_nhm_th_update(rtwdev, bb); + + return 0; +} + +static void __rtw89_phy_nhm_trigger(struct rtw89_dev *rtwdev, struct rtw89_bb_ctx *bb) +{ + struct rtw89_ccx_para_info para = { + .mntr_time = RTW89_NHM_MNTR_TIME, + .rac_lv = RTW89_RAC_LV_1, + .nhm_incld_cca = true, + }; + + rtw89_phy_ccx_racing_release(rtwdev, bb); + + rtw89_phy_nhm_set(rtwdev, bb, ¶); + rtw89_phy_ccx_trigger(rtwdev, bb, RTW89_PHY_ENV_MON_NHM); +} + +void rtw89_phy_nhm_trigger(struct rtw89_dev *rtwdev) +{ + const struct rtw89_chip_info *chip = rtwdev->chip; + struct rtw89_bb_ctx *bb; + + if (!chip->support_noise) + return; + + rtw89_for_each_active_bb(rtwdev, bb) + __rtw89_phy_nhm_trigger(rtwdev, bb); +} + static int rtw89_phy_ifs_clm_set(struct rtw89_dev *rtwdev, struct rtw89_bb_ctx *bb, struct rtw89_ccx_para_info *para) @@ -5816,7 +6175,7 @@ static void __rtw89_phy_env_monitor_track(struct rtw89_dev *rtwdev, if (rtw89_phy_ifs_clm_set(rtwdev, bb, ¶) == 0) chk_result |= RTW89_PHY_ENV_MON_IFS_CLM; if (chk_result) - rtw89_phy_ccx_trigger(rtwdev, bb); + rtw89_phy_ccx_trigger(rtwdev, bb, chk_result); rtw89_debug(rtwdev, RTW89_DBG_PHY_TRACK, "get_result=0x%x, chk_result:0x%x\n", @@ -5930,8 +6289,6 @@ static void __rtw89_physts_parsing_init(struct rtw89_dev *rtwdev, val |= BIT(RTW89_PHYSTS_IE13_DL_MU_DEF) | BIT(RTW89_PHYSTS_IE01_CMN_OFDM); } else if (i >= RTW89_CCK_PKT) { - val |= BIT(RTW89_PHYSTS_IE09_FTR_0); - val &= ~(GENMASK(RTW89_PHYSTS_IE07_CMN_EXT_PATH_D, RTW89_PHYSTS_IE04_CMN_EXT_PATH_A)); @@ -6910,6 +7267,7 @@ void rtw89_phy_dm_init(struct rtw89_dev *rtwdev) rtw89_chip_bb_sethw(rtwdev); rtw89_phy_env_monitor_init(rtwdev); + rtw89_phy_nhm_setting_init(rtwdev); rtw89_physts_parsing_init(rtwdev); rtw89_phy_dig_init(rtwdev); rtw89_phy_cfo_init(rtwdev); @@ -6935,6 +7293,43 @@ void rtw89_phy_dm_reinit(struct rtw89_dev *rtwdev) rtw89_physts_parsing_init(rtwdev); } +static void __rtw89_phy_dm_init_data(struct rtw89_dev *rtwdev, struct rtw89_bb_ctx *bb) +{ + struct rtw89_env_monitor_info *env = &bb->env_monitor; + const struct rtw89_chip_info *chip = rtwdev->chip; + struct ieee80211_supported_band *sband; + enum rtw89_band hw_band; + enum nl80211_band band; + u8 idx; + + if (!chip->support_noise) + return; + + for (band = 0; band < NUM_NL80211_BANDS; band++) { + sband = rtwdev->hw->wiphy->bands[band]; + if (!sband) + continue; + + hw_band = rtw89_nl80211_to_hw_band(band); + env->nhm_his[hw_band] = + devm_kcalloc(rtwdev->dev, sband->n_channels, + sizeof(*env->nhm_his[0]), GFP_KERNEL); + + for (idx = 0; idx < sband->n_channels; idx++) + INIT_LIST_HEAD(&env->nhm_his[hw_band][idx].list); + + INIT_LIST_HEAD(&env->nhm_rpt_list); + } +} + +void rtw89_phy_dm_init_data(struct rtw89_dev *rtwdev) +{ + struct rtw89_bb_ctx *bb; + + rtw89_for_each_capab_bb(rtwdev, bb) + __rtw89_phy_dm_init_data(rtwdev, bb); +} + void rtw89_phy_set_bss_color(struct rtw89_dev *rtwdev, struct rtw89_vif_link *rtwvif_link) { @@ -7590,6 +7985,15 @@ static const struct rtw89_ccx_regs rtw89_ccx_regs_ax = { .ifs_total_addr = R_IFSCNT, .ifs_cnt_done_mask = B_IFSCNT_DONE_MSK, .ifs_total_mask = B_IFSCNT_TOTAL_CNT_MSK, + .nhm = R_NHM_AX, + .nhm_ready = B_NHM_READY_MSK, + .nhm_config = R_NHM_CFG, + .nhm_period_mask = B_NHM_PERIOD_MSK, + .nhm_unit_mask = B_NHM_COUNTER_MSK, + .nhm_include_cca_mask = B_NHM_INCLUDE_CCA_MSK, + .nhm_en_mask = B_NHM_EN_MSK, + .nhm_method = R_NHM_TH9, + .nhm_pwr_method_msk = B_NHM_PWDB_METHOD_MSK, }; static const struct rtw89_physts_regs rtw89_physts_regs_ax = { |