]>
Commit | Line | Data |
---|---|---|
7442bdc9 GKH |
1 | From johannes@sipsolutions.net Tue Dec 6 13:55:26 2011 |
2 | From: Nikolay Martynov <mar.kolya@gmail.com> | |
3 | Date: Tue, 06 Dec 2011 15:39:32 +0100 | |
4 | Subject: mac80211: fix race condition caused by late addBA response | |
5 | To: Nikolay Martynov <mar.kolya@gmail.com>, John Linville <linville@tuxdriver.com>, Greg Kroah-Hartman <gregkh@suse.de> | |
6 | Cc: stable@vger.kernel.org | |
7 | Message-ID: <1323182372.4696.22.camel@jlt3.sipsolutions.net> | |
8 | ||
9 | ||
10 | From: Nikolay Martynov <mar.kolya@gmail.com> | |
11 | ||
12 | Upstream commit d305a6557b2c4dca0110f05ffe745b1ef94adb80. | |
13 | ||
14 | If addBA responses comes in just after addba_resp_timer has | |
15 | expired mac80211 will still accept it and try to open the | |
16 | aggregation session. This causes drivers to be confused and | |
17 | in some cases even crash. | |
18 | ||
19 | This patch fixes the race condition and makes sure that if | |
20 | addba_resp_timer has expired addBA response is not longer | |
21 | accepted and we do not try to open half-closed session. | |
22 | ||
23 | Signed-off-by: Nikolay Martynov <mar.kolya@gmail.com> | |
24 | [some adjustments] | |
25 | Signed-off-by: Johannes Berg <johannes.berg@intel.com> | |
26 | Signed-off-by: John W. Linville <linville@tuxdriver.com> | |
27 | --- | |
28 | net/mac80211/agg-tx.c | 17 ++++++++++++++++- | |
29 | 1 file changed, 16 insertions(+), 1 deletion(-) | |
30 | ||
31 | --- a/net/mac80211/agg-tx.c | |
32 | +++ b/net/mac80211/agg-tx.c | |
33 | @@ -792,12 +792,27 @@ void ieee80211_process_addba_resp(struct | |
34 | goto out; | |
35 | } | |
36 | ||
37 | - del_timer(&tid_tx->addba_resp_timer); | |
38 | + del_timer_sync(&tid_tx->addba_resp_timer); | |
39 | ||
40 | #ifdef CONFIG_MAC80211_HT_DEBUG | |
41 | printk(KERN_DEBUG "switched off addBA timer for tid %d\n", tid); | |
42 | #endif | |
43 | ||
44 | + /* | |
45 | + * addba_resp_timer may have fired before we got here, and | |
46 | + * caused WANT_STOP to be set. If the stop then was already | |
47 | + * processed further, STOPPING might be set. | |
48 | + */ | |
49 | + if (test_bit(HT_AGG_STATE_WANT_STOP, &tid_tx->state) || | |
50 | + test_bit(HT_AGG_STATE_STOPPING, &tid_tx->state)) { | |
51 | +#ifdef CONFIG_MAC80211_HT_DEBUG | |
52 | + printk(KERN_DEBUG | |
53 | + "got addBA resp for tid %d but we already gave up\n", | |
54 | + tid); | |
55 | +#endif | |
56 | + goto out; | |
57 | + } | |
58 | + | |
59 | if (le16_to_cpu(mgmt->u.action.u.addba_resp.status) | |
60 | == WLAN_STATUS_SUCCESS) { | |
61 | /* |