aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArik Nemtsov <arik@wizery.com>2014-03-23 10:18:40 -0400
committerEmmanuel Grumbach <emmanuel.grumbach@intel.com>2015-03-12 03:57:23 -0400
commit770ceda6158b00cd872e0c6713f4f65320c5ff8d (patch)
treecca4697875f03d573cfe1642d0055d30172f7577
parentaf45a9003f1f14af24804f7747f14238e8d51163 (diff)
iwlwifi: mvm: consider LAR support during NVM parse
Register to cfg80211 with all channels enabled when LAR is supported. Appropriate channels will later be disabled when a specific regulatory domain is defined. Signed-off-by: Arik Nemtsov <arikx.nemtsov@intel.com> Signed-off-by: Emmanuel Grumbach <emmanuel.grumbach@intel.com>
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-nvm-parse.c110
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-nvm-parse.h3
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/nvm.c3
3 files changed, 67 insertions, 49 deletions
diff --git a/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c b/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c
index d8d9a97ff14c..a49666f529f0 100644
--- a/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c
+++ b/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c
@@ -201,9 +201,53 @@ enum iwl_nvm_channel_flags {
201#define CHECK_AND_PRINT_I(x) \ 201#define CHECK_AND_PRINT_I(x) \
202 ((ch_flags & NVM_CHANNEL_##x) ? # x " " : "") 202 ((ch_flags & NVM_CHANNEL_##x) ? # x " " : "")
203 203
204static u32 iwl_get_channel_flags(u8 ch_num, int ch_idx, bool is_5ghz,
205 u16 nvm_flags)
206{
207 u32 flags = IEEE80211_CHAN_NO_HT40;
208
209 if (!is_5ghz && (nvm_flags & NVM_CHANNEL_40MHZ)) {
210 if (ch_num <= LAST_2GHZ_HT_PLUS)
211 flags &= ~IEEE80211_CHAN_NO_HT40PLUS;
212 if (ch_num >= FIRST_2GHZ_HT_MINUS)
213 flags &= ~IEEE80211_CHAN_NO_HT40MINUS;
214 } else if (ch_num <= LAST_5GHZ_HT && (nvm_flags & NVM_CHANNEL_40MHZ)) {
215 if ((ch_idx - NUM_2GHZ_CHANNELS) % 2 == 0)
216 flags &= ~IEEE80211_CHAN_NO_HT40PLUS;
217 else
218 flags &= ~IEEE80211_CHAN_NO_HT40MINUS;
219 }
220 if (!(nvm_flags & NVM_CHANNEL_80MHZ))
221 flags |= IEEE80211_CHAN_NO_80MHZ;
222 if (!(nvm_flags & NVM_CHANNEL_160MHZ))
223 flags |= IEEE80211_CHAN_NO_160MHZ;
224
225 if (!(nvm_flags & NVM_CHANNEL_IBSS))
226 flags |= IEEE80211_CHAN_NO_IR;
227
228 if (!(nvm_flags & NVM_CHANNEL_ACTIVE))
229 flags |= IEEE80211_CHAN_NO_IR;
230
231 if (nvm_flags & NVM_CHANNEL_RADAR)
232 flags |= IEEE80211_CHAN_RADAR;
233
234 if (nvm_flags & NVM_CHANNEL_INDOOR_ONLY)
235 flags |= IEEE80211_CHAN_INDOOR_ONLY;
236
237 /* Set the GO concurrent flag only in case that NO_IR is set.
238 * Otherwise it is meaningless
239 */
240 if ((nvm_flags & NVM_CHANNEL_GO_CONCURRENT) &&
241 (flags & IEEE80211_CHAN_NO_IR))
242 flags |= IEEE80211_CHAN_GO_CONCURRENT;
243
244 return flags;
245}
246
204static int iwl_init_channel_map(struct device *dev, const struct iwl_cfg *cfg, 247static int iwl_init_channel_map(struct device *dev, const struct iwl_cfg *cfg,
205 struct iwl_nvm_data *data, 248 struct iwl_nvm_data *data,
206 const __le16 * const nvm_ch_flags) 249 const __le16 * const nvm_ch_flags,
250 bool lar_supported)
207{ 251{
208 int ch_idx; 252 int ch_idx;
209 int n_channels = 0; 253 int n_channels = 0;
@@ -230,7 +274,7 @@ static int iwl_init_channel_map(struct device *dev, const struct iwl_cfg *cfg,
230 !data->sku_cap_band_52GHz_enable) 274 !data->sku_cap_band_52GHz_enable)
231 ch_flags &= ~NVM_CHANNEL_VALID; 275 ch_flags &= ~NVM_CHANNEL_VALID;
232 276
233 if (!(ch_flags & NVM_CHANNEL_VALID)) { 277 if (!lar_supported && !(ch_flags & NVM_CHANNEL_VALID)) {
234 IWL_DEBUG_EEPROM(dev, 278 IWL_DEBUG_EEPROM(dev,
235 "Ch. %d Flags %x [%sGHz] - No traffic\n", 279 "Ch. %d Flags %x [%sGHz] - No traffic\n",
236 nvm_chan[ch_idx], 280 nvm_chan[ch_idx],
@@ -250,45 +294,6 @@ static int iwl_init_channel_map(struct device *dev, const struct iwl_cfg *cfg,
250 ieee80211_channel_to_frequency( 294 ieee80211_channel_to_frequency(
251 channel->hw_value, channel->band); 295 channel->hw_value, channel->band);
252 296
253 /* TODO: Need to be dependent to the NVM */
254 channel->flags = IEEE80211_CHAN_NO_HT40;
255 if (ch_idx < num_2ghz_channels &&
256 (ch_flags & NVM_CHANNEL_40MHZ)) {
257 if (nvm_chan[ch_idx] <= LAST_2GHZ_HT_PLUS)
258 channel->flags &= ~IEEE80211_CHAN_NO_HT40PLUS;
259 if (nvm_chan[ch_idx] >= FIRST_2GHZ_HT_MINUS)
260 channel->flags &= ~IEEE80211_CHAN_NO_HT40MINUS;
261 } else if (nvm_chan[ch_idx] <= LAST_5GHZ_HT &&
262 (ch_flags & NVM_CHANNEL_40MHZ)) {
263 if ((ch_idx - num_2ghz_channels) % 2 == 0)
264 channel->flags &= ~IEEE80211_CHAN_NO_HT40PLUS;
265 else
266 channel->flags &= ~IEEE80211_CHAN_NO_HT40MINUS;
267 }
268 if (!(ch_flags & NVM_CHANNEL_80MHZ))
269 channel->flags |= IEEE80211_CHAN_NO_80MHZ;
270 if (!(ch_flags & NVM_CHANNEL_160MHZ))
271 channel->flags |= IEEE80211_CHAN_NO_160MHZ;
272
273 if (!(ch_flags & NVM_CHANNEL_IBSS))
274 channel->flags |= IEEE80211_CHAN_NO_IR;
275
276 if (!(ch_flags & NVM_CHANNEL_ACTIVE))
277 channel->flags |= IEEE80211_CHAN_NO_IR;
278
279 if (ch_flags & NVM_CHANNEL_RADAR)
280 channel->flags |= IEEE80211_CHAN_RADAR;
281
282 if (ch_flags & NVM_CHANNEL_INDOOR_ONLY)
283 channel->flags |= IEEE80211_CHAN_INDOOR_ONLY;
284
285 /* Set the GO concurrent flag only in case that NO_IR is set.
286 * Otherwise it is meaningless
287 */
288 if ((ch_flags & NVM_CHANNEL_GO_CONCURRENT) &&
289 (channel->flags & IEEE80211_CHAN_NO_IR))
290 channel->flags |= IEEE80211_CHAN_GO_CONCURRENT;
291
292 /* Initialize regulatory-based run-time data */ 297 /* Initialize regulatory-based run-time data */
293 298
294 /* 299 /*
@@ -297,6 +302,15 @@ static int iwl_init_channel_map(struct device *dev, const struct iwl_cfg *cfg,
297 */ 302 */
298 channel->max_power = IWL_DEFAULT_MAX_TX_POWER; 303 channel->max_power = IWL_DEFAULT_MAX_TX_POWER;
299 is_5ghz = channel->band == IEEE80211_BAND_5GHZ; 304 is_5ghz = channel->band == IEEE80211_BAND_5GHZ;
305
306 /* don't put limitations in case we're using LAR */
307 if (!lar_supported)
308 channel->flags = iwl_get_channel_flags(nvm_chan[ch_idx],
309 ch_idx, is_5ghz,
310 ch_flags);
311 else
312 channel->flags = 0;
313
300 IWL_DEBUG_EEPROM(dev, 314 IWL_DEBUG_EEPROM(dev,
301 "Ch. %d [%sGHz] %s%s%s%s%s%s%s(0x%02x %ddBm): Ad-Hoc %ssupported\n", 315 "Ch. %d [%sGHz] %s%s%s%s%s%s%s(0x%02x %ddBm): Ad-Hoc %ssupported\n",
302 channel->hw_value, 316 channel->hw_value,
@@ -371,7 +385,7 @@ static void iwl_init_vht_hw_capab(const struct iwl_cfg *cfg,
371static void iwl_init_sbands(struct device *dev, const struct iwl_cfg *cfg, 385static void iwl_init_sbands(struct device *dev, const struct iwl_cfg *cfg,
372 struct iwl_nvm_data *data, 386 struct iwl_nvm_data *data,
373 const __le16 *ch_section, bool enable_vht, 387 const __le16 *ch_section, bool enable_vht,
374 u8 tx_chains, u8 rx_chains) 388 u8 tx_chains, u8 rx_chains, bool lar_supported)
375{ 389{
376 int n_channels; 390 int n_channels;
377 int n_used = 0; 391 int n_used = 0;
@@ -380,11 +394,12 @@ static void iwl_init_sbands(struct device *dev, const struct iwl_cfg *cfg,
380 if (cfg->device_family != IWL_DEVICE_FAMILY_8000) 394 if (cfg->device_family != IWL_DEVICE_FAMILY_8000)
381 n_channels = iwl_init_channel_map( 395 n_channels = iwl_init_channel_map(
382 dev, cfg, data, 396 dev, cfg, data,
383 &ch_section[NVM_CHANNELS]); 397 &ch_section[NVM_CHANNELS], lar_supported);
384 else 398 else
385 n_channels = iwl_init_channel_map( 399 n_channels = iwl_init_channel_map(
386 dev, cfg, data, 400 dev, cfg, data,
387 &ch_section[NVM_CHANNELS_FAMILY_8000]); 401 &ch_section[NVM_CHANNELS_FAMILY_8000],
402 lar_supported);
388 403
389 sband = &data->bands[IEEE80211_BAND_2GHZ]; 404 sband = &data->bands[IEEE80211_BAND_2GHZ];
390 sband->band = IEEE80211_BAND_2GHZ; 405 sband->band = IEEE80211_BAND_2GHZ;
@@ -571,7 +586,8 @@ struct iwl_nvm_data *
571iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg, 586iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg,
572 const __le16 *nvm_hw, const __le16 *nvm_sw, 587 const __le16 *nvm_hw, const __le16 *nvm_sw,
573 const __le16 *nvm_calib, const __le16 *regulatory, 588 const __le16 *nvm_calib, const __le16 *regulatory,
574 const __le16 *mac_override, u8 tx_chains, u8 rx_chains) 589 const __le16 *mac_override, u8 tx_chains, u8 rx_chains,
590 bool lar_supported)
575{ 591{
576 struct iwl_nvm_data *data; 592 struct iwl_nvm_data *data;
577 u32 sku; 593 u32 sku;
@@ -627,7 +643,7 @@ iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg,
627 643
628 iwl_init_sbands(dev, cfg, data, nvm_sw, 644 iwl_init_sbands(dev, cfg, data, nvm_sw,
629 sku & NVM_SKU_CAP_11AC_ENABLE, tx_chains, 645 sku & NVM_SKU_CAP_11AC_ENABLE, tx_chains,
630 rx_chains); 646 rx_chains, lar_supported);
631 } else { 647 } else {
632 /* MAC address in family 8000 */ 648 /* MAC address in family 8000 */
633 iwl_set_hw_address_family_8000(dev, cfg, data, mac_override, 649 iwl_set_hw_address_family_8000(dev, cfg, data, mac_override,
@@ -635,7 +651,7 @@ iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg,
635 651
636 iwl_init_sbands(dev, cfg, data, regulatory, 652 iwl_init_sbands(dev, cfg, data, regulatory,
637 sku & NVM_SKU_CAP_11AC_ENABLE, tx_chains, 653 sku & NVM_SKU_CAP_11AC_ENABLE, tx_chains,
638 rx_chains); 654 rx_chains, lar_supported);
639 } 655 }
640 656
641 data->calib_version = 255; 657 data->calib_version = 255;
diff --git a/drivers/net/wireless/iwlwifi/iwl-nvm-parse.h b/drivers/net/wireless/iwlwifi/iwl-nvm-parse.h
index fa493ce01aad..c2fa930a9892 100644
--- a/drivers/net/wireless/iwlwifi/iwl-nvm-parse.h
+++ b/drivers/net/wireless/iwlwifi/iwl-nvm-parse.h
@@ -77,7 +77,8 @@ struct iwl_nvm_data *
77iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg, 77iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg,
78 const __le16 *nvm_hw, const __le16 *nvm_sw, 78 const __le16 *nvm_hw, const __le16 *nvm_sw,
79 const __le16 *nvm_calib, const __le16 *regulatory, 79 const __le16 *nvm_calib, const __le16 *regulatory,
80 const __le16 *mac_override, u8 tx_chains, u8 rx_chains); 80 const __le16 *mac_override, u8 tx_chains, u8 rx_chains,
81 bool lar_supported);
81 82
82/** 83/**
83 * iwl_parse_mcc_info - parse MCC (mobile country code) info coming from FW 84 * iwl_parse_mcc_info - parse MCC (mobile country code) info coming from FW
diff --git a/drivers/net/wireless/iwlwifi/mvm/nvm.c b/drivers/net/wireless/iwlwifi/mvm/nvm.c
index 26c5d94d3717..907e231f2c5c 100644
--- a/drivers/net/wireless/iwlwifi/mvm/nvm.c
+++ b/drivers/net/wireless/iwlwifi/mvm/nvm.c
@@ -302,7 +302,8 @@ iwl_parse_nvm_sections(struct iwl_mvm *mvm)
302 return iwl_parse_nvm_data(mvm->trans->dev, mvm->cfg, hw, sw, calib, 302 return iwl_parse_nvm_data(mvm->trans->dev, mvm->cfg, hw, sw, calib,
303 regulatory, mac_override, 303 regulatory, mac_override,
304 mvm->fw->valid_tx_ant, 304 mvm->fw->valid_tx_ant,
305 mvm->fw->valid_rx_ant); 305 mvm->fw->valid_rx_ant,
306 iwl_mvm_is_lar_supported(mvm));
306} 307}
307 308
308#define MAX_NVM_FILE_LEN 16384 309#define MAX_NVM_FILE_LEN 16384