mac80211: optimise mixed AP/VLAN station removal
Teach sta_info_flush() to optionally also remove stations from all VLANs associated with an AP interface to optimise the station removal (in particular, synchronize_net().) To not have to add the vlans argument throughout, do some refactoring. Signed-off-by: Johannes Berg <johannes.berg@intel.com>
This commit is contained in:
parent
d778207b06
commit
e716251d77
3 changed files with 14 additions and 6 deletions
|
@ -1097,9 +1097,7 @@ static int ieee80211_stop_ap(struct wiphy *wiphy, struct net_device *dev)
|
|||
if (old_probe_resp)
|
||||
kfree_rcu(old_probe_resp, rcu_head);
|
||||
|
||||
list_for_each_entry(vlan, &sdata->u.ap.vlans, u.vlan.list)
|
||||
sta_info_flush(vlan);
|
||||
sta_info_flush(sdata);
|
||||
__sta_info_flush(sdata, true);
|
||||
synchronize_net();
|
||||
list_for_each_entry(vlan, &sdata->u.ap.vlans, u.vlan.list)
|
||||
ieee80211_free_keys(vlan);
|
||||
|
|
|
@ -960,7 +960,7 @@ void sta_info_stop(struct ieee80211_local *local)
|
|||
}
|
||||
|
||||
|
||||
int sta_info_flush(struct ieee80211_sub_if_data *sdata)
|
||||
int __sta_info_flush(struct ieee80211_sub_if_data *sdata, bool vlans)
|
||||
{
|
||||
struct ieee80211_local *local = sdata->local;
|
||||
struct sta_info *sta, *tmp;
|
||||
|
@ -969,9 +969,13 @@ int sta_info_flush(struct ieee80211_sub_if_data *sdata)
|
|||
|
||||
might_sleep();
|
||||
|
||||
WARN_ON(vlans && sdata->vif.type != NL80211_IFTYPE_AP);
|
||||
WARN_ON(vlans && !sdata->bss);
|
||||
|
||||
mutex_lock(&local->sta_mtx);
|
||||
list_for_each_entry_safe(sta, tmp, &local->sta_list, list) {
|
||||
if (sdata == sta->sdata) {
|
||||
if (sdata == sta->sdata ||
|
||||
(vlans && sdata->bss == sta->sdata->bss)) {
|
||||
if (!WARN_ON(__sta_info_destroy_part1(sta)))
|
||||
list_add(&sta->free_list, &free_list);
|
||||
ret++;
|
||||
|
|
|
@ -613,8 +613,14 @@ void sta_info_stop(struct ieee80211_local *local);
|
|||
* Returns the number of removed STA entries.
|
||||
*
|
||||
* @sdata: sdata to remove all stations from
|
||||
* @vlans: if the given interface is an AP interface, also flush VLANs
|
||||
*/
|
||||
int sta_info_flush(struct ieee80211_sub_if_data *sdata);
|
||||
int __sta_info_flush(struct ieee80211_sub_if_data *sdata, bool vlans);
|
||||
|
||||
static inline int sta_info_flush(struct ieee80211_sub_if_data *sdata)
|
||||
{
|
||||
return __sta_info_flush(sdata, false);
|
||||
}
|
||||
|
||||
void sta_set_rate_info_tx(struct sta_info *sta,
|
||||
const struct ieee80211_tx_rate *rate,
|
||||
|
|
Loading…
Reference in a new issue