Patch "cfg80211: fix connect/disconnect edge cases" has been added to the 4.13-stable tree
Subsystems (2)
This is a note to let you know that I've just added the patch titled
cfg80211: fix connect/disconnect edge cases
to the 4.13-stable tree which can be found at:
http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary
The filename of the patch is:
cfg80211-fix-connect-disconnect-edge-cases.patch
and it can be found in the queue-4.13 subdirectory.
If you, or anyone else, feels it should not be added to the stable tree, please let <[email protected]> know about it.
Quoted 1 line
From
51e13359cd5ea34acc62c90627603352956380afMon Sep 17 00:00:00 2001
From: Johannes Berg <[email protected]>
Date: Tue, 17 Oct 2017 21:56:20 +0200
Subject: cfg80211: fix connect/disconnect edge cases
From: Johannes Berg <[email protected]>
commit 51e13359cd5ea34acc62c90627603352956380af upstream.
If we try to connect while already connected/connecting, but this fails, we set ssid_len=0 but leave current_bss hanging, leading to errors.
Check all of this better, first of all ensuring that we can't try to connect to a different SSID while connected/ing; ensure that prev_bssid is set for re-association attempts even in the case of the driver supporting the connect() method, and don't reset ssid_len in the failure cases.
While at it, also reset ssid_len while disconnecting unless we were connected and expect a disconnected event, and warn on a successful connection without ssid_len being set.
--- net/wireless/sme.c | 50 +++++++++++++++++++++++++++++++++++++++++--------- 1 file changed, 41 insertions(+), 9 deletions(-)
net/wireless/sme.c +41 -9
@@ -522,11 +522,6 @@ static int cfg80211_sme_connect(struct wreturn -EOPNOTSUPP ;if (wdev->current_bss) { -if (!prev_bssid) -return -EALREADY ; -if (prev_bssid && - !ether_addr_equal (prev_bssid, wdev->current_bss->pub.bssid)) -return -ENOTCONN ;cfg80211_unhold_bss (wdev->current_bss);cfg80211_put_bss (wdev->wiphy, &wdev->current_bss->pub); wdev->current_bss =NULL ;
@@ -1063,11 +1058,35 @@ int cfg80211_connect(struct cfg80211_regASSERT_WDEV_LOCK (wdev); -if (WARN_ON (wdev->connect_keys)) { -kzfree (wdev->connect_keys); - wdev->connect_keys =NULL ; +/* +* If we have an ssid_len, we're trying to connect or are +* already connected, so reject a new SSID unless it's the +* same (which is the case for re-association.) +*/ +if (wdev->ssid_len && + (wdev->ssid_len != connect->ssid_len || +memcmp (wdev->ssid, connect->ssid, wdev->ssid_len))) +return -EALREADY ; + +/* +* If connected, reject (re-)association unless prev_bssid +* matches the current BSSID. +*/ +if (wdev->current_bss) { +if (!prev_bssid) +return -EALREADY ; +if (!ether_addr_equal (prev_bssid, wdev->current_bss->pub.bssid)) +return -ENOTCONN ; } +/* +* Reject if we're in the process of connecting with WEP, +* this case isn't very interesting and trying to handle +* it would make the code much more complex. +*/ +if (wdev->connect_keys) +return -EINPROGRESS ; +cfg80211_oper_and_ht_capa (&connect->ht_capa_mask, rdev->wiphy.ht_capa_mod_mask);
@@ -1118,7 +1137,12 @@ int cfg80211_connect(struct cfg80211_regif (err) { wdev->connect_keys =NULL ; - wdev->ssid_len =0 ; +/* +* This could be reassoc getting refused, don't clear +* ssid_len in that case. +*/ +if (!wdev->current_bss) + wdev->ssid_len =0 ;return err; }
@@ -1145,6 +1169,14 @@ int cfg80211_disconnect(struct cfg80211_else if (wdev->ssid_len) err =rdev_disconnect (rdev, dev, reason); +/* +* Clear ssid_len unless we actually were fully connected, +* in which case cfg80211_disconnected() will take care of +* this later. +*/ +if (!wdev->current_bss) + wdev->ssid_len =0 ; +return err; }
Patches currently in stable-queue which might be from [email protected] are
queue-4.13/cfg80211-fix-connect-disconnect-edge-cases.patch