mirror of
git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-08-05 16:54:27 +00:00
wifi: mt76: mt7996: switch to single multi-radio wiphy
Use generic mt76 chanctx functions and look up phy from vif link. The driver now uses only a single phy to handle multiple interfaces on different channels. This is preparation for full MLO support. Link: https://patch.msgid.link/20250102163508.52945-23-nbd@nbd.name Signed-off-by: Felix Fietkau <nbd@nbd.name>
This commit is contained in:
parent
1f8dd5686e
commit
69d54ce749
7 changed files with 597 additions and 383 deletions
|
@ -305,6 +305,7 @@ int mt7996_eeprom_parse_hw_cap(struct mt7996_dev *dev, struct mt7996_phy *phy)
|
|||
|
||||
mphy->antenna_mask = BIT(nss) - 1;
|
||||
mphy->chainmask = (BIT(path) - 1) << dev->chainshift[band_idx];
|
||||
phy->orig_chainmask = mphy->chainmask;
|
||||
dev->chainmask |= mphy->chainmask;
|
||||
if (band_idx < MT_BAND2)
|
||||
dev->chainshift[band_idx + 1] = dev->chainshift[band_idx] +
|
||||
|
|
|
@ -14,6 +14,28 @@
|
|||
#include "coredump.h"
|
||||
#include "eeprom.h"
|
||||
|
||||
static const struct ieee80211_iface_limit if_limits_global = {
|
||||
.max = MT7996_MAX_INTERFACES * MT7996_MAX_RADIOS,
|
||||
.types = BIT(NL80211_IFTYPE_STATION)
|
||||
| BIT(NL80211_IFTYPE_ADHOC)
|
||||
| BIT(NL80211_IFTYPE_AP)
|
||||
#ifdef CONFIG_MAC80211_MESH
|
||||
| BIT(NL80211_IFTYPE_MESH_POINT)
|
||||
#endif
|
||||
};
|
||||
|
||||
static const struct ieee80211_iface_combination if_comb_global = {
|
||||
.limits = &if_limits_global,
|
||||
.n_limits = 1,
|
||||
.max_interfaces = MT7996_MAX_INTERFACES * MT7996_MAX_RADIOS,
|
||||
.num_different_channels = MT7996_MAX_RADIOS,
|
||||
.radar_detect_widths = BIT(NL80211_CHAN_WIDTH_20_NOHT) |
|
||||
BIT(NL80211_CHAN_WIDTH_20) |
|
||||
BIT(NL80211_CHAN_WIDTH_40) |
|
||||
BIT(NL80211_CHAN_WIDTH_80) |
|
||||
BIT(NL80211_CHAN_WIDTH_160),
|
||||
};
|
||||
|
||||
static const struct ieee80211_iface_limit if_limits[] = {
|
||||
{
|
||||
.max = 16,
|
||||
|
@ -27,8 +49,7 @@ static const struct ieee80211_iface_limit if_limits[] = {
|
|||
}
|
||||
};
|
||||
|
||||
static const struct ieee80211_iface_combination if_comb[] = {
|
||||
{
|
||||
static const struct ieee80211_iface_combination if_comb = {
|
||||
.limits = if_limits,
|
||||
.n_limits = ARRAY_SIZE(if_limits),
|
||||
.max_interfaces = MT7996_MAX_INTERFACES,
|
||||
|
@ -40,7 +61,6 @@ static const struct ieee80211_iface_combination if_comb[] = {
|
|||
BIT(NL80211_CHAN_WIDTH_80) |
|
||||
BIT(NL80211_CHAN_WIDTH_160),
|
||||
.beacon_int_min_gcd = 100,
|
||||
}
|
||||
};
|
||||
|
||||
static ssize_t mt7996_thermal_temp_show(struct device *dev,
|
||||
|
@ -177,28 +197,32 @@ static const struct thermal_cooling_device_ops mt7996_thermal_ops = {
|
|||
static void mt7996_unregister_thermal(struct mt7996_phy *phy)
|
||||
{
|
||||
struct wiphy *wiphy = phy->mt76->hw->wiphy;
|
||||
char name[sizeof("cooling_deviceXXX")];
|
||||
|
||||
if (!phy->cdev)
|
||||
return;
|
||||
|
||||
sysfs_remove_link(&wiphy->dev.kobj, "cooling_device");
|
||||
snprintf(name, sizeof(name), "cooling_device%d", phy->mt76->band_idx);
|
||||
sysfs_remove_link(&wiphy->dev.kobj, name);
|
||||
thermal_cooling_device_unregister(phy->cdev);
|
||||
}
|
||||
|
||||
static int mt7996_thermal_init(struct mt7996_phy *phy)
|
||||
{
|
||||
struct wiphy *wiphy = phy->mt76->hw->wiphy;
|
||||
char cname[sizeof("cooling_deviceXXX")];
|
||||
struct thermal_cooling_device *cdev;
|
||||
struct device *hwmon;
|
||||
const char *name;
|
||||
|
||||
name = devm_kasprintf(&wiphy->dev, GFP_KERNEL, "mt7996_%s",
|
||||
wiphy_name(wiphy));
|
||||
name = devm_kasprintf(&wiphy->dev, GFP_KERNEL, "mt7996_%s.%d",
|
||||
wiphy_name(wiphy), phy->mt76->band_idx);
|
||||
snprintf(cname, sizeof(cname), "cooling_device%d", phy->mt76->band_idx);
|
||||
|
||||
cdev = thermal_cooling_device_register(name, phy, &mt7996_thermal_ops);
|
||||
if (!IS_ERR(cdev)) {
|
||||
if (sysfs_create_link(&wiphy->dev.kobj, &cdev->device.kobj,
|
||||
"cooling_device") < 0)
|
||||
cname) < 0)
|
||||
thermal_cooling_device_unregister(cdev);
|
||||
else
|
||||
phy->cdev = cdev;
|
||||
|
@ -330,27 +354,87 @@ mt7996_regd_notifier(struct wiphy *wiphy,
|
|||
{
|
||||
struct ieee80211_hw *hw = wiphy_to_ieee80211_hw(wiphy);
|
||||
struct mt7996_dev *dev = mt7996_hw_dev(hw);
|
||||
struct mt7996_phy *phy = mt7996_hw_phy(hw);
|
||||
struct mt7996_phy *phy;
|
||||
|
||||
memcpy(dev->mt76.alpha2, request->alpha2, sizeof(dev->mt76.alpha2));
|
||||
dev->mt76.region = request->dfs_region;
|
||||
|
||||
mt7996_for_each_phy(dev, phy) {
|
||||
if (dev->mt76.region == NL80211_DFS_UNSET)
|
||||
mt7996_mcu_rdd_background_enable(phy, NULL);
|
||||
|
||||
mt7996_init_txpower(phy);
|
||||
|
||||
phy->mt76->dfs_state = MT_DFS_STATE_UNKNOWN;
|
||||
mt7996_dfs_init_radar_detector(phy);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
mt7996_init_wiphy_band(struct ieee80211_hw *hw, struct mt7996_phy *phy)
|
||||
{
|
||||
struct mt7996_dev *dev = phy->dev;
|
||||
struct wiphy *wiphy = hw->wiphy;
|
||||
int n_radios = hw->wiphy->n_radio;
|
||||
struct wiphy_radio_freq_range *freq = &dev->radio_freqs[n_radios];
|
||||
struct wiphy_radio *radio = &dev->radios[n_radios];
|
||||
|
||||
phy->slottime = 9;
|
||||
phy->beacon_rate = -1;
|
||||
|
||||
if (phy->mt76->cap.has_2ghz) {
|
||||
phy->mt76->sband_2g.sband.ht_cap.cap |=
|
||||
IEEE80211_HT_CAP_LDPC_CODING |
|
||||
IEEE80211_HT_CAP_MAX_AMSDU;
|
||||
phy->mt76->sband_2g.sband.ht_cap.ampdu_density =
|
||||
IEEE80211_HT_MPDU_DENSITY_2;
|
||||
freq->start_freq = 2400000;
|
||||
freq->end_freq = 2500000;
|
||||
} else if (phy->mt76->cap.has_5ghz) {
|
||||
phy->mt76->sband_5g.sband.ht_cap.cap |=
|
||||
IEEE80211_HT_CAP_LDPC_CODING |
|
||||
IEEE80211_HT_CAP_MAX_AMSDU;
|
||||
|
||||
phy->mt76->sband_5g.sband.vht_cap.cap |=
|
||||
IEEE80211_VHT_CAP_MAX_MPDU_LENGTH_11454 |
|
||||
IEEE80211_VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK |
|
||||
IEEE80211_VHT_CAP_SHORT_GI_160 |
|
||||
IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
|
||||
phy->mt76->sband_5g.sband.ht_cap.ampdu_density =
|
||||
IEEE80211_HT_MPDU_DENSITY_1;
|
||||
|
||||
ieee80211_hw_set(hw, SUPPORTS_VHT_EXT_NSS_BW);
|
||||
freq->start_freq = 5000000;
|
||||
freq->end_freq = 5900000;
|
||||
} else if (phy->mt76->cap.has_6ghz) {
|
||||
freq->start_freq = 5900000;
|
||||
freq->end_freq = 7200000;
|
||||
} else {
|
||||
return;
|
||||
}
|
||||
|
||||
dev->radio_phy[n_radios] = phy;
|
||||
radio->freq_range = freq;
|
||||
radio->n_freq_range = 1;
|
||||
radio->iface_combinations = &if_comb;
|
||||
radio->n_iface_combinations = 1;
|
||||
hw->wiphy->n_radio++;
|
||||
|
||||
wiphy->available_antennas_rx |= phy->mt76->chainmask;
|
||||
wiphy->available_antennas_tx |= phy->mt76->chainmask;
|
||||
|
||||
mt76_set_stream_caps(phy->mt76, true);
|
||||
mt7996_set_stream_vht_txbf_caps(phy);
|
||||
mt7996_set_stream_he_eht_caps(phy);
|
||||
mt7996_init_txpower(phy);
|
||||
}
|
||||
|
||||
static void
|
||||
mt7996_init_wiphy(struct ieee80211_hw *hw, struct mtk_wed_device *wed)
|
||||
{
|
||||
struct mt7996_phy *phy = mt7996_hw_phy(hw);
|
||||
struct mt76_dev *mdev = &phy->dev->mt76;
|
||||
struct mt7996_dev *dev = mt7996_hw_dev(hw);
|
||||
struct mt76_dev *mdev = &dev->mt76;
|
||||
struct wiphy *wiphy = hw->wiphy;
|
||||
u16 max_subframes = phy->dev->has_eht ? IEEE80211_MAX_AMPDU_BUF_EHT :
|
||||
u16 max_subframes = dev->has_eht ? IEEE80211_MAX_AMPDU_BUF_EHT :
|
||||
IEEE80211_MAX_AMPDU_BUF_HE;
|
||||
|
||||
hw->queues = 4;
|
||||
|
@ -363,14 +447,15 @@ mt7996_init_wiphy(struct ieee80211_hw *hw, struct mtk_wed_device *wed)
|
|||
hw->radiotap_timestamp.units_pos =
|
||||
IEEE80211_RADIOTAP_TIMESTAMP_UNIT_US;
|
||||
|
||||
phy->slottime = 9;
|
||||
phy->beacon_rate = -1;
|
||||
|
||||
hw->sta_data_size = sizeof(struct mt7996_sta);
|
||||
hw->vif_data_size = sizeof(struct mt7996_vif);
|
||||
hw->chanctx_data_size = sizeof(struct mt76_chanctx);
|
||||
|
||||
wiphy->iface_combinations = &if_comb_global;
|
||||
wiphy->n_iface_combinations = 1;
|
||||
|
||||
wiphy->radio = dev->radios;
|
||||
|
||||
wiphy->iface_combinations = if_comb;
|
||||
wiphy->n_iface_combinations = ARRAY_SIZE(if_comb);
|
||||
wiphy->reg_notifier = mt7996_regd_notifier;
|
||||
wiphy->flags |= WIPHY_FLAG_HAS_CHANNEL_SWITCH;
|
||||
wiphy->mbssid_max_interfaces = 16;
|
||||
|
@ -387,7 +472,7 @@ mt7996_init_wiphy(struct ieee80211_hw *hw, struct mtk_wed_device *wed)
|
|||
wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_CAN_REPLACE_PTK0);
|
||||
wiphy_ext_feature_set(wiphy, NL80211_EXT_FEATURE_MU_MIMO_AIR_SNIFFER);
|
||||
|
||||
if (mt7996_has_background_radar(phy->dev) &&
|
||||
if (mt7996_has_background_radar(dev) &&
|
||||
(!mdev->dev->of_node ||
|
||||
!of_property_read_bool(mdev->dev->of_node,
|
||||
"mediatek,disable-radar-background")))
|
||||
|
@ -397,51 +482,21 @@ mt7996_init_wiphy(struct ieee80211_hw *hw, struct mtk_wed_device *wed)
|
|||
ieee80211_hw_set(hw, HAS_RATE_CONTROL);
|
||||
ieee80211_hw_set(hw, SUPPORTS_TX_ENCAP_OFFLOAD);
|
||||
ieee80211_hw_set(hw, SUPPORTS_RX_DECAP_OFFLOAD);
|
||||
ieee80211_hw_set(hw, WANT_MONITOR_VIF);
|
||||
ieee80211_hw_set(hw, NO_VIRTUAL_MONITOR);
|
||||
ieee80211_hw_set(hw, SUPPORTS_MULTI_BSSID);
|
||||
|
||||
hw->max_tx_fragments = 4;
|
||||
|
||||
if (phy->mt76->cap.has_2ghz) {
|
||||
phy->mt76->sband_2g.sband.ht_cap.cap |=
|
||||
IEEE80211_HT_CAP_LDPC_CODING |
|
||||
IEEE80211_HT_CAP_MAX_AMSDU;
|
||||
phy->mt76->sband_2g.sband.ht_cap.ampdu_density =
|
||||
IEEE80211_HT_MPDU_DENSITY_2;
|
||||
}
|
||||
|
||||
if (phy->mt76->cap.has_5ghz) {
|
||||
phy->mt76->sband_5g.sband.ht_cap.cap |=
|
||||
IEEE80211_HT_CAP_LDPC_CODING |
|
||||
IEEE80211_HT_CAP_MAX_AMSDU;
|
||||
|
||||
phy->mt76->sband_5g.sband.vht_cap.cap |=
|
||||
IEEE80211_VHT_CAP_MAX_MPDU_LENGTH_11454 |
|
||||
IEEE80211_VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK |
|
||||
IEEE80211_VHT_CAP_SHORT_GI_160 |
|
||||
IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
|
||||
phy->mt76->sband_5g.sband.ht_cap.ampdu_density =
|
||||
IEEE80211_HT_MPDU_DENSITY_1;
|
||||
|
||||
ieee80211_hw_set(hw, SUPPORTS_VHT_EXT_NSS_BW);
|
||||
}
|
||||
|
||||
/* init led callbacks */
|
||||
if (IS_ENABLED(CONFIG_MT76_LEDS)) {
|
||||
phy->mt76->leds.cdev.brightness_set = mt7996_led_set_brightness;
|
||||
phy->mt76->leds.cdev.blink_set = mt7996_led_set_blink;
|
||||
dev->mphy.leds.cdev.brightness_set = mt7996_led_set_brightness;
|
||||
dev->mphy.leds.cdev.blink_set = mt7996_led_set_blink;
|
||||
}
|
||||
|
||||
mt76_set_stream_caps(phy->mt76, true);
|
||||
mt7996_set_stream_vht_txbf_caps(phy);
|
||||
mt7996_set_stream_he_eht_caps(phy);
|
||||
mt7996_init_txpower(phy);
|
||||
|
||||
wiphy->available_antennas_rx = phy->mt76->antenna_mask;
|
||||
wiphy->available_antennas_tx = phy->mt76->antenna_mask;
|
||||
|
||||
wiphy->max_scan_ssids = 4;
|
||||
wiphy->max_scan_ie_len = IEEE80211_MAX_DATA_LEN;
|
||||
|
||||
mt7996_init_wiphy_band(hw, &dev->phy);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -562,18 +617,15 @@ int mt7996_txbf_init(struct mt7996_dev *dev)
|
|||
return mt7996_mcu_set_txbf(dev, BF_HW_EN_UPDATE);
|
||||
}
|
||||
|
||||
static int mt7996_register_phy(struct mt7996_dev *dev, struct mt7996_phy *phy,
|
||||
enum mt76_band_id band)
|
||||
static int mt7996_register_phy(struct mt7996_dev *dev, enum mt76_band_id band)
|
||||
{
|
||||
struct mt7996_phy *phy;
|
||||
struct mt76_phy *mphy;
|
||||
u32 mac_ofs, hif1_ofs = 0;
|
||||
int ret;
|
||||
struct mtk_wed_device *wed = &dev->mt76.mmio.wed;
|
||||
|
||||
if (!mt7996_band_valid(dev, band) || band == MT_BAND0)
|
||||
return 0;
|
||||
|
||||
if (phy)
|
||||
if (!mt7996_band_valid(dev, band))
|
||||
return 0;
|
||||
|
||||
if (is_mt7996(&dev->mt76) && band == MT_BAND2 && dev->hif2) {
|
||||
|
@ -581,7 +633,7 @@ static int mt7996_register_phy(struct mt7996_dev *dev, struct mt7996_phy *phy,
|
|||
wed = &dev->mt76.mmio.wed_hif2;
|
||||
}
|
||||
|
||||
mphy = mt76_alloc_phy(&dev->mt76, sizeof(*phy), &mt7996_ops, band);
|
||||
mphy = mt76_alloc_radio_phy(&dev->mt76, sizeof(*phy), band);
|
||||
if (!mphy)
|
||||
return -ENOMEM;
|
||||
|
||||
|
@ -612,7 +664,7 @@ static int mt7996_register_phy(struct mt7996_dev *dev, struct mt7996_phy *phy,
|
|||
mt76_eeprom_override(mphy);
|
||||
|
||||
/* init wiphy according to mphy and phy */
|
||||
mt7996_init_wiphy(mphy->hw, wed);
|
||||
mt7996_init_wiphy_band(mphy->hw, phy);
|
||||
ret = mt7996_init_tx_queues(mphy->priv,
|
||||
MT_TXQ_ID(band),
|
||||
MT7996_TX_RING_SIZE,
|
||||
|
@ -626,10 +678,6 @@ static int mt7996_register_phy(struct mt7996_dev *dev, struct mt7996_phy *phy,
|
|||
if (ret)
|
||||
goto error;
|
||||
|
||||
ret = mt7996_thermal_init(phy);
|
||||
if (ret)
|
||||
goto error;
|
||||
|
||||
if (wed == &dev->mt76.mmio.wed_hif2 && mtk_wed_device_active(wed)) {
|
||||
u32 irq_mask = dev->mt76.mmio.irqmask | MT_INT_TX_DONE_BAND2;
|
||||
|
||||
|
@ -641,24 +689,14 @@ static int mt7996_register_phy(struct mt7996_dev *dev, struct mt7996_phy *phy,
|
|||
|
||||
error:
|
||||
mphy->dev->phys[band] = NULL;
|
||||
ieee80211_free_hw(mphy->hw);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
mt7996_unregister_phy(struct mt7996_phy *phy, enum mt76_band_id band)
|
||||
mt7996_unregister_phy(struct mt7996_phy *phy)
|
||||
{
|
||||
struct mt76_phy *mphy;
|
||||
|
||||
if (!phy)
|
||||
return;
|
||||
|
||||
if (phy)
|
||||
mt7996_unregister_thermal(phy);
|
||||
|
||||
mphy = phy->dev->mt76.phys[band];
|
||||
mt76_unregister_phy(mphy);
|
||||
ieee80211_free_hw(mphy->hw);
|
||||
phy->dev->mt76.phys[band] = NULL;
|
||||
}
|
||||
|
||||
static void mt7996_init_work(struct work_struct *work)
|
||||
|
@ -1412,6 +1450,7 @@ void mt7996_set_stream_he_eht_caps(struct mt7996_phy *phy)
|
|||
int mt7996_register_device(struct mt7996_dev *dev)
|
||||
{
|
||||
struct ieee80211_hw *hw = mt76_hw(dev);
|
||||
struct mt7996_phy *phy;
|
||||
int ret;
|
||||
|
||||
dev->phy.dev = dev;
|
||||
|
@ -1433,22 +1472,21 @@ int mt7996_register_device(struct mt7996_dev *dev)
|
|||
|
||||
mt7996_init_wiphy(hw, &dev->mt76.mmio.wed);
|
||||
|
||||
ret = mt7996_register_phy(dev, MT_BAND1);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = mt7996_register_phy(dev, MT_BAND2);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = mt76_register_device(&dev->mt76, true, mt76_rates,
|
||||
ARRAY_SIZE(mt76_rates));
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = mt7996_thermal_init(&dev->phy);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = mt7996_register_phy(dev, mt7996_phy2(dev), MT_BAND1);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = mt7996_register_phy(dev, mt7996_phy3(dev), MT_BAND2);
|
||||
if (ret)
|
||||
return ret;
|
||||
mt7996_for_each_phy(dev, phy)
|
||||
mt7996_thermal_init(phy);
|
||||
|
||||
ieee80211_queue_work(mt76_hw(dev), &dev->init_work);
|
||||
|
||||
|
@ -1473,8 +1511,8 @@ error:
|
|||
void mt7996_unregister_device(struct mt7996_dev *dev)
|
||||
{
|
||||
cancel_work_sync(&dev->wed_rro.work);
|
||||
mt7996_unregister_phy(mt7996_phy3(dev), MT_BAND2);
|
||||
mt7996_unregister_phy(mt7996_phy2(dev), MT_BAND1);
|
||||
mt7996_unregister_phy(mt7996_phy3(dev));
|
||||
mt7996_unregister_phy(mt7996_phy2(dev));
|
||||
mt7996_unregister_thermal(&dev->phy);
|
||||
mt7996_coredump_unregister(dev);
|
||||
mt76_unregister_device(&dev->mt76);
|
||||
|
|
|
@ -1738,19 +1738,19 @@ mt7996_mac_restart(struct mt7996_dev *dev)
|
|||
ret = mt7996_txbf_init(dev);
|
||||
|
||||
if (test_bit(MT76_STATE_RUNNING, &dev->mphy.state)) {
|
||||
ret = mt7996_run(dev->mphy.hw);
|
||||
ret = mt7996_run(&dev->phy);
|
||||
if (ret)
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (phy2 && test_bit(MT76_STATE_RUNNING, &phy2->mt76->state)) {
|
||||
ret = mt7996_run(phy2->mt76->hw);
|
||||
ret = mt7996_run(phy2);
|
||||
if (ret)
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (phy3 && test_bit(MT76_STATE_RUNNING, &phy3->mt76->state)) {
|
||||
ret = mt7996_run(phy3->mt76->hw);
|
||||
ret = mt7996_run(phy3);
|
||||
if (ret)
|
||||
goto out;
|
||||
}
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -2572,18 +2572,24 @@ int mt7996_mcu_beacon_inband_discov(struct mt7996_dev *dev,
|
|||
#define OFFLOAD_TX_MODE_SU BIT(0)
|
||||
#define OFFLOAD_TX_MODE_MU BIT(1)
|
||||
struct ieee80211_hw *hw = mt76_hw(dev);
|
||||
struct mt7996_phy *phy = mt7996_hw_phy(hw);
|
||||
struct mt7996_vif *mvif = (struct mt7996_vif *)vif->drv_priv;
|
||||
struct cfg80211_chan_def *chandef = &mvif->deflink.phy->mt76->chandef;
|
||||
enum nl80211_band band = chandef->chan->band;
|
||||
struct mt7996_phy *phy = mt7996_vif_link_phy(&mvif->deflink);
|
||||
struct mt76_wcid *wcid = &dev->mt76.global_wcid;
|
||||
struct bss_inband_discovery_tlv *discov;
|
||||
struct ieee80211_tx_info *info;
|
||||
struct sk_buff *rskb, *skb = NULL;
|
||||
struct cfg80211_chan_def *chandef;
|
||||
enum nl80211_band band;
|
||||
struct tlv *tlv;
|
||||
u8 *buf, interval;
|
||||
int len;
|
||||
|
||||
if (!phy)
|
||||
return -EINVAL;
|
||||
|
||||
chandef = &phy->mt76->chandef;
|
||||
band = chandef->chan->band;
|
||||
|
||||
if (vif->bss_conf.nontransmitted)
|
||||
return 0;
|
||||
|
||||
|
@ -4495,7 +4501,6 @@ int mt7996_mcu_set_txpower_sku(struct mt7996_phy *phy)
|
|||
#define TX_POWER_LIMIT_TABLE_RATE 0
|
||||
struct mt7996_dev *dev = phy->dev;
|
||||
struct mt76_phy *mphy = phy->mt76;
|
||||
struct ieee80211_hw *hw = mphy->hw;
|
||||
struct tx_power_limit_table_ctrl {
|
||||
u8 __rsv1[4];
|
||||
|
||||
|
@ -4515,7 +4520,7 @@ int mt7996_mcu_set_txpower_sku(struct mt7996_phy *phy)
|
|||
struct sk_buff *skb;
|
||||
int i, tx_power;
|
||||
|
||||
tx_power = mt7996_get_power_bound(phy, hw->conf.power_level);
|
||||
tx_power = mt7996_get_power_bound(phy, phy->txpower);
|
||||
tx_power = mt76_get_rate_power_limits(mphy, mphy->chandef.chan,
|
||||
&la, tx_power);
|
||||
mphy->txpower_cur = tx_power;
|
||||
|
|
|
@ -605,6 +605,7 @@ struct mt7996_dev *mt7996_mmio_probe(struct device *pdev,
|
|||
static const struct mt76_driver_ops drv_ops = {
|
||||
/* txwi_size = txd size + txp size */
|
||||
.txwi_size = MT_TXD_SIZE + sizeof(struct mt76_connac_fw_txp),
|
||||
.link_data_size = sizeof(struct mt7996_vif_link),
|
||||
.drv_flags = MT_DRV_TXWI_NO_FREE |
|
||||
MT_DRV_AMSDU_OFFLOAD |
|
||||
MT_DRV_HW_MGMT_TXQ,
|
||||
|
@ -622,6 +623,8 @@ struct mt7996_dev *mt7996_mmio_probe(struct device *pdev,
|
|||
.sta_remove = mt7996_mac_sta_remove,
|
||||
.update_survey = mt7996_update_channel,
|
||||
.set_channel = mt7996_set_channel,
|
||||
.vif_link_add = mt7996_vif_link_add,
|
||||
.vif_link_remove = mt7996_vif_link_remove,
|
||||
};
|
||||
struct mt7996_dev *dev;
|
||||
struct mt76_dev *mdev;
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
#include "../mt76_connac.h"
|
||||
#include "regs.h"
|
||||
|
||||
#define MT7996_MAX_RADIOS 3
|
||||
#define MT7996_MAX_INTERFACES 19 /* per-band */
|
||||
#define MT7996_MAX_WMM_SETS 4
|
||||
#define MT7996_WTBL_BMC_SIZE (is_mt7992(&dev->mt76) ? 32 : 64)
|
||||
|
@ -270,11 +271,15 @@ struct mt7996_phy {
|
|||
|
||||
u32 rx_ampdu_ts;
|
||||
u32 ampdu_ref;
|
||||
int txpower;
|
||||
|
||||
struct mt76_mib_stats mib;
|
||||
struct mt76_channel_state state_ts;
|
||||
|
||||
u16 orig_chainmask;
|
||||
|
||||
bool has_aux_rx;
|
||||
bool counter_reset;
|
||||
};
|
||||
|
||||
struct mt7996_dev {
|
||||
|
@ -283,6 +288,10 @@ struct mt7996_dev {
|
|||
struct mt76_phy mphy;
|
||||
};
|
||||
|
||||
struct mt7996_phy *radio_phy[MT7996_MAX_RADIOS];
|
||||
struct wiphy_radio radios[MT7996_MAX_RADIOS];
|
||||
struct wiphy_radio_freq_range radio_freqs[MT7996_MAX_RADIOS];
|
||||
|
||||
struct mt7996_hif *hif2;
|
||||
struct mt7996_reg_desc reg;
|
||||
u8 q_id[MT7996_MAX_QUEUE];
|
||||
|
@ -402,14 +411,6 @@ enum mt7996_rdd_cmd {
|
|||
RDD_IRQ_OFF,
|
||||
};
|
||||
|
||||
static inline struct mt7996_phy *
|
||||
mt7996_hw_phy(struct ieee80211_hw *hw)
|
||||
{
|
||||
struct mt76_phy *phy = hw->priv;
|
||||
|
||||
return phy->priv;
|
||||
}
|
||||
|
||||
static inline struct mt7996_dev *
|
||||
mt7996_hw_dev(struct ieee80211_hw *hw)
|
||||
{
|
||||
|
@ -469,12 +470,35 @@ mt7996_has_background_radar(struct mt7996_dev *dev)
|
|||
return true;
|
||||
}
|
||||
|
||||
static inline struct mt7996_phy *
|
||||
mt7996_band_phy(struct mt7996_dev *dev, enum nl80211_band band)
|
||||
{
|
||||
struct mt76_phy *mphy;
|
||||
|
||||
mphy = dev->mt76.band_phys[band];
|
||||
if (!mphy)
|
||||
return NULL;
|
||||
|
||||
return mphy->priv;
|
||||
}
|
||||
|
||||
static inline struct mt7996_vif_link *
|
||||
mt7996_vif_link(struct mt7996_dev *dev, struct ieee80211_vif *vif, int link_id)
|
||||
{
|
||||
return (struct mt7996_vif_link *)mt76_vif_link(&dev->mt76, vif, link_id);
|
||||
}
|
||||
|
||||
static inline struct mt7996_phy *
|
||||
mt7996_vif_link_phy(struct mt7996_vif_link *link)
|
||||
{
|
||||
struct mt76_phy *mphy = mt76_vif_link_phy(&link->mt76);
|
||||
|
||||
if (!mphy)
|
||||
return NULL;
|
||||
|
||||
return mphy->priv;
|
||||
}
|
||||
|
||||
static inline struct mt7996_vif_link *
|
||||
mt7996_vif_conf_link(struct mt7996_dev *dev, struct ieee80211_vif *vif,
|
||||
struct ieee80211_bss_conf *link_conf)
|
||||
|
@ -483,6 +507,10 @@ mt7996_vif_conf_link(struct mt7996_dev *dev, struct ieee80211_vif *vif,
|
|||
link_conf);
|
||||
}
|
||||
|
||||
#define mt7996_for_each_phy(dev, phy) \
|
||||
for (int __i = 0; __i < ARRAY_SIZE((dev)->radio_phy); __i++) \
|
||||
if (((phy) = (dev)->radio_phy[__i]) != NULL)
|
||||
|
||||
extern const struct ieee80211_ops mt7996_ops;
|
||||
extern struct pci_driver mt7996_pci_driver;
|
||||
extern struct pci_driver mt7996_hif_driver;
|
||||
|
@ -494,6 +522,12 @@ irqreturn_t mt7996_irq_handler(int irq, void *dev_instance);
|
|||
u64 __mt7996_get_tsf(struct ieee80211_hw *hw, struct mt7996_vif *mvif);
|
||||
int mt7996_register_device(struct mt7996_dev *dev);
|
||||
void mt7996_unregister_device(struct mt7996_dev *dev);
|
||||
int mt7996_vif_link_add(struct mt76_phy *mphy, struct ieee80211_vif *vif,
|
||||
struct ieee80211_bss_conf *link_conf,
|
||||
struct mt76_vif_link *mlink);
|
||||
void mt7996_vif_link_remove(struct mt76_phy *mphy, struct ieee80211_vif *vif,
|
||||
struct ieee80211_bss_conf *link_conf,
|
||||
struct mt76_vif_link *mlink);
|
||||
int mt7996_eeprom_init(struct mt7996_dev *dev);
|
||||
int mt7996_eeprom_parse_hw_cap(struct mt7996_dev *dev, struct mt7996_phy *phy);
|
||||
int mt7996_eeprom_get_target_power(struct mt7996_dev *dev,
|
||||
|
@ -509,7 +543,7 @@ int mt7996_init_tx_queues(struct mt7996_phy *phy, int idx,
|
|||
void mt7996_init_txpower(struct mt7996_phy *phy);
|
||||
int mt7996_txbf_init(struct mt7996_dev *dev);
|
||||
void mt7996_reset(struct mt7996_dev *dev);
|
||||
int mt7996_run(struct ieee80211_hw *hw);
|
||||
int mt7996_run(struct mt7996_phy *phy);
|
||||
int mt7996_mcu_init(struct mt7996_dev *dev);
|
||||
int mt7996_mcu_init_firmware(struct mt7996_dev *dev);
|
||||
int mt7996_mcu_twt_agrt_update(struct mt7996_dev *dev,
|
||||
|
|
Loading…
Add table
Reference in a new issue