Commit 0b8e2d69 authored by Lorenzo Bianconi's avatar Lorenzo Bianconi Committed by Felix Fietkau
Browse files

wifi: mt76: mt7996: rely on mt76_connac2_mac_tx_rate_val



In order to fix a possible NULL pointer dereference in
mt7996_mac_write_txwi() of vif pointer, export
mt76_connac2_mac_tx_rate_val utility routine and reuse it
in mt7996 driver.

Fixes: 98686cd2 ("wifi: mt76: mt7996: add driver for MediaTek Wi-Fi 7 (802.11be) devices")
Signed-off-by: default avatarLorenzo Bianconi <lorenzo@kernel.org>
Signed-off-by: default avatarFelix Fietkau <nbd@nbd.name>
parent 888d8903
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -370,6 +370,9 @@ void mt76_connac2_mac_write_txwi(struct mt76_dev *dev, __le32 *txwi,
				 struct sk_buff *skb, struct mt76_wcid *wcid,
				 struct ieee80211_key_conf *key, int pid,
				 enum mt76_txq_id qid, u32 changed);
u16 mt76_connac2_mac_tx_rate_val(struct mt76_phy *mphy,
				 struct ieee80211_vif *vif,
				 bool beacon, bool mcast);
bool mt76_connac2_mac_fill_txs(struct mt76_dev *dev, struct mt76_wcid *wcid,
			       __le32 *txs_data);
bool mt76_connac2_mac_add_txs_skb(struct mt76_dev *dev, struct mt76_wcid *wcid,
+4 −3
Original line number Diff line number Diff line
@@ -267,8 +267,8 @@ int mt76_connac_init_tx_queues(struct mt76_phy *phy, int idx, int n_desc,
}
EXPORT_SYMBOL_GPL(mt76_connac_init_tx_queues);

static u16
mt76_connac2_mac_tx_rate_val(struct mt76_phy *mphy, struct ieee80211_vif *vif,
u16 mt76_connac2_mac_tx_rate_val(struct mt76_phy *mphy,
				 struct ieee80211_vif *vif,
				 bool beacon, bool mcast)
{
	u8 mode = 0, band = mphy->chandef.chan->band;
@@ -319,6 +319,7 @@ mt76_connac2_mac_tx_rate_val(struct mt76_phy *mphy, struct ieee80211_vif *vif,
	return FIELD_PREP(MT_TX_RATE_IDX, rateidx) |
	       FIELD_PREP(MT_TX_RATE_MODE, mode);
}
EXPORT_SYMBOL_GPL(mt76_connac2_mac_tx_rate_val);

static void
mt76_connac2_mac_write_txwi_8023(__le32 *txwi, struct sk_buff *skb,
+2 −46
Original line number Diff line number Diff line
@@ -959,51 +959,6 @@ mt7996_mac_write_txwi_80211(struct mt7996_dev *dev, __le32 *txwi,
	}
}

static u16
mt7996_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 mt7996_mac_write_txwi(struct mt7996_dev *dev, __le32 *txwi,
			   struct sk_buff *skb, struct mt76_wcid *wcid, int pid,
			   struct ieee80211_key_conf *key, u32 changed)
@@ -1091,7 +1046,8 @@ void mt7996_mac_write_txwi(struct mt7996_dev *dev, __le32 *txwi,
		/* Fixed rata is available just for 802.11 txd */
		struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
		bool multicast = is_multicast_ether_addr(hdr->addr1);
		u16 rate = mt7996_mac_tx_rate_val(mphy, vif, beacon, multicast);
		u16 rate = mt76_connac2_mac_tx_rate_val(mphy, vif, beacon,
							multicast);

		/* fix to bw 20 */
		val = MT_TXD6_FIXED_BW |