mac80211: implement sta_add/sta_remove in sta_state
authorJohannes Berg <johannes.berg@intel.com>
Fri, 20 Jan 2012 12:55:22 +0000 (13:55 +0100)
committerJohn W. Linville <linville@tuxdriver.com>
Mon, 6 Feb 2012 19:48:25 +0000 (14:48 -0500)
Instead of maintaining separate sta_add/sta_remove
callsites, implement it in sta_state when the driver
has no sta_state implementation.

The only behavioural change this should cause is in
secure mesh mode: with this the station entries will
only be created after the stations are set to AUTH.
Given which drivers support mesh, this seems to not
be a problem.

Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
net/mac80211/driver-ops.h
net/mac80211/pm.c
net/mac80211/sta_info.c
net/mac80211/util.c

index 4bd266ec5333ff46c95f2e7b3e596da981cec3fd..70dfb6415c20cef5a138fb4bc453292a9d783535 100644 (file)
@@ -493,9 +493,18 @@ int drv_sta_state(struct ieee80211_local *local,
        check_sdata_in_driver(sdata);
 
        trace_drv_sta_state(local, sdata, &sta->sta, old_state, new_state);
-       if (local->ops->sta_state)
+       if (local->ops->sta_state) {
                ret = local->ops->sta_state(&local->hw, &sdata->vif, &sta->sta,
                                            old_state, new_state);
+       } else if (old_state == IEEE80211_STA_AUTH &&
+                  new_state == IEEE80211_STA_ASSOC) {
+               ret = drv_sta_add(local, sdata, &sta->sta);
+               if (ret == 0)
+                       sta->uploaded = true;
+       } else if (old_state == IEEE80211_STA_ASSOC &&
+                  new_state == IEEE80211_STA_AUTH) {
+               drv_sta_remove(local, sdata, &sta->sta);
+       }
        trace_drv_return_int(local, ret);
        return ret;
 }
index af49ac4f08261ec8f199591bbd1155f8c5f97a1d..2b53a5348aceca296705217fa76301dfcdbc424d 100644 (file)
@@ -100,8 +100,6 @@ int __ieee80211_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wowlan)
                if (sta->uploaded) {
                        enum ieee80211_sta_state state;
 
-                       drv_sta_remove(local, sta->sdata, &sta->sta);
-
                        state = sta->sta_state;
                        for (; state > IEEE80211_STA_NOTEXIST; state--)
                                WARN_ON(drv_sta_state(local, sdata, sta,
index fcd9027c669961aa873cc82e6ba3ecbd138582d6..5e577bd0e6aa4d4f53f0d1bc632d3fa4c652652a 100644 (file)
@@ -365,7 +365,12 @@ static int sta_info_insert_drv_state(struct ieee80211_local *local,
        }
 
        if (!err) {
-               sta->uploaded = true;
+               /*
+                * Drivers using legacy sta_add/sta_remove callbacks only
+                * get uploaded set to true after sta_add is called.
+                */
+               if (!local->ops->sta_add)
+                       sta->uploaded = true;
                return 0;
        }
 
@@ -417,18 +422,9 @@ static int sta_info_insert_finish(struct sta_info *sta) __acquires(RCU)
 
        if (!sta->dummy || dummy_reinsert) {
                /* notify driver */
-               err = drv_sta_add(local, sdata, &sta->sta);
-               if (err) {
-                       if (sdata->vif.type != NL80211_IFTYPE_ADHOC)
-                               goto out_err;
-                       printk(KERN_DEBUG "%s: failed to add IBSS STA %pM to "
-                                         "driver (%d) - keeping it anyway.\n",
-                              sdata->name, sta->sta.addr, err);
-               } else {
-                       err = sta_info_insert_drv_state(local, sdata, sta);
-                       if (err)
-                               goto out_err;
-               }
+               err = sta_info_insert_drv_state(local, sdata, sta);
+               if (err)
+                       goto out_err;
        }
 
        if (!dummy_reinsert) {
@@ -802,7 +798,6 @@ int __must_check __sta_info_destroy(struct sta_info *sta)
        }
 
        if (sta->uploaded) {
-               drv_sta_remove(local, sdata, &sta->sta);
                ret = drv_sta_state(local, sdata, sta, IEEE80211_STA_NONE,
                                    IEEE80211_STA_NOTEXIST);
                WARN_ON_ONCE(ret != 0);
index 8f8b4ecc776fd7b08e3989d33d550b7ad94b38d1..264397aee8114eb6c26f477f877be6e16f4e4c80 100644 (file)
@@ -1187,8 +1187,6 @@ int ieee80211_reconfig(struct ieee80211_local *local)
                if (sta->uploaded) {
                        enum ieee80211_sta_state state;
 
-                       WARN_ON(drv_sta_add(local, sta->sdata, &sta->sta));
-
                        for (state = IEEE80211_STA_NOTEXIST;
                             state < sta->sta_state - 1; state++)
                                WARN_ON(drv_sta_state(local, sta->sdata, sta,