X-Git-Url: http://git.openwrt.org/?a=blobdiff_plain;f=package%2Fkernel%2Fmac80211%2Fpatches%2F300-pending_work.patch;h=0a2e86b1d7bc2f539b84d4b4a23ec5a1eb413ec9;hb=ca49c000b6f0dc520921f102f05f4b281664b897;hp=deae67a4204c9140cd9648bfba66aadcbefb705e;hpb=b8795d6b664578b9a5a4cdf6165ec1e394a7a1a4;p=openwrt%2Fopenwrt.git diff --git a/package/kernel/mac80211/patches/300-pending_work.patch b/package/kernel/mac80211/patches/300-pending_work.patch index deae67a420..0a2e86b1d7 100644 --- a/package/kernel/mac80211/patches/300-pending_work.patch +++ b/package/kernel/mac80211/patches/300-pending_work.patch @@ -1,28 +1,163 @@ -commit 93f310a38a1d81a4bc8fcd9bf29628bd721cf2ef +commit 6df35206bc6c1c6aad1d8077df5786b4a7f77873 Author: Felix Fietkau -Date: Sun Apr 6 23:35:28 2014 +0200 +Date: Fri May 23 19:58:14 2014 +0200 - ath9k_hw: reduce ANI firstep range for older chips + mac80211: reduce packet loss notifications under load - Use 0-8 instead of 0-16, which is closer to the old implementation. - Also drop the overwrite of the firstep_low parameter to improve - stability. + During strong signal fluctuations under high throughput, few consecutive + failed A-MPDU transmissions can easily trigger packet loss notification, + and thus (in AP mode) client disconnection. + Reduce the number of false positives by checking the A-MPDU status flag + and treating a failed A-MPDU as a single packet. + + Signed-off-by: Felix Fietkau + +commit 7b7843a36fbcc568834404c7430ff895d8502131 +Author: Felix Fietkau +Date: Fri May 23 19:26:32 2014 +0200 + + mac80211: fix a memory leak on sta rate selection table + + Cc: stable@vger.kernel.org + Reported-by: Christophe Prévotaux Signed-off-by: Felix Fietkau +commit 96892d6aa0a153423070addf3070bc79578b3897 +Author: Felix Fietkau +Date: Mon May 19 21:20:49 2014 +0200 + + ath9k: avoid passing buffers to the hardware during flush + + The commit "ath9k: fix possible hang on flush" changed the receive code + to always link rx descriptors of processed frames, even when flushing. + In some cases, this leads to flushed rx buffers being passed to the + hardware while rx is already stopped. + + Signed-off-by: Felix Fietkau ---- a/drivers/net/wireless/ath/ath9k/ar5008_phy.c -+++ b/drivers/net/wireless/ath/ath9k/ar5008_phy.c -@@ -1004,11 +1004,9 @@ static bool ar5008_hw_ani_control_new(st - case ATH9K_ANI_FIRSTEP_LEVEL:{ - u32 level = param; - -- value = level * 2; -+ value = level; - REG_RMW_FIELD(ah, AR_PHY_FIND_SIG, - AR_PHY_FIND_SIG_FIRSTEP, value); -- REG_RMW_FIELD(ah, AR_PHY_FIND_SIG_LOW, -- AR_PHY_FIND_SIG_FIRSTEP_LOW, value); - - if (level != aniState->firstepLevel) { - ath_dbg(common, ANI, +--- a/drivers/net/wireless/ath/ath9k/recv.c ++++ b/drivers/net/wireless/ath/ath9k/recv.c +@@ -34,7 +34,8 @@ static inline bool ath9k_check_auto_slee + * buffer (or rx fifo). This can incorrectly acknowledge packets + * to a sender if last desc is self-linked. + */ +-static void ath_rx_buf_link(struct ath_softc *sc, struct ath_rxbuf *bf) ++static void ath_rx_buf_link(struct ath_softc *sc, struct ath_rxbuf *bf, ++ bool flush) + { + struct ath_hw *ah = sc->sc_ah; + struct ath_common *common = ath9k_hw_common(ah); +@@ -59,18 +60,19 @@ static void ath_rx_buf_link(struct ath_s + common->rx_bufsize, + 0); + +- if (sc->rx.rxlink == NULL) +- ath9k_hw_putrxbuf(ah, bf->bf_daddr); +- else ++ if (sc->rx.rxlink) + *sc->rx.rxlink = bf->bf_daddr; ++ else if (!flush) ++ ath9k_hw_putrxbuf(ah, bf->bf_daddr); + + sc->rx.rxlink = &ds->ds_link; + } + +-static void ath_rx_buf_relink(struct ath_softc *sc, struct ath_rxbuf *bf) ++static void ath_rx_buf_relink(struct ath_softc *sc, struct ath_rxbuf *bf, ++ bool flush) + { + if (sc->rx.buf_hold) +- ath_rx_buf_link(sc, sc->rx.buf_hold); ++ ath_rx_buf_link(sc, sc->rx.buf_hold, flush); + + sc->rx.buf_hold = bf; + } +@@ -442,7 +444,7 @@ int ath_startrecv(struct ath_softc *sc) + sc->rx.buf_hold = NULL; + sc->rx.rxlink = NULL; + list_for_each_entry_safe(bf, tbf, &sc->rx.rxbuf, list) { +- ath_rx_buf_link(sc, bf); ++ ath_rx_buf_link(sc, bf, false); + } + + /* We could have deleted elements so the list may be empty now */ +@@ -1118,12 +1120,12 @@ requeue_drop_frag: + requeue: + list_add_tail(&bf->list, &sc->rx.rxbuf); + +- if (edma) { +- ath_rx_edma_buf_link(sc, qtype); +- } else { +- ath_rx_buf_relink(sc, bf); ++ if (!edma) { ++ ath_rx_buf_relink(sc, bf, flush); + if (!flush) + ath9k_hw_rxena(ah); ++ } else if (!flush) { ++ ath_rx_edma_buf_link(sc, qtype); + } + + if (!budget--) +--- a/net/mac80211/sta_info.c ++++ b/net/mac80211/sta_info.c +@@ -227,6 +227,7 @@ struct sta_info *sta_info_get_by_idx(str + */ + void sta_info_free(struct ieee80211_local *local, struct sta_info *sta) + { ++ struct ieee80211_sta_rates *rates; + int i; + + if (sta->rate_ctrl) +@@ -238,6 +239,10 @@ void sta_info_free(struct ieee80211_loca + kfree(sta->tx_lat); + } + ++ rates = rcu_dereference_protected(sta->sta.rates, true); ++ if (rates) ++ kfree(rates); ++ + sta_dbg(sta->sdata, "Destroyed STA %pM\n", sta->sta.addr); + + kfree(sta); +--- a/net/mac80211/status.c ++++ b/net/mac80211/status.c +@@ -541,6 +541,23 @@ static void ieee80211_tx_latency_end_msr + */ + #define STA_LOST_PKT_THRESHOLD 50 + ++static void ieee80211_lost_packet(struct sta_info *sta, struct sk_buff *skb) ++{ ++ struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); ++ ++ /* This packet was aggregated but doesn't carry status info */ ++ if ((info->flags & IEEE80211_TX_CTL_AMPDU) && ++ !(info->flags & IEEE80211_TX_STAT_AMPDU)) ++ return; ++ ++ if (++sta->lost_packets < STA_LOST_PKT_THRESHOLD) ++ return; ++ ++ cfg80211_cqm_pktloss_notify(sta->sdata->dev, sta->sta.addr, ++ sta->lost_packets, GFP_ATOMIC); ++ sta->lost_packets = 0; ++} ++ + void ieee80211_tx_status(struct ieee80211_hw *hw, struct sk_buff *skb) + { + struct sk_buff *skb2; +@@ -680,12 +697,8 @@ void ieee80211_tx_status(struct ieee8021 + if (info->flags & IEEE80211_TX_STAT_ACK) { + if (sta->lost_packets) + sta->lost_packets = 0; +- } else if (++sta->lost_packets >= STA_LOST_PKT_THRESHOLD) { +- cfg80211_cqm_pktloss_notify(sta->sdata->dev, +- sta->sta.addr, +- sta->lost_packets, +- GFP_ATOMIC); +- sta->lost_packets = 0; ++ } else { ++ ieee80211_lost_packet(sta, skb); + } + } +