Message ID | 20211006040938.9531-4-alokad@codeaurora.org (mailing list archive) |
---|---|
State | Changes Requested |
Delegated to: | Johannes Berg |
Headers | show |
Series | MBSSID and EMA support in AP mode | expand |
On Tue, 2021-10-05 at 21:09 -0700, Aloka Dixit wrote: > From: John Crispin <john@phrozen.org> > > Trigger ieee80211_csa_finish() on the non-transmitting interfaces > when channel switch concludes on the transmitting interface. > > Signed-off-by: John Crispin <john@phrozen.org> > Co-developed-by: Aloka Dixit <alokad@codeaurora.org> > Signed-off-by: Aloka Dixit <alokad@codeaurora.org> > --- > v13: Replaced list_for_each_entry_safe() by list_for_each_entry() > Uh, ouch. I guess I miscommunicated that. What I really meant was that the list iteration here: > + if (vif->mbssid_tx_vif == vif) { > + struct ieee80211_sub_if_data *child; > + > + list_for_each_entry(child, &sdata->local->interfaces, > list) does not seem correct, since it's not locked, and you don't have any guarantees that it's not being modified since the only thing here is that the vif pointer is coming in valid from the driver? johannes
diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c index cfe99de457cb..8a107439451c 100644 --- a/net/mac80211/cfg.c +++ b/net/mac80211/cfg.c @@ -3271,8 +3271,18 @@ void ieee80211_csa_finish(struct ieee80211_vif *vif) { struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif); - ieee80211_queue_work(&sdata->local->hw, - &sdata->csa_finalize_work); + if (vif->mbssid_tx_vif == vif) { + struct ieee80211_sub_if_data *child; + + list_for_each_entry(child, &sdata->local->interfaces, list) + if (child != sdata && child->vif.mbssid_tx_vif == vif && + ieee80211_sdata_running(child)) { + ieee80211_queue_work(&child->local->hw, + &child->csa_finalize_work); + } + } + + ieee80211_queue_work(&sdata->local->hw, &sdata->csa_finalize_work); } EXPORT_SYMBOL(ieee80211_csa_finish);