summaryrefslogtreecommitdiffstats
path: root/net
diff options
context:
space:
mode:
authorChristian Lamparter <chunkeey@googlemail.com>2010-11-29 20:53:23 +0100
committerJohn W. Linville <linville@tuxdriver.com>2010-11-30 13:23:06 -0500
commit2c31333a8fde7e26936a9f5371d02ff12c490993 (patch)
tree75bb0fc716caa240e7afc0245da0b5089bd3e420 /net
parentcf63495d0dbe435b475a44672f5dee150da6471b (diff)
mac80211: ignore non-bcast mcast deauth/disassoc franes
This patch fixes an curious issue due to insufficient rx frame filtering. Saqeb Akhter reported frequent disconnects while streaming videos over samba: <http://marc.info/?m=128600031109136> > [ 1166.512087] wlan1: deauthenticated from 30:46:9a:10:49:f7 (Reason: 7) > [ 1526.059997] wlan1: deauthenticated from 30:46:9a:10:49:f7 (Reason: 7) > [ 2125.324356] wlan1: deauthenticated from 30:46:9a:10:49:f7 (Reason: 7) > [...] The reason is that the device generates frames with slightly bogus SA/TA addresses. e.g.: [ 2314.402316] Ignore 9f:1f:31:f8:64:ff [ 2314.402321] Ignore 9f:1f:31:f8:64:ff [ 2352.453804] Ignore 0d:1f:31:f8:64:ff [ 2352.453808] Ignore 0d:1f:31:f8:64:ff ^^ the group-address flag is set! (the correct SA/TA would be: 00:1f:31:f8:64:ff) Since the AP does not know from where the frames come, it generates a DEAUTH response for the (invalid) mcast address. This mcast deauth frame then passes through all filters and tricks the stack into thinking that the AP brutally kicked us! This patch fixes the problem by simply ignoring non-broadcast, group-addressed deauth/disassoc frames. Cc: Jouni Malinen <j@w1.fi> Cc: Johannes Berg <johannes@sipsolutions.net> Reported-by: Saqeb Akhter <saqeb.akhter@gmail.com> Signed-off-by: Christian Lamparter <chunkeey@googlemail.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'net')
-rw-r--r--net/mac80211/rx.c4
1 files changed, 4 insertions, 0 deletions
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c
index 902b03ee8f6..3c87293cb07 100644
--- a/net/mac80211/rx.c
+++ b/net/mac80211/rx.c
@@ -2247,6 +2247,10 @@ ieee80211_rx_h_mgmt(struct ieee80211_rx_data *rx)
break;
case cpu_to_le16(IEEE80211_STYPE_DEAUTH):
case cpu_to_le16(IEEE80211_STYPE_DISASSOC):
+ if (is_multicast_ether_addr(mgmt->da) &&
+ !is_broadcast_ether_addr(mgmt->da))
+ return RX_DROP_MONITOR;
+
/* process only for station */
if (sdata->vif.type != NL80211_IFTYPE_STATION)
return RX_DROP_MONITOR;