Preparation for supporting a single hw with multiple radios Signed-off-by: Felix Fietkau <nbd@xxxxxxxx> --- drivers/net/wireless/mediatek/mt76/mac80211.c | 39 ++++++++++++++++--- drivers/net/wireless/mediatek/mt76/mt76.h | 2 + 2 files changed, 36 insertions(+), 5 deletions(-) diff --git a/drivers/net/wireless/mediatek/mt76/mac80211.c b/drivers/net/wireless/mediatek/mt76/mac80211.c index 69fcea08e3fd..5a77f94b7f82 100644 --- a/drivers/net/wireless/mediatek/mt76/mac80211.c +++ b/drivers/net/wireless/mediatek/mt76/mac80211.c @@ -411,13 +411,15 @@ mt76_check_sband(struct mt76_phy *phy, struct mt76_sband *msband, } if (found) { - phy->chandef.chan = &sband->channels[0]; + cfg80211_chandef_create(&phy->chandef, &sband->channels[0], + NL80211_CHAN_HT20); phy->chan_state = &msband->chan[0]; return; } sband->n_channels = 0; - phy->hw->wiphy->bands[band] = NULL; + if (phy->hw->wiphy->bands[band] == sband) + phy->hw->wiphy->bands[band] = NULL; } static int @@ -429,6 +431,9 @@ mt76_phy_init(struct mt76_phy *phy, struct ieee80211_hw *hw) INIT_LIST_HEAD(&phy->tx_list); spin_lock_init(&phy->tx_lock); + if ((void *)phy != hw->priv) + return 0; + SET_IEEE80211_DEV(hw, dev->dev); SET_IEEE80211_PERM_ADDR(hw, phy->macaddr); @@ -480,6 +485,28 @@ mt76_phy_init(struct mt76_phy *phy, struct ieee80211_hw *hw) return 0; } +struct mt76_phy * +mt76_alloc_radio_phy(struct mt76_dev *dev, unsigned int size, + u8 band_idx) +{ + struct ieee80211_hw *hw = dev->phy.hw; + unsigned int phy_size; + struct mt76_phy *phy; + + phy_size = ALIGN(sizeof(*phy), 8); + phy = devm_kzalloc(dev->dev, size + phy_size, GFP_KERNEL); + if (!phy) + return NULL; + + phy->dev = dev; + phy->hw = hw; + phy->priv = (void *)phy + phy_size; + phy->band_idx = band_idx; + + return phy; +} +EXPORT_SYMBOL_GPL(mt76_alloc_radio_phy); + struct mt76_phy * mt76_alloc_phy(struct mt76_dev *dev, unsigned int size, const struct ieee80211_ops *ops, u8 band_idx) @@ -552,9 +579,11 @@ int mt76_register_phy(struct mt76_phy *phy, bool vht, mt76_check_sband(phy, &phy->sband_5g, NL80211_BAND_5GHZ); mt76_check_sband(phy, &phy->sband_6g, NL80211_BAND_6GHZ); - ret = ieee80211_register_hw(phy->hw); - if (ret) - return ret; + if ((void *)phy == phy->hw->priv) { + ret = ieee80211_register_hw(phy->hw); + if (ret) + return ret; + } set_bit(MT76_STATE_REGISTERED, &phy->state); phy->dev->phys[phy->band_idx] = phy; diff --git a/drivers/net/wireless/mediatek/mt76/mt76.h b/drivers/net/wireless/mediatek/mt76/mt76.h index b649039f384b..aac8ca7265c2 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76.h +++ b/drivers/net/wireless/mediatek/mt76/mt76.h @@ -1177,6 +1177,8 @@ void mt76_unregister_device(struct mt76_dev *dev); void mt76_free_device(struct mt76_dev *dev); void mt76_unregister_phy(struct mt76_phy *phy); +struct mt76_phy *mt76_alloc_radio_phy(struct mt76_dev *dev, unsigned int size, + u8 band_idx); struct mt76_phy *mt76_alloc_phy(struct mt76_dev *dev, unsigned int size, const struct ieee80211_ops *ops, u8 band_idx); -- 2.47.1