mirror of
https://github.com/torvalds/linux.git
synced 2026-05-26 16:12:59 +02:00
mt76 fixes for 6.16
-----BEGIN PGP SIGNATURE----- Comment: GPGTools - http://gpgtools.org iF0EABECAB0WIQR10Rp9kadxD0kAQu/XfRQdAqdu9QUCaGws0wAKCRDXfRQdAqdu 9cxcAKCKrKFhB8TKyWHwfiH8QEC86XyyMQCeJ6T0seeKLXopyvdb3s120ehCcdY= =4/7B -----END PGP SIGNATURE----- Merge tag 'mt76-fixes-2025-07-07' of https://github.com/nbd168/wireless Felix Fietkau says: =================== mt76 fixes for 6.16 =================== Signed-off-by: Johannes Berg <johannes.berg@intel.com>
This commit is contained in:
commit
5300e5e24b
|
|
@ -1224,6 +1224,16 @@ static inline int mt76_wed_dma_setup(struct mt76_dev *dev, struct mt76_queue *q,
|
|||
#define mt76_dereference(p, dev) \
|
||||
rcu_dereference_protected(p, lockdep_is_held(&(dev)->mutex))
|
||||
|
||||
static inline struct mt76_wcid *
|
||||
__mt76_wcid_ptr(struct mt76_dev *dev, u16 idx)
|
||||
{
|
||||
if (idx >= ARRAY_SIZE(dev->wcid))
|
||||
return NULL;
|
||||
return rcu_dereference(dev->wcid[idx]);
|
||||
}
|
||||
|
||||
#define mt76_wcid_ptr(dev, idx) __mt76_wcid_ptr(&(dev)->mt76, idx)
|
||||
|
||||
struct mt76_dev *mt76_alloc_device(struct device *pdev, unsigned int size,
|
||||
const struct ieee80211_ops *ops,
|
||||
const struct mt76_driver_ops *drv_ops);
|
||||
|
|
|
|||
|
|
@ -44,7 +44,7 @@ mt7603_rx_loopback_skb(struct mt7603_dev *dev, struct sk_buff *skb)
|
|||
if (idx >= MT7603_WTBL_STA - 1)
|
||||
goto free;
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (!wcid)
|
||||
goto free;
|
||||
|
||||
|
|
|
|||
|
|
@ -487,10 +487,7 @@ mt7603_rx_get_wcid(struct mt7603_dev *dev, u8 idx, bool unicast)
|
|||
struct mt7603_sta *sta;
|
||||
struct mt76_wcid *wcid;
|
||||
|
||||
if (idx >= MT7603_WTBL_SIZE)
|
||||
return NULL;
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (unicast || !wcid)
|
||||
return wcid;
|
||||
|
||||
|
|
@ -1266,12 +1263,9 @@ void mt7603_mac_add_txs(struct mt7603_dev *dev, void *data)
|
|||
if (pid == MT_PACKET_ID_NO_ACK)
|
||||
return;
|
||||
|
||||
if (wcidx >= MT7603_WTBL_SIZE)
|
||||
return;
|
||||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wcidx]);
|
||||
wcid = mt76_wcid_ptr(dev, wcidx);
|
||||
if (!wcid)
|
||||
goto out;
|
||||
|
||||
|
|
|
|||
|
|
@ -90,10 +90,7 @@ static struct mt76_wcid *mt7615_rx_get_wcid(struct mt7615_dev *dev,
|
|||
struct mt7615_sta *sta;
|
||||
struct mt76_wcid *wcid;
|
||||
|
||||
if (idx >= MT7615_WTBL_SIZE)
|
||||
return NULL;
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (unicast || !wcid)
|
||||
return wcid;
|
||||
|
||||
|
|
@ -1504,7 +1501,7 @@ static void mt7615_mac_add_txs(struct mt7615_dev *dev, void *data)
|
|||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wcidx]);
|
||||
wcid = mt76_wcid_ptr(dev, wcidx);
|
||||
if (!wcid)
|
||||
goto out;
|
||||
|
||||
|
|
|
|||
|
|
@ -1172,7 +1172,7 @@ void mt76_connac2_txwi_free(struct mt76_dev *dev, struct mt76_txwi_cache *t,
|
|||
wcid_idx = wcid->idx;
|
||||
} else {
|
||||
wcid_idx = le32_get_bits(txwi[1], MT_TXD1_WLAN_IDX);
|
||||
wcid = rcu_dereference(dev->wcid[wcid_idx]);
|
||||
wcid = __mt76_wcid_ptr(dev, wcid_idx);
|
||||
|
||||
if (wcid && wcid->sta) {
|
||||
sta = container_of((void *)wcid, struct ieee80211_sta,
|
||||
|
|
|
|||
|
|
@ -287,7 +287,7 @@ __mt76_connac_mcu_alloc_sta_req(struct mt76_dev *dev, struct mt76_vif_link *mvif
|
|||
|
||||
mt76_connac_mcu_get_wlan_idx(dev, wcid, &hdr.wlan_idx_lo,
|
||||
&hdr.wlan_idx_hi);
|
||||
skb = mt76_mcu_msg_alloc(dev, NULL, len);
|
||||
skb = __mt76_mcu_msg_alloc(dev, NULL, len, len, GFP_ATOMIC);
|
||||
if (!skb)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
|
||||
|
|
@ -1740,8 +1740,8 @@ int mt76_connac_mcu_hw_scan(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
|||
if (!sreq->ssids[i].ssid_len)
|
||||
continue;
|
||||
|
||||
req->ssids[i].ssid_len = cpu_to_le32(sreq->ssids[i].ssid_len);
|
||||
memcpy(req->ssids[i].ssid, sreq->ssids[i].ssid,
|
||||
req->ssids[n_ssids].ssid_len = cpu_to_le32(sreq->ssids[i].ssid_len);
|
||||
memcpy(req->ssids[n_ssids].ssid, sreq->ssids[i].ssid,
|
||||
sreq->ssids[i].ssid_len);
|
||||
n_ssids++;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -262,10 +262,7 @@ mt76x02_rx_get_sta(struct mt76_dev *dev, u8 idx)
|
|||
{
|
||||
struct mt76_wcid *wcid;
|
||||
|
||||
if (idx >= MT76x02_N_WCIDS)
|
||||
return NULL;
|
||||
|
||||
wcid = rcu_dereference(dev->wcid[idx]);
|
||||
wcid = __mt76_wcid_ptr(dev, idx);
|
||||
if (!wcid)
|
||||
return NULL;
|
||||
|
||||
|
|
|
|||
|
|
@ -564,9 +564,7 @@ void mt76x02_send_tx_status(struct mt76x02_dev *dev,
|
|||
|
||||
rcu_read_lock();
|
||||
|
||||
if (stat->wcid < MT76x02_N_WCIDS)
|
||||
wcid = rcu_dereference(dev->mt76.wcid[stat->wcid]);
|
||||
|
||||
wcid = mt76_wcid_ptr(dev, stat->wcid);
|
||||
if (wcid && wcid->sta) {
|
||||
void *priv;
|
||||
|
||||
|
|
|
|||
|
|
@ -56,10 +56,7 @@ static struct mt76_wcid *mt7915_rx_get_wcid(struct mt7915_dev *dev,
|
|||
struct mt7915_sta *sta;
|
||||
struct mt76_wcid *wcid;
|
||||
|
||||
if (idx >= ARRAY_SIZE(dev->mt76.wcid))
|
||||
return NULL;
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (unicast || !wcid)
|
||||
return wcid;
|
||||
|
||||
|
|
@ -917,7 +914,7 @@ mt7915_mac_tx_free(struct mt7915_dev *dev, void *data, int len)
|
|||
u16 idx;
|
||||
|
||||
idx = FIELD_GET(MT_TX_FREE_WLAN_ID, info);
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
sta = wcid_to_sta(wcid);
|
||||
if (!sta)
|
||||
continue;
|
||||
|
|
@ -1013,12 +1010,9 @@ static void mt7915_mac_add_txs(struct mt7915_dev *dev, void *data)
|
|||
if (pid < MT_PACKET_ID_WED)
|
||||
return;
|
||||
|
||||
if (wcidx >= mt7915_wtbl_size(dev))
|
||||
return;
|
||||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wcidx]);
|
||||
wcid = mt76_wcid_ptr(dev, wcidx);
|
||||
if (!wcid)
|
||||
goto out;
|
||||
|
||||
|
|
|
|||
|
|
@ -3986,7 +3986,7 @@ int mt7915_mcu_wed_wa_tx_stats(struct mt7915_dev *dev, u16 wlan_idx)
|
|||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wlan_idx]);
|
||||
wcid = mt76_wcid_ptr(dev, wlan_idx);
|
||||
if (wcid)
|
||||
wcid->stats.tx_packets += le32_to_cpu(res->tx_packets);
|
||||
else
|
||||
|
|
|
|||
|
|
@ -587,12 +587,9 @@ static void mt7915_mmio_wed_update_rx_stats(struct mtk_wed_device *wed,
|
|||
|
||||
dev = container_of(wed, struct mt7915_dev, mt76.mmio.wed);
|
||||
|
||||
if (idx >= mt7915_wtbl_size(dev))
|
||||
return;
|
||||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (wcid) {
|
||||
wcid->stats.rx_bytes += le32_to_cpu(stats->rx_byte_cnt);
|
||||
wcid->stats.rx_packets += le32_to_cpu(stats->rx_pkt_cnt);
|
||||
|
|
|
|||
|
|
@ -465,7 +465,7 @@ void mt7921_mac_add_txs(struct mt792x_dev *dev, void *data)
|
|||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wcidx]);
|
||||
wcid = mt76_wcid_ptr(dev, wcidx);
|
||||
if (!wcid)
|
||||
goto out;
|
||||
|
||||
|
|
@ -516,7 +516,7 @@ static void mt7921_mac_tx_free(struct mt792x_dev *dev, void *data, int len)
|
|||
|
||||
count++;
|
||||
idx = FIELD_GET(MT_TX_FREE_WLAN_ID, info);
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
sta = wcid_to_sta(wcid);
|
||||
if (!sta)
|
||||
continue;
|
||||
|
|
@ -816,7 +816,7 @@ void mt7921_usb_sdio_tx_complete_skb(struct mt76_dev *mdev,
|
|||
u16 idx;
|
||||
|
||||
idx = le32_get_bits(txwi[1], MT_TXD1_WLAN_IDX);
|
||||
wcid = rcu_dereference(mdev->wcid[idx]);
|
||||
wcid = __mt76_wcid_ptr(mdev, idx);
|
||||
sta = wcid_to_sta(wcid);
|
||||
|
||||
if (sta && likely(e->skb->protocol != cpu_to_be16(ETH_P_PAE)))
|
||||
|
|
|
|||
|
|
@ -1180,6 +1180,9 @@ static void mt7921_sta_set_decap_offload(struct ieee80211_hw *hw,
|
|||
struct mt792x_sta *msta = (struct mt792x_sta *)sta->drv_priv;
|
||||
struct mt792x_dev *dev = mt792x_hw_dev(hw);
|
||||
|
||||
if (!msta->deflink.wcid.sta)
|
||||
return;
|
||||
|
||||
mt792x_mutex_acquire(dev);
|
||||
|
||||
if (enabled)
|
||||
|
|
|
|||
|
|
@ -52,6 +52,8 @@ static int mt7925_thermal_init(struct mt792x_phy *phy)
|
|||
|
||||
name = devm_kasprintf(&wiphy->dev, GFP_KERNEL, "mt7925_%s",
|
||||
wiphy_name(wiphy));
|
||||
if (!name)
|
||||
return -ENOMEM;
|
||||
|
||||
hwmon = devm_hwmon_device_register_with_groups(&wiphy->dev, name, phy,
|
||||
mt7925_hwmon_groups);
|
||||
|
|
|
|||
|
|
@ -1040,7 +1040,7 @@ void mt7925_mac_add_txs(struct mt792x_dev *dev, void *data)
|
|||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wcidx]);
|
||||
wcid = mt76_wcid_ptr(dev, wcidx);
|
||||
if (!wcid)
|
||||
goto out;
|
||||
|
||||
|
|
@ -1122,7 +1122,7 @@ mt7925_mac_tx_free(struct mt792x_dev *dev, void *data, int len)
|
|||
u16 idx;
|
||||
|
||||
idx = FIELD_GET(MT_TXFREE_INFO_WLAN_ID, info);
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
sta = wcid_to_sta(wcid);
|
||||
if (!sta)
|
||||
continue;
|
||||
|
|
@ -1445,7 +1445,7 @@ void mt7925_usb_sdio_tx_complete_skb(struct mt76_dev *mdev,
|
|||
u16 idx;
|
||||
|
||||
idx = le32_get_bits(txwi[1], MT_TXD1_WLAN_IDX);
|
||||
wcid = rcu_dereference(mdev->wcid[idx]);
|
||||
wcid = __mt76_wcid_ptr(mdev, idx);
|
||||
sta = wcid_to_sta(wcid);
|
||||
|
||||
if (sta && likely(e->skb->protocol != cpu_to_be16(ETH_P_PAE)))
|
||||
|
|
|
|||
|
|
@ -1481,7 +1481,7 @@ mt7925_start_sched_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif,
|
|||
|
||||
mt792x_mutex_acquire(dev);
|
||||
|
||||
err = mt7925_mcu_sched_scan_req(mphy, vif, req);
|
||||
err = mt7925_mcu_sched_scan_req(mphy, vif, req, ies);
|
||||
if (err < 0)
|
||||
goto out;
|
||||
|
||||
|
|
@ -1603,6 +1603,9 @@ static void mt7925_sta_set_decap_offload(struct ieee80211_hw *hw,
|
|||
unsigned long valid = mvif->valid_links;
|
||||
u8 i;
|
||||
|
||||
if (!msta->vif)
|
||||
return;
|
||||
|
||||
mt792x_mutex_acquire(dev);
|
||||
|
||||
valid = ieee80211_vif_is_mld(vif) ? mvif->valid_links : BIT(0);
|
||||
|
|
@ -1617,6 +1620,9 @@ static void mt7925_sta_set_decap_offload(struct ieee80211_hw *hw,
|
|||
else
|
||||
clear_bit(MT_WCID_FLAG_HDR_TRANS, &mlink->wcid.flags);
|
||||
|
||||
if (!mlink->wcid.sta)
|
||||
continue;
|
||||
|
||||
mt7925_mcu_wtbl_update_hdr_trans(dev, vif, sta, i);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -164,6 +164,7 @@ mt7925_connac_mcu_set_wow_ctrl(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
|||
bool suspend, struct cfg80211_wowlan *wowlan)
|
||||
{
|
||||
struct mt76_vif_link *mvif = (struct mt76_vif_link *)vif->drv_priv;
|
||||
struct ieee80211_scan_ies ies = {};
|
||||
struct mt76_dev *dev = phy->dev;
|
||||
struct {
|
||||
struct {
|
||||
|
|
@ -194,7 +195,7 @@ mt7925_connac_mcu_set_wow_ctrl(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
|||
req.wow_ctrl_tlv.trigger |= (UNI_WOW_DETECT_TYPE_DISCONNECT |
|
||||
UNI_WOW_DETECT_TYPE_BCN_LOST);
|
||||
if (wowlan->nd_config) {
|
||||
mt7925_mcu_sched_scan_req(phy, vif, wowlan->nd_config);
|
||||
mt7925_mcu_sched_scan_req(phy, vif, wowlan->nd_config, &ies);
|
||||
req.wow_ctrl_tlv.trigger |= UNI_WOW_DETECT_TYPE_SCH_SCAN_HIT;
|
||||
mt7925_mcu_sched_scan_enable(phy, vif, suspend);
|
||||
}
|
||||
|
|
@ -2818,6 +2819,54 @@ int mt7925_mcu_set_dbdc(struct mt76_phy *phy, bool enable)
|
|||
return err;
|
||||
}
|
||||
|
||||
static void
|
||||
mt7925_mcu_build_scan_ie_tlv(struct mt76_dev *mdev,
|
||||
struct sk_buff *skb,
|
||||
struct ieee80211_scan_ies *scan_ies)
|
||||
{
|
||||
u32 max_len = sizeof(struct scan_ie_tlv) + MT76_CONNAC_SCAN_IE_LEN;
|
||||
struct scan_ie_tlv *ie;
|
||||
enum nl80211_band i;
|
||||
struct tlv *tlv;
|
||||
const u8 *ies;
|
||||
u16 ies_len;
|
||||
|
||||
for (i = 0; i <= NL80211_BAND_6GHZ; i++) {
|
||||
if (i == NL80211_BAND_60GHZ)
|
||||
continue;
|
||||
|
||||
ies = scan_ies->ies[i];
|
||||
ies_len = scan_ies->len[i];
|
||||
|
||||
if (!ies || !ies_len)
|
||||
continue;
|
||||
|
||||
if (ies_len > max_len)
|
||||
return;
|
||||
|
||||
tlv = mt76_connac_mcu_add_tlv(skb, UNI_SCAN_IE,
|
||||
sizeof(*ie) + ies_len);
|
||||
ie = (struct scan_ie_tlv *)tlv;
|
||||
|
||||
memcpy(ie->ies, ies, ies_len);
|
||||
ie->ies_len = cpu_to_le16(ies_len);
|
||||
|
||||
switch (i) {
|
||||
case NL80211_BAND_2GHZ:
|
||||
ie->band = 1;
|
||||
break;
|
||||
case NL80211_BAND_6GHZ:
|
||||
ie->band = 3;
|
||||
break;
|
||||
default:
|
||||
ie->band = 2;
|
||||
break;
|
||||
}
|
||||
|
||||
max_len -= (sizeof(*ie) + ies_len);
|
||||
}
|
||||
}
|
||||
|
||||
int mt7925_mcu_hw_scan(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
||||
struct ieee80211_scan_request *scan_req)
|
||||
{
|
||||
|
|
@ -2843,7 +2892,8 @@ int mt7925_mcu_hw_scan(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
|||
|
||||
max_len = sizeof(*hdr) + sizeof(*req) + sizeof(*ssid) +
|
||||
sizeof(*bssid) * MT7925_RNR_SCAN_MAX_BSSIDS +
|
||||
sizeof(*chan_info) + sizeof(*misc) + sizeof(*ie);
|
||||
sizeof(*chan_info) + sizeof(*misc) + sizeof(*ie) +
|
||||
MT76_CONNAC_SCAN_IE_LEN;
|
||||
|
||||
skb = mt76_mcu_msg_alloc(mdev, NULL, max_len);
|
||||
if (!skb)
|
||||
|
|
@ -2869,8 +2919,8 @@ int mt7925_mcu_hw_scan(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
|||
if (i > MT7925_RNR_SCAN_MAX_BSSIDS)
|
||||
break;
|
||||
|
||||
ssid->ssids[i].ssid_len = cpu_to_le32(sreq->ssids[i].ssid_len);
|
||||
memcpy(ssid->ssids[i].ssid, sreq->ssids[i].ssid,
|
||||
ssid->ssids[n_ssids].ssid_len = cpu_to_le32(sreq->ssids[i].ssid_len);
|
||||
memcpy(ssid->ssids[n_ssids].ssid, sreq->ssids[i].ssid,
|
||||
sreq->ssids[i].ssid_len);
|
||||
n_ssids++;
|
||||
}
|
||||
|
|
@ -2925,13 +2975,6 @@ int mt7925_mcu_hw_scan(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
|||
}
|
||||
chan_info->channel_type = sreq->n_channels ? 4 : 0;
|
||||
|
||||
tlv = mt76_connac_mcu_add_tlv(skb, UNI_SCAN_IE, sizeof(*ie));
|
||||
ie = (struct scan_ie_tlv *)tlv;
|
||||
if (sreq->ie_len > 0) {
|
||||
memcpy(ie->ies, sreq->ie, sreq->ie_len);
|
||||
ie->ies_len = cpu_to_le16(sreq->ie_len);
|
||||
}
|
||||
|
||||
req->scan_func |= SCAN_FUNC_SPLIT_SCAN;
|
||||
|
||||
tlv = mt76_connac_mcu_add_tlv(skb, UNI_SCAN_MISC, sizeof(*misc));
|
||||
|
|
@ -2942,6 +2985,9 @@ int mt7925_mcu_hw_scan(struct mt76_phy *phy, struct ieee80211_vif *vif,
|
|||
req->scan_func |= SCAN_FUNC_RANDOM_MAC;
|
||||
}
|
||||
|
||||
/* Append scan probe IEs as the last tlv */
|
||||
mt7925_mcu_build_scan_ie_tlv(mdev, skb, &scan_req->ies);
|
||||
|
||||
err = mt76_mcu_skb_send_msg(mdev, skb, MCU_UNI_CMD(SCAN_REQ),
|
||||
true);
|
||||
if (err < 0)
|
||||
|
|
@ -2953,7 +2999,8 @@ EXPORT_SYMBOL_GPL(mt7925_mcu_hw_scan);
|
|||
|
||||
int mt7925_mcu_sched_scan_req(struct mt76_phy *phy,
|
||||
struct ieee80211_vif *vif,
|
||||
struct cfg80211_sched_scan_request *sreq)
|
||||
struct cfg80211_sched_scan_request *sreq,
|
||||
struct ieee80211_scan_ies *ies)
|
||||
{
|
||||
struct mt76_vif_link *mvif = (struct mt76_vif_link *)vif->drv_priv;
|
||||
struct ieee80211_channel **scan_list = sreq->channels;
|
||||
|
|
@ -3041,12 +3088,8 @@ int mt7925_mcu_sched_scan_req(struct mt76_phy *phy,
|
|||
}
|
||||
chan_info->channel_type = sreq->n_channels ? 4 : 0;
|
||||
|
||||
tlv = mt76_connac_mcu_add_tlv(skb, UNI_SCAN_IE, sizeof(*ie));
|
||||
ie = (struct scan_ie_tlv *)tlv;
|
||||
if (sreq->ie_len > 0) {
|
||||
memcpy(ie->ies, sreq->ie, sreq->ie_len);
|
||||
ie->ies_len = cpu_to_le16(sreq->ie_len);
|
||||
}
|
||||
/* Append scan probe IEs as the last tlv */
|
||||
mt7925_mcu_build_scan_ie_tlv(mdev, skb, ies);
|
||||
|
||||
return mt76_mcu_skb_send_msg(mdev, skb, MCU_UNI_CMD(SCAN_REQ),
|
||||
true);
|
||||
|
|
|
|||
|
|
@ -269,7 +269,7 @@ struct scan_ie_tlv {
|
|||
__le16 ies_len;
|
||||
u8 band;
|
||||
u8 pad;
|
||||
u8 ies[MT76_CONNAC_SCAN_IE_LEN];
|
||||
u8 ies[];
|
||||
};
|
||||
|
||||
struct scan_misc_tlv {
|
||||
|
|
@ -673,7 +673,8 @@ int mt7925_mcu_cancel_hw_scan(struct mt76_phy *phy,
|
|||
struct ieee80211_vif *vif);
|
||||
int mt7925_mcu_sched_scan_req(struct mt76_phy *phy,
|
||||
struct ieee80211_vif *vif,
|
||||
struct cfg80211_sched_scan_request *sreq);
|
||||
struct cfg80211_sched_scan_request *sreq,
|
||||
struct ieee80211_scan_ies *ies);
|
||||
int mt7925_mcu_sched_scan_enable(struct mt76_phy *phy,
|
||||
struct ieee80211_vif *vif,
|
||||
bool enable);
|
||||
|
|
|
|||
|
|
@ -58,7 +58,7 @@
|
|||
|
||||
#define MT_INT_TX_DONE_MCU (MT_INT_TX_DONE_MCU_WM | \
|
||||
MT_INT_TX_DONE_FWDL)
|
||||
#define MT_INT_TX_DONE_ALL (MT_INT_TX_DONE_MCU_WM | \
|
||||
#define MT_INT_TX_DONE_ALL (MT_INT_TX_DONE_MCU | \
|
||||
MT_INT_TX_DONE_BAND0 | \
|
||||
GENMASK(18, 4))
|
||||
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ static const struct ieee80211_iface_combination if_comb[] = {
|
|||
},
|
||||
};
|
||||
|
||||
static const struct ieee80211_iface_limit if_limits_chanctx[] = {
|
||||
static const struct ieee80211_iface_limit if_limits_chanctx_mcc[] = {
|
||||
{
|
||||
.max = 2,
|
||||
.types = BIT(NL80211_IFTYPE_STATION) |
|
||||
|
|
@ -36,8 +36,23 @@ static const struct ieee80211_iface_limit if_limits_chanctx[] = {
|
|||
},
|
||||
{
|
||||
.max = 1,
|
||||
.types = BIT(NL80211_IFTYPE_AP) |
|
||||
BIT(NL80211_IFTYPE_P2P_GO)
|
||||
.types = BIT(NL80211_IFTYPE_P2P_GO)
|
||||
},
|
||||
{
|
||||
.max = 1,
|
||||
.types = BIT(NL80211_IFTYPE_P2P_DEVICE)
|
||||
}
|
||||
};
|
||||
|
||||
static const struct ieee80211_iface_limit if_limits_chanctx_scc[] = {
|
||||
{
|
||||
.max = 2,
|
||||
.types = BIT(NL80211_IFTYPE_STATION) |
|
||||
BIT(NL80211_IFTYPE_P2P_CLIENT)
|
||||
},
|
||||
{
|
||||
.max = 1,
|
||||
.types = BIT(NL80211_IFTYPE_AP)
|
||||
},
|
||||
{
|
||||
.max = 1,
|
||||
|
|
@ -47,11 +62,18 @@ static const struct ieee80211_iface_limit if_limits_chanctx[] = {
|
|||
|
||||
static const struct ieee80211_iface_combination if_comb_chanctx[] = {
|
||||
{
|
||||
.limits = if_limits_chanctx,
|
||||
.n_limits = ARRAY_SIZE(if_limits_chanctx),
|
||||
.limits = if_limits_chanctx_mcc,
|
||||
.n_limits = ARRAY_SIZE(if_limits_chanctx_mcc),
|
||||
.max_interfaces = 3,
|
||||
.num_different_channels = 2,
|
||||
.beacon_int_infra_match = false,
|
||||
},
|
||||
{
|
||||
.limits = if_limits_chanctx_scc,
|
||||
.n_limits = ARRAY_SIZE(if_limits_chanctx_scc),
|
||||
.max_interfaces = 3,
|
||||
.num_different_channels = 1,
|
||||
.beacon_int_infra_match = false,
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -142,10 +142,7 @@ struct mt76_wcid *mt792x_rx_get_wcid(struct mt792x_dev *dev, u16 idx,
|
|||
struct mt792x_sta *sta;
|
||||
struct mt76_wcid *wcid;
|
||||
|
||||
if (idx >= ARRAY_SIZE(dev->mt76.wcid))
|
||||
return NULL;
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (unicast || !wcid)
|
||||
return wcid;
|
||||
|
||||
|
|
|
|||
|
|
@ -61,10 +61,7 @@ static struct mt76_wcid *mt7996_rx_get_wcid(struct mt7996_dev *dev,
|
|||
struct mt76_wcid *wcid;
|
||||
int i;
|
||||
|
||||
if (idx >= ARRAY_SIZE(dev->mt76.wcid))
|
||||
return NULL;
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (!wcid)
|
||||
return NULL;
|
||||
|
||||
|
|
@ -1249,7 +1246,7 @@ mt7996_mac_tx_free(struct mt7996_dev *dev, void *data, int len)
|
|||
u16 idx;
|
||||
|
||||
idx = FIELD_GET(MT_TXFREE_INFO_WLAN_ID, info);
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
sta = wcid_to_sta(wcid);
|
||||
if (!sta)
|
||||
goto next;
|
||||
|
|
@ -1471,12 +1468,9 @@ static void mt7996_mac_add_txs(struct mt7996_dev *dev, void *data)
|
|||
if (pid < MT_PACKET_ID_NO_SKB)
|
||||
return;
|
||||
|
||||
if (wcidx >= mt7996_wtbl_size(dev))
|
||||
return;
|
||||
|
||||
rcu_read_lock();
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wcidx]);
|
||||
wcid = mt76_wcid_ptr(dev, wcidx);
|
||||
if (!wcid)
|
||||
goto out;
|
||||
|
||||
|
|
@ -2353,20 +2347,12 @@ void mt7996_mac_update_stats(struct mt7996_phy *phy)
|
|||
void mt7996_mac_sta_rc_work(struct work_struct *work)
|
||||
{
|
||||
struct mt7996_dev *dev = container_of(work, struct mt7996_dev, rc_work);
|
||||
struct ieee80211_bss_conf *link_conf;
|
||||
struct ieee80211_link_sta *link_sta;
|
||||
struct mt7996_sta_link *msta_link;
|
||||
struct mt7996_vif_link *link;
|
||||
struct mt76_vif_link *mlink;
|
||||
struct ieee80211_sta *sta;
|
||||
struct ieee80211_vif *vif;
|
||||
struct mt7996_sta *msta;
|
||||
struct mt7996_vif *mvif;
|
||||
LIST_HEAD(list);
|
||||
u32 changed;
|
||||
u8 link_id;
|
||||
|
||||
rcu_read_lock();
|
||||
spin_lock_bh(&dev->mt76.sta_poll_lock);
|
||||
list_splice_init(&dev->sta_rc_list, &list);
|
||||
|
||||
|
|
@ -2377,46 +2363,28 @@ void mt7996_mac_sta_rc_work(struct work_struct *work)
|
|||
|
||||
changed = msta_link->changed;
|
||||
msta_link->changed = 0;
|
||||
|
||||
sta = wcid_to_sta(&msta_link->wcid);
|
||||
link_id = msta_link->wcid.link_id;
|
||||
msta = msta_link->sta;
|
||||
mvif = msta->vif;
|
||||
vif = container_of((void *)mvif, struct ieee80211_vif, drv_priv);
|
||||
|
||||
mlink = rcu_dereference(mvif->mt76.link[link_id]);
|
||||
if (!mlink)
|
||||
continue;
|
||||
|
||||
link_sta = rcu_dereference(sta->link[link_id]);
|
||||
if (!link_sta)
|
||||
continue;
|
||||
|
||||
link_conf = rcu_dereference(vif->link_conf[link_id]);
|
||||
if (!link_conf)
|
||||
continue;
|
||||
mvif = msta_link->sta->vif;
|
||||
vif = container_of((void *)mvif, struct ieee80211_vif,
|
||||
drv_priv);
|
||||
|
||||
spin_unlock_bh(&dev->mt76.sta_poll_lock);
|
||||
|
||||
link = (struct mt7996_vif_link *)mlink;
|
||||
|
||||
if (changed & (IEEE80211_RC_SUPP_RATES_CHANGED |
|
||||
IEEE80211_RC_NSS_CHANGED |
|
||||
IEEE80211_RC_BW_CHANGED))
|
||||
mt7996_mcu_add_rate_ctrl(dev, vif, link_conf,
|
||||
link_sta, link, msta_link,
|
||||
mt7996_mcu_add_rate_ctrl(dev, msta_link->sta, vif,
|
||||
msta_link->wcid.link_id,
|
||||
true);
|
||||
|
||||
if (changed & IEEE80211_RC_SMPS_CHANGED)
|
||||
mt7996_mcu_set_fixed_field(dev, link_sta, link,
|
||||
msta_link, NULL,
|
||||
mt7996_mcu_set_fixed_field(dev, msta_link->sta, NULL,
|
||||
msta_link->wcid.link_id,
|
||||
RATE_PARAM_MMPS_UPDATE);
|
||||
|
||||
spin_lock_bh(&dev->mt76.sta_poll_lock);
|
||||
}
|
||||
|
||||
spin_unlock_bh(&dev->mt76.sta_poll_lock);
|
||||
rcu_read_unlock();
|
||||
}
|
||||
|
||||
void mt7996_mac_work(struct work_struct *work)
|
||||
|
|
|
|||
|
|
@ -1112,9 +1112,8 @@ mt7996_mac_sta_event(struct mt7996_dev *dev, struct ieee80211_vif *vif,
|
|||
if (err)
|
||||
return err;
|
||||
|
||||
err = mt7996_mcu_add_rate_ctrl(dev, vif, link_conf,
|
||||
link_sta, link,
|
||||
msta_link, false);
|
||||
err = mt7996_mcu_add_rate_ctrl(dev, msta_link->sta, vif,
|
||||
link_id, false);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
|
|
|
|||
|
|
@ -555,7 +555,7 @@ mt7996_mcu_rx_all_sta_info_event(struct mt7996_dev *dev, struct sk_buff *skb)
|
|||
switch (le16_to_cpu(res->tag)) {
|
||||
case UNI_ALL_STA_TXRX_RATE:
|
||||
wlan_idx = le16_to_cpu(res->rate[i].wlan_idx);
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wlan_idx]);
|
||||
wcid = mt76_wcid_ptr(dev, wlan_idx);
|
||||
|
||||
if (!wcid)
|
||||
break;
|
||||
|
|
@ -565,7 +565,7 @@ mt7996_mcu_rx_all_sta_info_event(struct mt7996_dev *dev, struct sk_buff *skb)
|
|||
break;
|
||||
case UNI_ALL_STA_TXRX_ADM_STAT:
|
||||
wlan_idx = le16_to_cpu(res->adm_stat[i].wlan_idx);
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wlan_idx]);
|
||||
wcid = mt76_wcid_ptr(dev, wlan_idx);
|
||||
|
||||
if (!wcid)
|
||||
break;
|
||||
|
|
@ -579,7 +579,7 @@ mt7996_mcu_rx_all_sta_info_event(struct mt7996_dev *dev, struct sk_buff *skb)
|
|||
break;
|
||||
case UNI_ALL_STA_TXRX_MSDU_COUNT:
|
||||
wlan_idx = le16_to_cpu(res->msdu_cnt[i].wlan_idx);
|
||||
wcid = rcu_dereference(dev->mt76.wcid[wlan_idx]);
|
||||
wcid = mt76_wcid_ptr(dev, wlan_idx);
|
||||
|
||||
if (!wcid)
|
||||
break;
|
||||
|
|
@ -676,10 +676,7 @@ mt7996_mcu_wed_rro_event(struct mt7996_dev *dev, struct sk_buff *skb)
|
|||
|
||||
e = (void *)skb->data;
|
||||
idx = le16_to_cpu(e->wlan_id);
|
||||
if (idx >= ARRAY_SIZE(dev->mt76.wcid))
|
||||
break;
|
||||
|
||||
wcid = rcu_dereference(dev->mt76.wcid[idx]);
|
||||
wcid = mt76_wcid_ptr(dev, idx);
|
||||
if (!wcid || !wcid->sta)
|
||||
break;
|
||||
|
||||
|
|
@ -1905,22 +1902,35 @@ int mt7996_mcu_set_fixed_rate_ctrl(struct mt7996_dev *dev,
|
|||
MCU_WM_UNI_CMD(RA), true);
|
||||
}
|
||||
|
||||
int mt7996_mcu_set_fixed_field(struct mt7996_dev *dev,
|
||||
struct ieee80211_link_sta *link_sta,
|
||||
struct mt7996_vif_link *link,
|
||||
struct mt7996_sta_link *msta_link,
|
||||
void *data, u32 field)
|
||||
int mt7996_mcu_set_fixed_field(struct mt7996_dev *dev, struct mt7996_sta *msta,
|
||||
void *data, u8 link_id, u32 field)
|
||||
{
|
||||
struct sta_phy_uni *phy = data;
|
||||
struct mt7996_vif *mvif = msta->vif;
|
||||
struct mt7996_sta_link *msta_link;
|
||||
struct sta_rec_ra_fixed_uni *ra;
|
||||
struct sta_phy_uni *phy = data;
|
||||
struct mt76_vif_link *mlink;
|
||||
struct sk_buff *skb;
|
||||
int err = -ENODEV;
|
||||
struct tlv *tlv;
|
||||
|
||||
skb = __mt76_connac_mcu_alloc_sta_req(&dev->mt76, &link->mt76,
|
||||
rcu_read_lock();
|
||||
|
||||
mlink = rcu_dereference(mvif->mt76.link[link_id]);
|
||||
if (!mlink)
|
||||
goto error_unlock;
|
||||
|
||||
msta_link = rcu_dereference(msta->link[link_id]);
|
||||
if (!msta_link)
|
||||
goto error_unlock;
|
||||
|
||||
skb = __mt76_connac_mcu_alloc_sta_req(&dev->mt76, mlink,
|
||||
&msta_link->wcid,
|
||||
MT7996_STA_UPDATE_MAX_SIZE);
|
||||
if (IS_ERR(skb))
|
||||
return PTR_ERR(skb);
|
||||
if (IS_ERR(skb)) {
|
||||
err = PTR_ERR(skb);
|
||||
goto error_unlock;
|
||||
}
|
||||
|
||||
tlv = mt76_connac_mcu_add_tlv(skb, STA_REC_RA_UPDATE, sizeof(*ra));
|
||||
ra = (struct sta_rec_ra_fixed_uni *)tlv;
|
||||
|
|
@ -1935,106 +1945,149 @@ int mt7996_mcu_set_fixed_field(struct mt7996_dev *dev,
|
|||
if (phy)
|
||||
ra->phy = *phy;
|
||||
break;
|
||||
case RATE_PARAM_MMPS_UPDATE:
|
||||
case RATE_PARAM_MMPS_UPDATE: {
|
||||
struct ieee80211_sta *sta = wcid_to_sta(&msta_link->wcid);
|
||||
struct ieee80211_link_sta *link_sta;
|
||||
|
||||
link_sta = rcu_dereference(sta->link[link_id]);
|
||||
if (!link_sta) {
|
||||
dev_kfree_skb(skb);
|
||||
goto error_unlock;
|
||||
}
|
||||
|
||||
ra->mmps_mode = mt7996_mcu_get_mmps_mode(link_sta->smps_mode);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
ra->field = cpu_to_le32(field);
|
||||
|
||||
rcu_read_unlock();
|
||||
|
||||
return mt76_mcu_skb_send_msg(&dev->mt76, skb,
|
||||
MCU_WMWA_UNI_CMD(STA_REC_UPDATE), true);
|
||||
error_unlock:
|
||||
rcu_read_unlock();
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
static int
|
||||
mt7996_mcu_add_rate_ctrl_fixed(struct mt7996_dev *dev,
|
||||
struct ieee80211_link_sta *link_sta,
|
||||
struct mt7996_vif_link *link,
|
||||
struct mt7996_sta_link *msta_link)
|
||||
mt7996_mcu_add_rate_ctrl_fixed(struct mt7996_dev *dev, struct mt7996_sta *msta,
|
||||
struct ieee80211_vif *vif, u8 link_id)
|
||||
{
|
||||
struct cfg80211_chan_def *chandef = &link->phy->mt76->chandef;
|
||||
struct cfg80211_bitrate_mask *mask = &link->bitrate_mask;
|
||||
enum nl80211_band band = chandef->chan->band;
|
||||
struct ieee80211_link_sta *link_sta;
|
||||
struct cfg80211_bitrate_mask mask;
|
||||
struct mt7996_sta_link *msta_link;
|
||||
struct mt7996_vif_link *link;
|
||||
struct sta_phy_uni phy = {};
|
||||
int ret, nrates = 0;
|
||||
struct ieee80211_sta *sta;
|
||||
int ret, nrates = 0, idx;
|
||||
enum nl80211_band band;
|
||||
bool has_he;
|
||||
|
||||
#define __sta_phy_bitrate_mask_check(_mcs, _gi, _ht, _he) \
|
||||
do { \
|
||||
u8 i, gi = mask->control[band]._gi; \
|
||||
u8 i, gi = mask.control[band]._gi; \
|
||||
gi = (_he) ? gi : gi == NL80211_TXRATE_FORCE_SGI; \
|
||||
phy.sgi = gi; \
|
||||
phy.he_ltf = mask->control[band].he_ltf; \
|
||||
for (i = 0; i < ARRAY_SIZE(mask->control[band]._mcs); i++) { \
|
||||
if (!mask->control[band]._mcs[i]) \
|
||||
phy.he_ltf = mask.control[band].he_ltf; \
|
||||
for (i = 0; i < ARRAY_SIZE(mask.control[band]._mcs); i++) { \
|
||||
if (!mask.control[band]._mcs[i]) \
|
||||
continue; \
|
||||
nrates += hweight16(mask->control[band]._mcs[i]); \
|
||||
phy.mcs = ffs(mask->control[band]._mcs[i]) - 1; \
|
||||
nrates += hweight16(mask.control[band]._mcs[i]); \
|
||||
phy.mcs = ffs(mask.control[band]._mcs[i]) - 1; \
|
||||
if (_ht) \
|
||||
phy.mcs += 8 * i; \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
if (link_sta->he_cap.has_he) {
|
||||
rcu_read_lock();
|
||||
|
||||
link = mt7996_vif_link(dev, vif, link_id);
|
||||
if (!link)
|
||||
goto error_unlock;
|
||||
|
||||
msta_link = rcu_dereference(msta->link[link_id]);
|
||||
if (!msta_link)
|
||||
goto error_unlock;
|
||||
|
||||
sta = wcid_to_sta(&msta_link->wcid);
|
||||
link_sta = rcu_dereference(sta->link[link_id]);
|
||||
if (!link_sta)
|
||||
goto error_unlock;
|
||||
|
||||
band = link->phy->mt76->chandef.chan->band;
|
||||
has_he = link_sta->he_cap.has_he;
|
||||
mask = link->bitrate_mask;
|
||||
idx = msta_link->wcid.idx;
|
||||
|
||||
if (has_he) {
|
||||
__sta_phy_bitrate_mask_check(he_mcs, he_gi, 0, 1);
|
||||
} else if (link_sta->vht_cap.vht_supported) {
|
||||
__sta_phy_bitrate_mask_check(vht_mcs, gi, 0, 0);
|
||||
} else if (link_sta->ht_cap.ht_supported) {
|
||||
__sta_phy_bitrate_mask_check(ht_mcs, gi, 1, 0);
|
||||
} else {
|
||||
nrates = hweight32(mask->control[band].legacy);
|
||||
phy.mcs = ffs(mask->control[band].legacy) - 1;
|
||||
nrates = hweight32(mask.control[band].legacy);
|
||||
phy.mcs = ffs(mask.control[band].legacy) - 1;
|
||||
}
|
||||
|
||||
rcu_read_unlock();
|
||||
|
||||
#undef __sta_phy_bitrate_mask_check
|
||||
|
||||
/* fall back to auto rate control */
|
||||
if (mask->control[band].gi == NL80211_TXRATE_DEFAULT_GI &&
|
||||
mask->control[band].he_gi == GENMASK(7, 0) &&
|
||||
mask->control[band].he_ltf == GENMASK(7, 0) &&
|
||||
if (mask.control[band].gi == NL80211_TXRATE_DEFAULT_GI &&
|
||||
mask.control[band].he_gi == GENMASK(7, 0) &&
|
||||
mask.control[band].he_ltf == GENMASK(7, 0) &&
|
||||
nrates != 1)
|
||||
return 0;
|
||||
|
||||
/* fixed single rate */
|
||||
if (nrates == 1) {
|
||||
ret = mt7996_mcu_set_fixed_field(dev, link_sta, link,
|
||||
msta_link, &phy,
|
||||
ret = mt7996_mcu_set_fixed_field(dev, msta, &phy, link_id,
|
||||
RATE_PARAM_FIXED_MCS);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* fixed GI */
|
||||
if (mask->control[band].gi != NL80211_TXRATE_DEFAULT_GI ||
|
||||
mask->control[band].he_gi != GENMASK(7, 0)) {
|
||||
if (mask.control[band].gi != NL80211_TXRATE_DEFAULT_GI ||
|
||||
mask.control[band].he_gi != GENMASK(7, 0)) {
|
||||
u32 addr;
|
||||
|
||||
/* firmware updates only TXCMD but doesn't take WTBL into
|
||||
* account, so driver should update here to reflect the
|
||||
* actual txrate hardware sends out.
|
||||
*/
|
||||
addr = mt7996_mac_wtbl_lmac_addr(dev, msta_link->wcid.idx, 7);
|
||||
if (link_sta->he_cap.has_he)
|
||||
addr = mt7996_mac_wtbl_lmac_addr(dev, idx, 7);
|
||||
if (has_he)
|
||||
mt76_rmw_field(dev, addr, GENMASK(31, 24), phy.sgi);
|
||||
else
|
||||
mt76_rmw_field(dev, addr, GENMASK(15, 12), phy.sgi);
|
||||
|
||||
ret = mt7996_mcu_set_fixed_field(dev, link_sta, link,
|
||||
msta_link, &phy,
|
||||
ret = mt7996_mcu_set_fixed_field(dev, msta, &phy, link_id,
|
||||
RATE_PARAM_FIXED_GI);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* fixed HE_LTF */
|
||||
if (mask->control[band].he_ltf != GENMASK(7, 0)) {
|
||||
ret = mt7996_mcu_set_fixed_field(dev, link_sta, link,
|
||||
msta_link, &phy,
|
||||
if (mask.control[band].he_ltf != GENMASK(7, 0)) {
|
||||
ret = mt7996_mcu_set_fixed_field(dev, msta, &phy, link_id,
|
||||
RATE_PARAM_FIXED_HE_LTF);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
error_unlock:
|
||||
rcu_read_unlock();
|
||||
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -2145,21 +2198,44 @@ mt7996_mcu_sta_rate_ctrl_tlv(struct sk_buff *skb, struct mt7996_dev *dev,
|
|||
memset(ra->rx_rcpi, INIT_RCPI, sizeof(ra->rx_rcpi));
|
||||
}
|
||||
|
||||
int mt7996_mcu_add_rate_ctrl(struct mt7996_dev *dev,
|
||||
struct ieee80211_vif *vif,
|
||||
struct ieee80211_bss_conf *link_conf,
|
||||
struct ieee80211_link_sta *link_sta,
|
||||
struct mt7996_vif_link *link,
|
||||
struct mt7996_sta_link *msta_link, bool changed)
|
||||
int mt7996_mcu_add_rate_ctrl(struct mt7996_dev *dev, struct mt7996_sta *msta,
|
||||
struct ieee80211_vif *vif, u8 link_id,
|
||||
bool changed)
|
||||
{
|
||||
struct ieee80211_bss_conf *link_conf;
|
||||
struct ieee80211_link_sta *link_sta;
|
||||
struct mt7996_sta_link *msta_link;
|
||||
struct mt7996_vif_link *link;
|
||||
struct ieee80211_sta *sta;
|
||||
struct sk_buff *skb;
|
||||
int ret;
|
||||
int ret = -ENODEV;
|
||||
|
||||
rcu_read_lock();
|
||||
|
||||
link = mt7996_vif_link(dev, vif, link_id);
|
||||
if (!link)
|
||||
goto error_unlock;
|
||||
|
||||
msta_link = rcu_dereference(msta->link[link_id]);
|
||||
if (!msta_link)
|
||||
goto error_unlock;
|
||||
|
||||
sta = wcid_to_sta(&msta_link->wcid);
|
||||
link_sta = rcu_dereference(sta->link[link_id]);
|
||||
if (!link_sta)
|
||||
goto error_unlock;
|
||||
|
||||
link_conf = rcu_dereference(vif->link_conf[link_id]);
|
||||
if (!link_conf)
|
||||
goto error_unlock;
|
||||
|
||||
skb = __mt76_connac_mcu_alloc_sta_req(&dev->mt76, &link->mt76,
|
||||
&msta_link->wcid,
|
||||
MT7996_STA_UPDATE_MAX_SIZE);
|
||||
if (IS_ERR(skb))
|
||||
return PTR_ERR(skb);
|
||||
if (IS_ERR(skb)) {
|
||||
ret = PTR_ERR(skb);
|
||||
goto error_unlock;
|
||||
}
|
||||
|
||||
/* firmware rc algorithm refers to sta_rec_he for HE control.
|
||||
* once dev->rc_work changes the settings driver should also
|
||||
|
|
@ -2173,12 +2249,19 @@ int mt7996_mcu_add_rate_ctrl(struct mt7996_dev *dev,
|
|||
*/
|
||||
mt7996_mcu_sta_rate_ctrl_tlv(skb, dev, vif, link_conf, link_sta, link);
|
||||
|
||||
rcu_read_unlock();
|
||||
|
||||
ret = mt76_mcu_skb_send_msg(&dev->mt76, skb,
|
||||
MCU_WMWA_UNI_CMD(STA_REC_UPDATE), true);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
return mt7996_mcu_add_rate_ctrl_fixed(dev, link_sta, link, msta_link);
|
||||
return mt7996_mcu_add_rate_ctrl_fixed(dev, msta, vif, link_id);
|
||||
|
||||
error_unlock:
|
||||
rcu_read_unlock();
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int
|
||||
|
|
|
|||
|
|
@ -620,23 +620,17 @@ int mt7996_mcu_beacon_inband_discov(struct mt7996_dev *dev,
|
|||
int mt7996_mcu_add_obss_spr(struct mt7996_phy *phy,
|
||||
struct mt7996_vif_link *link,
|
||||
struct ieee80211_he_obss_pd *he_obss_pd);
|
||||
int mt7996_mcu_add_rate_ctrl(struct mt7996_dev *dev,
|
||||
struct ieee80211_vif *vif,
|
||||
struct ieee80211_bss_conf *link_conf,
|
||||
struct ieee80211_link_sta *link_sta,
|
||||
struct mt7996_vif_link *link,
|
||||
struct mt7996_sta_link *msta_link, bool changed);
|
||||
int mt7996_mcu_add_rate_ctrl(struct mt7996_dev *dev, struct mt7996_sta *msta,
|
||||
struct ieee80211_vif *vif, u8 link_id,
|
||||
bool changed);
|
||||
int mt7996_set_channel(struct mt76_phy *mphy);
|
||||
int mt7996_mcu_set_chan_info(struct mt7996_phy *phy, u16 tag);
|
||||
int mt7996_mcu_set_tx(struct mt7996_dev *dev, struct ieee80211_vif *vif,
|
||||
struct ieee80211_bss_conf *link_conf);
|
||||
int mt7996_mcu_set_fixed_rate_ctrl(struct mt7996_dev *dev,
|
||||
void *data, u16 version);
|
||||
int mt7996_mcu_set_fixed_field(struct mt7996_dev *dev,
|
||||
struct ieee80211_link_sta *link_sta,
|
||||
struct mt7996_vif_link *link,
|
||||
struct mt7996_sta_link *msta_link,
|
||||
void *data, u32 field);
|
||||
int mt7996_mcu_set_fixed_field(struct mt7996_dev *dev, struct mt7996_sta *msta,
|
||||
void *data, u8 link_id, u32 field);
|
||||
int mt7996_mcu_set_eeprom(struct mt7996_dev *dev);
|
||||
int mt7996_mcu_get_eeprom(struct mt7996_dev *dev, u32 offset, u8 *buf, u32 buf_len);
|
||||
int mt7996_mcu_get_eeprom_free_block(struct mt7996_dev *dev, u8 *block_num);
|
||||
|
|
|
|||
|
|
@ -64,7 +64,7 @@ mt76_tx_status_unlock(struct mt76_dev *dev, struct sk_buff_head *list)
|
|||
struct mt76_tx_cb *cb = mt76_tx_skb_cb(skb);
|
||||
struct mt76_wcid *wcid;
|
||||
|
||||
wcid = rcu_dereference(dev->wcid[cb->wcid]);
|
||||
wcid = __mt76_wcid_ptr(dev, cb->wcid);
|
||||
if (wcid) {
|
||||
status.sta = wcid_to_sta(wcid);
|
||||
if (status.sta && (wcid->rate.flags || wcid->rate.legacy)) {
|
||||
|
|
@ -251,9 +251,7 @@ void __mt76_tx_complete_skb(struct mt76_dev *dev, u16 wcid_idx, struct sk_buff *
|
|||
|
||||
rcu_read_lock();
|
||||
|
||||
if (wcid_idx < ARRAY_SIZE(dev->wcid))
|
||||
wcid = rcu_dereference(dev->wcid[wcid_idx]);
|
||||
|
||||
wcid = __mt76_wcid_ptr(dev, wcid_idx);
|
||||
mt76_tx_check_non_aql(dev, wcid, skb);
|
||||
|
||||
#ifdef CONFIG_NL80211_TESTMODE
|
||||
|
|
@ -538,7 +536,7 @@ mt76_txq_schedule_list(struct mt76_phy *phy, enum mt76_txq_id qid)
|
|||
break;
|
||||
|
||||
mtxq = (struct mt76_txq *)txq->drv_priv;
|
||||
wcid = rcu_dereference(dev->wcid[mtxq->wcid]);
|
||||
wcid = __mt76_wcid_ptr(dev, mtxq->wcid);
|
||||
if (!wcid || test_bit(MT_WCID_FLAG_PS, &wcid->flags))
|
||||
continue;
|
||||
|
||||
|
|
@ -617,7 +615,8 @@ mt76_txq_schedule_pending_wcid(struct mt76_phy *phy, struct mt76_wcid *wcid,
|
|||
if ((dev->drv->drv_flags & MT_DRV_HW_MGMT_TXQ) &&
|
||||
!(info->flags & IEEE80211_TX_CTL_HW_80211_ENCAP) &&
|
||||
!ieee80211_is_data(hdr->frame_control) &&
|
||||
!ieee80211_is_bufferable_mmpdu(skb))
|
||||
(!ieee80211_is_bufferable_mmpdu(skb) ||
|
||||
ieee80211_is_deauth(hdr->frame_control)))
|
||||
qid = MT_TXQ_PSD;
|
||||
|
||||
q = phy->q_tx[qid];
|
||||
|
|
|
|||
|
|
@ -83,7 +83,7 @@ int mt76_get_min_avg_rssi(struct mt76_dev *dev, u8 phy_idx)
|
|||
if (!(mask & 1))
|
||||
continue;
|
||||
|
||||
wcid = rcu_dereference(dev->wcid[j]);
|
||||
wcid = __mt76_wcid_ptr(dev, j);
|
||||
if (!wcid || wcid->phy_idx != phy_idx)
|
||||
continue;
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user