- REG_RMW_FIELD(ah, AR_PHY_PAPRD_CTRL0_B0,
---- a/drivers/net/wireless/ath/ath9k/ar9003_phy.c
-+++ b/drivers/net/wireless/ath/ath9k/ar9003_phy.c
-@@ -373,7 +373,7 @@ static void ar9003_hw_spur_ofdm_work(str
- else
- spur_subchannel_sd = 0;
-
-- spur_freq_sd = (freq_offset << 9) / 11;
-+ spur_freq_sd = ((freq_offset + 10) << 9) / 11;
-
- } else {
- if (REG_READ_FIELD(ah, AR_PHY_GEN_CTRL,
-@@ -382,7 +382,7 @@ static void ar9003_hw_spur_ofdm_work(str
- else
- spur_subchannel_sd = 1;
-
-- spur_freq_sd = (freq_offset << 9) / 11;
-+ spur_freq_sd = ((freq_offset - 10) << 9) / 11;
-
- }
-
-@@ -526,22 +526,10 @@ static void ar9003_hw_init_bb(struct ath
- * Value is in 100ns increments.
- */
- synthDelay = REG_READ(ah, AR_PHY_RX_DELAY) & AR_PHY_RX_DELAY_DELAY;
-- if (IS_CHAN_B(chan))
-- synthDelay = (4 * synthDelay) / 22;
-- else
-- synthDelay /= 10;
-
- /* Activate the PHY (includes baseband activate + synthesizer on) */
- REG_WRITE(ah, AR_PHY_ACTIVE, AR_PHY_ACTIVE_EN);
--
-- /*
-- * There is an issue if the AP starts the calibration before
-- * the base band timeout completes. This could result in the
-- * rx_clear false triggering. As a workaround we add delay an
-- * extra BASE_ACTIVATE_DELAY usecs to ensure this condition
-- * does not happen.
-- */
-- udelay(synthDelay + BASE_ACTIVATE_DELAY);
-+ ath9k_hw_synth_delay(ah, chan, synthDelay);
- }
-
- static void ar9003_hw_set_chain_masks(struct ath_hw *ah, u8 rx, u8 tx)
-@@ -692,7 +680,7 @@ static int ar9003_hw_process_ini(struct
- ar9003_hw_override_ini(ah);
- ar9003_hw_set_channel_regs(ah, chan);
- ar9003_hw_set_chain_masks(ah, ah->rxchainmask, ah->txchainmask);
-- ath9k_hw_apply_txpower(ah, chan);
-+ ath9k_hw_apply_txpower(ah, chan, false);
-
- if (AR_SREV_9462(ah)) {
- if (REG_READ_FIELD(ah, AR_PHY_TX_IQCAL_CONTROL_0,
-@@ -723,6 +711,14 @@ static void ar9003_hw_set_rfmode(struct
-
- if (IS_CHAN_A_FAST_CLOCK(ah, chan))
- rfMode |= (AR_PHY_MODE_DYNAMIC | AR_PHY_MODE_DYN_CCK_DISABLE);
-+ if (IS_CHAN_QUARTER_RATE(chan))
-+ rfMode |= AR_PHY_MODE_QUARTER;
-+ if (IS_CHAN_HALF_RATE(chan))
-+ rfMode |= AR_PHY_MODE_HALF;
-+
-+ if (rfMode & (AR_PHY_MODE_QUARTER | AR_PHY_MODE_HALF))
-+ REG_RMW_FIELD(ah, AR_PHY_FRAME_CTL,
-+ AR_PHY_FRAME_CTL_CF_OVERLAP_WINDOW, 3);
-
- REG_WRITE(ah, AR_PHY_MODE, rfMode);
- }
-@@ -793,12 +789,8 @@ static bool ar9003_hw_rfbus_req(struct a
- static void ar9003_hw_rfbus_done(struct ath_hw *ah)
- {
- u32 synthDelay = REG_READ(ah, AR_PHY_RX_DELAY) & AR_PHY_RX_DELAY_DELAY;
-- if (IS_CHAN_B(ah->curchan))
-- synthDelay = (4 * synthDelay) / 22;
-- else
-- synthDelay /= 10;
-
-- udelay(synthDelay + BASE_ACTIVATE_DELAY);
-+ ath9k_hw_synth_delay(ah, ah->curchan, synthDelay);
-
- REG_WRITE(ah, AR_PHY_RFBUS_REQ, 0);
- }
---- a/drivers/net/wireless/ath/ath9k/ar9003_phy.h
-+++ b/drivers/net/wireless/ath/ath9k/ar9003_phy.h
-@@ -468,6 +468,9 @@
- #define AR_PHY_ADDAC_PARA_CTL (AR_SM_BASE + 0x150)
- #define AR_PHY_XPA_CFG (AR_SM_BASE + 0x158)
-
-+#define AR_PHY_FRAME_CTL_CF_OVERLAP_WINDOW 3
-+#define AR_PHY_FRAME_CTL_CF_OVERLAP_WINDOW_S 0
-+
- #define AR_PHY_SPUR_MASK_A_CF_PUNC_MASK_IDX_A 0x0001FC00
- #define AR_PHY_SPUR_MASK_A_CF_PUNC_MASK_IDX_A_S 10
- #define AR_PHY_SPUR_MASK_A_CF_PUNC_MASK_A 0x3FF
---- a/drivers/net/wireless/ath/ath9k/eeprom_9287.c
-+++ b/drivers/net/wireless/ath/ath9k/eeprom_9287.c
-@@ -798,6 +798,8 @@ static void ath9k_hw_ar9287_set_txpower(
- regulatory->max_power_level = ratesArray[i];
- }
-
-+ ath9k_hw_update_regulatory_maxpower(ah);
-+
- if (test)
- return;
-
---- a/drivers/net/wireless/ath/ath9k/hw.c
-+++ b/drivers/net/wireless/ath/ath9k/hw.c
-@@ -191,6 +191,22 @@ bool ath9k_hw_wait(struct ath_hw *ah, u3
- }
- EXPORT_SYMBOL(ath9k_hw_wait);
-
-+void ath9k_hw_synth_delay(struct ath_hw *ah, struct ath9k_channel *chan,
-+ int hw_delay)
-+{
-+ if (IS_CHAN_B(chan))
-+ hw_delay = (4 * hw_delay) / 22;
-+ else
-+ hw_delay /= 10;
-+
-+ if (IS_CHAN_HALF_RATE(chan))
-+ hw_delay *= 2;
-+ else if (IS_CHAN_QUARTER_RATE(chan))
-+ hw_delay *= 4;
-+
-+ udelay(hw_delay + BASE_ACTIVATE_DELAY);
-+}
-+
- void ath9k_hw_write_array(struct ath_hw *ah, struct ar5416IniArray *array,
- int column, unsigned int *writecnt)
- {
-@@ -1020,7 +1036,7 @@ void ath9k_hw_init_global_settings(struc
- struct ath_common *common = ath9k_hw_common(ah);
- struct ieee80211_conf *conf = &common->hw->conf;
- const struct ath9k_channel *chan = ah->curchan;
-- int acktimeout, ctstimeout;
-+ int acktimeout, ctstimeout, ack_offset = 0;
- int slottime;
- int sifstime;
- int rx_lat = 0, tx_lat = 0, eifs = 0;
-@@ -1041,6 +1057,11 @@ void ath9k_hw_init_global_settings(struc
- rx_lat = 37;
- tx_lat = 54;
-
-+ if (IS_CHAN_5GHZ(chan))
-+ sifstime = 16;
-+ else
-+ sifstime = 10;
-+
- if (IS_CHAN_HALF_RATE(chan)) {
- eifs = 175;
- rx_lat *= 2;
-@@ -1048,8 +1069,9 @@ void ath9k_hw_init_global_settings(struc
- if (IS_CHAN_A_FAST_CLOCK(ah, chan))
- tx_lat += 11;
-
-+ sifstime *= 2;
-+ ack_offset = 16;
- slottime = 13;
-- sifstime = 32;
- } else if (IS_CHAN_QUARTER_RATE(chan)) {
- eifs = 340;
- rx_lat = (rx_lat * 4) - 1;
-@@ -1057,8 +1079,9 @@ void ath9k_hw_init_global_settings(struc
- if (IS_CHAN_A_FAST_CLOCK(ah, chan))
- tx_lat += 22;
-
-+ sifstime *= 4;
-+ ack_offset = 32;
- slottime = 21;
-- sifstime = 64;
- } else {
- if (AR_SREV_9287(ah) && AR_SREV_9287_13_OR_LATER(ah)) {
- eifs = AR_D_GBL_IFS_EIFS_ASYNC_FIFO;
-@@ -1072,14 +1095,10 @@ void ath9k_hw_init_global_settings(struc
- tx_lat = MS(reg, AR_USEC_TX_LAT);
-
- slottime = ah->slottime;
-- if (IS_CHAN_5GHZ(chan))
-- sifstime = 16;
-- else
-- sifstime = 10;
- }
-
- /* As defined by IEEE 802.11-2007 17.3.8.6 */
-- acktimeout = slottime + sifstime + 3 * ah->coverage_class;
-+ acktimeout = slottime + sifstime + 3 * ah->coverage_class + ack_offset;
- ctstimeout = acktimeout;
-
- /*
-@@ -1089,7 +1108,8 @@ void ath9k_hw_init_global_settings(struc
- * BA frames in some implementations, but it has been found to fix ACK
- * timeout issues in other cases as well.
- */
-- if (conf->channel && conf->channel->band == IEEE80211_BAND_2GHZ) {
-+ if (conf->channel && conf->channel->band == IEEE80211_BAND_2GHZ &&
-+ !IS_CHAN_HALF_RATE(chan) && !IS_CHAN_QUARTER_RATE(chan)) {
- acktimeout += 64 - sifstime - ah->slottime;
- ctstimeout += 48 - sifstime - ah->slottime;
- }
-@@ -1469,6 +1489,10 @@ static bool ath9k_hw_channel_change(stru
- CHANNEL_5GHZ));
- mode_diff = (chan->chanmode != ah->curchan->chanmode);
-
-+ if ((ah->curchan->channelFlags | chan->channelFlags) &
-+ (CHANNEL_HALF | CHANNEL_QUARTER))
-+ return false;
-+
- for (qnum = 0; qnum < AR_NUM_QCU; qnum++) {
- if (ath9k_hw_numtxpending(ah, qnum)) {
- ath_dbg(common, QUEUE,
-@@ -1502,7 +1526,7 @@ static bool ath9k_hw_channel_change(stru
- return false;
- }
- ath9k_hw_set_clockrate(ah);
-- ath9k_hw_apply_txpower(ah, chan);
-+ ath9k_hw_apply_txpower(ah, chan, false);
- ath9k_hw_rfbus_done(ah);
-
- if (IS_CHAN_OFDM(chan) || IS_CHAN_HT(chan))
-@@ -2773,7 +2797,8 @@ static int get_antenna_gain(struct ath_h
- return ah->eep_ops->get_eeprom(ah, gain_param);
- }
-
--void ath9k_hw_apply_txpower(struct ath_hw *ah, struct ath9k_channel *chan)
-+void ath9k_hw_apply_txpower(struct ath_hw *ah, struct ath9k_channel *chan,
-+ bool test)
- {
- struct ath_regulatory *reg = ath9k_hw_regulatory(ah);
- struct ieee80211_channel *channel;
-@@ -2794,7 +2819,7 @@ void ath9k_hw_apply_txpower(struct ath_h
-
- ah->eep_ops->set_txpower(ah, chan,
- ath9k_regd_get_ctl(reg, chan),
-- ant_reduction, new_pwr, false);
-+ ant_reduction, new_pwr, test);
- }
-
- void ath9k_hw_set_txpowerlimit(struct ath_hw *ah, u32 limit, bool test)
-@@ -2807,7 +2832,7 @@ void ath9k_hw_set_txpowerlimit(struct at
- if (test)
- channel->max_power = MAX_RATE_POWER / 2;
-
-- ath9k_hw_apply_txpower(ah, chan);
-+ ath9k_hw_apply_txpower(ah, chan, test);
-
- if (test)
- channel->max_power = DIV_ROUND_UP(reg->max_power_level, 2);
---- a/drivers/net/wireless/ath/ath9k/hw.h
-+++ b/drivers/net/wireless/ath/ath9k/hw.h
-@@ -923,6 +923,8 @@ void ath9k_hw_set_gpio(struct ath_hw *ah
- void ath9k_hw_setantenna(struct ath_hw *ah, u32 antenna);
-
- /* General Operation */
-+void ath9k_hw_synth_delay(struct ath_hw *ah, struct ath9k_channel *chan,
-+ int hw_delay);
- bool ath9k_hw_wait(struct ath_hw *ah, u32 reg, u32 mask, u32 val, u32 timeout);
- void ath9k_hw_write_array(struct ath_hw *ah, struct ar5416IniArray *array,
- int column, unsigned int *writecnt);
-@@ -982,7 +984,8 @@ void ath9k_hw_name(struct ath_hw *ah, ch
- /* PHY */
- void ath9k_hw_get_delta_slope_vals(struct ath_hw *ah, u32 coef_scaled,
- u32 *coef_mantissa, u32 *coef_exponent);
--void ath9k_hw_apply_txpower(struct ath_hw *ah, struct ath9k_channel *chan);
-+void ath9k_hw_apply_txpower(struct ath_hw *ah, struct ath9k_channel *chan,
-+ bool test);
-
- /*
- * Code Specific to AR5008, AR9001 or AR9002,
---- a/drivers/net/wireless/ath/ath9k/init.c
-+++ b/drivers/net/wireless/ath/ath9k/init.c
-@@ -647,6 +647,24 @@ void ath9k_reload_chainmask_settings(str
- setup_ht_cap(sc, &sc->sbands[IEEE80211_BAND_5GHZ].ht_cap);
- }
-
-+static const struct ieee80211_iface_limit if_limits[] = {
-+ { .max = 2048, .types = BIT(NL80211_IFTYPE_STATION) |
-+ BIT(NL80211_IFTYPE_P2P_CLIENT) |
-+ BIT(NL80211_IFTYPE_WDS) },
-+ { .max = 8, .types =
-+#ifdef CONFIG_MAC80211_MESH
-+ BIT(NL80211_IFTYPE_MESH_POINT) |
-+#endif
-+ BIT(NL80211_IFTYPE_AP) |
-+ BIT(NL80211_IFTYPE_P2P_GO) },
-+};
-+
-+static const struct ieee80211_iface_combination if_comb = {
-+ .limits = if_limits,
-+ .n_limits = ARRAY_SIZE(if_limits),
-+ .max_interfaces = 2048,
-+ .num_different_channels = 1,
-+};
-
- void ath9k_set_hw_capab(struct ath_softc *sc, struct ieee80211_hw *hw)
- {
-@@ -676,6 +694,9 @@ void ath9k_set_hw_capab(struct ath_softc
- BIT(NL80211_IFTYPE_ADHOC) |
- BIT(NL80211_IFTYPE_MESH_POINT);
-
-+ hw->wiphy->iface_combinations = &if_comb;
-+ hw->wiphy->n_iface_combinations = 1;
-+
- if (AR_SREV_5416(sc->sc_ah))
- hw->wiphy->flags &= ~WIPHY_FLAG_PS_ON_BY_DEFAULT;
-
---- a/drivers/net/wireless/ath/ath9k/mac.c
-+++ b/drivers/net/wireless/ath/ath9k/mac.c
-@@ -133,8 +133,16 @@ EXPORT_SYMBOL(ath9k_hw_updatetxtriglevel
-
- void ath9k_hw_abort_tx_dma(struct ath_hw *ah)
- {
-+ int maxdelay = 1000;
- int i, q;
-
-+ if (ah->curchan) {
-+ if (IS_CHAN_HALF_RATE(ah->curchan))
-+ maxdelay *= 2;
-+ else if (IS_CHAN_QUARTER_RATE(ah->curchan))
-+ maxdelay *= 4;
-+ }
-+
- REG_WRITE(ah, AR_Q_TXD, AR_Q_TXD_M);
-
- REG_SET_BIT(ah, AR_PCU_MISC, AR_PCU_FORCE_QUIET_COLL | AR_PCU_CLEAR_VMF);
-@@ -142,7 +150,7 @@ void ath9k_hw_abort_tx_dma(struct ath_hw
- REG_SET_BIT(ah, AR_D_GBL_IFS_MISC, AR_D_GBL_IFS_MISC_IGNORE_BACKOFF);
-
- for (q = 0; q < AR_NUM_QCU; q++) {
-- for (i = 0; i < 1000; i++) {
-+ for (i = 0; i < maxdelay; i++) {
- if (i)
- udelay(5);
-