OSDN Git Service

mac80211: use HE 6 GHz band capability and pass it to the driver
authorJohannes Berg <johannes.berg@intel.com>
Thu, 28 May 2020 19:34:38 +0000 (21:34 +0200)
committerJohannes Berg <johannes.berg@intel.com>
Sun, 31 May 2020 09:27:03 +0000 (11:27 +0200)
In order to handle 6 GHz AP side, take the HE 6 GHz band capability
data and pass it to the driver (which needs it for A-MPDU spacing
and A-MPDU length).

Link: https://lore.kernel.org/r/1589399105-25472-6-git-send-email-rmanohar@codeaurora.org
Co-developed-by: Rajkumar Manoharan <rmanohar@codeaurora.org>
Signed-off-by: Rajkumar Manoharan <rmanohar@codeaurora.org>
Link: https://lore.kernel.org/r/20200528213443.784e4890d82f.I5f1230d5ab27e84e7bbe88e3645b24ea15a0c146@changeid
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
include/net/mac80211.h
net/mac80211/cfg.c
net/mac80211/he.c
net/mac80211/ieee80211_i.h
net/mac80211/mesh_plink.c
net/mac80211/mlme.c

index 7cb7124..11d5610 100644 (file)
@@ -7,7 +7,7 @@
  * Copyright 2007-2010 Johannes Berg <johannes@sipsolutions.net>
  * Copyright 2013-2014  Intel Mobile Communications GmbH
  * Copyright (C) 2015 - 2017 Intel Deutschland GmbH
- * Copyright (C) 2018 - 2019 Intel Corporation
+ * Copyright (C) 2018 - 2020 Intel Corporation
  */
 
 #ifndef MAC80211_H
@@ -1977,6 +1977,7 @@ struct ieee80211_sta_txpwr {
  * @ht_cap: HT capabilities of this STA; restricted to our own capabilities
  * @vht_cap: VHT capabilities of this STA; restricted to our own capabilities
  * @he_cap: HE capabilities of this STA
+ * @he_6ghz_capa: on 6 GHz, holds the HE 6 GHz band capabilities
  * @max_rx_aggregation_subframes: maximal amount of frames in a single AMPDU
  *     that this station is allowed to transmit to us.
  *     Can be modified by driver.
@@ -2016,6 +2017,7 @@ struct ieee80211_sta {
        struct ieee80211_sta_ht_cap ht_cap;
        struct ieee80211_sta_vht_cap vht_cap;
        struct ieee80211_sta_he_cap he_cap;
+       struct ieee80211_he_6ghz_capa he_6ghz_capa;
        u16 max_rx_aggregation_subframes;
        bool wme;
        u8 uapsd_queues;
index 06a2b76..90a07d0 100644 (file)
@@ -1520,7 +1520,9 @@ static int sta_apply_parameters(struct ieee80211_local *local,
        if (params->he_capa)
                ieee80211_he_cap_ie_to_sta_he_cap(sdata, sband,
                                                  (void *)params->he_capa,
-                                                 params->he_capa_len, sta);
+                                                 params->he_capa_len,
+                                                 (void *)params->he_6ghz_capa,
+                                                 sta);
 
        if (params->opmode_notif_used) {
                /* returned value is only needed for rc update, but the
index f520552..cc26f23 100644 (file)
@@ -8,10 +8,55 @@
 
 #include "ieee80211_i.h"
 
+static void
+ieee80211_update_from_he_6ghz_capa(const struct ieee80211_he_6ghz_capa *he_6ghz_capa,
+                                  struct sta_info *sta)
+{
+       enum ieee80211_smps_mode smps_mode;
+
+       if (sta->sdata->vif.type == NL80211_IFTYPE_AP ||
+           sta->sdata->vif.type == NL80211_IFTYPE_AP_VLAN) {
+               switch (le16_get_bits(he_6ghz_capa->capa,
+                                     IEEE80211_HE_6GHZ_CAP_SM_PS)) {
+               case WLAN_HT_CAP_SM_PS_INVALID:
+               case WLAN_HT_CAP_SM_PS_STATIC:
+                       smps_mode = IEEE80211_SMPS_STATIC;
+                       break;
+               case WLAN_HT_CAP_SM_PS_DYNAMIC:
+                       smps_mode = IEEE80211_SMPS_DYNAMIC;
+                       break;
+               case WLAN_HT_CAP_SM_PS_DISABLED:
+                       smps_mode = IEEE80211_SMPS_OFF;
+                       break;
+               }
+
+               sta->sta.smps_mode = smps_mode;
+       } else {
+               sta->sta.smps_mode = IEEE80211_SMPS_OFF;
+       }
+
+       switch (le16_get_bits(he_6ghz_capa->capa,
+                             IEEE80211_HE_6GHZ_CAP_MAX_MPDU_LEN)) {
+       case IEEE80211_VHT_CAP_MAX_MPDU_LENGTH_11454:
+               sta->sta.max_amsdu_len = IEEE80211_MAX_MPDU_LEN_VHT_11454;
+               break;
+       case IEEE80211_VHT_CAP_MAX_MPDU_LENGTH_7991:
+               sta->sta.max_amsdu_len = IEEE80211_MAX_MPDU_LEN_VHT_7991;
+               break;
+       case IEEE80211_VHT_CAP_MAX_MPDU_LENGTH_3895:
+       default:
+               sta->sta.max_amsdu_len = IEEE80211_MAX_MPDU_LEN_VHT_3895;
+               break;
+       }
+
+       sta->sta.he_6ghz_capa = *he_6ghz_capa;
+}
+
 void
 ieee80211_he_cap_ie_to_sta_he_cap(struct ieee80211_sub_if_data *sdata,
                                  struct ieee80211_supported_band *sband,
                                  const u8 *he_cap_ie, u8 he_cap_len,
+                                 const struct ieee80211_he_6ghz_capa *he_6ghz_capa,
                                  struct sta_info *sta)
 {
        struct ieee80211_sta_he_cap *he_cap = &sta->sta.he_cap;
@@ -53,6 +98,9 @@ ieee80211_he_cap_ie_to_sta_he_cap(struct ieee80211_sub_if_data *sdata,
 
        sta->cur_max_bandwidth = ieee80211_sta_cap_rx_bw(sta);
        sta->sta.bandwidth = ieee80211_sta_cur_vht_bw(sta);
+
+       if (sband->band == NL80211_BAND_6GHZ && he_6ghz_capa)
+               ieee80211_update_from_he_6ghz_capa(he_6ghz_capa, sta);
 }
 
 void
index 6cac5bf..24dc1fd 100644 (file)
@@ -1899,6 +1899,7 @@ void
 ieee80211_he_cap_ie_to_sta_he_cap(struct ieee80211_sub_if_data *sdata,
                                  struct ieee80211_supported_band *sband,
                                  const u8 *he_cap_ie, u8 he_cap_len,
+                                 const struct ieee80211_he_6ghz_capa *he_6ghz_capa,
                                  struct sta_info *sta);
 void
 ieee80211_he_spr_ie_to_bss_conf(struct ieee80211_vif *vif,
index fbbfc5d..798e4b6 100644 (file)
@@ -444,7 +444,9 @@ static void mesh_sta_info_init(struct ieee80211_sub_if_data *sdata,
                                            elems->vht_cap_elem, sta);
 
        ieee80211_he_cap_ie_to_sta_he_cap(sdata, sband, elems->he_cap,
-                                         elems->he_cap_len, sta);
+                                         elems->he_cap_len,
+                                         elems->he_6ghz_capa,
+                                         sta);
 
        if (bw != sta->sta.bandwidth)
                changed |= IEEE80211_RC_BW_CHANGED;
index c534cd1..8a37089 100644 (file)
@@ -3430,6 +3430,7 @@ static bool ieee80211_assoc_success(struct ieee80211_sub_if_data *sdata,
                ieee80211_he_cap_ie_to_sta_he_cap(sdata, sband,
                                                  elems->he_cap,
                                                  elems->he_cap_len,
+                                                 elems->he_6ghz_capa,
                                                  sta);
 
                bss_conf->he_support = sta->sta.he_cap.has_he;