Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4fa00437 authored by Sujith's avatar Sujith Committed by John W. Linville
Browse files

mac80211: Fix HT rate control configuration



Handling HT configuration changes involved setting the channel
with the new HT parameters and then issuing a rate_update()
notification to the driver.

This behavior changed after the off-channel changes. Now, the channel
is not updated with the new HT params in enable_ht() - instead, it
is now done when the scan work terminates. This results in the driver
depending on stale information, defaulting to non-HT mode always.

Fix this by passing the new channel type to the driver.

Cc: stable@kernel.org
Signed-off-by: default avatarSujith <Sujith.Manoharan@atheros.com>
Signed-off-by: default avatarJohn W. Linville <linville@tuxdriver.com>
parent b08dfd04
Loading
Loading
Loading
Loading
+3 −3
Original line number Original line Diff line number Diff line
@@ -1323,7 +1323,7 @@ static void ath_rate_init(void *priv, struct ieee80211_supported_band *sband,


static void ath_rate_update(void *priv, struct ieee80211_supported_band *sband,
static void ath_rate_update(void *priv, struct ieee80211_supported_band *sband,
			    struct ieee80211_sta *sta, void *priv_sta,
			    struct ieee80211_sta *sta, void *priv_sta,
			    u32 changed)
			    u32 changed, enum nl80211_channel_type oper_chan_type)
{
{
	struct ath_softc *sc = priv;
	struct ath_softc *sc = priv;
	struct ath_rate_priv *ath_rc_priv = priv_sta;
	struct ath_rate_priv *ath_rc_priv = priv_sta;
@@ -1340,8 +1340,8 @@ static void ath_rate_update(void *priv, struct ieee80211_supported_band *sband,
		if (sc->sc_ah->opmode != NL80211_IFTYPE_STATION)
		if (sc->sc_ah->opmode != NL80211_IFTYPE_STATION)
			return;
			return;


		if (sc->hw->conf.channel_type == NL80211_CHAN_HT40MINUS ||
		if (oper_chan_type == NL80211_CHAN_HT40MINUS ||
		    sc->hw->conf.channel_type == NL80211_CHAN_HT40PLUS)
		    oper_chan_type == NL80211_CHAN_HT40PLUS)
			oper_cw40 = true;
			oper_cw40 = true;


		oper_sgi40 = (sta->ht_cap.cap & IEEE80211_HT_CAP_SGI_40) ?
		oper_sgi40 = (sta->ht_cap.cap & IEEE80211_HT_CAP_SGI_40) ?
+2 −1
Original line number Original line Diff line number Diff line
@@ -2426,7 +2426,8 @@ struct rate_control_ops {
			  struct ieee80211_sta *sta, void *priv_sta);
			  struct ieee80211_sta *sta, void *priv_sta);
	void (*rate_update)(void *priv, struct ieee80211_supported_band *sband,
	void (*rate_update)(void *priv, struct ieee80211_supported_band *sband,
			    struct ieee80211_sta *sta,
			    struct ieee80211_sta *sta,
			    void *priv_sta, u32 changed);
			    void *priv_sta, u32 changed,
			    enum nl80211_channel_type oper_chan_type);
	void (*free_sta)(void *priv, struct ieee80211_sta *sta,
	void (*free_sta)(void *priv, struct ieee80211_sta *sta,
			 void *priv_sta);
			 void *priv_sta);


+2 −1
Original line number Original line Diff line number Diff line
@@ -177,7 +177,8 @@ static u32 ieee80211_enable_ht(struct ieee80211_sub_if_data *sdata,
		sta = sta_info_get(sdata, bssid);
		sta = sta_info_get(sdata, bssid);
		if (sta)
		if (sta)
			rate_control_rate_update(local, sband, sta,
			rate_control_rate_update(local, sband, sta,
						 IEEE80211_RC_HT_CHANGED);
						 IEEE80211_RC_HT_CHANGED,
						 local->oper_channel_type);
		rcu_read_unlock();
		rcu_read_unlock();
        }
        }


+3 −2
Original line number Original line Diff line number Diff line
@@ -66,7 +66,8 @@ static inline void rate_control_rate_init(struct sta_info *sta)


static inline void rate_control_rate_update(struct ieee80211_local *local,
static inline void rate_control_rate_update(struct ieee80211_local *local,
				    struct ieee80211_supported_band *sband,
				    struct ieee80211_supported_band *sband,
				    struct sta_info *sta, u32 changed)
				    struct sta_info *sta, u32 changed,
				    enum nl80211_channel_type oper_chan_type)
{
{
	struct rate_control_ref *ref = local->rate_ctrl;
	struct rate_control_ref *ref = local->rate_ctrl;
	struct ieee80211_sta *ista = &sta->sta;
	struct ieee80211_sta *ista = &sta->sta;
@@ -74,7 +75,7 @@ static inline void rate_control_rate_update(struct ieee80211_local *local,


	if (ref && ref->ops->rate_update)
	if (ref && ref->ops->rate_update)
		ref->ops->rate_update(ref->priv, sband, ista,
		ref->ops->rate_update(ref->priv, sband, ista,
				      priv_sta, changed);
				      priv_sta, changed, oper_chan_type);
}
}


static inline void *rate_control_alloc_sta(struct rate_control_ref *ref,
static inline void *rate_control_alloc_sta(struct rate_control_ref *ref,