wifi: mt76: mt7996: rework radar HWRDD idx

The definition of MT_RX_SEL (for rdd_rx_sel) is mixed with the
definition of HWRDD idx.
For example, MT_RX_SEL2 is for background HWRDD idx, not an
option of rdd_rx_sel.
Additionally, HWRDD idx does not exactly map to band idx for
Connac 3 chips. So, add mt7996_get_rdd_idx as a helper function.

Finally, remove some parts of the code inherited from the legacy chips.
For instance,
1. rdd_state is used for single-band-dual-HWRDD chips (for 80+80),
especially the 76xx series.
2. rdd_rx_sel is also used for single-band-dual-HWRDD chips
rx_sel = 0 => RDD0 for WF0, RDD1 for WF2
rx_sel = 1 => RDD0 for WF1, RDD1 for WF3

Chip Variants              | 5G rdd idx     | Background rdd idx
---------------------------|----------------|-------------------
MT7996 (except 205/255)    | 1              | 2
MT7992                     | 1              | 2
MT7990                     | 1              | 2

Signed-off-by: StanleyYP Wang <StanleyYP.Wang@mediatek.com>
Reviewed-by: Shayne Chen <shayne.chen@mediatek.com>
Reviewed-by: Money Wang <money.wang@mediatek.com>
Link: https://patch.msgid.link/20250320015926.3948672-1-StanleyYP.Wang@mediatek.com
Signed-off-by: Felix Fietkau <nbd@nbd.name>
This commit is contained in:
StanleyYP Wang 2025-03-20 09:59:26 +08:00 committed by Felix Fietkau
parent 758e0cc3a4
commit 1529e335f9
5 changed files with 75 additions and 69 deletions

View File

@ -222,18 +222,27 @@ static const struct file_operations mt7996_sys_recovery_ops = {
static int
mt7996_radar_trigger(void *data, u64 val)
{
#define RADAR_MAIN_CHAIN 1
#define RADAR_BACKGROUND 2
struct mt7996_dev *dev = data;
struct mt7996_phy *phy = mt7996_band_phy(dev, NL80211_BAND_5GHZ);
int rdd_idx;
if (val > MT_RX_SEL2)
if (!phy || !val || val > RADAR_BACKGROUND)
return -EINVAL;
if (val == MT_RX_SEL2 && !dev->rdd2_phy) {
if (val == RADAR_BACKGROUND && !dev->rdd2_phy) {
dev_err(dev->mt76.dev, "Background radar is not enabled\n");
return -EINVAL;
}
return mt7996_mcu_rdd_cmd(dev, RDD_RADAR_EMULATE,
val, 0, 0);
rdd_idx = mt7996_get_rdd_idx(phy, val == RADAR_BACKGROUND);
if (rdd_idx < 0) {
dev_err(dev->mt76.dev, "No RDD found\n");
return -EINVAL;
}
return mt7996_mcu_rdd_cmd(dev, RDD_RADAR_EMULATE, rdd_idx, 0);
}
DEFINE_DEBUGFS_ATTRIBUTE(fops_radar_trigger, NULL,

View File

@ -2441,16 +2441,15 @@ void mt7996_mac_work(struct work_struct *work)
static void mt7996_dfs_stop_radar_detector(struct mt7996_phy *phy)
{
struct mt7996_dev *dev = phy->dev;
int rdd_idx = mt7996_get_rdd_idx(phy, false);
if (phy->rdd_state & BIT(0))
mt7996_mcu_rdd_cmd(dev, RDD_STOP, 0,
MT_RX_SEL0, 0);
if (phy->rdd_state & BIT(1))
mt7996_mcu_rdd_cmd(dev, RDD_STOP, 1,
MT_RX_SEL0, 0);
if (rdd_idx < 0)
return;
mt7996_mcu_rdd_cmd(dev, RDD_STOP, rdd_idx, 0);
}
static int mt7996_dfs_start_rdd(struct mt7996_dev *dev, int chain)
static int mt7996_dfs_start_rdd(struct mt7996_dev *dev, int rdd_idx)
{
int err, region;
@ -2467,44 +2466,30 @@ static int mt7996_dfs_start_rdd(struct mt7996_dev *dev, int chain)
break;
}
err = mt7996_mcu_rdd_cmd(dev, RDD_START, chain,
MT_RX_SEL0, region);
err = mt7996_mcu_rdd_cmd(dev, RDD_START, rdd_idx, region);
if (err < 0)
return err;
return mt7996_mcu_rdd_cmd(dev, RDD_DET_MODE, chain,
MT_RX_SEL0, 1);
return mt7996_mcu_rdd_cmd(dev, RDD_DET_MODE, rdd_idx, 1);
}
static int mt7996_dfs_start_radar_detector(struct mt7996_phy *phy)
{
struct cfg80211_chan_def *chandef = &phy->mt76->chandef;
struct mt7996_dev *dev = phy->dev;
u8 band_idx = phy->mt76->band_idx;
int err;
int err, rdd_idx;
rdd_idx = mt7996_get_rdd_idx(phy, false);
if (rdd_idx < 0)
return -EINVAL;
/* start CAC */
err = mt7996_mcu_rdd_cmd(dev, RDD_CAC_START, band_idx,
MT_RX_SEL0, 0);
err = mt7996_mcu_rdd_cmd(dev, RDD_CAC_START, rdd_idx, 0);
if (err < 0)
return err;
err = mt7996_dfs_start_rdd(dev, band_idx);
if (err < 0)
return err;
err = mt7996_dfs_start_rdd(dev, rdd_idx);
phy->rdd_state |= BIT(band_idx);
if (chandef->width == NL80211_CHAN_WIDTH_160 ||
chandef->width == NL80211_CHAN_WIDTH_80P80) {
err = mt7996_dfs_start_rdd(dev, 1);
if (err < 0)
return err;
phy->rdd_state |= BIT(1);
}
return 0;
return err;
}
static int
@ -2545,12 +2530,12 @@ int mt7996_dfs_init_radar_detector(struct mt7996_phy *phy)
{
struct mt7996_dev *dev = phy->dev;
enum mt76_dfs_state dfs_state, prev_state;
int err;
int err, rdd_idx = mt7996_get_rdd_idx(phy, false);
prev_state = phy->mt76->dfs_state;
dfs_state = mt76_phy_dfs_state(phy->mt76);
if (prev_state == dfs_state)
if (prev_state == dfs_state || rdd_idx < 0)
return 0;
if (prev_state == MT_DFS_STATE_UNKNOWN)
@ -2574,8 +2559,7 @@ int mt7996_dfs_init_radar_detector(struct mt7996_phy *phy)
if (dfs_state == MT_DFS_STATE_CAC)
return 0;
err = mt7996_mcu_rdd_cmd(dev, RDD_CAC_END,
phy->mt76->band_idx, MT_RX_SEL0, 0);
err = mt7996_mcu_rdd_cmd(dev, RDD_CAC_END, rdd_idx, 0);
if (err < 0) {
phy->mt76->dfs_state = MT_DFS_STATE_UNKNOWN;
return err;
@ -2585,8 +2569,7 @@ int mt7996_dfs_init_radar_detector(struct mt7996_phy *phy)
return 0;
stop:
err = mt7996_mcu_rdd_cmd(dev, RDD_NORMAL_START,
phy->mt76->band_idx, MT_RX_SEL0, 0);
err = mt7996_mcu_rdd_cmd(dev, RDD_NORMAL_START, rdd_idx, 0);
if (err < 0)
return err;

View File

@ -380,21 +380,27 @@ mt7996_mcu_rx_radar_detected(struct mt7996_dev *dev, struct sk_buff *skb)
r = (struct mt7996_mcu_rdd_report *)skb->data;
if (r->band_idx >= ARRAY_SIZE(dev->mt76.phys))
return;
if (r->band_idx == MT_RX_SEL2 && !dev->rdd2_phy)
return;
if (r->band_idx == MT_RX_SEL2)
switch (r->rdd_idx) {
case MT_RDD_IDX_BAND2:
mphy = dev->mt76.phys[MT_BAND2];
break;
case MT_RDD_IDX_BAND1:
mphy = dev->mt76.phys[MT_BAND1];
break;
case MT_RDD_IDX_BACKGROUND:
if (!dev->rdd2_phy)
return;
mphy = dev->rdd2_phy->mt76;
else
mphy = dev->mt76.phys[r->band_idx];
break;
default:
dev_err(dev->mt76.dev, "Unknown RDD idx %d\n", r->rdd_idx);
return;
}
if (!mphy)
return;
if (r->band_idx == MT_RX_SEL2)
if (r->rdd_idx == MT_RDD_IDX_BACKGROUND)
cfg80211_background_radar_event(mphy->hw->wiphy,
&dev->rdd2_chandef,
GFP_ATOMIC);
@ -3557,11 +3563,10 @@ int mt7996_mcu_rdd_background_enable(struct mt7996_phy *phy,
struct cfg80211_chan_def *chandef)
{
struct mt7996_dev *dev = phy->dev;
int err, region;
int err, region, rdd_idx = mt7996_get_rdd_idx(phy, true);
if (!chandef) { /* disable offchain */
err = mt7996_mcu_rdd_cmd(dev, RDD_STOP, MT_RX_SEL2,
0, 0);
err = mt7996_mcu_rdd_cmd(dev, RDD_STOP, rdd_idx, 0);
if (err)
return err;
@ -3587,8 +3592,7 @@ int mt7996_mcu_rdd_background_enable(struct mt7996_phy *phy,
break;
}
return mt7996_mcu_rdd_cmd(dev, RDD_START, MT_RX_SEL2,
0, region);
return mt7996_mcu_rdd_cmd(dev, RDD_START, rdd_idx, region);
}
int mt7996_mcu_set_chan_info(struct mt7996_phy *phy, u16 tag)
@ -4455,8 +4459,7 @@ int mt7996_mcu_set_radio_en(struct mt7996_phy *phy, bool enable)
&req, sizeof(req), true);
}
int mt7996_mcu_rdd_cmd(struct mt7996_dev *dev, int cmd, u8 index,
u8 rx_sel, u8 val)
int mt7996_mcu_rdd_cmd(struct mt7996_dev *dev, int cmd, u8 rdd_idx, u8 val)
{
struct {
u8 _rsv[4];
@ -4473,8 +4476,7 @@ int mt7996_mcu_rdd_cmd(struct mt7996_dev *dev, int cmd, u8 index,
.tag = cpu_to_le16(UNI_RDD_CTRL_PARM),
.len = cpu_to_le16(sizeof(req) - 4),
.ctrl = cmd,
.rdd_idx = index,
.rdd_rx_sel = rx_sel,
.rdd_idx = rdd_idx,
.val = val,
};

View File

@ -69,7 +69,7 @@ struct mt7996_mcu_rdd_report {
__le16 tag;
__le16 len;
u8 band_idx;
u8 rdd_idx;
u8 long_detected;
u8 constant_prf_detected;
u8 staggered_prf_detected;

View File

@ -302,8 +302,6 @@ struct mt7996_phy {
s16 coverage_class;
u8 slottime;
u8 rdd_state;
u16 beacon_rate;
u32 rx_ampdu_ts;
@ -426,10 +424,10 @@ enum {
__MT_WFDMA_MAX,
};
enum {
MT_RX_SEL0,
MT_RX_SEL1,
MT_RX_SEL2, /* monitor chain */
enum rdd_idx {
MT_RDD_IDX_BAND2, /* RDD idx for band idx 2 */
MT_RDD_IDX_BAND1, /* RDD idx for band idx 1 */
MT_RDD_IDX_BACKGROUND, /* RDD idx for background chain */
};
enum mt7996_rdd_cmd {
@ -448,6 +446,21 @@ enum mt7996_rdd_cmd {
RDD_IRQ_OFF,
};
static inline int
mt7996_get_rdd_idx(struct mt7996_phy *phy, bool is_background)
{
if (!phy->mt76->cap.has_5ghz)
return -1;
if (is_background)
return MT_RDD_IDX_BACKGROUND;
if (phy->mt76->band_idx == MT_BAND2)
return MT_RDD_IDX_BAND2;
return MT_RDD_IDX_BAND1;
}
static inline struct mt7996_dev *
mt7996_hw_dev(struct ieee80211_hw *hw)
{
@ -640,8 +653,7 @@ int mt7996_mcu_get_temperature(struct mt7996_phy *phy);
int mt7996_mcu_set_thermal_throttling(struct mt7996_phy *phy, u8 state);
int mt7996_mcu_set_thermal_protect(struct mt7996_phy *phy, bool enable);
int mt7996_mcu_set_txpower_sku(struct mt7996_phy *phy);
int mt7996_mcu_rdd_cmd(struct mt7996_dev *dev, int cmd, u8 index,
u8 rx_sel, u8 val);
int mt7996_mcu_rdd_cmd(struct mt7996_dev *dev, int cmd, u8 rdd_idx, u8 val);
int mt7996_mcu_rdd_background_enable(struct mt7996_phy *phy,
struct cfg80211_chan_def *chandef);
int mt7996_mcu_set_fixed_rate_table(struct mt7996_phy *phy, u8 table_idx,