| From 66024478ac9ed5a373ab6abfa055a46b156906ff Mon Sep 17 00:00:00 2001 |
| From: Senthil Balasubramanian <senthilkumar@atheros.com> |
| Date: Thu, 11 Mar 2010 12:10:12 -0800 |
| Subject: ath9k: Enable TIM timer interrupt only when needed. |
| |
| From: Senthil Balasubramanian <senthilkumar@atheros.com> |
| |
| commit 3f7c5c10e9dc6bf90179eb9f7c06151d508fb324 upstream. |
| |
| The TIM timer interrupt is enabled even before the ACK of nullqos |
| is received which is unnecessary. |
| |
| Also clean up the CONF_PS part of config callback properly for |
| better readability. |
| |
| Signed-off-by: Senthil Balasubramanian <senthilkumar@atheros.com> |
| Signed-off-by: John W. Linville <linville@tuxdriver.com> |
| Signed-off-by: Luis R. Rodriguez <lrodriguez@atheros.com> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de> |
| |
| --- |
| drivers/net/wireless/ath/ath9k/ath9k.h | 1 + |
| drivers/net/wireless/ath/ath9k/main.c | 24 ++++++++++++++---------- |
| drivers/net/wireless/ath/ath9k/xmit.c | 7 +++---- |
| 3 files changed, 18 insertions(+), 14 deletions(-) |
| |
| --- a/drivers/net/wireless/ath/ath9k/ath9k.h |
| +++ b/drivers/net/wireless/ath/ath9k/ath9k.h |
| @@ -267,6 +267,7 @@ void ath_tx_aggr_start(struct ath_softc |
| u16 tid, u16 *ssn); |
| void ath_tx_aggr_stop(struct ath_softc *sc, struct ieee80211_sta *sta, u16 tid); |
| void ath_tx_aggr_resume(struct ath_softc *sc, struct ieee80211_sta *sta, u16 tid); |
| +void ath9k_enable_ps(struct ath_softc *sc); |
| |
| /********/ |
| /* VIFs */ |
| --- a/drivers/net/wireless/ath/ath9k/main.c |
| +++ b/drivers/net/wireless/ath/ath9k/main.c |
| @@ -2681,6 +2681,19 @@ static void ath9k_remove_interface(struc |
| mutex_unlock(&sc->mutex); |
| } |
| |
| +void ath9k_enable_ps(struct ath_softc *sc) |
| +{ |
| + sc->ps_enabled = true; |
| + if (!(sc->sc_ah->caps.hw_caps & ATH9K_HW_CAP_AUTOSLEEP)) { |
| + if ((sc->imask & ATH9K_INT_TIM_TIMER) == 0) { |
| + sc->imask |= ATH9K_INT_TIM_TIMER; |
| + ath9k_hw_set_interrupts(sc->sc_ah, |
| + sc->imask); |
| + } |
| + } |
| + ath9k_hw_setrxabort(sc->sc_ah, 1); |
| +} |
| + |
| static int ath9k_config(struct ieee80211_hw *hw, u32 changed) |
| { |
| struct ath_wiphy *aphy = hw->priv; |
| @@ -2734,22 +2747,13 @@ static int ath9k_config(struct ieee80211 |
| if (changed & IEEE80211_CONF_CHANGE_PS) { |
| if (conf->flags & IEEE80211_CONF_PS) { |
| sc->sc_flags |= SC_OP_PS_ENABLED; |
| - if (!(ah->caps.hw_caps & |
| - ATH9K_HW_CAP_AUTOSLEEP)) { |
| - if ((sc->imask & ATH9K_INT_TIM_TIMER) == 0) { |
| - sc->imask |= ATH9K_INT_TIM_TIMER; |
| - ath9k_hw_set_interrupts(sc->sc_ah, |
| - sc->imask); |
| - } |
| - } |
| /* |
| * At this point we know hardware has received an ACK |
| * of a previously sent null data frame. |
| */ |
| if ((sc->sc_flags & SC_OP_NULLFUNC_COMPLETED)) { |
| sc->sc_flags &= ~SC_OP_NULLFUNC_COMPLETED; |
| - sc->ps_enabled = true; |
| - ath9k_hw_setrxabort(sc->sc_ah, 1); |
| + ath9k_enable_ps(sc); |
| } |
| } else { |
| sc->ps_enabled = false; |
| --- a/drivers/net/wireless/ath/ath9k/xmit.c |
| +++ b/drivers/net/wireless/ath/ath9k/xmit.c |
| @@ -2034,10 +2034,9 @@ static void ath_tx_processq(struct ath_s |
| */ |
| if (bf->bf_isnullfunc && |
| (ds->ds_txstat.ts_status & ATH9K_TX_ACKED)) { |
| - if ((sc->sc_flags & SC_OP_PS_ENABLED)) { |
| - sc->ps_enabled = true; |
| - ath9k_hw_setrxabort(sc->sc_ah, 1); |
| - } else |
| + if ((sc->sc_flags & SC_OP_PS_ENABLED)) |
| + ath9k_enable_ps(sc); |
| + else |
| sc->sc_flags |= SC_OP_NULLFUNC_COMPLETED; |
| } |
| |