Fix kern/196290 - don't announce 11n HTINFO rates if the channel is

configured as 11b.

This came up when debugging other issues surrounding scanning and
channel modes.

What's going on:

* The VAP comes up as an 11b VAP, but on an 11n capable NIC;
* .. it announces HTINFO and MCS rates;
* The AP thinks it's an 11n capable device and transmits 11n frames
  to the STA;
* But the STA is in 11b mode, and thus doesn't receive/ACK the frames.

It didn't happen for the ath(4) devices as the AR5416/AR9300 HALs
unconditionally enable MCS frame reception, even if the channel
mode is not 11n.  But the Intel NICs are configured in 11b/11a/11g
modes when doing those, even if 11n is enabled and available.

So, don't announce 11n capabilities if the VAP isn't on an 11n
channel when sending management assocation request / reassociation
request frames.

TODO:

* Lots more testing - 11n should be "upgraded" after association,
  and I just want to make sure I haven't broken 11n upgrade.
  I shouldn't have - this is only happening for /sending/ association
  requests, which APs aren't doing.

Tested:

* ath(4) APs (AR9331, AR7161+AR9280, AR934x)
* AR5416, STA mode
* Intel 5100, STA mode

PR:		kern/196290
This commit is contained in:
adrian 2015-02-27 04:45:47 +00:00
parent ace438b760
commit d43da4a89c

View File

@ -2322,18 +2322,33 @@ ieee80211_send_mgmt(struct ieee80211_node *ni, int type, int arg)
ic->ic_curchan);
frm = ieee80211_add_supportedchannels(frm, ic);
}
/*
* Check the channel - we may be using an 11n NIC with an
* 11n capable station, but we're configured to be an 11b
* channel.
*/
if ((vap->iv_flags_ht & IEEE80211_FHT_HT) &&
IEEE80211_IS_CHAN_HT(ni->ni_chan) &&
ni->ni_ies.htcap_ie != NULL &&
ni->ni_ies.htcap_ie[0] == IEEE80211_ELEMID_HTCAP)
ni->ni_ies.htcap_ie[0] == IEEE80211_ELEMID_HTCAP) {
frm = ieee80211_add_htcap(frm, ni);
}
frm = ieee80211_add_wpa(frm, vap);
if ((ic->ic_flags & IEEE80211_F_WME) &&
ni->ni_ies.wme_ie != NULL)
frm = ieee80211_add_wme_info(frm, &ic->ic_wme);
/*
* Same deal - only send HT info if we're on an 11n
* capable channel.
*/
if ((vap->iv_flags_ht & IEEE80211_FHT_HT) &&
IEEE80211_IS_CHAN_HT(ni->ni_chan) &&
ni->ni_ies.htcap_ie != NULL &&
ni->ni_ies.htcap_ie[0] == IEEE80211_ELEMID_VENDOR)
ni->ni_ies.htcap_ie[0] == IEEE80211_ELEMID_VENDOR) {
frm = ieee80211_add_htcap_vendor(frm, ni);
}
#ifdef IEEE80211_SUPPORT_SUPERG
if (IEEE80211_ATH_CAP(vap, ni, IEEE80211_F_ATHEROS)) {
frm = ieee80211_add_ath(frm,