]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
ath9k: Fix STA disconnect issue due to received MIC failed bcast frames
authorSenthil Balasubramanian <senthilkumar@atheros.com>
Tue, 30 Nov 2010 14:45:39 +0000 (20:15 +0530)
committerGreg Kroah-Hartman <gregkh@suse.de>
Fri, 7 Jan 2011 21:58:21 +0000 (13:58 -0800)
commit 916448e77f6bcaaa7f13c3de0c3851783ae2bfd0 upstream.

AR_RxKeyIdxValid will not be set for bcast/mcast frames and so relying
this status for MIC failed frames is buggy.

Due to this, MIC failure events for broadcast frames are not sent to
supplicant resulted in AP disconnecting the STA.

Able to pass Wifi Test case 5.2.18 with this fix.

Signed-off-by: Senthil Balasubramanian <senthilkumar@atheros.com>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
drivers/net/wireless/ath/ath9k/mac.c
drivers/net/wireless/ath/ath9k/recv.c

index 3efda8a8a3c1e66e1b0ed71a7a5bbad2a936bb28..79302b1e09105cee17ce48582c1e4cddf33379b1 100644 (file)
@@ -711,8 +711,7 @@ int ath9k_hw_rxprocdesc(struct ath_hw *ah, struct ath_desc *ds,
                        rs->rs_phyerr = phyerr;
                } else if (ads.ds_rxstatus8 & AR_DecryptCRCErr)
                        rs->rs_status |= ATH9K_RXERR_DECRYPT;
-               else if ((ads.ds_rxstatus8 & AR_MichaelErr) &&
-                        rs->rs_keyix != ATH9K_RXKEYIX_INVALID)
+               else if (ads.ds_rxstatus8 & AR_MichaelErr)
                        rs->rs_status |= ATH9K_RXERR_MIC;
                else if (ads.ds_rxstatus8 & AR_KeyMiss)
                        rs->rs_status |= ATH9K_RXERR_DECRYPT;
index 41ebd623a7a9b57e9816f88e2eb87fddbdad11c3..685258bf543c641add68b6d7b836433fbeff44fc 100644 (file)
@@ -1035,9 +1035,11 @@ static void ath9k_rx_skb_postprocess(struct ath_common *common,
        int hdrlen, padpos, padsize;
        u8 keyix;
        __le16 fc;
+       bool is_mc;
 
        /* see if any padding is done by the hw and remove it */
        hdr = (struct ieee80211_hdr *) skb->data;
+       is_mc = !!is_multicast_ether_addr(hdr->addr1);
        hdrlen = ieee80211_get_hdrlen_from_skb(skb);
        fc = hdr->frame_control;
        padpos = ath9k_cmn_padpos(hdr->frame_control);
@@ -1058,7 +1060,7 @@ static void ath9k_rx_skb_postprocess(struct ath_common *common,
 
        keyix = rx_stats->rs_keyix;
 
-       if (!(keyix == ATH9K_RXKEYIX_INVALID) && !decrypt_error &&
+       if ((is_mc || !(keyix == ATH9K_RXKEYIX_INVALID)) && !decrypt_error &&
            ieee80211_has_protected(fc)) {
                rxs->flag |= RX_FLAG_DECRYPTED;
        } else if (ieee80211_has_protected(fc)