From c7dd40c92af1f28b84995a07aa88ccd3068ee4de Mon Sep 17 00:00:00 2001 From: Sujith Manoharan Date: Fri, 22 Aug 2014 20:39:30 +0530 Subject: ath9k: Isolate P2P powersave routines Use CONFIG_ATH9K_CHANNEL_CONTEXT to conditionally compile P2P-PS code. Signed-off-by: Sujith Manoharan Signed-off-by: John W. Linville --- drivers/net/wireless/ath/ath9k/channel.c | 78 ++++++++++++++++++++++++++++---- 1 file changed, 68 insertions(+), 10 deletions(-) (limited to 'drivers/net/wireless/ath/ath9k/channel.c') diff --git a/drivers/net/wireless/ath/ath9k/channel.c b/drivers/net/wireless/ath/ath9k/channel.c index 77bf0055e953..c54a3dfb42b6 100644 --- a/drivers/net/wireless/ath/ath9k/channel.c +++ b/drivers/net/wireless/ath/ath9k/channel.c @@ -514,7 +514,9 @@ static void ath_chanctx_setup_timer(struct ath_softc *sc, u32 tsf_time) { struct ath_hw *ah = sc->sc_ah; +#ifdef CONFIG_ATH9K_CHANNEL_CONTEXT ath9k_hw_gen_timer_start(ah, sc->p2p_ps_timer, tsf_time, 1000000); +#endif tsf_time -= ath9k_hw_gettsf32(ah); tsf_time = msecs_to_jiffies(tsf_time / 1000) + 1; mod_timer(&sc->sched.timer, tsf_time); @@ -945,7 +947,13 @@ void ath_offchannel_timer(unsigned long data) } } -void ath9k_update_p2p_ps_timer(struct ath_softc *sc, struct ath_vif *avp) +#ifdef CONFIG_ATH9K_CHANNEL_CONTEXT + +/*****************/ +/* P2P Powersave */ +/*****************/ + +static void ath9k_update_p2p_ps_timer(struct ath_softc *sc, struct ath_vif *avp) { struct ath_hw *ah = sc->sc_ah; s32 tsf, target_tsf; @@ -967,6 +975,23 @@ void ath9k_update_p2p_ps_timer(struct ath_softc *sc, struct ath_vif *avp) ath9k_hw_gen_timer_start(ah, sc->p2p_ps_timer, (u32) target_tsf, 1000000); } +static void ath9k_update_p2p_ps(struct ath_softc *sc, struct ieee80211_vif *vif) +{ + struct ath_vif *avp = (void *)vif->drv_priv; + u32 tsf; + + if (!sc->p2p_ps_timer) + return; + + if (vif->type != NL80211_IFTYPE_STATION || !vif->p2p) + return; + + sc->p2p_ps_vif = avp; + tsf = ath9k_hw_gettsf32(sc->sc_ah); + ieee80211_parse_p2p_noa(&vif->bss_conf.p2p_noa_attr, &avp->noa, tsf); + ath9k_update_p2p_ps_timer(sc, avp); +} + void ath9k_p2p_ps_timer(void *priv) { struct ath_softc *sc = priv; @@ -1014,19 +1039,52 @@ out: rcu_read_unlock(); } -void ath9k_update_p2p_ps(struct ath_softc *sc, struct ieee80211_vif *vif) +void ath9k_p2p_bss_info_changed(struct ath_softc *sc, + struct ieee80211_vif *vif) +{ + unsigned long flags; + + spin_lock_bh(&sc->sc_pcu_lock); + spin_lock_irqsave(&sc->sc_pm_lock, flags); + if (!(sc->ps_flags & PS_BEACON_SYNC)) + ath9k_update_p2p_ps(sc, vif); + spin_unlock_irqrestore(&sc->sc_pm_lock, flags); + spin_unlock_bh(&sc->sc_pcu_lock); +} + +void ath9k_p2p_beacon_sync(struct ath_softc *sc) +{ + if (sc->p2p_ps_vif) + ath9k_update_p2p_ps(sc, sc->p2p_ps_vif->vif); +} + +void ath9k_p2p_remove_vif(struct ath_softc *sc, + struct ieee80211_vif *vif) { struct ath_vif *avp = (void *)vif->drv_priv; - u32 tsf; + spin_lock_bh(&sc->sc_pcu_lock); + if (avp == sc->p2p_ps_vif) { + sc->p2p_ps_vif = NULL; + ath9k_update_p2p_ps_timer(sc, NULL); + } + spin_unlock_bh(&sc->sc_pcu_lock); +} + +int ath9k_init_p2p(struct ath_softc *sc) +{ + sc->p2p_ps_timer = ath_gen_timer_alloc(sc->sc_ah, ath9k_p2p_ps_timer, + NULL, sc, AR_FIRST_NDP_TIMER); if (!sc->p2p_ps_timer) - return; + return -ENOMEM; - if (vif->type != NL80211_IFTYPE_STATION || !vif->p2p) - return; + return 0; +} - sc->p2p_ps_vif = avp; - tsf = ath9k_hw_gettsf32(sc->sc_ah); - ieee80211_parse_p2p_noa(&vif->bss_conf.p2p_noa_attr, &avp->noa, tsf); - ath9k_update_p2p_ps_timer(sc, avp); +void ath9k_deinit_p2p(struct ath_softc *sc) +{ + if (sc->p2p_ps_timer) + ath_gen_timer_free(sc->sc_ah, sc->p2p_ps_timer); } + +#endif /* CONFIG_ATH9K_CHANNEL_CONTEXT */ -- cgit v1.2.3