/*
 * Copyright (c) 2014 Qualcomm Atheros, Inc.
 *
 * Permission to use, copy, modify, and/or distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

#include "ath9k.h"

/* Set/change channels.  If the channel is really being changed, it's done
 * by reseting the chip.  To accomplish this we must first cleanup any pending
 * DMA, then restart stuff.
 */
static int ath_set_channel(struct ath_softc *sc)
{
	struct ath_hw *ah = sc->sc_ah;
	struct ath_common *common = ath9k_hw_common(ah);
	struct ieee80211_hw *hw = sc->hw;
	struct ath9k_channel *hchan;
	struct cfg80211_chan_def *chandef = &sc->cur_chan->chandef;
	struct ieee80211_channel *chan = chandef->chan;
	int pos = chan->hw_value;
	int old_pos = -1;
	int r;

	if (test_bit(ATH_OP_INVALID, &common->op_flags))
		return -EIO;

	if (ah->curchan)
		old_pos = ah->curchan - &ah->channels[0];

	ath_dbg(common, CONFIG, "Set channel: %d MHz width: %d\n",
		chan->center_freq, chandef->width);

	/* update survey stats for the old channel before switching */
	spin_lock_bh(&common->cc_lock);
	ath_update_survey_stats(sc);
	spin_unlock_bh(&common->cc_lock);

	ath9k_cmn_get_channel(hw, ah, chandef);

	/* If the operating channel changes, change the survey in-use flags
	 * along with it.
	 * Reset the survey data for the new channel, unless we're switching
	 * back to the operating channel from an off-channel operation.
	 */
	if (!sc->cur_chan->offchannel && sc->cur_survey != &sc->survey[pos]) {
		if (sc->cur_survey)
			sc->cur_survey->filled &= ~SURVEY_INFO_IN_USE;

		sc->cur_survey = &sc->survey[pos];

		memset(sc->cur_survey, 0, sizeof(struct survey_info));
		sc->cur_survey->filled |= SURVEY_INFO_IN_USE;
	} else if (!(sc->survey[pos].filled & SURVEY_INFO_IN_USE)) {
		memset(&sc->survey[pos], 0, sizeof(struct survey_info));
	}

	hchan = &sc->sc_ah->channels[pos];
	r = ath_reset_internal(sc, hchan);
	if (r)
		return r;

	/* The most recent snapshot of channel->noisefloor for the old
	 * channel is only available after the hardware reset. Copy it to
	 * the survey stats now.
	 */
	if (old_pos >= 0)
		ath_update_survey_nf(sc, old_pos);

	/* Enable radar pulse detection if on a DFS channel. Spectral
	 * scanning and radar detection can not be used concurrently.
	 */
	if (hw->conf.radar_enabled) {
		u32 rxfilter;

		rxfilter = ath9k_hw_getrxfilter(ah);
		rxfilter |= ATH9K_RX_FILTER_PHYRADAR |
				ATH9K_RX_FILTER_PHYERR;
		ath9k_hw_setrxfilter(ah, rxfilter);
		ath_dbg(common, DFS, "DFS enabled at freq %d\n",
			chan->center_freq);
	} else {
		/* perform spectral scan if requested. */
		if (test_bit(ATH_OP_SCANNING, &common->op_flags) &&
			sc->spectral_mode == SPECTRAL_CHANSCAN)
			ath9k_spectral_scan_trigger(hw);
	}

	return 0;
}

void ath_chanctx_init(struct ath_softc *sc)
{
	struct ath_chanctx *ctx;
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct ieee80211_supported_band *sband;
	struct ieee80211_channel *chan;
	int i, j;

	sband = &common->sbands[IEEE80211_BAND_2GHZ];
	if (!sband->n_channels)
		sband = &common->sbands[IEEE80211_BAND_5GHZ];

	chan = &sband->channels[0];
	for (i = 0; i < ATH9K_NUM_CHANCTX; i++) {
		ctx = &sc->chanctx[i];
		cfg80211_chandef_create(&ctx->chandef, chan, NL80211_CHAN_HT20);
		INIT_LIST_HEAD(&ctx->vifs);
		ctx->txpower = ATH_TXPOWER_MAX;
		for (j = 0; j < ARRAY_SIZE(ctx->acq); j++)
			INIT_LIST_HEAD(&ctx->acq[j]);
	}
}

void ath_chanctx_set_channel(struct ath_softc *sc, struct ath_chanctx *ctx,
			     struct cfg80211_chan_def *chandef)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	bool cur_chan;

	spin_lock_bh(&sc->chan_lock);
	if (chandef)
		memcpy(&ctx->chandef, chandef, sizeof(*chandef));
	cur_chan = sc->cur_chan == ctx;
	spin_unlock_bh(&sc->chan_lock);

	if (!cur_chan) {
		ath_dbg(common, CHAN_CTX,
			"Current context differs from the new context\n");
		return;
	}

	ath_set_channel(sc);
}

#ifdef CPTCFG_ATH9K_CHANNEL_CONTEXT

/**********************************************************/
/* Functions to handle the channel context state machine. */
/**********************************************************/

static const char *offchannel_state_string(enum ath_offchannel_state state)
{
	switch (state) {
		case_rtn_string(ATH_OFFCHANNEL_IDLE);
		case_rtn_string(ATH_OFFCHANNEL_PROBE_SEND);
		case_rtn_string(ATH_OFFCHANNEL_PROBE_WAIT);
		case_rtn_string(ATH_OFFCHANNEL_SUSPEND);
		case_rtn_string(ATH_OFFCHANNEL_ROC_START);
		case_rtn_string(ATH_OFFCHANNEL_ROC_WAIT);
		case_rtn_string(ATH_OFFCHANNEL_ROC_DONE);
	default:
		return "unknown";
	}
}

static const char *chanctx_event_string(enum ath_chanctx_event ev)
{
	switch (ev) {
		case_rtn_string(ATH_CHANCTX_EVENT_BEACON_PREPARE);
		case_rtn_string(ATH_CHANCTX_EVENT_BEACON_SENT);
		case_rtn_string(ATH_CHANCTX_EVENT_TSF_TIMER);
		case_rtn_string(ATH_CHANCTX_EVENT_BEACON_RECEIVED);
		case_rtn_string(ATH_CHANCTX_EVENT_ASSOC);
		case_rtn_string(ATH_CHANCTX_EVENT_SWITCH);
		case_rtn_string(ATH_CHANCTX_EVENT_ASSIGN);
		case_rtn_string(ATH_CHANCTX_EVENT_UNASSIGN);
		case_rtn_string(ATH_CHANCTX_EVENT_CHANGE);
		case_rtn_string(ATH_CHANCTX_EVENT_ENABLE_MULTICHANNEL);
	default:
		return "unknown";
	}
}

static const char *chanctx_state_string(enum ath_chanctx_state state)
{
	switch (state) {
		case_rtn_string(ATH_CHANCTX_STATE_IDLE);
		case_rtn_string(ATH_CHANCTX_STATE_WAIT_FOR_BEACON);
		case_rtn_string(ATH_CHANCTX_STATE_WAIT_FOR_TIMER);
		case_rtn_string(ATH_CHANCTX_STATE_SWITCH);
		case_rtn_string(ATH_CHANCTX_STATE_FORCE_ACTIVE);
	default:
		return "unknown";
	}
}

void ath_chanctx_check_active(struct ath_softc *sc, struct ath_chanctx *ctx)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct ath_vif *avp;
	bool active = false;
	u8 n_active = 0;

	if (!ctx)
		return;

	list_for_each_entry(avp, &ctx->vifs, list) {
		struct ieee80211_vif *vif = avp->vif;

		switch (vif->type) {
		case NL80211_IFTYPE_P2P_CLIENT:
		case NL80211_IFTYPE_STATION:
			if (avp->assoc)
				active = true;
			break;
		default:
			active = true;
			break;
		}
	}
	ctx->active = active;

	ath_for_each_chanctx(sc, ctx) {
		if (!ctx->assigned || list_empty(&ctx->vifs))
			continue;
		n_active++;
	}

	if (n_active <= 1) {
		clear_bit(ATH_OP_MULTI_CHANNEL, &common->op_flags);
		return;
	}
	if (test_and_set_bit(ATH_OP_MULTI_CHANNEL, &common->op_flags))
		return;

	if (ath9k_is_chanctx_enabled()) {
		ath_chanctx_event(sc, NULL,
				  ATH_CHANCTX_EVENT_ENABLE_MULTICHANNEL);
	}
}

static struct ath_chanctx *
ath_chanctx_get_next(struct ath_softc *sc, struct ath_chanctx *ctx)
{
	int idx = ctx - &sc->chanctx[0];

	return &sc->chanctx[!idx];
}

static void ath_chanctx_adjust_tbtt_delta(struct ath_softc *sc)
{
	struct ath_chanctx *prev, *cur;
	struct timespec ts;
	u32 cur_tsf, prev_tsf, beacon_int;
	s32 offset;

	beacon_int = TU_TO_USEC(sc->cur_chan->beacon.beacon_interval);

	cur = sc->cur_chan;
	prev = ath_chanctx_get_next(sc, cur);

	if (!prev->switch_after_beacon)
		return;

	getrawmonotonic(&ts);
	cur_tsf = (u32) cur->tsf_val +
		  ath9k_hw_get_tsf_offset(&cur->tsf_ts, &ts);

	prev_tsf = prev->last_beacon - (u32) prev->tsf_val + cur_tsf;
	prev_tsf -= ath9k_hw_get_tsf_offset(&prev->tsf_ts, &ts);

	/* Adjust the TSF time of the AP chanctx to keep its beacons
	 * at half beacon interval offset relative to the STA chanctx.
	 */
	offset = cur_tsf - prev_tsf;

	/* Ignore stale data or spurious timestamps */
	if (offset < 0 || offset > 3 * beacon_int)
		return;

	offset = beacon_int / 2 - (offset % beacon_int);
	prev->tsf_val += offset;
}

/* Configure the TSF based hardware timer for a channel switch.
 * Also set up backup software timer, in case the gen timer fails.
 * This could be caused by a hardware reset.
 */
static void ath_chanctx_setup_timer(struct ath_softc *sc, u32 tsf_time)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct ath_hw *ah = sc->sc_ah;

	ath9k_hw_gen_timer_start(ah, sc->p2p_ps_timer, tsf_time, 1000000);
	tsf_time -= ath9k_hw_gettsf32(ah);
	tsf_time = msecs_to_jiffies(tsf_time / 1000) + 1;
	mod_timer(&sc->sched.timer, jiffies + tsf_time);

	ath_dbg(common, CHAN_CTX,
		"Setup chanctx timer with timeout: %d ms\n", jiffies_to_msecs(tsf_time));
}

void ath_chanctx_event(struct ath_softc *sc, struct ieee80211_vif *vif,
		       enum ath_chanctx_event ev)
{
	struct ath_hw *ah = sc->sc_ah;
	struct ath_common *common = ath9k_hw_common(ah);
	struct ath_beacon_config *cur_conf;
	struct ath_vif *avp = NULL;
	struct ath_chanctx *ctx;
	u32 tsf_time;
	u32 beacon_int;

	if (vif)
		avp = (struct ath_vif *) vif->drv_priv;

	spin_lock_bh(&sc->chan_lock);

	ath_dbg(common, CHAN_CTX, "cur_chan: %d MHz, event: %s, state: %s\n",
		sc->cur_chan->chandef.center_freq1,
		chanctx_event_string(ev),
		chanctx_state_string(sc->sched.state));

	switch (ev) {
	case ATH_CHANCTX_EVENT_BEACON_PREPARE:
		if (avp->offchannel_duration)
			avp->offchannel_duration = 0;

		if (avp->chanctx != sc->cur_chan) {
			ath_dbg(common, CHAN_CTX,
				"Contexts differ, not preparing beacon\n");
			break;
		}

		if (sc->sched.offchannel_pending && !sc->sched.wait_switch) {
			sc->sched.offchannel_pending = false;
			sc->next_chan = &sc->offchannel.chan;
			sc->sched.state = ATH_CHANCTX_STATE_WAIT_FOR_BEACON;
			ath_dbg(common, CHAN_CTX,
				"Setting offchannel_pending to false\n");
		}

		ctx = ath_chanctx_get_next(sc, sc->cur_chan);
		if (ctx->active && sc->sched.state == ATH_CHANCTX_STATE_IDLE) {
			sc->next_chan = ctx;
			sc->sched.state = ATH_CHANCTX_STATE_WAIT_FOR_BEACON;
			ath_dbg(common, CHAN_CTX,
				"Set next context, move chanctx state to WAIT_FOR_BEACON\n");
		}

		/* if the timer missed its window, use the next interval */
		if (sc->sched.state == ATH_CHANCTX_STATE_WAIT_FOR_TIMER) {
			sc->sched.state = ATH_CHANCTX_STATE_WAIT_FOR_BEACON;
			ath_dbg(common, CHAN_CTX,
				"Move chanctx state from WAIT_FOR_TIMER to WAIT_FOR_BEACON\n");
		}

		if (sc->sched.state != ATH_CHANCTX_STATE_WAIT_FOR_BEACON)
			break;

		ath_dbg(common, CHAN_CTX, "Preparing beacon for vif: %pM\n", vif->addr);

		sc->sched.beacon_pending = true;
		sc->sched.next_tbtt = REG_READ(ah, AR_NEXT_TBTT_TIMER);

		cur_conf = &sc->cur_chan->beacon;
		beacon_int = TU_TO_USEC(cur_conf->beacon_interval);

		/* defer channel switch by a quarter beacon interval */
		tsf_time = sc->sched.next_tbtt + beacon_int / 4;
		sc->sched.switch_start_time = tsf_time;
		sc->cur_chan->last_beacon = sc->sched.next_tbtt;

		/*
		 * If an offchannel switch is scheduled to happen after
		 * a beacon transmission, update the NoA with one-shot
		 * values and increment the index.
		 */
		if (sc->next_chan == &sc->offchannel.chan) {
			avp->noa_index++;
			avp->offchannel_start = tsf_time;
			avp->offchannel_duration = sc->sched.offchannel_duration;

			ath_dbg(common, CHAN_CTX,
				"offchannel noa_duration: %d, noa_start: %d, noa_index: %d\n",
				avp->offchannel_duration,
				avp->offchannel_start,
				avp->noa_index);

			/*
			 * When multiple contexts are active, the NoA
			 * has to be recalculated and advertised after
			 * an offchannel operation.
			 */
			if (ctx->active && avp->noa_duration)
				avp->noa_duration = 0;

			break;
		}

		/*
		 * Clear the extend_absence flag if it had been
		 * set during the previous beacon transmission,
		 * since we need to revert to the normal NoA
		 * schedule.
		 */
		if (ctx->active && sc->sched.extend_absence) {
			avp->noa_duration = 0;
			sc->sched.extend_absence = false;
		}

		/* If at least two consecutive beacons were missed on the STA
		 * chanctx, stay on the STA channel for one extra beacon period,
		 * to resync the timer properly.
		 */
		if (ctx->active && sc->sched.beacon_miss >= 2) {
			avp->noa_duration = 0;
			sc->sched.extend_absence = true;
		}

		/* Prevent wrap-around issues */
		if (avp->noa_duration && tsf_time - avp->noa_start > BIT(30))
			avp->noa_duration = 0;

		/*
		 * If multiple contexts are active, start periodic
		 * NoA and increment the index for the first
		 * announcement.
		 */
		if (ctx->active &&
		    (!avp->noa_duration || sc->sched.force_noa_update)) {
			avp->noa_index++;
			avp->noa_start = tsf_time;

			if (sc->sched.extend_absence)
				avp->noa_duration = (3 * beacon_int / 2) +
					sc->sched.channel_switch_time;
			else
				avp->noa_duration =
					TU_TO_USEC(cur_conf->beacon_interval) / 2 +
					sc->sched.channel_switch_time;

			if (test_bit(ATH_OP_SCANNING, &common->op_flags) ||
			    sc->sched.extend_absence)
				avp->periodic_noa = false;
			else
				avp->periodic_noa = true;

			ath_dbg(common, CHAN_CTX,
				"noa_duration: %d, noa_start: %d, noa_index: %d, periodic: %d\n",
				avp->noa_duration,
				avp->noa_start,
				avp->noa_index,
				avp->periodic_noa);
		}

		if (ctx->active && sc->sched.force_noa_update)
			sc->sched.force_noa_update = false;

		break;
	case ATH_CHANCTX_EVENT_BEACON_SENT:
		if (!sc->sched.beacon_pending) {
			ath_dbg(common, CHAN_CTX,
				"No pending beacon\n");
			break;
		}

		sc->sched.beacon_pending = false;
		if (sc->sched.state != ATH_CHANCTX_STATE_WAIT_FOR_BEACON)
			break;

		ath_dbg(common, CHAN_CTX,
			"Move chanctx state to WAIT_FOR_TIMER\n");

		sc->sched.state = ATH_CHANCTX_STATE_WAIT_FOR_TIMER;
		ath_chanctx_setup_timer(sc, sc->sched.switch_start_time);
		break;
	case ATH_CHANCTX_EVENT_TSF_TIMER:
		if (sc->sched.state != ATH_CHANCTX_STATE_WAIT_FOR_TIMER)
			break;

		if (!sc->cur_chan->switch_after_beacon &&
		    sc->sched.beacon_pending)
			sc->sched.beacon_miss++;

		ath_dbg(common, CHAN_CTX,
			"Move chanctx state to SWITCH\n");

		sc->sched.state = ATH_CHANCTX_STATE_SWITCH;
		ieee80211_queue_work(sc->hw, &sc->chanctx_work);
		break;
	case ATH_CHANCTX_EVENT_BEACON_RECEIVED:
		if (!test_bit(ATH_OP_MULTI_CHANNEL, &common->op_flags) ||
		    sc->cur_chan == &sc->offchannel.chan)
			break;

		ath_chanctx_adjust_tbtt_delta(sc);
		sc->sched.beacon_pending = false;
		sc->sched.beacon_miss = 0;

		/* TSF time might have been updated by the incoming beacon,
		 * need update the channel switch timer to reflect the change.
		 */
		tsf_time = sc->sched.switch_start_time;
		tsf_time -= (u32) sc->cur_chan->tsf_val +
			ath9k_hw_get_tsf_offset(&sc->cur_chan->tsf_ts, NULL);
		tsf_time += ath9k_hw_gettsf32(ah);


		ath_chanctx_setup_timer(sc, tsf_time);
		break;
	case ATH_CHANCTX_EVENT_ASSOC:
		if (sc->sched.state != ATH_CHANCTX_STATE_FORCE_ACTIVE ||
		    avp->chanctx != sc->cur_chan)
			break;

		ath_dbg(common, CHAN_CTX,
			"Move chanctx state from FORCE_ACTIVE to IDLE\n");

		sc->sched.state = ATH_CHANCTX_STATE_IDLE;
		/* fall through */
	case ATH_CHANCTX_EVENT_SWITCH:
		if (!test_bit(ATH_OP_MULTI_CHANNEL, &common->op_flags) ||
		    sc->sched.state == ATH_CHANCTX_STATE_FORCE_ACTIVE ||
		    sc->cur_chan->switch_after_beacon ||
		    sc->cur_chan == &sc->offchannel.chan)
			break;

		/* If this is a station chanctx, stay active for a half
		 * beacon period (minus channel switch time)
		 */
		sc->next_chan = ath_chanctx_get_next(sc, sc->cur_chan);
		cur_conf = &sc->cur_chan->beacon;

		ath_dbg(common, CHAN_CTX,
			"Move chanctx state to WAIT_FOR_TIMER (event SWITCH)\n");

		sc->sched.state = ATH_CHANCTX_STATE_WAIT_FOR_TIMER;
		sc->sched.wait_switch = false;

		tsf_time = TU_TO_USEC(cur_conf->beacon_interval) / 2;

		if (sc->sched.extend_absence) {
			sc->sched.beacon_miss = 0;
			tsf_time *= 3;
		}

		tsf_time -= sc->sched.channel_switch_time;
		tsf_time += ath9k_hw_gettsf32(sc->sc_ah);
		sc->sched.switch_start_time = tsf_time;

		ath_chanctx_setup_timer(sc, tsf_time);
		sc->sched.beacon_pending = true;
		break;
	case ATH_CHANCTX_EVENT_ENABLE_MULTICHANNEL:
		if (sc->cur_chan == &sc->offchannel.chan ||
		    sc->cur_chan->switch_after_beacon)
			break;

		sc->next_chan = ath_chanctx_get_next(sc, sc->cur_chan);
		ieee80211_queue_work(sc->hw, &sc->chanctx_work);
		break;
	case ATH_CHANCTX_EVENT_UNASSIGN:
		if (sc->cur_chan->assigned) {
			if (sc->next_chan && !sc->next_chan->assigned &&
			    sc->next_chan != &sc->offchannel.chan)
				sc->sched.state = ATH_CHANCTX_STATE_IDLE;
			break;
		}

		ctx = ath_chanctx_get_next(sc, sc->cur_chan);
		sc->sched.state = ATH_CHANCTX_STATE_IDLE;
		if (!ctx->assigned)
			break;

		sc->next_chan = ctx;
		ieee80211_queue_work(sc->hw, &sc->chanctx_work);
		break;
	case ATH_CHANCTX_EVENT_ASSIGN:
		/*
		 * When adding a new channel context, check if a scan
		 * is in progress and abort it since the addition of
		 * a new channel context is usually followed by VIF
		 * assignment, in which case we have to start multi-channel
		 * operation.
		 */
		if (test_bit(ATH_OP_SCANNING, &common->op_flags)) {
			ath_dbg(common, CHAN_CTX,
				"Aborting HW scan to add new context\n");

			spin_unlock_bh(&sc->chan_lock);
			del_timer_sync(&sc->offchannel.timer);
			ath_scan_complete(sc, true);
			spin_lock_bh(&sc->chan_lock);
		}
		break;
	case ATH_CHANCTX_EVENT_CHANGE:
		break;
	}

	spin_unlock_bh(&sc->chan_lock);
}

void ath_chanctx_beacon_sent_ev(struct ath_softc *sc,
				enum ath_chanctx_event ev)
{
	if (sc->sched.beacon_pending)
		ath_chanctx_event(sc, NULL, ev);
}

void ath_chanctx_beacon_recv_ev(struct ath_softc *sc,
				enum ath_chanctx_event ev)
{
	ath_chanctx_event(sc, NULL, ev);
}

static int ath_scan_channel_duration(struct ath_softc *sc,
				     struct ieee80211_channel *chan)
{
	struct cfg80211_scan_request *req = sc->offchannel.scan_req;

	if (!req->n_ssids || (chan->flags & IEEE80211_CHAN_NO_IR))
		return (HZ / 9); /* ~110 ms */

	return (HZ / 16); /* ~60 ms */
}

static void ath_chanctx_switch(struct ath_softc *sc, struct ath_chanctx *ctx,
			       struct cfg80211_chan_def *chandef)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);

	spin_lock_bh(&sc->chan_lock);

	if (test_bit(ATH_OP_MULTI_CHANNEL, &common->op_flags) &&
	    (sc->cur_chan != ctx) && (ctx == &sc->offchannel.chan)) {
		if (chandef)
			ctx->chandef = *chandef;

		sc->sched.offchannel_pending = true;
		sc->sched.wait_switch = true;
		sc->sched.offchannel_duration =
			jiffies_to_usecs(sc->offchannel.duration) +
			sc->sched.channel_switch_time;

		spin_unlock_bh(&sc->chan_lock);
		ath_dbg(common, CHAN_CTX,
			"Set offchannel_pending to true\n");
		return;
	}

	sc->next_chan = ctx;
	if (chandef) {
		ctx->chandef = *chandef;
		ath_dbg(common, CHAN_CTX,
			"Assigned next_chan to %d MHz\n", chandef->center_freq1);
	}

	if (sc->next_chan == &sc->offchannel.chan) {
		sc->sched.offchannel_duration =
			jiffies_to_usecs(sc->offchannel.duration) +
			sc->sched.channel_switch_time;

		if (chandef) {
			ath_dbg(common, CHAN_CTX,
				"Offchannel duration for chan %d MHz : %u\n",
				chandef->center_freq1,
				sc->sched.offchannel_duration);
		}
	}
	spin_unlock_bh(&sc->chan_lock);
	ieee80211_queue_work(sc->hw, &sc->chanctx_work);
}

static void ath_chanctx_offchan_switch(struct ath_softc *sc,
				       struct ieee80211_channel *chan)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct cfg80211_chan_def chandef;

	cfg80211_chandef_create(&chandef, chan, NL80211_CHAN_NO_HT);
	ath_dbg(common, CHAN_CTX,
		"Channel definition created: %d MHz\n", chandef.center_freq1);

	ath_chanctx_switch(sc, &sc->offchannel.chan, &chandef);
}

static struct ath_chanctx *ath_chanctx_get_oper_chan(struct ath_softc *sc,
						     bool active)
{
	struct ath_chanctx *ctx;

	ath_for_each_chanctx(sc, ctx) {
		if (!ctx->assigned || list_empty(&ctx->vifs))
			continue;
		if (active && !ctx->active)
			continue;

		if (ctx->switch_after_beacon)
			return ctx;
	}

	return &sc->chanctx[0];
}

static void
ath_scan_next_channel(struct ath_softc *sc)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct cfg80211_scan_request *req = sc->offchannel.scan_req;
	struct ieee80211_channel *chan;

	if (sc->offchannel.scan_idx >= req->n_channels) {
		ath_dbg(common, CHAN_CTX,
			"Moving offchannel state to ATH_OFFCHANNEL_IDLE, "
			"scan_idx: %d, n_channels: %d\n",
			sc->offchannel.scan_idx,
			req->n_channels);

		sc->offchannel.state = ATH_OFFCHANNEL_IDLE;
		ath_chanctx_switch(sc, ath_chanctx_get_oper_chan(sc, false),
				   NULL);
		return;
	}

	ath_dbg(common, CHAN_CTX,
		"Moving offchannel state to ATH_OFFCHANNEL_PROBE_SEND, scan_idx: %d\n",
		sc->offchannel.scan_idx);

	chan = req->channels[sc->offchannel.scan_idx++];
	sc->offchannel.duration = ath_scan_channel_duration(sc, chan);
	sc->offchannel.state = ATH_OFFCHANNEL_PROBE_SEND;

	ath_chanctx_offchan_switch(sc, chan);
}

void ath_offchannel_next(struct ath_softc *sc)
{
	struct ieee80211_vif *vif;

	if (sc->offchannel.scan_req) {
		vif = sc->offchannel.scan_vif;
		sc->offchannel.chan.txpower = vif->bss_conf.txpower;
		ath_scan_next_channel(sc);
	} else if (sc->offchannel.roc_vif) {
		vif = sc->offchannel.roc_vif;
		sc->offchannel.chan.txpower = vif->bss_conf.txpower;
		sc->offchannel.duration =
			msecs_to_jiffies(sc->offchannel.roc_duration);
		sc->offchannel.state = ATH_OFFCHANNEL_ROC_START;
		ath_chanctx_offchan_switch(sc, sc->offchannel.roc_chan);
	} else {
		ath_chanctx_switch(sc, ath_chanctx_get_oper_chan(sc, false),
				   NULL);
		sc->offchannel.state = ATH_OFFCHANNEL_IDLE;
		if (sc->ps_idle)
			ath_cancel_work(sc);
	}
}

void ath_roc_complete(struct ath_softc *sc, bool abort)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);

	if (abort)
		ath_dbg(common, CHAN_CTX, "RoC aborted\n");
	else
		ath_dbg(common, CHAN_CTX, "RoC expired\n");

	sc->offchannel.roc_vif = NULL;
	sc->offchannel.roc_chan = NULL;
	if (!abort)
		ieee80211_remain_on_channel_expired(sc->hw);
	ath_offchannel_next(sc);
	ath9k_ps_restore(sc);
}

void ath_scan_complete(struct ath_softc *sc, bool abort)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);

	if (abort)
		ath_dbg(common, CHAN_CTX, "HW scan aborted\n");
	else
		ath_dbg(common, CHAN_CTX, "HW scan complete\n");

	sc->offchannel.scan_req = NULL;
	sc->offchannel.scan_vif = NULL;
	sc->offchannel.state = ATH_OFFCHANNEL_IDLE;
	ieee80211_scan_completed(sc->hw, abort);
	clear_bit(ATH_OP_SCANNING, &common->op_flags);
	spin_lock_bh(&sc->chan_lock);
	if (test_bit(ATH_OP_MULTI_CHANNEL, &common->op_flags))
		sc->sched.force_noa_update = true;
	spin_unlock_bh(&sc->chan_lock);
	ath_offchannel_next(sc);
	ath9k_ps_restore(sc);
}

static void ath_scan_send_probe(struct ath_softc *sc,
				struct cfg80211_ssid *ssid)
{
	struct cfg80211_scan_request *req = sc->offchannel.scan_req;
	struct ieee80211_vif *vif = sc->offchannel.scan_vif;
	struct ath_tx_control txctl = {};
	struct sk_buff *skb;
	struct ieee80211_tx_info *info;
	int band = sc->offchannel.chan.chandef.chan->band;

	skb = ieee80211_probereq_get(sc->hw, vif,
			ssid->ssid, ssid->ssid_len, req->ie_len);
	if (!skb)
		return;

	info = IEEE80211_SKB_CB(skb);
	if (req->no_cck)
		info->flags |= IEEE80211_TX_CTL_NO_CCK_RATE;

	if (req->ie_len)
		memcpy(skb_put(skb, req->ie_len), req->ie, req->ie_len);

	skb_set_queue_mapping(skb, IEEE80211_AC_VO);

	if (!ieee80211_tx_prepare_skb(sc->hw, vif, skb, band, NULL))
		goto error;

	txctl.txq = sc->tx.txq_map[IEEE80211_AC_VO];
	txctl.force_channel = true;
	if (ath_tx_start(sc->hw, skb, &txctl))
		goto error;

	return;

error:
	ieee80211_free_txskb(sc->hw, skb);
}

static void ath_scan_channel_start(struct ath_softc *sc)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct cfg80211_scan_request *req = sc->offchannel.scan_req;
	int i;

	if (!(sc->cur_chan->chandef.chan->flags & IEEE80211_CHAN_NO_IR) &&
	    req->n_ssids) {
		for (i = 0; i < req->n_ssids; i++)
			ath_scan_send_probe(sc, &req->ssids[i]);

	}

	ath_dbg(common, CHAN_CTX,
		"Moving offchannel state to ATH_OFFCHANNEL_PROBE_WAIT\n");

	sc->offchannel.state = ATH_OFFCHANNEL_PROBE_WAIT;
	mod_timer(&sc->offchannel.timer, jiffies + sc->offchannel.duration);
}

static void ath_chanctx_timer(unsigned long data)
{
	struct ath_softc *sc = (struct ath_softc *) data;
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);

	ath_dbg(common, CHAN_CTX,
		"Channel context timer invoked\n");

	ath_chanctx_event(sc, NULL, ATH_CHANCTX_EVENT_TSF_TIMER);
}

static void ath_offchannel_timer(unsigned long data)
{
	struct ath_softc *sc = (struct ath_softc *)data;
	struct ath_chanctx *ctx;
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);

	ath_dbg(common, CHAN_CTX, "%s: offchannel state: %s\n",
		__func__, offchannel_state_string(sc->offchannel.state));

	switch (sc->offchannel.state) {
	case ATH_OFFCHANNEL_PROBE_WAIT:
		if (!sc->offchannel.scan_req)
			return;

		/* get first active channel context */
		ctx = ath_chanctx_get_oper_chan(sc, true);
		if (ctx->active) {
			ath_dbg(common, CHAN_CTX,
				"Switch to oper/active context, "
				"move offchannel state to ATH_OFFCHANNEL_SUSPEND\n");

			sc->offchannel.state = ATH_OFFCHANNEL_SUSPEND;
			ath_chanctx_switch(sc, ctx, NULL);
			mod_timer(&sc->offchannel.timer, jiffies + HZ / 10);
			break;
		}
		/* fall through */
	case ATH_OFFCHANNEL_SUSPEND:
		if (!sc->offchannel.scan_req)
			return;

		ath_scan_next_channel(sc);
		break;
	case ATH_OFFCHANNEL_ROC_START:
	case ATH_OFFCHANNEL_ROC_WAIT:
		ctx = ath_chanctx_get_oper_chan(sc, false);
		sc->offchannel.state = ATH_OFFCHANNEL_ROC_DONE;
		ath_chanctx_switch(sc, ctx, NULL);
		break;
	default:
		break;
	}
}

static bool
ath_chanctx_send_vif_ps_frame(struct ath_softc *sc, struct ath_vif *avp,
			      bool powersave)
{
	struct ieee80211_vif *vif = avp->vif;
	struct ieee80211_sta *sta = NULL;
	struct ieee80211_hdr_3addr *nullfunc;
	struct ath_tx_control txctl;
	struct sk_buff *skb;
	int band = sc->cur_chan->chandef.chan->band;

	switch (vif->type) {
	case NL80211_IFTYPE_STATION:
		if (!avp->assoc)
			return false;

		skb = ieee80211_nullfunc_get(sc->hw, vif);
		if (!skb)
			return false;

		nullfunc = (struct ieee80211_hdr_3addr *) skb->data;
		if (powersave)
			nullfunc->frame_control |=
				cpu_to_le16(IEEE80211_FCTL_PM);

		skb_set_queue_mapping(skb, IEEE80211_AC_VO);
		if (!ieee80211_tx_prepare_skb(sc->hw, vif, skb, band, &sta)) {
			dev_kfree_skb_any(skb);
			return false;
		}
		break;
	default:
		return false;
	}

	memset(&txctl, 0, sizeof(txctl));
	txctl.txq = sc->tx.txq_map[IEEE80211_AC_VO];
	txctl.sta = sta;
	txctl.force_channel = true;
	if (ath_tx_start(sc->hw, skb, &txctl)) {
		ieee80211_free_txskb(sc->hw, skb);
		return false;
	}

	return true;
}

static bool
ath_chanctx_send_ps_frame(struct ath_softc *sc, bool powersave)
{
	struct ath_vif *avp;
	bool sent = false;

	rcu_read_lock();
	list_for_each_entry(avp, &sc->cur_chan->vifs, list) {
		if (ath_chanctx_send_vif_ps_frame(sc, avp, powersave))
			sent = true;
	}
	rcu_read_unlock();

	return sent;
}

static bool ath_chanctx_defer_switch(struct ath_softc *sc)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);

	if (sc->cur_chan == &sc->offchannel.chan)
		return false;

	switch (sc->sched.state) {
	case ATH_CHANCTX_STATE_SWITCH:
		return false;
	case ATH_CHANCTX_STATE_IDLE:
		if (!sc->cur_chan->switch_after_beacon)
			return false;

		ath_dbg(common, CHAN_CTX,
			"Defer switch, set chanctx state to WAIT_FOR_BEACON\n");

		sc->sched.state = ATH_CHANCTX_STATE_WAIT_FOR_BEACON;
		break;
	default:
		break;
	}

	return true;
}

static void ath_offchannel_channel_change(struct ath_softc *sc)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);

	ath_dbg(common, CHAN_CTX, "%s: offchannel state: %s\n",
		__func__, offchannel_state_string(sc->offchannel.state));

	switch (sc->offchannel.state) {
	case ATH_OFFCHANNEL_PROBE_SEND:
		if (!sc->offchannel.scan_req)
			return;

		if (sc->cur_chan->chandef.chan !=
		    sc->offchannel.chan.chandef.chan)
			return;

		ath_scan_channel_start(sc);
		break;
	case ATH_OFFCHANNEL_IDLE:
		if (!sc->offchannel.scan_req)
			return;

		ath_scan_complete(sc, false);
		break;
	case ATH_OFFCHANNEL_ROC_START:
		if (sc->cur_chan != &sc->offchannel.chan)
			break;

		sc->offchannel.state = ATH_OFFCHANNEL_ROC_WAIT;
		mod_timer(&sc->offchannel.timer,
			  jiffies + sc->offchannel.duration);
		ieee80211_ready_on_channel(sc->hw);
		break;
	case ATH_OFFCHANNEL_ROC_DONE:
		ath_roc_complete(sc, false);
		break;
	default:
		break;
	}
}

void ath_chanctx_set_next(struct ath_softc *sc, bool force)
{
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct ath_chanctx *old_ctx;
	struct timespec ts;
	bool measure_time = false;
	bool send_ps = false;
	bool queues_stopped = false;

	spin_lock_bh(&sc->chan_lock);
	if (!sc->next_chan) {
		spin_unlock_bh(&sc->chan_lock);
		return;
	}

	if (!force && ath_chanctx_defer_switch(sc)) {
		spin_unlock_bh(&sc->chan_lock);
		return;
	}

	ath_dbg(common, CHAN_CTX,
		"%s: current: %d MHz, next: %d MHz\n",
		__func__,
		sc->cur_chan->chandef.center_freq1,
		sc->next_chan->chandef.center_freq1);

	if (sc->cur_chan != sc->next_chan) {
		ath_dbg(common, CHAN_CTX,
			"Stopping current chanctx: %d\n",
			sc->cur_chan->chandef.center_freq1);
		sc->cur_chan->stopped = true;
		spin_unlock_bh(&sc->chan_lock);

		if (sc->next_chan == &sc->offchannel.chan) {
			getrawmonotonic(&ts);
			measure_time = true;
		}

		ath9k_chanctx_stop_queues(sc, sc->cur_chan);
		queues_stopped = true;

		__ath9k_flush(sc->hw, ~0, true);

		if (ath_chanctx_send_ps_frame(sc, true))
			__ath9k_flush(sc->hw, BIT(IEEE80211_AC_VO), false);

		send_ps = true;
		spin_lock_bh(&sc->chan_lock);

		if (sc->cur_chan != &sc->offchannel.chan) {
			getrawmonotonic(&sc->cur_chan->tsf_ts);
			sc->cur_chan->tsf_val = ath9k_hw_gettsf64(sc->sc_ah);
		}
	}
	old_ctx = sc->cur_chan;
	sc->cur_chan = sc->next_chan;
	sc->cur_chan->stopped = false;
	sc->next_chan = NULL;

	if (!sc->sched.offchannel_pending)
		sc->sched.offchannel_duration = 0;

	if (sc->sched.state != ATH_CHANCTX_STATE_FORCE_ACTIVE)
		sc->sched.state = ATH_CHANCTX_STATE_IDLE;

	spin_unlock_bh(&sc->chan_lock);

	if (sc->sc_ah->chip_fullsleep ||
	    memcmp(&sc->cur_chandef, &sc->cur_chan->chandef,
		   sizeof(sc->cur_chandef))) {
		ath_dbg(common, CHAN_CTX,
			"%s: Set channel %d MHz\n",
			__func__, sc->cur_chan->chandef.center_freq1);
		ath_set_channel(sc);
		if (measure_time)
			sc->sched.channel_switch_time =
				ath9k_hw_get_tsf_offset(&ts, NULL);
		/*
		 * A reset will ensure that all queues are woken up,
		 * so there is no need to awaken them again.
		 */
		goto out;
	}

	if (queues_stopped)
		ath9k_chanctx_wake_queues(sc, old_ctx);
out:
	if (send_ps)
		ath_chanctx_send_ps_frame(sc, false);

	ath_offchannel_channel_change(sc);
	ath_chanctx_event(sc, NULL, ATH_CHANCTX_EVENT_SWITCH);
}

static void ath_chanctx_work(struct work_struct *work)
{
	struct ath_softc *sc = container_of(work, struct ath_softc,
					    chanctx_work);
	mutex_lock(&sc->mutex);
	ath_chanctx_set_next(sc, false);
	mutex_unlock(&sc->mutex);
}

void ath9k_offchannel_init(struct ath_softc *sc)
{
	struct ath_chanctx *ctx;
	struct ath_common *common = ath9k_hw_common(sc->sc_ah);
	struct ieee80211_supported_band *sband;
	struct ieee80211_channel *chan;
	int i;

	sband = &common->sbands[IEEE80211_BAND_2GHZ];
	if (!sband->n_channels)
		sband = &common->sbands[IEEE80211_BAND_5GHZ];

	chan = &sband->channels[0];

	ctx = &sc->offchannel.chan;
	INIT_LIST_HEAD(&ctx->vifs);
	ctx->txpower = ATH_TXPOWER_MAX;
	cfg80211_chandef_create(&ctx->chandef, chan, NL80211_CHAN_HT20);

	for (i = 0; i < ARRAY_SIZE(ctx->acq); i++)
		INIT_LIST_HEAD(&ctx->acq[i]);

	sc->offchannel.chan.offchannel = true;
}

void ath9k_init_channel_context(struct ath_softc *sc)
{
	INIT_WORK(&sc->chanctx_work, ath_chanctx_work);

	setup_timer(&sc->offchannel.timer, ath_offchannel_timer,
		    (unsigned long)sc);
	setup_timer(&sc->sched.timer, ath_chanctx_timer,
		    (unsigned long)sc);
}

void ath9k_deinit_channel_context(struct ath_softc *sc)
{
	cancel_work_sync(&sc->chanctx_work);
}

bool ath9k_is_chanctx_enabled(void)
{
	return (ath9k_use_chanctx == 1);
}

/********************/
/* Queue management */
/********************/

void ath9k_chanctx_stop_queues(struct ath_softc *sc, struct ath_chanctx *ctx)
{
	struct ath_hw *ah = sc->sc_ah;
	int i;

	if (ctx == &sc->offchannel.chan) {
		ieee80211_stop_queue(sc->hw,
				     sc->hw->offchannel_tx_hw_queue);
	} else {
		for (i = 0; i < IEEE80211_NUM_ACS; i++)
			ieee80211_stop_queue(sc->hw,
					     ctx->hw_queue_base + i);
	}

	if (ah->opmode == NL80211_IFTYPE_AP)
		ieee80211_stop_queue(sc->hw, sc->hw->queues - 2);
}


void ath9k_chanctx_wake_queues(struct ath_softc *sc, struct ath_chanctx *ctx)
{
	struct ath_hw *ah = sc->sc_ah;
	int i;

	if (ctx == &sc->offchannel.chan) {
		ieee80211_wake_queue(sc->hw,
				     sc->hw->offchannel_tx_hw_queue);
	} else {
		for (i = 0; i < IEEE80211_NUM_ACS; i++)
			ieee80211_wake_queue(sc->hw,
					     ctx->hw_queue_base + i);
	}

	if (ah->opmode == NL80211_IFTYPE_AP)
		ieee80211_wake_queue(sc->hw, sc->hw->queues - 2);
}

/*****************/
/* 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;

	if (!avp || !avp->noa.has_next_tsf)
		return;

	ath9k_hw_gen_timer_stop(ah, sc->p2p_ps_timer);

	tsf = ath9k_hw_gettsf32(sc->sc_ah);

	target_tsf = avp->noa.next_tsf;
	if (!avp->noa.absent)
		target_tsf -= ATH_P2P_PS_STOP_TIME;

	if (target_tsf - tsf < ATH_P2P_PS_STOP_TIME)
		target_tsf = tsf + ATH_P2P_PS_STOP_TIME;

	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);
}

static u8 ath9k_get_ctwin(struct ath_softc *sc, struct ath_vif *avp)
{
	struct ath_beacon_config *cur_conf = &sc->cur_chan->beacon;
	u8 switch_time, ctwin;

	/*
	 * Channel switch in multi-channel mode is deferred
	 * by a quarter beacon interval when handling
	 * ATH_CHANCTX_EVENT_BEACON_PREPARE, so the P2P-GO
	 * interface is guaranteed to be discoverable
	 * for that duration after a TBTT.
	 */
	switch_time = cur_conf->beacon_interval / 4;

	ctwin = avp->vif->bss_conf.p2p_noa_attr.oppps_ctwindow;
	if (ctwin && (ctwin < switch_time))
		return ctwin;

	if (switch_time < P2P_DEFAULT_CTWIN)
		return 0;

	return P2P_DEFAULT_CTWIN;
}

void ath9k_beacon_add_noa(struct ath_softc *sc, struct ath_vif *avp,
			  struct sk_buff *skb)
{
	static const u8 noa_ie_hdr[] = {
		WLAN_EID_VENDOR_SPECIFIC,	/* type */
		0,				/* length */
		0x50, 0x6f, 0x9a,		/* WFA OUI */
		0x09,				/* P2P subtype */
		0x0c,				/* Notice of Absence */
		0x00,				/* LSB of little-endian len */
		0x00,				/* MSB of little-endian len */
	};

	struct ieee80211_p2p_noa_attr *noa;
	int noa_len, noa_desc, i = 0;
	u8 *hdr;

	if (!avp->offchannel_duration && !avp->noa_duration)
		return;

	noa_desc = !!avp->offchannel_duration + !!avp->noa_duration;
	noa_len = 2 + sizeof(struct ieee80211_p2p_noa_desc) * noa_desc;

	hdr = skb_put(skb, sizeof(noa_ie_hdr));
	memcpy(hdr, noa_ie_hdr, sizeof(noa_ie_hdr));
	hdr[1] = sizeof(noa_ie_hdr) + noa_len - 2;
	hdr[7] = noa_len;

	noa = (void *) skb_put(skb, noa_len);
	memset(noa, 0, noa_len);

	noa->index = avp->noa_index;
	noa->oppps_ctwindow = ath9k_get_ctwin(sc, avp);

	if (avp->noa_duration) {
		if (avp->periodic_noa) {
			u32 interval = TU_TO_USEC(sc->cur_chan->beacon.beacon_interval);
			noa->desc[i].count = 255;
			noa->desc[i].interval = cpu_to_le32(interval);
		} else {
			noa->desc[i].count = 1;
		}

		noa->desc[i].start_time = cpu_to_le32(avp->noa_start);
		noa->desc[i].duration = cpu_to_le32(avp->noa_duration);
		i++;
	}

	if (avp->offchannel_duration) {
		noa->desc[i].count = 1;
		noa->desc[i].start_time = cpu_to_le32(avp->offchannel_start);
		noa->desc[i].duration = cpu_to_le32(avp->offchannel_duration);
	}
}

void ath9k_p2p_ps_timer(void *priv)
{
	struct ath_softc *sc = priv;
	struct ath_vif *avp = sc->p2p_ps_vif;
	struct ieee80211_vif *vif;
	struct ieee80211_sta *sta;
	struct ath_node *an;
	u32 tsf;

	del_timer_sync(&sc->sched.timer);
	ath9k_hw_gen_timer_stop(sc->sc_ah, sc->p2p_ps_timer);
	ath_chanctx_event(sc, NULL, ATH_CHANCTX_EVENT_TSF_TIMER);

	if (!avp || avp->chanctx != sc->cur_chan)
		return;

	tsf = ath9k_hw_gettsf32(sc->sc_ah);
	if (!avp->noa.absent)
		tsf += ATH_P2P_PS_STOP_TIME;

	if (!avp->noa.has_next_tsf ||
	    avp->noa.next_tsf - tsf > BIT(31))
		ieee80211_update_p2p_noa(&avp->noa, tsf);

	ath9k_update_p2p_ps_timer(sc, avp);

	rcu_read_lock();

	vif = avp->vif;
	sta = ieee80211_find_sta(vif, avp->bssid);
	if (!sta)
		goto out;

	an = (void *) sta->drv_priv;
	if (an->sleeping == !!avp->noa.absent)
		goto out;

	an->sleeping = avp->noa.absent;
	if (an->sleeping)
		ath_tx_aggr_sleep(sta, sc, an);
	else
		ath_tx_aggr_wakeup(sc, an);

out:
	rcu_read_unlock();
}

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;

	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 -ENOMEM;

	return 0;
}

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 /* CPTCFG_ATH9K_CHANNEL_CONTEXT */
