OSDN Git Service

mt76: mt7915: enable configured beacon tx rate
authorRyder Lee <ryder.lee@mediatek.com>
Sat, 28 Aug 2021 20:01:02 +0000 (04:01 +0800)
committerFelix Fietkau <nbd@nbd.name>
Wed, 20 Oct 2021 08:36:40 +0000 (10:36 +0200)
The user is allowed to change beacon tx rate (HT/VHT/HE) from hostapd.

Signed-off-by: Ryder Lee <ryder.lee@mediatek.com>
Signed-off-by: Felix Fietkau <nbd@nbd.name>
drivers/net/wireless/mediatek/mt76/mt7915/init.c
drivers/net/wireless/mediatek/mt76/mt7915/mac.c

index 4c4abda..d87b151 100644 (file)
@@ -326,6 +326,10 @@ mt7915_init_wiphy(struct ieee80211_hw *hw)
 
        wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_BSS_COLOR);
        wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_VHT_IBSS);
+       wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_BEACON_RATE_LEGACY);
+       wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_BEACON_RATE_HT);
+       wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_BEACON_RATE_VHT);
+       wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_BEACON_RATE_HE);
 
        ieee80211_hw_set(hw, HAS_RATE_CONTROL);
        ieee80211_hw_set(hw, SUPPORTS_TX_ENCAP_OFFLOAD);
index 81cde3c..5e29707 100644 (file)
@@ -981,6 +981,51 @@ mt7915_mac_write_txwi_80211(struct mt7915_dev *dev, __le32 *txwi,
        txwi[7] |= cpu_to_le32(val);
 }
 
+static u16
+mt7915_mac_tx_rate_val(struct mt76_phy *mphy, struct ieee80211_vif *vif,
+                      bool beacon, bool mcast)
+{
+       u8 mode = 0, band = mphy->chandef.chan->band;
+       int rateidx = 0, mcast_rate;
+
+       if (beacon) {
+               struct cfg80211_bitrate_mask *mask;
+
+               mask = &vif->bss_conf.beacon_tx_rate;
+               if (hweight16(mask->control[band].he_mcs[0]) == 1) {
+                       rateidx = ffs(mask->control[band].he_mcs[0]) - 1;
+                       mode = MT_PHY_TYPE_HE_SU;
+                       goto out;
+               } else if (hweight16(mask->control[band].vht_mcs[0]) == 1) {
+                       rateidx = ffs(mask->control[band].vht_mcs[0]) - 1;
+                       mode = MT_PHY_TYPE_VHT;
+                       goto out;
+               } else if (hweight8(mask->control[band].ht_mcs[0]) == 1) {
+                       rateidx = ffs(mask->control[band].ht_mcs[0]) - 1;
+                       mode = MT_PHY_TYPE_HT;
+                       goto out;
+               } else if (hweight32(mask->control[band].legacy) == 1) {
+                       rateidx = ffs(mask->control[band].legacy) - 1;
+                       goto legacy;
+               }
+       }
+
+       mcast_rate = vif->bss_conf.mcast_rate[band];
+       if (mcast && mcast_rate > 0)
+               rateidx = mcast_rate - 1;
+       else
+               rateidx = ffs(vif->bss_conf.basic_rates) - 1;
+
+legacy:
+       rateidx = mt76_calculate_default_rate(mphy, rateidx);
+       mode = rateidx >> 8;
+       rateidx &= GENMASK(7, 0);
+
+out:
+       return FIELD_PREP(MT_TX_RATE_IDX, rateidx) |
+              FIELD_PREP(MT_TX_RATE_MODE, mode);
+}
+
 void mt7915_mac_write_txwi(struct mt7915_dev *dev, __le32 *txwi,
                           struct sk_buff *skb, struct mt76_wcid *wcid, int pid,
                           struct ieee80211_key_conf *key, bool beacon)
@@ -1057,23 +1102,11 @@ void mt7915_mac_write_txwi(struct mt7915_dev *dev, __le32 *txwi,
                mt7915_mac_write_txwi_80211(dev, txwi, skb, key, &mcast);
 
        if (txwi[2] & cpu_to_le32(MT_TXD2_FIX_RATE)) {
-               u8 band = mphy->chandef.chan->band;
-               int rateidx, mcast_rate = vif->bss_conf.mcast_rate[band];
-               u16 rate, mode;
+               u16 rate = mt7915_mac_tx_rate_val(mphy, vif, beacon, mcast);
 
                /* hardware won't add HTC for mgmt/ctrl frame */
                txwi[2] |= cpu_to_le32(MT_TXD2_HTC_VLD);
 
-               if (mcast && mcast_rate > 0)
-                       rateidx = mcast_rate - 1;
-               else
-                       rateidx = ffs(vif->bss_conf.basic_rates) - 1;
-
-               rate = mt76_calculate_default_rate(mphy, rateidx);
-               mode = rate >> 8;
-               rate &= GENMASK(7, 0);
-               rate |= FIELD_PREP(MT_TX_RATE_MODE, mode);
-
                val = MT_TXD6_FIXED_BW |
                      FIELD_PREP(MT_TXD6_TX_RATE, rate);
                txwi[6] |= cpu_to_le32(val);