aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/iwlwifi/mvm
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/wireless/iwlwifi/mvm')
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/Makefile4
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/coex.c (renamed from drivers/net/wireless/iwlwifi/mvm/bt-coex.c)474
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/constants.h4
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/d3.c226
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c119
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/debugfs.c485
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-api-coex.h (renamed from drivers/net/wireless/iwlwifi/mvm/fw-api-bt-coex.h)21
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-api-d3.h14
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-api-power.h33
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-api-rs.h3
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-api-sta.h31
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-api-tx.h3
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-api.h134
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw-error-dump.h106
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw.c79
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/led.c2
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c78
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/mac80211.c601
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/mvm.h259
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/nvm.c87
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/offloading.c215
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/ops.c481
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c4
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/power.c426
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/power_legacy.c319
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/quota.c100
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/rs.c210
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/rs.h2
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/rx.c33
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/scan.c255
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/sta.c213
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/sta.h62
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/time-event.c8
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/tt.c7
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/tx.c43
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/utils.c138
36 files changed, 3958 insertions, 1321 deletions
diff --git a/drivers/net/wireless/iwlwifi/mvm/Makefile b/drivers/net/wireless/iwlwifi/mvm/Makefile
index f98ec2b23898..ccdd3b7c4cce 100644
--- a/drivers/net/wireless/iwlwifi/mvm/Makefile
+++ b/drivers/net/wireless/iwlwifi/mvm/Makefile
@@ -2,8 +2,8 @@ obj-$(CONFIG_IWLMVM) += iwlmvm.o
2iwlmvm-y += fw.o mac80211.o nvm.o ops.o phy-ctxt.o mac-ctxt.o 2iwlmvm-y += fw.o mac80211.o nvm.o ops.o phy-ctxt.o mac-ctxt.o
3iwlmvm-y += utils.o rx.o tx.o binding.o quota.o sta.o sf.o 3iwlmvm-y += utils.o rx.o tx.o binding.o quota.o sta.o sf.o
4iwlmvm-y += scan.o time-event.o rs.o 4iwlmvm-y += scan.o time-event.o rs.o
5iwlmvm-y += power.o power_legacy.o bt-coex.o 5iwlmvm-y += power.o coex.o
6iwlmvm-y += led.o tt.o 6iwlmvm-y += led.o tt.o offloading.o
7iwlmvm-$(CONFIG_IWLWIFI_DEBUGFS) += debugfs.o debugfs-vif.o 7iwlmvm-$(CONFIG_IWLWIFI_DEBUGFS) += debugfs.o debugfs-vif.o
8iwlmvm-$(CONFIG_PM_SLEEP) += d3.o 8iwlmvm-$(CONFIG_PM_SLEEP) += d3.o
9 9
diff --git a/drivers/net/wireless/iwlwifi/mvm/bt-coex.c b/drivers/net/wireless/iwlwifi/mvm/coex.c
index 18a895a949d4..685f7e8e6943 100644
--- a/drivers/net/wireless/iwlwifi/mvm/bt-coex.c
+++ b/drivers/net/wireless/iwlwifi/mvm/coex.c
@@ -61,9 +61,11 @@
61 * 61 *
62 *****************************************************************************/ 62 *****************************************************************************/
63 63
64#include <linux/ieee80211.h>
65#include <linux/etherdevice.h>
64#include <net/mac80211.h> 66#include <net/mac80211.h>
65 67
66#include "fw-api-bt-coex.h" 68#include "fw-api-coex.h"
67#include "iwl-modparams.h" 69#include "iwl-modparams.h"
68#include "mvm.h" 70#include "mvm.h"
69#include "iwl-debug.h" 71#include "iwl-debug.h"
@@ -305,6 +307,215 @@ static const __le32 iwl_bt_mprio_lut[BT_COEX_MULTI_PRIO_LUT_SIZE] = {
305 cpu_to_le32(0x33113311), 307 cpu_to_le32(0x33113311),
306}; 308};
307 309
310struct corunning_block_luts {
311 u8 range;
312 __le32 lut20[BT_COEX_CORUN_LUT_SIZE];
313};
314
315/*
316 * Ranges for the antenna coupling calibration / co-running block LUT:
317 * LUT0: [ 0, 12[
318 * LUT1: [12, 20[
319 * LUT2: [20, 21[
320 * LUT3: [21, 23[
321 * LUT4: [23, 27[
322 * LUT5: [27, 30[
323 * LUT6: [30, 32[
324 * LUT7: [32, 33[
325 * LUT8: [33, - [
326 */
327static const struct corunning_block_luts antenna_coupling_ranges[] = {
328 {
329 .range = 0,
330 .lut20 = {
331 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
332 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
333 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
334 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
335 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
336 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
337 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
338 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
339 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
340 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
341 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
342 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
343 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
344 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
345 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
346 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
347 },
348 },
349 {
350 .range = 12,
351 .lut20 = {
352 cpu_to_le32(0x00000001), cpu_to_le32(0x00000000),
353 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
354 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
355 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
356 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
357 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
358 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
359 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
360 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
361 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
362 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
363 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
364 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
365 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
366 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
367 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
368 },
369 },
370 {
371 .range = 20,
372 .lut20 = {
373 cpu_to_le32(0x00000002), cpu_to_le32(0x00000000),
374 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
375 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
376 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
377 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
378 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
379 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
380 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
381 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
382 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
383 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
384 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
385 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
386 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
387 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
388 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
389 },
390 },
391 {
392 .range = 21,
393 .lut20 = {
394 cpu_to_le32(0x00000003), cpu_to_le32(0x00000000),
395 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
396 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
397 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
398 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
399 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
400 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
401 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
402 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
403 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
404 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
405 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
406 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
407 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
408 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
409 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
410 },
411 },
412 {
413 .range = 23,
414 .lut20 = {
415 cpu_to_le32(0x00000004), cpu_to_le32(0x00000000),
416 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
417 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
418 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
419 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
420 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
421 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
422 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
423 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
424 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
425 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
426 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
427 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
428 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
429 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
430 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
431 },
432 },
433 {
434 .range = 27,
435 .lut20 = {
436 cpu_to_le32(0x00000005), cpu_to_le32(0x00000000),
437 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
438 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
439 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
440 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
441 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
442 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
443 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
444 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
445 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
446 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
447 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
448 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
449 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
450 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
451 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
452 },
453 },
454 {
455 .range = 30,
456 .lut20 = {
457 cpu_to_le32(0x00000006), cpu_to_le32(0x00000000),
458 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
459 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
460 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
461 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
462 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
463 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
464 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
465 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
466 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
467 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
468 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
469 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
470 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
471 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
472 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
473 },
474 },
475 {
476 .range = 32,
477 .lut20 = {
478 cpu_to_le32(0x00000007), cpu_to_le32(0x00000000),
479 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
480 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
481 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
482 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
483 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
484 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
485 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
486 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
487 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
488 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
489 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
490 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
491 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
492 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
493 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
494 },
495 },
496 {
497 .range = 33,
498 .lut20 = {
499 cpu_to_le32(0x00000008), cpu_to_le32(0x00000000),
500 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
501 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
502 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
503 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
504 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
505 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
506 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
507 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
508 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
509 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
510 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
511 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
512 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
513 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
514 cpu_to_le32(0x00000000), cpu_to_le32(0x00000000),
515 },
516 },
517};
518
308static enum iwl_bt_coex_lut_type 519static enum iwl_bt_coex_lut_type
309iwl_get_coex_type(struct iwl_mvm *mvm, const struct ieee80211_vif *vif) 520iwl_get_coex_type(struct iwl_mvm *mvm, const struct ieee80211_vif *vif)
310{ 521{
@@ -378,7 +589,6 @@ int iwl_send_bt_init_conf(struct iwl_mvm *mvm)
378 589
379 flags = iwlwifi_mod_params.bt_coex_active ? 590 flags = iwlwifi_mod_params.bt_coex_active ?
380 BT_COEX_NW : BT_COEX_DISABLE; 591 BT_COEX_NW : BT_COEX_DISABLE;
381 flags |= BT_CH_PRIMARY_EN | BT_CH_SECONDARY_EN | BT_SYNC_2_BT_DISABLE;
382 bt_cmd->flags = cpu_to_le32(flags); 592 bt_cmd->flags = cpu_to_le32(flags);
383 593
384 bt_cmd->valid_bit_msk = cpu_to_le32(BT_VALID_ENABLE | 594 bt_cmd->valid_bit_msk = cpu_to_le32(BT_VALID_ENABLE |
@@ -391,14 +601,26 @@ int iwl_send_bt_init_conf(struct iwl_mvm *mvm)
391 BT_VALID_LUT | 601 BT_VALID_LUT |
392 BT_VALID_WIFI_RX_SW_PRIO_BOOST | 602 BT_VALID_WIFI_RX_SW_PRIO_BOOST |
393 BT_VALID_WIFI_TX_SW_PRIO_BOOST | 603 BT_VALID_WIFI_TX_SW_PRIO_BOOST |
394 BT_VALID_CORUN_LUT_20 |
395 BT_VALID_CORUN_LUT_40 |
396 BT_VALID_ANT_ISOLATION | 604 BT_VALID_ANT_ISOLATION |
397 BT_VALID_ANT_ISOLATION_THRS | 605 BT_VALID_ANT_ISOLATION_THRS |
398 BT_VALID_TXTX_DELTA_FREQ_THRS | 606 BT_VALID_TXTX_DELTA_FREQ_THRS |
399 BT_VALID_TXRX_MAX_FREQ_0 | 607 BT_VALID_TXRX_MAX_FREQ_0 |
400 BT_VALID_SYNC_TO_SCO); 608 BT_VALID_SYNC_TO_SCO);
401 609
610 if (IWL_MVM_BT_COEX_SYNC2SCO)
611 bt_cmd->flags |= cpu_to_le32(BT_COEX_SYNC2SCO);
612
613 if (IWL_MVM_BT_COEX_CORUNNING) {
614 bt_cmd->valid_bit_msk = cpu_to_le32(BT_VALID_CORUN_LUT_20 |
615 BT_VALID_CORUN_LUT_40);
616 bt_cmd->flags |= cpu_to_le32(BT_COEX_CORUNNING);
617 }
618
619 if (IWL_MVM_BT_COEX_MPLUT) {
620 bt_cmd->flags |= cpu_to_le32(BT_COEX_MPLUT);
621 bt_cmd->valid_bit_msk = cpu_to_le32(BT_VALID_MULTI_PRIO_LUT);
622 }
623
402 if (mvm->cfg->bt_shared_single_ant) 624 if (mvm->cfg->bt_shared_single_ant)
403 memcpy(&bt_cmd->decision_lut, iwl_single_shared_ant, 625 memcpy(&bt_cmd->decision_lut, iwl_single_shared_ant,
404 sizeof(iwl_single_shared_ant)); 626 sizeof(iwl_single_shared_ant));
@@ -406,6 +628,12 @@ int iwl_send_bt_init_conf(struct iwl_mvm *mvm)
406 memcpy(&bt_cmd->decision_lut, iwl_combined_lookup, 628 memcpy(&bt_cmd->decision_lut, iwl_combined_lookup,
407 sizeof(iwl_combined_lookup)); 629 sizeof(iwl_combined_lookup));
408 630
631 /* Take first Co-running block LUT to get started */
632 memcpy(bt_cmd->bt4_corun_lut20, antenna_coupling_ranges[0].lut20,
633 sizeof(bt_cmd->bt4_corun_lut20));
634 memcpy(bt_cmd->bt4_corun_lut40, antenna_coupling_ranges[0].lut20,
635 sizeof(bt_cmd->bt4_corun_lut40));
636
409 memcpy(&bt_cmd->bt_prio_boost, iwl_bt_prio_boost, 637 memcpy(&bt_cmd->bt_prio_boost, iwl_bt_prio_boost,
410 sizeof(iwl_bt_prio_boost)); 638 sizeof(iwl_bt_prio_boost));
411 memcpy(&bt_cmd->bt4_multiprio_lut, iwl_bt_mprio_lut, 639 memcpy(&bt_cmd->bt4_multiprio_lut, iwl_bt_mprio_lut,
@@ -489,36 +717,26 @@ static int iwl_mvm_bt_udpate_ctrl_kill_msk(struct iwl_mvm *mvm,
489 return ret; 717 return ret;
490} 718}
491 719
492static int iwl_mvm_bt_coex_reduced_txp(struct iwl_mvm *mvm, u8 sta_id, 720int iwl_mvm_bt_coex_reduced_txp(struct iwl_mvm *mvm, u8 sta_id, bool enable)
493 bool enable)
494{ 721{
495 struct iwl_bt_coex_cmd *bt_cmd; 722 struct iwl_bt_coex_cmd *bt_cmd;
496 /* Send ASYNC since this can be sent from an atomic context */ 723 /* Send ASYNC since this can be sent from an atomic context */
497 struct iwl_host_cmd cmd = { 724 struct iwl_host_cmd cmd = {
498 .id = BT_CONFIG, 725 .id = BT_CONFIG,
499 .len = { sizeof(*bt_cmd), }, 726 .len = { sizeof(*bt_cmd), },
500 .dataflags = { IWL_HCMD_DFL_DUP, }, 727 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
501 .flags = CMD_ASYNC, 728 .flags = CMD_ASYNC,
502 }; 729 };
503
504 struct ieee80211_sta *sta;
505 struct iwl_mvm_sta *mvmsta; 730 struct iwl_mvm_sta *mvmsta;
506 int ret; 731 int ret;
507 732
508 if (sta_id == IWL_MVM_STATION_COUNT) 733 mvmsta = iwl_mvm_sta_from_staid_protected(mvm, sta_id);
734 if (!mvmsta)
509 return 0; 735 return 0;
510 736
511 sta = rcu_dereference_protected(mvm->fw_id_to_mac_id[sta_id],
512 lockdep_is_held(&mvm->mutex));
513
514 /* This can happen if the station has been removed right now */
515 if (IS_ERR_OR_NULL(sta))
516 return 0;
517
518 mvmsta = iwl_mvm_sta_from_mac80211(sta);
519
520 /* nothing to do */ 737 /* nothing to do */
521 if (mvmsta->bt_reduced_txpower == enable) 738 if (mvmsta->bt_reduced_txpower_dbg ||
739 mvmsta->bt_reduced_txpower == enable)
522 return 0; 740 return 0;
523 741
524 bt_cmd = kzalloc(sizeof(*bt_cmd), GFP_ATOMIC); 742 bt_cmd = kzalloc(sizeof(*bt_cmd), GFP_ATOMIC);
@@ -552,6 +770,7 @@ struct iwl_bt_iterator_data {
552 bool reduced_tx_power; 770 bool reduced_tx_power;
553 struct ieee80211_chanctx_conf *primary; 771 struct ieee80211_chanctx_conf *primary;
554 struct ieee80211_chanctx_conf *secondary; 772 struct ieee80211_chanctx_conf *secondary;
773 bool primary_ll;
555}; 774};
556 775
557static inline 776static inline
@@ -577,72 +796,113 @@ static void iwl_mvm_bt_notif_iterator(void *_data, u8 *mac,
577 struct iwl_mvm *mvm = data->mvm; 796 struct iwl_mvm *mvm = data->mvm;
578 struct ieee80211_chanctx_conf *chanctx_conf; 797 struct ieee80211_chanctx_conf *chanctx_conf;
579 enum ieee80211_smps_mode smps_mode; 798 enum ieee80211_smps_mode smps_mode;
799 u32 bt_activity_grading;
580 int ave_rssi; 800 int ave_rssi;
581 801
582 lockdep_assert_held(&mvm->mutex); 802 lockdep_assert_held(&mvm->mutex);
583 803
584 if (vif->type != NL80211_IFTYPE_STATION && 804 switch (vif->type) {
585 vif->type != NL80211_IFTYPE_AP) 805 case NL80211_IFTYPE_STATION:
586 return; 806 /* default smps_mode for BSS / P2P client is AUTOMATIC */
807 smps_mode = IEEE80211_SMPS_AUTOMATIC;
808 data->num_bss_ifaces++;
587 809
588 smps_mode = IEEE80211_SMPS_AUTOMATIC; 810 /*
811 * Count unassoc BSSes, relax SMSP constraints
812 * and disable reduced Tx Power
813 */
814 if (!vif->bss_conf.assoc) {
815 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX,
816 smps_mode);
817 if (iwl_mvm_bt_coex_reduced_txp(mvm,
818 mvmvif->ap_sta_id,
819 false))
820 IWL_ERR(mvm, "Couldn't send BT_CONFIG cmd\n");
821 return;
822 }
823 break;
824 case NL80211_IFTYPE_AP:
825 /* default smps_mode for AP / GO is OFF */
826 smps_mode = IEEE80211_SMPS_OFF;
827 if (!mvmvif->ap_ibss_active) {
828 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX,
829 smps_mode);
830 return;
831 }
832
833 /* the Ack / Cts kill mask must be default if AP / GO */
834 data->reduced_tx_power = false;
835 break;
836 default:
837 return;
838 }
589 839
590 chanctx_conf = rcu_dereference(vif->chanctx_conf); 840 chanctx_conf = rcu_dereference(vif->chanctx_conf);
591 841
592 /* If channel context is invalid or not on 2.4GHz .. */ 842 /* If channel context is invalid or not on 2.4GHz .. */
593 if ((!chanctx_conf || 843 if ((!chanctx_conf ||
594 chanctx_conf->def.chan->band != IEEE80211_BAND_2GHZ)) { 844 chanctx_conf->def.chan->band != IEEE80211_BAND_2GHZ)) {
595 /* ... and it is an associated STATION, relax constraints */ 845 /* ... relax constraints and disable rssi events */
596 if (vif->type == NL80211_IFTYPE_STATION && vif->bss_conf.assoc) 846 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX,
597 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX, 847 smps_mode);
598 smps_mode); 848 if (vif->type == NL80211_IFTYPE_STATION)
599 iwl_mvm_bt_coex_enable_rssi_event(mvm, vif, false, 0); 849 iwl_mvm_bt_coex_enable_rssi_event(mvm, vif, false, 0);
600 return; 850 return;
601 } 851 }
602 852
603 /* SoftAP / GO will always be primary */ 853 bt_activity_grading = le32_to_cpu(data->notif->bt_activity_grading);
604 if (vif->type == NL80211_IFTYPE_AP) { 854 if (bt_activity_grading >= BT_HIGH_TRAFFIC)
605 if (!mvmvif->ap_ibss_active) 855 smps_mode = IEEE80211_SMPS_STATIC;
606 return; 856 else if (bt_activity_grading >= BT_LOW_TRAFFIC)
857 smps_mode = vif->type == NL80211_IFTYPE_AP ?
858 IEEE80211_SMPS_OFF :
859 IEEE80211_SMPS_DYNAMIC;
860 IWL_DEBUG_COEX(data->mvm,
861 "mac %d: bt_status %d bt_activity_grading %d smps_req %d\n",
862 mvmvif->id, data->notif->bt_status, bt_activity_grading,
863 smps_mode);
607 864
608 /* the Ack / Cts kill mask must be default if AP / GO */ 865 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX, smps_mode);
609 data->reduced_tx_power = false;
610 866
611 if (chanctx_conf == data->primary) 867 /* low latency is always primary */
612 return; 868 if (iwl_mvm_vif_low_latency(mvmvif)) {
869 data->primary_ll = true;
613 870
614 /* downgrade the current primary no matter what its type is */
615 data->secondary = data->primary; 871 data->secondary = data->primary;
616 data->primary = chanctx_conf; 872 data->primary = chanctx_conf;
617 return;
618 } 873 }
619 874
620 data->num_bss_ifaces++; 875 if (vif->type == NL80211_IFTYPE_AP) {
876 if (!mvmvif->ap_ibss_active)
877 return;
621 878
622 /* we are now a STA / P2P Client, and take associated ones only */ 879 if (chanctx_conf == data->primary)
623 if (!vif->bss_conf.assoc) 880 return;
881
882 if (!data->primary_ll) {
883 /*
884 * downgrade the current primary no matter what its
885 * type is.
886 */
887 data->secondary = data->primary;
888 data->primary = chanctx_conf;
889 } else {
890 /* there is low latency vif - we will be secondary */
891 data->secondary = chanctx_conf;
892 }
624 return; 893 return;
894 }
625 895
626 /* STA / P2P Client, try to be primary if first vif */ 896 /*
897 * STA / P2P Client, try to be primary if first vif. If we are in low
898 * latency mode, we are already in primary and just don't do much
899 */
627 if (!data->primary || data->primary == chanctx_conf) 900 if (!data->primary || data->primary == chanctx_conf)
628 data->primary = chanctx_conf; 901 data->primary = chanctx_conf;
629 else if (!data->secondary) 902 else if (!data->secondary)
630 /* if secondary is not NULL, it might be a GO */ 903 /* if secondary is not NULL, it might be a GO */
631 data->secondary = chanctx_conf; 904 data->secondary = chanctx_conf;
632 905
633 if (le32_to_cpu(data->notif->bt_activity_grading) >= BT_HIGH_TRAFFIC)
634 smps_mode = IEEE80211_SMPS_STATIC;
635 else if (le32_to_cpu(data->notif->bt_activity_grading) >=
636 BT_LOW_TRAFFIC)
637 smps_mode = IEEE80211_SMPS_DYNAMIC;
638
639 IWL_DEBUG_COEX(data->mvm,
640 "mac %d: bt_status %d bt_activity_grading %d smps_req %d\n",
641 mvmvif->id, data->notif->bt_status,
642 data->notif->bt_activity_grading, smps_mode);
643
644 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX, smps_mode);
645
646 /* don't reduce the Tx power if in loose scheme */ 906 /* don't reduce the Tx power if in loose scheme */
647 if (iwl_get_coex_type(mvm, vif) == BT_COEX_LOOSE_LUT || 907 if (iwl_get_coex_type(mvm, vif) == BT_COEX_LOOSE_LUT ||
648 mvm->cfg->bt_shared_single_ant) { 908 mvm->cfg->bt_shared_single_ant) {
@@ -918,8 +1178,8 @@ void iwl_mvm_bt_rssi_event(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
918#define LINK_QUAL_AGG_TIME_LIMIT_DEF (4000) 1178#define LINK_QUAL_AGG_TIME_LIMIT_DEF (4000)
919#define LINK_QUAL_AGG_TIME_LIMIT_BT_ACT (1200) 1179#define LINK_QUAL_AGG_TIME_LIMIT_BT_ACT (1200)
920 1180
921u16 iwl_mvm_bt_coex_agg_time_limit(struct iwl_mvm *mvm, 1181u16 iwl_mvm_coex_agg_time_limit(struct iwl_mvm *mvm,
922 struct ieee80211_sta *sta) 1182 struct ieee80211_sta *sta)
923{ 1183{
924 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); 1184 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta);
925 enum iwl_bt_coex_lut_type lut_type; 1185 enum iwl_bt_coex_lut_type lut_type;
@@ -955,6 +1215,38 @@ bool iwl_mvm_bt_coex_is_mimo_allowed(struct iwl_mvm *mvm,
955 return iwl_get_coex_type(mvm, mvmsta->vif) == BT_COEX_TIGHT_LUT; 1215 return iwl_get_coex_type(mvm, mvmsta->vif) == BT_COEX_TIGHT_LUT;
956} 1216}
957 1217
1218u8 iwl_mvm_bt_coex_tx_prio(struct iwl_mvm *mvm, struct ieee80211_hdr *hdr,
1219 struct ieee80211_tx_info *info, u8 ac)
1220{
1221 __le16 fc = hdr->frame_control;
1222
1223 if (info->band != IEEE80211_BAND_2GHZ)
1224 return 0;
1225
1226 if (unlikely(mvm->bt_tx_prio))
1227 return mvm->bt_tx_prio - 1;
1228
1229 /* High prio packet (wrt. BT coex) if it is EAPOL, MCAST or MGMT */
1230 if (info->control.flags & IEEE80211_TX_CTRL_PORT_CTRL_PROTO ||
1231 is_multicast_ether_addr(hdr->addr1) ||
1232 ieee80211_is_ctl(fc) || ieee80211_is_mgmt(fc) ||
1233 ieee80211_is_nullfunc(fc) || ieee80211_is_qos_nullfunc(fc))
1234 return 3;
1235
1236 switch (ac) {
1237 case IEEE80211_AC_BE:
1238 return 1;
1239 case IEEE80211_AC_VO:
1240 return 3;
1241 case IEEE80211_AC_VI:
1242 return 2;
1243 default:
1244 break;
1245 }
1246
1247 return 0;
1248}
1249
958void iwl_mvm_bt_coex_vif_change(struct iwl_mvm *mvm) 1250void iwl_mvm_bt_coex_vif_change(struct iwl_mvm *mvm)
959{ 1251{
960 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_NEWBT_COEX)) 1252 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_NEWBT_COEX))
@@ -962,3 +1254,69 @@ void iwl_mvm_bt_coex_vif_change(struct iwl_mvm *mvm)
962 1254
963 iwl_mvm_bt_coex_notif_handle(mvm); 1255 iwl_mvm_bt_coex_notif_handle(mvm);
964} 1256}
1257
1258int iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm,
1259 struct iwl_rx_cmd_buffer *rxb,
1260 struct iwl_device_cmd *dev_cmd)
1261{
1262 struct iwl_rx_packet *pkt = rxb_addr(rxb);
1263 u32 ant_isolation = le32_to_cpup((void *)pkt->data);
1264 u8 __maybe_unused lower_bound, upper_bound;
1265 u8 lut;
1266
1267 struct iwl_bt_coex_cmd *bt_cmd;
1268 struct iwl_host_cmd cmd = {
1269 .id = BT_CONFIG,
1270 .len = { sizeof(*bt_cmd), },
1271 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
1272 .flags = CMD_SYNC,
1273 };
1274
1275 if (!IWL_MVM_BT_COEX_CORUNNING)
1276 return 0;
1277
1278 lockdep_assert_held(&mvm->mutex);
1279
1280 if (ant_isolation == mvm->last_ant_isol)
1281 return 0;
1282
1283 for (lut = 0; lut < ARRAY_SIZE(antenna_coupling_ranges) - 1; lut++)
1284 if (ant_isolation < antenna_coupling_ranges[lut + 1].range)
1285 break;
1286
1287 lower_bound = antenna_coupling_ranges[lut].range;
1288
1289 if (lut < ARRAY_SIZE(antenna_coupling_ranges) - 1)
1290 upper_bound = antenna_coupling_ranges[lut + 1].range;
1291 else
1292 upper_bound = antenna_coupling_ranges[lut].range;
1293
1294 IWL_DEBUG_COEX(mvm, "Antenna isolation=%d in range [%d,%d[, lut=%d\n",
1295 ant_isolation, lower_bound, upper_bound, lut);
1296
1297 mvm->last_ant_isol = ant_isolation;
1298
1299 if (mvm->last_corun_lut == lut)
1300 return 0;
1301
1302 mvm->last_corun_lut = lut;
1303
1304 bt_cmd = kzalloc(sizeof(*bt_cmd), GFP_KERNEL);
1305 if (!bt_cmd)
1306 return 0;
1307 cmd.data[0] = bt_cmd;
1308
1309 bt_cmd->flags = cpu_to_le32(BT_COEX_NW);
1310 bt_cmd->valid_bit_msk |= cpu_to_le32(BT_VALID_ENABLE |
1311 BT_VALID_CORUN_LUT_20 |
1312 BT_VALID_CORUN_LUT_40);
1313
1314 /* For the moment, use the same LUT for 20GHz and 40GHz */
1315 memcpy(bt_cmd->bt4_corun_lut20, antenna_coupling_ranges[lut].lut20,
1316 sizeof(bt_cmd->bt4_corun_lut20));
1317
1318 memcpy(bt_cmd->bt4_corun_lut40, antenna_coupling_ranges[lut].lut20,
1319 sizeof(bt_cmd->bt4_corun_lut40));
1320
1321 return 0;
1322}
diff --git a/drivers/net/wireless/iwlwifi/mvm/constants.h b/drivers/net/wireless/iwlwifi/mvm/constants.h
index 036857698565..51685693af2e 100644
--- a/drivers/net/wireless/iwlwifi/mvm/constants.h
+++ b/drivers/net/wireless/iwlwifi/mvm/constants.h
@@ -78,5 +78,9 @@
78#define IWL_MVM_PS_SNOOZE_INTERVAL 25 78#define IWL_MVM_PS_SNOOZE_INTERVAL 25
79#define IWL_MVM_PS_SNOOZE_WINDOW 50 79#define IWL_MVM_PS_SNOOZE_WINDOW 50
80#define IWL_MVM_WOWLAN_PS_SNOOZE_WINDOW 25 80#define IWL_MVM_WOWLAN_PS_SNOOZE_WINDOW 25
81#define IWL_MVM_LOWLAT_QUOTA_MIN_PERCENT 64
82#define IWL_MVM_BT_COEX_SYNC2SCO 1
83#define IWL_MVM_BT_COEX_CORUNNING 1
84#define IWL_MVM_BT_COEX_MPLUT 1
81 85
82#endif /* __MVM_CONSTANTS_H */ 86#endif /* __MVM_CONSTANTS_H */
diff --git a/drivers/net/wireless/iwlwifi/mvm/d3.c b/drivers/net/wireless/iwlwifi/mvm/d3.c
index f36a7ee0267f..e56f5a0edf85 100644
--- a/drivers/net/wireless/iwlwifi/mvm/d3.c
+++ b/drivers/net/wireless/iwlwifi/mvm/d3.c
@@ -376,139 +376,6 @@ static int iwl_mvm_send_patterns(struct iwl_mvm *mvm,
376 return err; 376 return err;
377} 377}
378 378
379static int iwl_mvm_send_proto_offload(struct iwl_mvm *mvm,
380 struct ieee80211_vif *vif)
381{
382 union {
383 struct iwl_proto_offload_cmd_v1 v1;
384 struct iwl_proto_offload_cmd_v2 v2;
385 struct iwl_proto_offload_cmd_v3_small v3s;
386 struct iwl_proto_offload_cmd_v3_large v3l;
387 } cmd = {};
388 struct iwl_host_cmd hcmd = {
389 .id = PROT_OFFLOAD_CONFIG_CMD,
390 .flags = CMD_SYNC,
391 .data[0] = &cmd,
392 .dataflags[0] = IWL_HCMD_DFL_DUP,
393 };
394 struct iwl_proto_offload_cmd_common *common;
395 u32 enabled = 0, size;
396 u32 capa_flags = mvm->fw->ucode_capa.flags;
397#if IS_ENABLED(CONFIG_IPV6)
398 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
399 int i;
400
401 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL ||
402 capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_LARGE) {
403 struct iwl_ns_config *nsc;
404 struct iwl_targ_addr *addrs;
405 int n_nsc, n_addrs;
406 int c;
407
408 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL) {
409 nsc = cmd.v3s.ns_config;
410 n_nsc = IWL_PROTO_OFFLOAD_NUM_NS_CONFIG_V3S;
411 addrs = cmd.v3s.targ_addrs;
412 n_addrs = IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V3S;
413 } else {
414 nsc = cmd.v3l.ns_config;
415 n_nsc = IWL_PROTO_OFFLOAD_NUM_NS_CONFIG_V3L;
416 addrs = cmd.v3l.targ_addrs;
417 n_addrs = IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V3L;
418 }
419
420 if (mvmvif->num_target_ipv6_addrs)
421 enabled |= IWL_D3_PROTO_OFFLOAD_NS;
422
423 /*
424 * For each address we have (and that will fit) fill a target
425 * address struct and combine for NS offload structs with the
426 * solicited node addresses.
427 */
428 for (i = 0, c = 0;
429 i < mvmvif->num_target_ipv6_addrs &&
430 i < n_addrs && c < n_nsc; i++) {
431 struct in6_addr solicited_addr;
432 int j;
433
434 addrconf_addr_solict_mult(&mvmvif->target_ipv6_addrs[i],
435 &solicited_addr);
436 for (j = 0; j < c; j++)
437 if (ipv6_addr_cmp(&nsc[j].dest_ipv6_addr,
438 &solicited_addr) == 0)
439 break;
440 if (j == c)
441 c++;
442 addrs[i].addr = mvmvif->target_ipv6_addrs[i];
443 addrs[i].config_num = cpu_to_le32(j);
444 nsc[j].dest_ipv6_addr = solicited_addr;
445 memcpy(nsc[j].target_mac_addr, vif->addr, ETH_ALEN);
446 }
447
448 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL)
449 cmd.v3s.num_valid_ipv6_addrs = cpu_to_le32(i);
450 else
451 cmd.v3l.num_valid_ipv6_addrs = cpu_to_le32(i);
452 } else if (capa_flags & IWL_UCODE_TLV_FLAGS_D3_6_IPV6_ADDRS) {
453 if (mvmvif->num_target_ipv6_addrs) {
454 enabled |= IWL_D3_PROTO_OFFLOAD_NS;
455 memcpy(cmd.v2.ndp_mac_addr, vif->addr, ETH_ALEN);
456 }
457
458 BUILD_BUG_ON(sizeof(cmd.v2.target_ipv6_addr[0]) !=
459 sizeof(mvmvif->target_ipv6_addrs[0]));
460
461 for (i = 0; i < min(mvmvif->num_target_ipv6_addrs,
462 IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V2); i++)
463 memcpy(cmd.v2.target_ipv6_addr[i],
464 &mvmvif->target_ipv6_addrs[i],
465 sizeof(cmd.v2.target_ipv6_addr[i]));
466 } else {
467 if (mvmvif->num_target_ipv6_addrs) {
468 enabled |= IWL_D3_PROTO_OFFLOAD_NS;
469 memcpy(cmd.v1.ndp_mac_addr, vif->addr, ETH_ALEN);
470 }
471
472 BUILD_BUG_ON(sizeof(cmd.v1.target_ipv6_addr[0]) !=
473 sizeof(mvmvif->target_ipv6_addrs[0]));
474
475 for (i = 0; i < min(mvmvif->num_target_ipv6_addrs,
476 IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V1); i++)
477 memcpy(cmd.v1.target_ipv6_addr[i],
478 &mvmvif->target_ipv6_addrs[i],
479 sizeof(cmd.v1.target_ipv6_addr[i]));
480 }
481#endif
482
483 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL) {
484 common = &cmd.v3s.common;
485 size = sizeof(cmd.v3s);
486 } else if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_LARGE) {
487 common = &cmd.v3l.common;
488 size = sizeof(cmd.v3l);
489 } else if (capa_flags & IWL_UCODE_TLV_FLAGS_D3_6_IPV6_ADDRS) {
490 common = &cmd.v2.common;
491 size = sizeof(cmd.v2);
492 } else {
493 common = &cmd.v1.common;
494 size = sizeof(cmd.v1);
495 }
496
497 if (vif->bss_conf.arp_addr_cnt) {
498 enabled |= IWL_D3_PROTO_OFFLOAD_ARP;
499 common->host_ipv4_addr = vif->bss_conf.arp_addr_list[0];
500 memcpy(common->arp_mac_addr, vif->addr, ETH_ALEN);
501 }
502
503 if (!enabled)
504 return 0;
505
506 common->enabled = cpu_to_le32(enabled);
507
508 hcmd.len[0] = size;
509 return iwl_mvm_send_cmd(mvm, &hcmd);
510}
511
512enum iwl_mvm_tcp_packet_type { 379enum iwl_mvm_tcp_packet_type {
513 MVM_TCP_TX_SYN, 380 MVM_TCP_TX_SYN,
514 MVM_TCP_RX_SYNACK, 381 MVM_TCP_RX_SYNACK,
@@ -846,8 +713,8 @@ static int iwl_mvm_d3_reprogram(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
846 quota_cmd.quotas[0].id_and_color = 713 quota_cmd.quotas[0].id_and_color =
847 cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->phy_ctxt->id, 714 cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->phy_ctxt->id,
848 mvmvif->phy_ctxt->color)); 715 mvmvif->phy_ctxt->color));
849 quota_cmd.quotas[0].quota = cpu_to_le32(100); 716 quota_cmd.quotas[0].quota = cpu_to_le32(IWL_MVM_MAX_QUOTA);
850 quota_cmd.quotas[0].max_duration = cpu_to_le32(1000); 717 quota_cmd.quotas[0].max_duration = cpu_to_le32(IWL_MVM_MAX_QUOTA);
851 718
852 for (i = 1; i < MAX_BINDINGS; i++) 719 for (i = 1; i < MAX_BINDINGS; i++)
853 quota_cmd.quotas[i].id_and_color = cpu_to_le32(FW_CTXT_INVALID); 720 quota_cmd.quotas[i].id_and_color = cpu_to_le32(FW_CTXT_INVALID);
@@ -927,6 +794,20 @@ void iwl_mvm_set_last_nonqos_seq(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
927 IWL_ERR(mvm, "failed to set non-QoS seqno\n"); 794 IWL_ERR(mvm, "failed to set non-QoS seqno\n");
928} 795}
929 796
797static int
798iwl_mvm_send_wowlan_config_cmd(struct iwl_mvm *mvm,
799 const struct iwl_wowlan_config_cmd_v3 *cmd)
800{
801 /* start only with the v2 part of the command */
802 u16 cmd_len = sizeof(cmd->common);
803
804 if (mvm->fw->ucode_capa.api[0] & IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID)
805 cmd_len = sizeof(*cmd);
806
807 return iwl_mvm_send_cmd_pdu(mvm, WOWLAN_CONFIGURATION, CMD_SYNC,
808 cmd_len, cmd);
809}
810
930static int __iwl_mvm_suspend(struct ieee80211_hw *hw, 811static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
931 struct cfg80211_wowlan *wowlan, 812 struct cfg80211_wowlan *wowlan,
932 bool test) 813 bool test)
@@ -939,7 +820,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
939 struct iwl_mvm_vif *mvmvif; 820 struct iwl_mvm_vif *mvmvif;
940 struct ieee80211_sta *ap_sta; 821 struct ieee80211_sta *ap_sta;
941 struct iwl_mvm_sta *mvm_ap_sta; 822 struct iwl_mvm_sta *mvm_ap_sta;
942 struct iwl_wowlan_config_cmd wowlan_config_cmd = {}; 823 struct iwl_wowlan_config_cmd_v3 wowlan_config_cmd = {};
943 struct iwl_wowlan_kek_kck_material_cmd kek_kck_cmd = {}; 824 struct iwl_wowlan_kek_kck_material_cmd kek_kck_cmd = {};
944 struct iwl_wowlan_tkip_params_cmd tkip_cmd = {}; 825 struct iwl_wowlan_tkip_params_cmd tkip_cmd = {};
945 struct iwl_d3_manager_config d3_cfg_cmd_data = { 826 struct iwl_d3_manager_config d3_cfg_cmd_data = {
@@ -961,9 +842,8 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
961 .tkip = &tkip_cmd, 842 .tkip = &tkip_cmd,
962 .use_tkip = false, 843 .use_tkip = false,
963 }; 844 };
964 int ret, i; 845 int ret;
965 int len __maybe_unused; 846 int len __maybe_unused;
966 u8 old_aux_sta_id, old_ap_sta_id = IWL_MVM_STATION_COUNT;
967 847
968 if (!wowlan) { 848 if (!wowlan) {
969 /* 849 /*
@@ -980,8 +860,6 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
980 860
981 mutex_lock(&mvm->mutex); 861 mutex_lock(&mvm->mutex);
982 862
983 old_aux_sta_id = mvm->aux_sta.sta_id;
984
985 /* see if there's only a single BSS vif and it's associated */ 863 /* see if there's only a single BSS vif and it's associated */
986 ieee80211_iterate_active_interfaces_atomic( 864 ieee80211_iterate_active_interfaces_atomic(
987 mvm->hw, IEEE80211_IFACE_ITER_NORMAL, 865 mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
@@ -1005,49 +883,41 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1005 883
1006 mvm_ap_sta = (struct iwl_mvm_sta *)ap_sta->drv_priv; 884 mvm_ap_sta = (struct iwl_mvm_sta *)ap_sta->drv_priv;
1007 885
1008 /* TODO: wowlan_config_cmd.wowlan_ba_teardown_tids */ 886 /* TODO: wowlan_config_cmd.common.wowlan_ba_teardown_tids */
1009 887
1010 wowlan_config_cmd.is_11n_connection = ap_sta->ht_cap.ht_supported; 888 wowlan_config_cmd.common.is_11n_connection =
889 ap_sta->ht_cap.ht_supported;
1011 890
1012 /* Query the last used seqno and set it */ 891 /* Query the last used seqno and set it */
1013 ret = iwl_mvm_get_last_nonqos_seq(mvm, vif); 892 ret = iwl_mvm_get_last_nonqos_seq(mvm, vif);
1014 if (ret < 0) 893 if (ret < 0)
1015 goto out_noreset; 894 goto out_noreset;
1016 wowlan_config_cmd.non_qos_seq = cpu_to_le16(ret); 895 wowlan_config_cmd.common.non_qos_seq = cpu_to_le16(ret);
1017 896
1018 /* 897 iwl_mvm_set_wowlan_qos_seq(mvm_ap_sta, &wowlan_config_cmd.common);
1019 * For QoS counters, we store the one to use next, so subtract 0x10
1020 * since the uCode will add 0x10 *before* using the value while we
1021 * increment after using the value (i.e. store the next value to use).
1022 */
1023 for (i = 0; i < IWL_MAX_TID_COUNT; i++) {
1024 u16 seq = mvm_ap_sta->tid_data[i].seq_number;
1025 seq -= 0x10;
1026 wowlan_config_cmd.qos_seq[i] = cpu_to_le16(seq);
1027 }
1028 898
1029 if (wowlan->disconnect) 899 if (wowlan->disconnect)
1030 wowlan_config_cmd.wakeup_filter |= 900 wowlan_config_cmd.common.wakeup_filter |=
1031 cpu_to_le32(IWL_WOWLAN_WAKEUP_BEACON_MISS | 901 cpu_to_le32(IWL_WOWLAN_WAKEUP_BEACON_MISS |
1032 IWL_WOWLAN_WAKEUP_LINK_CHANGE); 902 IWL_WOWLAN_WAKEUP_LINK_CHANGE);
1033 if (wowlan->magic_pkt) 903 if (wowlan->magic_pkt)
1034 wowlan_config_cmd.wakeup_filter |= 904 wowlan_config_cmd.common.wakeup_filter |=
1035 cpu_to_le32(IWL_WOWLAN_WAKEUP_MAGIC_PACKET); 905 cpu_to_le32(IWL_WOWLAN_WAKEUP_MAGIC_PACKET);
1036 if (wowlan->gtk_rekey_failure) 906 if (wowlan->gtk_rekey_failure)
1037 wowlan_config_cmd.wakeup_filter |= 907 wowlan_config_cmd.common.wakeup_filter |=
1038 cpu_to_le32(IWL_WOWLAN_WAKEUP_GTK_REKEY_FAIL); 908 cpu_to_le32(IWL_WOWLAN_WAKEUP_GTK_REKEY_FAIL);
1039 if (wowlan->eap_identity_req) 909 if (wowlan->eap_identity_req)
1040 wowlan_config_cmd.wakeup_filter |= 910 wowlan_config_cmd.common.wakeup_filter |=
1041 cpu_to_le32(IWL_WOWLAN_WAKEUP_EAP_IDENT_REQ); 911 cpu_to_le32(IWL_WOWLAN_WAKEUP_EAP_IDENT_REQ);
1042 if (wowlan->four_way_handshake) 912 if (wowlan->four_way_handshake)
1043 wowlan_config_cmd.wakeup_filter |= 913 wowlan_config_cmd.common.wakeup_filter |=
1044 cpu_to_le32(IWL_WOWLAN_WAKEUP_4WAY_HANDSHAKE); 914 cpu_to_le32(IWL_WOWLAN_WAKEUP_4WAY_HANDSHAKE);
1045 if (wowlan->n_patterns) 915 if (wowlan->n_patterns)
1046 wowlan_config_cmd.wakeup_filter |= 916 wowlan_config_cmd.common.wakeup_filter |=
1047 cpu_to_le32(IWL_WOWLAN_WAKEUP_PATTERN_MATCH); 917 cpu_to_le32(IWL_WOWLAN_WAKEUP_PATTERN_MATCH);
1048 918
1049 if (wowlan->rfkill_release) 919 if (wowlan->rfkill_release)
1050 wowlan_config_cmd.wakeup_filter |= 920 wowlan_config_cmd.common.wakeup_filter |=
1051 cpu_to_le32(IWL_WOWLAN_WAKEUP_RF_KILL_DEASSERT); 921 cpu_to_le32(IWL_WOWLAN_WAKEUP_RF_KILL_DEASSERT);
1052 922
1053 if (wowlan->tcp) { 923 if (wowlan->tcp) {
@@ -1055,7 +925,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1055 * Set the "link change" (really "link lost") flag as well 925 * Set the "link change" (really "link lost") flag as well
1056 * since that implies losing the TCP connection. 926 * since that implies losing the TCP connection.
1057 */ 927 */
1058 wowlan_config_cmd.wakeup_filter |= 928 wowlan_config_cmd.common.wakeup_filter |=
1059 cpu_to_le32(IWL_WOWLAN_WAKEUP_REMOTE_LINK_LOSS | 929 cpu_to_le32(IWL_WOWLAN_WAKEUP_REMOTE_LINK_LOSS |
1060 IWL_WOWLAN_WAKEUP_REMOTE_SIGNATURE_TABLE | 930 IWL_WOWLAN_WAKEUP_REMOTE_SIGNATURE_TABLE |
1061 IWL_WOWLAN_WAKEUP_REMOTE_WAKEUP_PACKET | 931 IWL_WOWLAN_WAKEUP_REMOTE_WAKEUP_PACKET |
@@ -1067,16 +937,6 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1067 iwl_trans_stop_device(mvm->trans); 937 iwl_trans_stop_device(mvm->trans);
1068 938
1069 /* 939 /*
1070 * The D3 firmware still hardcodes the AP station ID for the
1071 * BSS we're associated with as 0. Store the real STA ID here
1072 * and assign 0. When we leave this function, we'll restore
1073 * the original value for the resume code.
1074 */
1075 old_ap_sta_id = mvm_ap_sta->sta_id;
1076 mvm_ap_sta->sta_id = 0;
1077 mvmvif->ap_sta_id = 0;
1078
1079 /*
1080 * Set the HW restart bit -- this is mostly true as we're 940 * Set the HW restart bit -- this is mostly true as we're
1081 * going to load new firmware and reprogram that, though 941 * going to load new firmware and reprogram that, though
1082 * the reprogramming is going to be manual to avoid adding 942 * the reprogramming is going to be manual to avoid adding
@@ -1096,16 +956,6 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1096 mvm->ptk_ivlen = 0; 956 mvm->ptk_ivlen = 0;
1097 mvm->ptk_icvlen = 0; 957 mvm->ptk_icvlen = 0;
1098 958
1099 /*
1100 * The D3 firmware still hardcodes the AP station ID for the
1101 * BSS we're associated with as 0. As a result, we have to move
1102 * the auxiliary station to ID 1 so the ID 0 remains free for
1103 * the AP station for later.
1104 * We set the sta_id to 1 here, and reset it to its previous
1105 * value (that we stored above) later.
1106 */
1107 mvm->aux_sta.sta_id = 1;
1108
1109 ret = iwl_mvm_load_d3_fw(mvm); 959 ret = iwl_mvm_load_d3_fw(mvm);
1110 if (ret) 960 if (ret)
1111 goto out; 961 goto out;
@@ -1173,9 +1023,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1173 } 1023 }
1174 } 1024 }
1175 1025
1176 ret = iwl_mvm_send_cmd_pdu(mvm, WOWLAN_CONFIGURATION, 1026 ret = iwl_mvm_send_wowlan_config_cmd(mvm, &wowlan_config_cmd);
1177 CMD_SYNC, sizeof(wowlan_config_cmd),
1178 &wowlan_config_cmd);
1179 if (ret) 1027 if (ret)
1180 goto out; 1028 goto out;
1181 1029
@@ -1183,7 +1031,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1183 if (ret) 1031 if (ret)
1184 goto out; 1032 goto out;
1185 1033
1186 ret = iwl_mvm_send_proto_offload(mvm, vif); 1034 ret = iwl_mvm_send_proto_offload(mvm, vif, false, CMD_SYNC);
1187 if (ret) 1035 if (ret)
1188 goto out; 1036 goto out;
1189 1037
@@ -1191,11 +1039,11 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1191 if (ret) 1039 if (ret)
1192 goto out; 1040 goto out;
1193 1041
1194 ret = iwl_mvm_power_update_device_mode(mvm); 1042 ret = iwl_mvm_power_update_device(mvm);
1195 if (ret) 1043 if (ret)
1196 goto out; 1044 goto out;
1197 1045
1198 ret = iwl_mvm_power_update_mode(mvm, vif); 1046 ret = iwl_mvm_power_update_mac(mvm, vif);
1199 if (ret) 1047 if (ret)
1200 goto out; 1048 goto out;
1201 1049
@@ -1222,10 +1070,6 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1222 1070
1223 iwl_trans_d3_suspend(mvm->trans, test); 1071 iwl_trans_d3_suspend(mvm->trans, test);
1224 out: 1072 out:
1225 mvm->aux_sta.sta_id = old_aux_sta_id;
1226 mvm_ap_sta->sta_id = old_ap_sta_id;
1227 mvmvif->ap_sta_id = old_ap_sta_id;
1228
1229 if (ret < 0) 1073 if (ret < 0)
1230 ieee80211_restart_hw(mvm->hw); 1074 ieee80211_restart_hw(mvm->hw);
1231 out_noreset: 1075 out_noreset:
diff --git a/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c b/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c
index 0e29cd83a06a..9b59e1d7ae71 100644
--- a/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c
+++ b/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c
@@ -185,7 +185,7 @@ static ssize_t iwl_dbgfs_pm_params_write(struct ieee80211_vif *vif, char *buf,
185 185
186 mutex_lock(&mvm->mutex); 186 mutex_lock(&mvm->mutex);
187 iwl_dbgfs_update_pm(mvm, vif, param, val); 187 iwl_dbgfs_update_pm(mvm, vif, param, val);
188 ret = iwl_mvm_power_update_mode(mvm, vif); 188 ret = iwl_mvm_power_update_mac(mvm, vif);
189 mutex_unlock(&mvm->mutex); 189 mutex_unlock(&mvm->mutex);
190 190
191 return ret ?: count; 191 return ret ?: count;
@@ -202,7 +202,7 @@ static ssize_t iwl_dbgfs_pm_params_read(struct file *file,
202 int bufsz = sizeof(buf); 202 int bufsz = sizeof(buf);
203 int pos; 203 int pos;
204 204
205 pos = iwl_mvm_power_dbgfs_read(mvm, vif, buf, bufsz); 205 pos = iwl_mvm_power_mac_dbgfs_read(mvm, vif, buf, bufsz);
206 206
207 return simple_read_from_buffer(user_buf, count, ppos, buf, pos); 207 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
208} 208}
@@ -225,6 +225,29 @@ static ssize_t iwl_dbgfs_mac_params_read(struct file *file,
225 225
226 ap_sta_id = mvmvif->ap_sta_id; 226 ap_sta_id = mvmvif->ap_sta_id;
227 227
228 switch (ieee80211_vif_type_p2p(vif)) {
229 case NL80211_IFTYPE_ADHOC:
230 pos += scnprintf(buf+pos, bufsz-pos, "type: ibss\n");
231 break;
232 case NL80211_IFTYPE_STATION:
233 pos += scnprintf(buf+pos, bufsz-pos, "type: bss\n");
234 break;
235 case NL80211_IFTYPE_AP:
236 pos += scnprintf(buf+pos, bufsz-pos, "type: ap\n");
237 break;
238 case NL80211_IFTYPE_P2P_CLIENT:
239 pos += scnprintf(buf+pos, bufsz-pos, "type: p2p client\n");
240 break;
241 case NL80211_IFTYPE_P2P_GO:
242 pos += scnprintf(buf+pos, bufsz-pos, "type: p2p go\n");
243 break;
244 case NL80211_IFTYPE_P2P_DEVICE:
245 pos += scnprintf(buf+pos, bufsz-pos, "type: p2p dev\n");
246 break;
247 default:
248 break;
249 }
250
228 pos += scnprintf(buf+pos, bufsz-pos, "mac id/color: %d / %d\n", 251 pos += scnprintf(buf+pos, bufsz-pos, "mac id/color: %d / %d\n",
229 mvmvif->id, mvmvif->color); 252 mvmvif->id, mvmvif->color);
230 pos += scnprintf(buf+pos, bufsz-pos, "bssid: %pM\n", 253 pos += scnprintf(buf+pos, bufsz-pos, "bssid: %pM\n",
@@ -249,9 +272,10 @@ static ssize_t iwl_dbgfs_mac_params_read(struct file *file,
249 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv; 272 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv;
250 273
251 pos += scnprintf(buf+pos, bufsz-pos, 274 pos += scnprintf(buf+pos, bufsz-pos,
252 "ap_sta_id %d - reduced Tx power %d\n", 275 "ap_sta_id %d - reduced Tx power %d force %d\n",
253 ap_sta_id, 276 ap_sta_id,
254 mvm_sta->bt_reduced_txpower); 277 mvm_sta->bt_reduced_txpower,
278 mvm_sta->bt_reduced_txpower_dbg);
255 } 279 }
256 } 280 }
257 281
@@ -269,6 +293,41 @@ static ssize_t iwl_dbgfs_mac_params_read(struct file *file,
269 return simple_read_from_buffer(user_buf, count, ppos, buf, pos); 293 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
270} 294}
271 295
296static ssize_t iwl_dbgfs_reduced_txp_write(struct ieee80211_vif *vif,
297 char *buf, size_t count,
298 loff_t *ppos)
299{
300 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
301 struct iwl_mvm *mvm = mvmvif->mvm;
302 struct iwl_mvm_sta *mvmsta;
303 bool reduced_tx_power;
304 int ret;
305
306 if (mvmvif->ap_sta_id >= ARRAY_SIZE(mvm->fw_id_to_mac_id))
307 return -ENOTCONN;
308
309 if (strtobool(buf, &reduced_tx_power) != 0)
310 return -EINVAL;
311
312 mutex_lock(&mvm->mutex);
313
314 mvmsta = iwl_mvm_sta_from_staid_protected(mvm, mvmvif->ap_sta_id);
315 if (IS_ERR_OR_NULL(mvmsta)) {
316 mutex_unlock(&mvm->mutex);
317 return -ENOTCONN;
318 }
319
320 mvmsta->bt_reduced_txpower_dbg = false;
321 ret = iwl_mvm_bt_coex_reduced_txp(mvm, mvmvif->ap_sta_id,
322 reduced_tx_power);
323 if (!ret)
324 mvmsta->bt_reduced_txpower_dbg = true;
325
326 mutex_unlock(&mvm->mutex);
327
328 return ret ? : count;
329}
330
272static void iwl_dbgfs_update_bf(struct ieee80211_vif *vif, 331static void iwl_dbgfs_update_bf(struct ieee80211_vif *vif,
273 enum iwl_dbgfs_bf_mask param, int value) 332 enum iwl_dbgfs_bf_mask param, int value)
274{ 333{
@@ -403,9 +462,9 @@ static ssize_t iwl_dbgfs_bf_params_write(struct ieee80211_vif *vif, char *buf,
403 mutex_lock(&mvm->mutex); 462 mutex_lock(&mvm->mutex);
404 iwl_dbgfs_update_bf(vif, param, value); 463 iwl_dbgfs_update_bf(vif, param, value);
405 if (param == MVM_DEBUGFS_BF_ENABLE_BEACON_FILTER && !value) 464 if (param == MVM_DEBUGFS_BF_ENABLE_BEACON_FILTER && !value)
406 ret = iwl_mvm_disable_beacon_filter(mvm, vif); 465 ret = iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC);
407 else 466 else
408 ret = iwl_mvm_enable_beacon_filter(mvm, vif); 467 ret = iwl_mvm_enable_beacon_filter(mvm, vif, CMD_SYNC);
409 mutex_unlock(&mvm->mutex); 468 mutex_unlock(&mvm->mutex);
410 469
411 return ret ?: count; 470 return ret ?: count;
@@ -460,6 +519,41 @@ static ssize_t iwl_dbgfs_bf_params_read(struct file *file,
460 return simple_read_from_buffer(user_buf, count, ppos, buf, pos); 519 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
461} 520}
462 521
522static ssize_t iwl_dbgfs_low_latency_write(struct ieee80211_vif *vif, char *buf,
523 size_t count, loff_t *ppos)
524{
525 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
526 struct iwl_mvm *mvm = mvmvif->mvm;
527 u8 value;
528 int ret;
529
530 ret = kstrtou8(buf, 0, &value);
531 if (ret)
532 return ret;
533 if (value > 1)
534 return -EINVAL;
535
536 mutex_lock(&mvm->mutex);
537 iwl_mvm_update_low_latency(mvm, vif, value);
538 mutex_unlock(&mvm->mutex);
539
540 return count;
541}
542
543static ssize_t iwl_dbgfs_low_latency_read(struct file *file,
544 char __user *user_buf,
545 size_t count, loff_t *ppos)
546{
547 struct ieee80211_vif *vif = file->private_data;
548 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
549 char buf[3];
550
551 buf[0] = mvmvif->low_latency ? '1' : '0';
552 buf[1] = '\n';
553 buf[2] = '\0';
554 return simple_read_from_buffer(user_buf, count, ppos, buf, sizeof(buf));
555}
556
463#define MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz) \ 557#define MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz) \
464 _MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz, struct ieee80211_vif) 558 _MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz, struct ieee80211_vif)
465#define MVM_DEBUGFS_READ_WRITE_FILE_OPS(name, bufsz) \ 559#define MVM_DEBUGFS_READ_WRITE_FILE_OPS(name, bufsz) \
@@ -473,6 +567,8 @@ static ssize_t iwl_dbgfs_bf_params_read(struct file *file,
473MVM_DEBUGFS_READ_FILE_OPS(mac_params); 567MVM_DEBUGFS_READ_FILE_OPS(mac_params);
474MVM_DEBUGFS_READ_WRITE_FILE_OPS(pm_params, 32); 568MVM_DEBUGFS_READ_WRITE_FILE_OPS(pm_params, 32);
475MVM_DEBUGFS_READ_WRITE_FILE_OPS(bf_params, 256); 569MVM_DEBUGFS_READ_WRITE_FILE_OPS(bf_params, 256);
570MVM_DEBUGFS_READ_WRITE_FILE_OPS(low_latency, 10);
571MVM_DEBUGFS_WRITE_FILE_OPS(reduced_txp, 10);
476 572
477void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif) 573void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
478{ 574{
@@ -496,15 +592,18 @@ void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
496 return; 592 return;
497 } 593 }
498 594
499 if (iwlmvm_mod_params.power_scheme != IWL_POWER_SCHEME_CAM && 595 if ((mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_PM_CMD_SUPPORT) &&
596 iwlmvm_mod_params.power_scheme != IWL_POWER_SCHEME_CAM &&
500 ((vif->type == NL80211_IFTYPE_STATION && !vif->p2p) || 597 ((vif->type == NL80211_IFTYPE_STATION && !vif->p2p) ||
501 (vif->type == NL80211_IFTYPE_STATION && vif->p2p && 598 (vif->type == NL80211_IFTYPE_STATION && vif->p2p &&
502 mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_P2P_PS))) 599 mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM)))
503 MVM_DEBUGFS_ADD_FILE_VIF(pm_params, mvmvif->dbgfs_dir, S_IWUSR | 600 MVM_DEBUGFS_ADD_FILE_VIF(pm_params, mvmvif->dbgfs_dir, S_IWUSR |
504 S_IRUSR); 601 S_IRUSR);
505 602
506 MVM_DEBUGFS_ADD_FILE_VIF(mac_params, mvmvif->dbgfs_dir, 603 MVM_DEBUGFS_ADD_FILE_VIF(mac_params, mvmvif->dbgfs_dir, S_IRUSR);
507 S_IRUSR); 604 MVM_DEBUGFS_ADD_FILE_VIF(reduced_txp, mvmvif->dbgfs_dir, S_IWUSR);
605 MVM_DEBUGFS_ADD_FILE_VIF(low_latency, mvmvif->dbgfs_dir,
606 S_IRUSR | S_IWUSR);
508 607
509 if (vif->type == NL80211_IFTYPE_STATION && !vif->p2p && 608 if (vif->type == NL80211_IFTYPE_STATION && !vif->p2p &&
510 mvmvif == mvm->bf_allowed_vif) 609 mvmvif == mvm->bf_allowed_vif)
diff --git a/drivers/net/wireless/iwlwifi/mvm/debugfs.c b/drivers/net/wireless/iwlwifi/mvm/debugfs.c
index 369d4c90e669..1b52deea6081 100644
--- a/drivers/net/wireless/iwlwifi/mvm/debugfs.c
+++ b/drivers/net/wireless/iwlwifi/mvm/debugfs.c
@@ -60,11 +60,14 @@
60 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 60 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
61 * 61 *
62 *****************************************************************************/ 62 *****************************************************************************/
63#include <linux/vmalloc.h>
64
63#include "mvm.h" 65#include "mvm.h"
64#include "sta.h" 66#include "sta.h"
65#include "iwl-io.h" 67#include "iwl-io.h"
66#include "iwl-prph.h" 68#include "iwl-prph.h"
67#include "debugfs.h" 69#include "debugfs.h"
70#include "fw-error-dump.h"
68 71
69static ssize_t iwl_dbgfs_tx_flush_write(struct iwl_mvm *mvm, char *buf, 72static ssize_t iwl_dbgfs_tx_flush_write(struct iwl_mvm *mvm, char *buf,
70 size_t count, loff_t *ppos) 73 size_t count, loff_t *ppos)
@@ -90,7 +93,7 @@ static ssize_t iwl_dbgfs_tx_flush_write(struct iwl_mvm *mvm, char *buf,
90static ssize_t iwl_dbgfs_sta_drain_write(struct iwl_mvm *mvm, char *buf, 93static ssize_t iwl_dbgfs_sta_drain_write(struct iwl_mvm *mvm, char *buf,
91 size_t count, loff_t *ppos) 94 size_t count, loff_t *ppos)
92{ 95{
93 struct ieee80211_sta *sta; 96 struct iwl_mvm_sta *mvmsta;
94 int sta_id, drain, ret; 97 int sta_id, drain, ret;
95 98
96 if (!mvm->ucode_loaded || mvm->cur_ucode != IWL_UCODE_REGULAR) 99 if (!mvm->ucode_loaded || mvm->cur_ucode != IWL_UCODE_REGULAR)
@@ -105,19 +108,63 @@ static ssize_t iwl_dbgfs_sta_drain_write(struct iwl_mvm *mvm, char *buf,
105 108
106 mutex_lock(&mvm->mutex); 109 mutex_lock(&mvm->mutex);
107 110
108 sta = rcu_dereference_protected(mvm->fw_id_to_mac_id[sta_id], 111 mvmsta = iwl_mvm_sta_from_staid_protected(mvm, sta_id);
109 lockdep_is_held(&mvm->mutex)); 112
110 if (IS_ERR_OR_NULL(sta)) 113 if (!mvmsta)
111 ret = -ENOENT; 114 ret = -ENOENT;
112 else 115 else
113 ret = iwl_mvm_drain_sta(mvm, (void *)sta->drv_priv, drain) ? : 116 ret = iwl_mvm_drain_sta(mvm, mvmsta, drain) ? : count;
114 count;
115 117
116 mutex_unlock(&mvm->mutex); 118 mutex_unlock(&mvm->mutex);
117 119
118 return ret; 120 return ret;
119} 121}
120 122
123static int iwl_dbgfs_fw_error_dump_open(struct inode *inode, struct file *file)
124{
125 struct iwl_mvm *mvm = inode->i_private;
126 int ret;
127
128 if (!mvm)
129 return -EINVAL;
130
131 mutex_lock(&mvm->mutex);
132 if (!mvm->fw_error_dump) {
133 ret = -ENODATA;
134 goto out;
135 }
136
137 file->private_data = mvm->fw_error_dump;
138 mvm->fw_error_dump = NULL;
139 kfree(mvm->fw_error_sram);
140 mvm->fw_error_sram = NULL;
141 mvm->fw_error_sram_len = 0;
142 ret = 0;
143
144out:
145 mutex_unlock(&mvm->mutex);
146 return ret;
147}
148
149static ssize_t iwl_dbgfs_fw_error_dump_read(struct file *file,
150 char __user *user_buf,
151 size_t count, loff_t *ppos)
152{
153 struct iwl_fw_error_dump_file *dump_file = file->private_data;
154
155 return simple_read_from_buffer(user_buf, count, ppos,
156 dump_file,
157 le32_to_cpu(dump_file->file_len));
158}
159
160static int iwl_dbgfs_fw_error_dump_release(struct inode *inode,
161 struct file *file)
162{
163 vfree(file->private_data);
164
165 return 0;
166}
167
121static ssize_t iwl_dbgfs_sram_read(struct file *file, char __user *user_buf, 168static ssize_t iwl_dbgfs_sram_read(struct file *file, char __user *user_buf,
122 size_t count, loff_t *ppos) 169 size_t count, loff_t *ppos)
123{ 170{
@@ -251,7 +298,7 @@ static ssize_t iwl_dbgfs_disable_power_off_write(struct iwl_mvm *mvm, char *buf,
251 } 298 }
252 299
253 mutex_lock(&mvm->mutex); 300 mutex_lock(&mvm->mutex);
254 ret = iwl_mvm_power_update_device_mode(mvm); 301 ret = iwl_mvm_power_update_device(mvm);
255 mutex_unlock(&mvm->mutex); 302 mutex_unlock(&mvm->mutex);
256 303
257 return ret ?: count; 304 return ret ?: count;
@@ -351,6 +398,9 @@ static ssize_t iwl_dbgfs_bt_notif_read(struct file *file, char __user *user_buf,
351 le32_to_cpu(notif->secondary_ch_lut)); 398 le32_to_cpu(notif->secondary_ch_lut));
352 pos += scnprintf(buf+pos, bufsz-pos, "bt_activity_grading = %d\n", 399 pos += scnprintf(buf+pos, bufsz-pos, "bt_activity_grading = %d\n",
353 le32_to_cpu(notif->bt_activity_grading)); 400 le32_to_cpu(notif->bt_activity_grading));
401 pos += scnprintf(buf+pos, bufsz-pos,
402 "antenna isolation = %d CORUN LUT index = %d\n",
403 mvm->last_ant_isol, mvm->last_corun_lut);
354 404
355 mutex_unlock(&mvm->mutex); 405 mutex_unlock(&mvm->mutex);
356 406
@@ -393,6 +443,22 @@ static ssize_t iwl_dbgfs_bt_cmd_read(struct file *file, char __user *user_buf,
393 return simple_read_from_buffer(user_buf, count, ppos, buf, pos); 443 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
394} 444}
395 445
446static ssize_t
447iwl_dbgfs_bt_tx_prio_write(struct iwl_mvm *mvm, char *buf,
448 size_t count, loff_t *ppos)
449{
450 u32 bt_tx_prio;
451
452 if (sscanf(buf, "%u", &bt_tx_prio) != 1)
453 return -EINVAL;
454 if (bt_tx_prio > 4)
455 return -EINVAL;
456
457 mvm->bt_tx_prio = bt_tx_prio;
458
459 return count;
460}
461
396#define PRINT_STATS_LE32(_str, _val) \ 462#define PRINT_STATS_LE32(_str, _val) \
397 pos += scnprintf(buf + pos, bufsz - pos, \ 463 pos += scnprintf(buf + pos, bufsz - pos, \
398 fmt_table, _str, \ 464 fmt_table, _str, \
@@ -532,6 +598,80 @@ static ssize_t iwl_dbgfs_fw_rx_stats_read(struct file *file,
532} 598}
533#undef PRINT_STAT_LE32 599#undef PRINT_STAT_LE32
534 600
601static ssize_t iwl_dbgfs_frame_stats_read(struct iwl_mvm *mvm,
602 char __user *user_buf, size_t count,
603 loff_t *ppos,
604 struct iwl_mvm_frame_stats *stats)
605{
606 char *buff, *pos, *endpos;
607 int idx, i;
608 int ret;
609 static const size_t bufsz = 1024;
610
611 buff = kmalloc(bufsz, GFP_KERNEL);
612 if (!buff)
613 return -ENOMEM;
614
615 spin_lock_bh(&mvm->drv_stats_lock);
616
617 pos = buff;
618 endpos = pos + bufsz;
619
620 pos += scnprintf(pos, endpos - pos,
621 "Legacy/HT/VHT\t:\t%d/%d/%d\n",
622 stats->legacy_frames,
623 stats->ht_frames,
624 stats->vht_frames);
625 pos += scnprintf(pos, endpos - pos, "20/40/80\t:\t%d/%d/%d\n",
626 stats->bw_20_frames,
627 stats->bw_40_frames,
628 stats->bw_80_frames);
629 pos += scnprintf(pos, endpos - pos, "NGI/SGI\t\t:\t%d/%d\n",
630 stats->ngi_frames,
631 stats->sgi_frames);
632 pos += scnprintf(pos, endpos - pos, "SISO/MIMO2\t:\t%d/%d\n",
633 stats->siso_frames,
634 stats->mimo2_frames);
635 pos += scnprintf(pos, endpos - pos, "FAIL/SCSS\t:\t%d/%d\n",
636 stats->fail_frames,
637 stats->success_frames);
638 pos += scnprintf(pos, endpos - pos, "MPDUs agg\t:\t%d\n",
639 stats->agg_frames);
640 pos += scnprintf(pos, endpos - pos, "A-MPDUs\t\t:\t%d\n",
641 stats->ampdu_count);
642 pos += scnprintf(pos, endpos - pos, "Avg MPDUs/A-MPDU:\t%d\n",
643 stats->ampdu_count > 0 ?
644 (stats->agg_frames / stats->ampdu_count) : 0);
645
646 pos += scnprintf(pos, endpos - pos, "Last Rates\n");
647
648 idx = stats->last_frame_idx - 1;
649 for (i = 0; i < ARRAY_SIZE(stats->last_rates); i++) {
650 idx = (idx + 1) % ARRAY_SIZE(stats->last_rates);
651 if (stats->last_rates[idx] == 0)
652 continue;
653 pos += scnprintf(pos, endpos - pos, "Rate[%d]: ",
654 (int)(ARRAY_SIZE(stats->last_rates) - i));
655 pos += rs_pretty_print_rate(pos, stats->last_rates[idx]);
656 }
657 spin_unlock_bh(&mvm->drv_stats_lock);
658
659 ret = simple_read_from_buffer(user_buf, count, ppos, buff, pos - buff);
660 kfree(buff);
661
662 return ret;
663}
664
665static ssize_t iwl_dbgfs_drv_rx_stats_read(struct file *file,
666 char __user *user_buf, size_t count,
667 loff_t *ppos)
668{
669 struct iwl_mvm *mvm = file->private_data;
670
671 return iwl_dbgfs_frame_stats_read(mvm, user_buf, count, ppos,
672 &mvm->drv_rx_stats);
673}
674
535static ssize_t iwl_dbgfs_fw_restart_write(struct iwl_mvm *mvm, char *buf, 675static ssize_t iwl_dbgfs_fw_restart_write(struct iwl_mvm *mvm, char *buf,
536 size_t count, loff_t *ppos) 676 size_t count, loff_t *ppos)
537{ 677{
@@ -592,7 +732,7 @@ iwl_dbgfs_scan_ant_rxchain_write(struct iwl_mvm *mvm, char *buf,
592 return -EINVAL; 732 return -EINVAL;
593 if (scan_rx_ant > ANT_ABC) 733 if (scan_rx_ant > ANT_ABC)
594 return -EINVAL; 734 return -EINVAL;
595 if (scan_rx_ant & ~iwl_fw_valid_rx_ant(mvm->fw)) 735 if (scan_rx_ant & ~mvm->fw->valid_rx_ant)
596 return -EINVAL; 736 return -EINVAL;
597 737
598 mvm->scan_rx_ant = scan_rx_ant; 738 mvm->scan_rx_ant = scan_rx_ant;
@@ -600,6 +740,187 @@ iwl_dbgfs_scan_ant_rxchain_write(struct iwl_mvm *mvm, char *buf,
600 return count; 740 return count;
601} 741}
602 742
743#define ADD_TEXT(...) pos += scnprintf(buf + pos, bufsz - pos, __VA_ARGS__)
744#ifdef CONFIG_IWLWIFI_BCAST_FILTERING
745static ssize_t iwl_dbgfs_bcast_filters_read(struct file *file,
746 char __user *user_buf,
747 size_t count, loff_t *ppos)
748{
749 struct iwl_mvm *mvm = file->private_data;
750 struct iwl_bcast_filter_cmd cmd;
751 const struct iwl_fw_bcast_filter *filter;
752 char *buf;
753 int bufsz = 1024;
754 int i, j, pos = 0;
755 ssize_t ret;
756
757 buf = kzalloc(bufsz, GFP_KERNEL);
758 if (!buf)
759 return -ENOMEM;
760
761 mutex_lock(&mvm->mutex);
762 if (!iwl_mvm_bcast_filter_build_cmd(mvm, &cmd)) {
763 ADD_TEXT("None\n");
764 mutex_unlock(&mvm->mutex);
765 goto out;
766 }
767 mutex_unlock(&mvm->mutex);
768
769 for (i = 0; cmd.filters[i].attrs[0].mask; i++) {
770 filter = &cmd.filters[i];
771
772 ADD_TEXT("Filter [%d]:\n", i);
773 ADD_TEXT("\tDiscard=%d\n", filter->discard);
774 ADD_TEXT("\tFrame Type: %s\n",
775 filter->frame_type ? "IPv4" : "Generic");
776
777 for (j = 0; j < ARRAY_SIZE(filter->attrs); j++) {
778 const struct iwl_fw_bcast_filter_attr *attr;
779
780 attr = &filter->attrs[j];
781 if (!attr->mask)
782 break;
783
784 ADD_TEXT("\tAttr [%d]: offset=%d (from %s), mask=0x%x, value=0x%x reserved=0x%x\n",
785 j, attr->offset,
786 attr->offset_type ? "IP End" :
787 "Payload Start",
788 be32_to_cpu(attr->mask),
789 be32_to_cpu(attr->val),
790 le16_to_cpu(attr->reserved1));
791 }
792 }
793out:
794 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
795 kfree(buf);
796 return ret;
797}
798
799static ssize_t iwl_dbgfs_bcast_filters_write(struct iwl_mvm *mvm, char *buf,
800 size_t count, loff_t *ppos)
801{
802 int pos, next_pos;
803 struct iwl_fw_bcast_filter filter = {};
804 struct iwl_bcast_filter_cmd cmd;
805 u32 filter_id, attr_id, mask, value;
806 int err = 0;
807
808 if (sscanf(buf, "%d %hhi %hhi %n", &filter_id, &filter.discard,
809 &filter.frame_type, &pos) != 3)
810 return -EINVAL;
811
812 if (filter_id >= ARRAY_SIZE(mvm->dbgfs_bcast_filtering.cmd.filters) ||
813 filter.frame_type > BCAST_FILTER_FRAME_TYPE_IPV4)
814 return -EINVAL;
815
816 for (attr_id = 0; attr_id < ARRAY_SIZE(filter.attrs);
817 attr_id++) {
818 struct iwl_fw_bcast_filter_attr *attr =
819 &filter.attrs[attr_id];
820
821 if (pos >= count)
822 break;
823
824 if (sscanf(&buf[pos], "%hhi %hhi %i %i %n",
825 &attr->offset, &attr->offset_type,
826 &mask, &value, &next_pos) != 4)
827 return -EINVAL;
828
829 attr->mask = cpu_to_be32(mask);
830 attr->val = cpu_to_be32(value);
831 if (mask)
832 filter.num_attrs++;
833
834 pos += next_pos;
835 }
836
837 mutex_lock(&mvm->mutex);
838 memcpy(&mvm->dbgfs_bcast_filtering.cmd.filters[filter_id],
839 &filter, sizeof(filter));
840
841 /* send updated bcast filtering configuration */
842 if (mvm->dbgfs_bcast_filtering.override &&
843 iwl_mvm_bcast_filter_build_cmd(mvm, &cmd))
844 err = iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, CMD_SYNC,
845 sizeof(cmd), &cmd);
846 mutex_unlock(&mvm->mutex);
847
848 return err ?: count;
849}
850
851static ssize_t iwl_dbgfs_bcast_filters_macs_read(struct file *file,
852 char __user *user_buf,
853 size_t count, loff_t *ppos)
854{
855 struct iwl_mvm *mvm = file->private_data;
856 struct iwl_bcast_filter_cmd cmd;
857 char *buf;
858 int bufsz = 1024;
859 int i, pos = 0;
860 ssize_t ret;
861
862 buf = kzalloc(bufsz, GFP_KERNEL);
863 if (!buf)
864 return -ENOMEM;
865
866 mutex_lock(&mvm->mutex);
867 if (!iwl_mvm_bcast_filter_build_cmd(mvm, &cmd)) {
868 ADD_TEXT("None\n");
869 mutex_unlock(&mvm->mutex);
870 goto out;
871 }
872 mutex_unlock(&mvm->mutex);
873
874 for (i = 0; i < ARRAY_SIZE(cmd.macs); i++) {
875 const struct iwl_fw_bcast_mac *mac = &cmd.macs[i];
876
877 ADD_TEXT("Mac [%d]: discard=%d attached_filters=0x%x\n",
878 i, mac->default_discard, mac->attached_filters);
879 }
880out:
881 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
882 kfree(buf);
883 return ret;
884}
885
886static ssize_t iwl_dbgfs_bcast_filters_macs_write(struct iwl_mvm *mvm,
887 char *buf, size_t count,
888 loff_t *ppos)
889{
890 struct iwl_bcast_filter_cmd cmd;
891 struct iwl_fw_bcast_mac mac = {};
892 u32 mac_id, attached_filters;
893 int err = 0;
894
895 if (!mvm->bcast_filters)
896 return -ENOENT;
897
898 if (sscanf(buf, "%d %hhi %i", &mac_id, &mac.default_discard,
899 &attached_filters) != 3)
900 return -EINVAL;
901
902 if (mac_id >= ARRAY_SIZE(cmd.macs) ||
903 mac.default_discard > 1 ||
904 attached_filters >= BIT(ARRAY_SIZE(cmd.filters)))
905 return -EINVAL;
906
907 mac.attached_filters = cpu_to_le16(attached_filters);
908
909 mutex_lock(&mvm->mutex);
910 memcpy(&mvm->dbgfs_bcast_filtering.cmd.macs[mac_id],
911 &mac, sizeof(mac));
912
913 /* send updated bcast filtering configuration */
914 if (mvm->dbgfs_bcast_filtering.override &&
915 iwl_mvm_bcast_filter_build_cmd(mvm, &cmd))
916 err = iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, CMD_SYNC,
917 sizeof(cmd), &cmd);
918 mutex_unlock(&mvm->mutex);
919
920 return err ?: count;
921}
922#endif
923
603#ifdef CONFIG_PM_SLEEP 924#ifdef CONFIG_PM_SLEEP
604static ssize_t iwl_dbgfs_d3_sram_write(struct iwl_mvm *mvm, char *buf, 925static ssize_t iwl_dbgfs_d3_sram_write(struct iwl_mvm *mvm, char *buf,
605 size_t count, loff_t *ppos) 926 size_t count, loff_t *ppos)
@@ -658,15 +979,117 @@ static ssize_t iwl_dbgfs_d3_sram_read(struct file *file, char __user *user_buf,
658} 979}
659#endif 980#endif
660 981
982#define PRINT_MVM_REF(ref) do { \
983 if (test_bit(ref, mvm->ref_bitmap)) \
984 pos += scnprintf(buf + pos, bufsz - pos, \
985 "\t(0x%lx) %s\n", \
986 BIT(ref), #ref); \
987} while (0)
988
989static ssize_t iwl_dbgfs_d0i3_refs_read(struct file *file,
990 char __user *user_buf,
991 size_t count, loff_t *ppos)
992{
993 struct iwl_mvm *mvm = file->private_data;
994 int pos = 0;
995 char buf[256];
996 const size_t bufsz = sizeof(buf);
997
998 pos += scnprintf(buf + pos, bufsz - pos, "taken mvm refs: 0x%lx\n",
999 mvm->ref_bitmap[0]);
1000
1001 PRINT_MVM_REF(IWL_MVM_REF_UCODE_DOWN);
1002 PRINT_MVM_REF(IWL_MVM_REF_SCAN);
1003 PRINT_MVM_REF(IWL_MVM_REF_ROC);
1004 PRINT_MVM_REF(IWL_MVM_REF_P2P_CLIENT);
1005 PRINT_MVM_REF(IWL_MVM_REF_AP_IBSS);
1006 PRINT_MVM_REF(IWL_MVM_REF_USER);
1007
1008 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
1009}
1010
1011static ssize_t iwl_dbgfs_d0i3_refs_write(struct iwl_mvm *mvm, char *buf,
1012 size_t count, loff_t *ppos)
1013{
1014 unsigned long value;
1015 int ret;
1016 bool taken;
1017
1018 ret = kstrtoul(buf, 10, &value);
1019 if (ret < 0)
1020 return ret;
1021
1022 mutex_lock(&mvm->mutex);
1023
1024 taken = test_bit(IWL_MVM_REF_USER, mvm->ref_bitmap);
1025 if (value == 1 && !taken)
1026 iwl_mvm_ref(mvm, IWL_MVM_REF_USER);
1027 else if (value == 0 && taken)
1028 iwl_mvm_unref(mvm, IWL_MVM_REF_USER);
1029 else
1030 ret = -EINVAL;
1031
1032 mutex_unlock(&mvm->mutex);
1033
1034 if (ret < 0)
1035 return ret;
1036 return count;
1037}
1038
661#define MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz) \ 1039#define MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz) \
662 _MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz, struct iwl_mvm) 1040 _MVM_DEBUGFS_WRITE_FILE_OPS(name, bufsz, struct iwl_mvm)
663#define MVM_DEBUGFS_READ_WRITE_FILE_OPS(name, bufsz) \ 1041#define MVM_DEBUGFS_READ_WRITE_FILE_OPS(name, bufsz) \
664 _MVM_DEBUGFS_READ_WRITE_FILE_OPS(name, bufsz, struct iwl_mvm) 1042 _MVM_DEBUGFS_READ_WRITE_FILE_OPS(name, bufsz, struct iwl_mvm)
665#define MVM_DEBUGFS_ADD_FILE(name, parent, mode) do { \ 1043#define MVM_DEBUGFS_ADD_FILE_ALIAS(alias, name, parent, mode) do { \
666 if (!debugfs_create_file(#name, mode, parent, mvm, \ 1044 if (!debugfs_create_file(alias, mode, parent, mvm, \
667 &iwl_dbgfs_##name##_ops)) \ 1045 &iwl_dbgfs_##name##_ops)) \
668 goto err; \ 1046 goto err; \
669 } while (0) 1047 } while (0)
1048#define MVM_DEBUGFS_ADD_FILE(name, parent, mode) \
1049 MVM_DEBUGFS_ADD_FILE_ALIAS(#name, name, parent, mode)
1050
1051static ssize_t
1052iwl_dbgfs_prph_reg_read(struct file *file,
1053 char __user *user_buf,
1054 size_t count, loff_t *ppos)
1055{
1056 struct iwl_mvm *mvm = file->private_data;
1057 int pos = 0;
1058 char buf[32];
1059 const size_t bufsz = sizeof(buf);
1060
1061 if (!mvm->dbgfs_prph_reg_addr)
1062 return -EINVAL;
1063
1064 pos += scnprintf(buf + pos, bufsz - pos, "Reg 0x%x: (0x%x)\n",
1065 mvm->dbgfs_prph_reg_addr,
1066 iwl_read_prph(mvm->trans, mvm->dbgfs_prph_reg_addr));
1067
1068 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
1069}
1070
1071static ssize_t
1072iwl_dbgfs_prph_reg_write(struct iwl_mvm *mvm, char *buf,
1073 size_t count, loff_t *ppos)
1074{
1075 u8 args;
1076 u32 value;
1077
1078 args = sscanf(buf, "%i %i", &mvm->dbgfs_prph_reg_addr, &value);
1079 /* if we only want to set the reg address - nothing more to do */
1080 if (args == 1)
1081 goto out;
1082
1083 /* otherwise, make sure we have both address and value */
1084 if (args != 2)
1085 return -EINVAL;
1086
1087 iwl_write_prph(mvm->trans, mvm->dbgfs_prph_reg_addr, value);
1088out:
1089 return count;
1090}
1091
1092MVM_DEBUGFS_READ_WRITE_FILE_OPS(prph_reg, 64);
670 1093
671/* Device wide debugfs entries */ 1094/* Device wide debugfs entries */
672MVM_DEBUGFS_WRITE_FILE_OPS(tx_flush, 16); 1095MVM_DEBUGFS_WRITE_FILE_OPS(tx_flush, 16);
@@ -677,9 +1100,23 @@ MVM_DEBUGFS_READ_FILE_OPS(bt_notif);
677MVM_DEBUGFS_READ_FILE_OPS(bt_cmd); 1100MVM_DEBUGFS_READ_FILE_OPS(bt_cmd);
678MVM_DEBUGFS_READ_WRITE_FILE_OPS(disable_power_off, 64); 1101MVM_DEBUGFS_READ_WRITE_FILE_OPS(disable_power_off, 64);
679MVM_DEBUGFS_READ_FILE_OPS(fw_rx_stats); 1102MVM_DEBUGFS_READ_FILE_OPS(fw_rx_stats);
1103MVM_DEBUGFS_READ_FILE_OPS(drv_rx_stats);
680MVM_DEBUGFS_WRITE_FILE_OPS(fw_restart, 10); 1104MVM_DEBUGFS_WRITE_FILE_OPS(fw_restart, 10);
681MVM_DEBUGFS_WRITE_FILE_OPS(fw_nmi, 10); 1105MVM_DEBUGFS_WRITE_FILE_OPS(fw_nmi, 10);
1106MVM_DEBUGFS_WRITE_FILE_OPS(bt_tx_prio, 10);
682MVM_DEBUGFS_READ_WRITE_FILE_OPS(scan_ant_rxchain, 8); 1107MVM_DEBUGFS_READ_WRITE_FILE_OPS(scan_ant_rxchain, 8);
1108MVM_DEBUGFS_READ_WRITE_FILE_OPS(d0i3_refs, 8);
1109
1110static const struct file_operations iwl_dbgfs_fw_error_dump_ops = {
1111 .open = iwl_dbgfs_fw_error_dump_open,
1112 .read = iwl_dbgfs_fw_error_dump_read,
1113 .release = iwl_dbgfs_fw_error_dump_release,
1114};
1115
1116#ifdef CONFIG_IWLWIFI_BCAST_FILTERING
1117MVM_DEBUGFS_READ_WRITE_FILE_OPS(bcast_filters, 256);
1118MVM_DEBUGFS_READ_WRITE_FILE_OPS(bcast_filters_macs, 256);
1119#endif
683 1120
684#ifdef CONFIG_PM_SLEEP 1121#ifdef CONFIG_PM_SLEEP
685MVM_DEBUGFS_READ_WRITE_FILE_OPS(d3_sram, 8); 1122MVM_DEBUGFS_READ_WRITE_FILE_OPS(d3_sram, 8);
@@ -687,24 +1124,52 @@ MVM_DEBUGFS_READ_WRITE_FILE_OPS(d3_sram, 8);
687 1124
688int iwl_mvm_dbgfs_register(struct iwl_mvm *mvm, struct dentry *dbgfs_dir) 1125int iwl_mvm_dbgfs_register(struct iwl_mvm *mvm, struct dentry *dbgfs_dir)
689{ 1126{
1127 struct dentry *bcast_dir __maybe_unused;
690 char buf[100]; 1128 char buf[100];
691 1129
1130 spin_lock_init(&mvm->drv_stats_lock);
1131
692 mvm->debugfs_dir = dbgfs_dir; 1132 mvm->debugfs_dir = dbgfs_dir;
693 1133
694 MVM_DEBUGFS_ADD_FILE(tx_flush, mvm->debugfs_dir, S_IWUSR); 1134 MVM_DEBUGFS_ADD_FILE(tx_flush, mvm->debugfs_dir, S_IWUSR);
695 MVM_DEBUGFS_ADD_FILE(sta_drain, mvm->debugfs_dir, S_IWUSR); 1135 MVM_DEBUGFS_ADD_FILE(sta_drain, mvm->debugfs_dir, S_IWUSR);
696 MVM_DEBUGFS_ADD_FILE(sram, mvm->debugfs_dir, S_IWUSR | S_IRUSR); 1136 MVM_DEBUGFS_ADD_FILE(sram, mvm->debugfs_dir, S_IWUSR | S_IRUSR);
697 MVM_DEBUGFS_ADD_FILE(stations, dbgfs_dir, S_IRUSR); 1137 MVM_DEBUGFS_ADD_FILE(stations, dbgfs_dir, S_IRUSR);
1138 MVM_DEBUGFS_ADD_FILE(fw_error_dump, dbgfs_dir, S_IRUSR);
698 MVM_DEBUGFS_ADD_FILE(bt_notif, dbgfs_dir, S_IRUSR); 1139 MVM_DEBUGFS_ADD_FILE(bt_notif, dbgfs_dir, S_IRUSR);
699 MVM_DEBUGFS_ADD_FILE(bt_cmd, dbgfs_dir, S_IRUSR); 1140 MVM_DEBUGFS_ADD_FILE(bt_cmd, dbgfs_dir, S_IRUSR);
700 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_DEVICE_PS_CMD) 1141 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_DEVICE_PS_CMD)
701 MVM_DEBUGFS_ADD_FILE(disable_power_off, mvm->debugfs_dir, 1142 MVM_DEBUGFS_ADD_FILE(disable_power_off, mvm->debugfs_dir,
702 S_IRUSR | S_IWUSR); 1143 S_IRUSR | S_IWUSR);
703 MVM_DEBUGFS_ADD_FILE(fw_rx_stats, mvm->debugfs_dir, S_IRUSR); 1144 MVM_DEBUGFS_ADD_FILE(fw_rx_stats, mvm->debugfs_dir, S_IRUSR);
1145 MVM_DEBUGFS_ADD_FILE(drv_rx_stats, mvm->debugfs_dir, S_IRUSR);
704 MVM_DEBUGFS_ADD_FILE(fw_restart, mvm->debugfs_dir, S_IWUSR); 1146 MVM_DEBUGFS_ADD_FILE(fw_restart, mvm->debugfs_dir, S_IWUSR);
705 MVM_DEBUGFS_ADD_FILE(fw_nmi, mvm->debugfs_dir, S_IWUSR); 1147 MVM_DEBUGFS_ADD_FILE(fw_nmi, mvm->debugfs_dir, S_IWUSR);
1148 MVM_DEBUGFS_ADD_FILE(bt_tx_prio, mvm->debugfs_dir, S_IWUSR);
706 MVM_DEBUGFS_ADD_FILE(scan_ant_rxchain, mvm->debugfs_dir, 1149 MVM_DEBUGFS_ADD_FILE(scan_ant_rxchain, mvm->debugfs_dir,
707 S_IWUSR | S_IRUSR); 1150 S_IWUSR | S_IRUSR);
1151 MVM_DEBUGFS_ADD_FILE(prph_reg, mvm->debugfs_dir, S_IWUSR | S_IRUSR);
1152 MVM_DEBUGFS_ADD_FILE(d0i3_refs, mvm->debugfs_dir, S_IRUSR | S_IWUSR);
1153
1154#ifdef CONFIG_IWLWIFI_BCAST_FILTERING
1155 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_BCAST_FILTERING) {
1156 bcast_dir = debugfs_create_dir("bcast_filtering",
1157 mvm->debugfs_dir);
1158 if (!bcast_dir)
1159 goto err;
1160
1161 if (!debugfs_create_bool("override", S_IRUSR | S_IWUSR,
1162 bcast_dir,
1163 &mvm->dbgfs_bcast_filtering.override))
1164 goto err;
1165
1166 MVM_DEBUGFS_ADD_FILE_ALIAS("filters", bcast_filters,
1167 bcast_dir, S_IWUSR | S_IRUSR);
1168 MVM_DEBUGFS_ADD_FILE_ALIAS("macs", bcast_filters_macs,
1169 bcast_dir, S_IWUSR | S_IRUSR);
1170 }
1171#endif
1172
708#ifdef CONFIG_PM_SLEEP 1173#ifdef CONFIG_PM_SLEEP
709 MVM_DEBUGFS_ADD_FILE(d3_sram, mvm->debugfs_dir, S_IRUSR | S_IWUSR); 1174 MVM_DEBUGFS_ADD_FILE(d3_sram, mvm->debugfs_dir, S_IRUSR | S_IWUSR);
710 MVM_DEBUGFS_ADD_FILE(d3_test, mvm->debugfs_dir, S_IRUSR); 1175 MVM_DEBUGFS_ADD_FILE(d3_test, mvm->debugfs_dir, S_IRUSR);
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-bt-coex.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-coex.h
index 1b4e54d416b0..21877e5966a8 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-api-bt-coex.h
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-coex.h
@@ -70,37 +70,28 @@
70 70
71/** 71/**
72 * enum iwl_bt_coex_flags - flags for BT_COEX command 72 * enum iwl_bt_coex_flags - flags for BT_COEX command
73 * @BT_CH_PRIMARY_EN:
74 * @BT_CH_SECONDARY_EN:
75 * @BT_NOTIF_COEX_OFF:
76 * @BT_COEX_MODE_POS: 73 * @BT_COEX_MODE_POS:
77 * @BT_COEX_MODE_MSK: 74 * @BT_COEX_MODE_MSK:
78 * @BT_COEX_DISABLE: 75 * @BT_COEX_DISABLE:
79 * @BT_COEX_2W: 76 * @BT_COEX_2W:
80 * @BT_COEX_3W: 77 * @BT_COEX_3W:
81 * @BT_COEX_NW: 78 * @BT_COEX_NW:
82 * @BT_USE_DEFAULTS: 79 * @BT_COEX_SYNC2SCO:
83 * @BT_SYNC_2_BT_DISABLE: 80 * @BT_COEX_CORUNNING:
84 * @BT_COEX_CORUNNING_TBL_EN: 81 * @BT_COEX_MPLUT:
85 * 82 *
86 * The COEX_MODE must be set for each command. Even if it is not changed. 83 * The COEX_MODE must be set for each command. Even if it is not changed.
87 */ 84 */
88enum iwl_bt_coex_flags { 85enum iwl_bt_coex_flags {
89 BT_CH_PRIMARY_EN = BIT(0),
90 BT_CH_SECONDARY_EN = BIT(1),
91 BT_NOTIF_COEX_OFF = BIT(2),
92 BT_COEX_MODE_POS = 3, 86 BT_COEX_MODE_POS = 3,
93 BT_COEX_MODE_MSK = BITS(3) << BT_COEX_MODE_POS, 87 BT_COEX_MODE_MSK = BITS(3) << BT_COEX_MODE_POS,
94 BT_COEX_DISABLE = 0x0 << BT_COEX_MODE_POS, 88 BT_COEX_DISABLE = 0x0 << BT_COEX_MODE_POS,
95 BT_COEX_2W = 0x1 << BT_COEX_MODE_POS, 89 BT_COEX_2W = 0x1 << BT_COEX_MODE_POS,
96 BT_COEX_3W = 0x2 << BT_COEX_MODE_POS, 90 BT_COEX_3W = 0x2 << BT_COEX_MODE_POS,
97 BT_COEX_NW = 0x3 << BT_COEX_MODE_POS, 91 BT_COEX_NW = 0x3 << BT_COEX_MODE_POS,
98 BT_USE_DEFAULTS = BIT(6), 92 BT_COEX_SYNC2SCO = BIT(7),
99 BT_SYNC_2_BT_DISABLE = BIT(7), 93 BT_COEX_CORUNNING = BIT(8),
100 BT_COEX_CORUNNING_TBL_EN = BIT(8), 94 BT_COEX_MPLUT = BIT(9),
101 BT_COEX_MPLUT_TBL_EN = BIT(9),
102 /* Bit 10 is reserved */
103 BT_COEX_WF_PRIO_BOOST_CHECK_EN = BIT(11),
104}; 95};
105 96
106/* 97/*
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-d3.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-d3.h
index 8415ff312d0e..10fcc1a79ebd 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-api-d3.h
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-d3.h
@@ -231,11 +231,15 @@ enum iwl_wowlan_wakeup_filters {
231 IWL_WOWLAN_WAKEUP_RF_KILL_DEASSERT = BIT(8), 231 IWL_WOWLAN_WAKEUP_RF_KILL_DEASSERT = BIT(8),
232 IWL_WOWLAN_WAKEUP_REMOTE_LINK_LOSS = BIT(9), 232 IWL_WOWLAN_WAKEUP_REMOTE_LINK_LOSS = BIT(9),
233 IWL_WOWLAN_WAKEUP_REMOTE_SIGNATURE_TABLE = BIT(10), 233 IWL_WOWLAN_WAKEUP_REMOTE_SIGNATURE_TABLE = BIT(10),
234 /* BIT(11) reserved */ 234 IWL_WOWLAN_WAKEUP_REMOTE_TCP_EXTERNAL = BIT(11),
235 IWL_WOWLAN_WAKEUP_REMOTE_WAKEUP_PACKET = BIT(12), 235 IWL_WOWLAN_WAKEUP_REMOTE_WAKEUP_PACKET = BIT(12),
236 IWL_WOWLAN_WAKEUP_IOAC_MAGIC_PACKET = BIT(13),
237 IWL_WOWLAN_WAKEUP_HOST_TIMER = BIT(14),
238 IWL_WOWLAN_WAKEUP_RX_FRAME = BIT(15),
239 IWL_WOWLAN_WAKEUP_BCN_FILTERING = BIT(16),
236}; /* WOWLAN_WAKEUP_FILTER_API_E_VER_4 */ 240}; /* WOWLAN_WAKEUP_FILTER_API_E_VER_4 */
237 241
238struct iwl_wowlan_config_cmd { 242struct iwl_wowlan_config_cmd_v2 {
239 __le32 wakeup_filter; 243 __le32 wakeup_filter;
240 __le16 non_qos_seq; 244 __le16 non_qos_seq;
241 __le16 qos_seq[8]; 245 __le16 qos_seq[8];
@@ -243,6 +247,12 @@ struct iwl_wowlan_config_cmd {
243 u8 is_11n_connection; 247 u8 is_11n_connection;
244} __packed; /* WOWLAN_CONFIG_API_S_VER_2 */ 248} __packed; /* WOWLAN_CONFIG_API_S_VER_2 */
245 249
250struct iwl_wowlan_config_cmd_v3 {
251 struct iwl_wowlan_config_cmd_v2 common;
252 u8 offloading_tid;
253 u8 reserved[3];
254} __packed; /* WOWLAN_CONFIG_API_S_VER_3 */
255
246/* 256/*
247 * WOWLAN_TSC_RSC_PARAMS 257 * WOWLAN_TSC_RSC_PARAMS
248 */ 258 */
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h
index 884c08725308..cbbcd8e284e4 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h
@@ -301,54 +301,65 @@ struct iwl_beacon_filter_cmd {
301 301
302/* Beacon filtering and beacon abort */ 302/* Beacon filtering and beacon abort */
303#define IWL_BF_ENERGY_DELTA_DEFAULT 5 303#define IWL_BF_ENERGY_DELTA_DEFAULT 5
304#define IWL_BF_ENERGY_DELTA_D0I3 20
304#define IWL_BF_ENERGY_DELTA_MAX 255 305#define IWL_BF_ENERGY_DELTA_MAX 255
305#define IWL_BF_ENERGY_DELTA_MIN 0 306#define IWL_BF_ENERGY_DELTA_MIN 0
306 307
307#define IWL_BF_ROAMING_ENERGY_DELTA_DEFAULT 1 308#define IWL_BF_ROAMING_ENERGY_DELTA_DEFAULT 1
309#define IWL_BF_ROAMING_ENERGY_DELTA_D0I3 20
308#define IWL_BF_ROAMING_ENERGY_DELTA_MAX 255 310#define IWL_BF_ROAMING_ENERGY_DELTA_MAX 255
309#define IWL_BF_ROAMING_ENERGY_DELTA_MIN 0 311#define IWL_BF_ROAMING_ENERGY_DELTA_MIN 0
310 312
311#define IWL_BF_ROAMING_STATE_DEFAULT 72 313#define IWL_BF_ROAMING_STATE_DEFAULT 72
314#define IWL_BF_ROAMING_STATE_D0I3 72
312#define IWL_BF_ROAMING_STATE_MAX 255 315#define IWL_BF_ROAMING_STATE_MAX 255
313#define IWL_BF_ROAMING_STATE_MIN 0 316#define IWL_BF_ROAMING_STATE_MIN 0
314 317
315#define IWL_BF_TEMP_THRESHOLD_DEFAULT 112 318#define IWL_BF_TEMP_THRESHOLD_DEFAULT 112
319#define IWL_BF_TEMP_THRESHOLD_D0I3 112
316#define IWL_BF_TEMP_THRESHOLD_MAX 255 320#define IWL_BF_TEMP_THRESHOLD_MAX 255
317#define IWL_BF_TEMP_THRESHOLD_MIN 0 321#define IWL_BF_TEMP_THRESHOLD_MIN 0
318 322
319#define IWL_BF_TEMP_FAST_FILTER_DEFAULT 1 323#define IWL_BF_TEMP_FAST_FILTER_DEFAULT 1
324#define IWL_BF_TEMP_FAST_FILTER_D0I3 1
320#define IWL_BF_TEMP_FAST_FILTER_MAX 255 325#define IWL_BF_TEMP_FAST_FILTER_MAX 255
321#define IWL_BF_TEMP_FAST_FILTER_MIN 0 326#define IWL_BF_TEMP_FAST_FILTER_MIN 0
322 327
323#define IWL_BF_TEMP_SLOW_FILTER_DEFAULT 5 328#define IWL_BF_TEMP_SLOW_FILTER_DEFAULT 5
329#define IWL_BF_TEMP_SLOW_FILTER_D0I3 5
324#define IWL_BF_TEMP_SLOW_FILTER_MAX 255 330#define IWL_BF_TEMP_SLOW_FILTER_MAX 255
325#define IWL_BF_TEMP_SLOW_FILTER_MIN 0 331#define IWL_BF_TEMP_SLOW_FILTER_MIN 0
326 332
327#define IWL_BF_ENABLE_BEACON_FILTER_DEFAULT 1 333#define IWL_BF_ENABLE_BEACON_FILTER_DEFAULT 1
328 334
329#define IWL_BF_DEBUG_FLAG_DEFAULT 0 335#define IWL_BF_DEBUG_FLAG_DEFAULT 0
336#define IWL_BF_DEBUG_FLAG_D0I3 0
330 337
331#define IWL_BF_ESCAPE_TIMER_DEFAULT 50 338#define IWL_BF_ESCAPE_TIMER_DEFAULT 50
339#define IWL_BF_ESCAPE_TIMER_D0I3 1024
332#define IWL_BF_ESCAPE_TIMER_MAX 1024 340#define IWL_BF_ESCAPE_TIMER_MAX 1024
333#define IWL_BF_ESCAPE_TIMER_MIN 0 341#define IWL_BF_ESCAPE_TIMER_MIN 0
334 342
335#define IWL_BA_ESCAPE_TIMER_DEFAULT 6 343#define IWL_BA_ESCAPE_TIMER_DEFAULT 6
344#define IWL_BA_ESCAPE_TIMER_D0I3 6
336#define IWL_BA_ESCAPE_TIMER_D3 9 345#define IWL_BA_ESCAPE_TIMER_D3 9
337#define IWL_BA_ESCAPE_TIMER_MAX 1024 346#define IWL_BA_ESCAPE_TIMER_MAX 1024
338#define IWL_BA_ESCAPE_TIMER_MIN 0 347#define IWL_BA_ESCAPE_TIMER_MIN 0
339 348
340#define IWL_BA_ENABLE_BEACON_ABORT_DEFAULT 1 349#define IWL_BA_ENABLE_BEACON_ABORT_DEFAULT 1
341 350
342#define IWL_BF_CMD_CONFIG_DEFAULTS \ 351#define IWL_BF_CMD_CONFIG(mode) \
343 .bf_energy_delta = cpu_to_le32(IWL_BF_ENERGY_DELTA_DEFAULT), \ 352 .bf_energy_delta = cpu_to_le32(IWL_BF_ENERGY_DELTA ## mode), \
344 .bf_roaming_energy_delta = \ 353 .bf_roaming_energy_delta = \
345 cpu_to_le32(IWL_BF_ROAMING_ENERGY_DELTA_DEFAULT), \ 354 cpu_to_le32(IWL_BF_ROAMING_ENERGY_DELTA ## mode), \
346 .bf_roaming_state = cpu_to_le32(IWL_BF_ROAMING_STATE_DEFAULT), \ 355 .bf_roaming_state = cpu_to_le32(IWL_BF_ROAMING_STATE ## mode), \
347 .bf_temp_threshold = cpu_to_le32(IWL_BF_TEMP_THRESHOLD_DEFAULT), \ 356 .bf_temp_threshold = cpu_to_le32(IWL_BF_TEMP_THRESHOLD ## mode), \
348 .bf_temp_fast_filter = cpu_to_le32(IWL_BF_TEMP_FAST_FILTER_DEFAULT), \ 357 .bf_temp_fast_filter = cpu_to_le32(IWL_BF_TEMP_FAST_FILTER ## mode), \
349 .bf_temp_slow_filter = cpu_to_le32(IWL_BF_TEMP_SLOW_FILTER_DEFAULT), \ 358 .bf_temp_slow_filter = cpu_to_le32(IWL_BF_TEMP_SLOW_FILTER ## mode), \
350 .bf_debug_flag = cpu_to_le32(IWL_BF_DEBUG_FLAG_DEFAULT), \ 359 .bf_debug_flag = cpu_to_le32(IWL_BF_DEBUG_FLAG ## mode), \
351 .bf_escape_timer = cpu_to_le32(IWL_BF_ESCAPE_TIMER_DEFAULT), \ 360 .bf_escape_timer = cpu_to_le32(IWL_BF_ESCAPE_TIMER ## mode), \
352 .ba_escape_timer = cpu_to_le32(IWL_BA_ESCAPE_TIMER_DEFAULT) 361 .ba_escape_timer = cpu_to_le32(IWL_BA_ESCAPE_TIMER ## mode)
353 362
363#define IWL_BF_CMD_CONFIG_DEFAULTS IWL_BF_CMD_CONFIG(_DEFAULT)
364#define IWL_BF_CMD_CONFIG_D0I3 IWL_BF_CMD_CONFIG(_D0I3)
354#endif 365#endif
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-rs.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-rs.h
index 85057219cc43..39148b5bb332 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-api-rs.h
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-rs.h
@@ -257,7 +257,8 @@ enum {
257 257
258/* Bit 17-18: (0) SS, (1) SS*2 */ 258/* Bit 17-18: (0) SS, (1) SS*2 */
259#define RATE_MCS_STBC_POS 17 259#define RATE_MCS_STBC_POS 17
260#define RATE_MCS_STBC_MSK (1 << RATE_MCS_STBC_POS) 260#define RATE_MCS_HT_STBC_MSK (3 << RATE_MCS_STBC_POS)
261#define RATE_MCS_VHT_STBC_MSK (1 << RATE_MCS_STBC_POS)
261 262
262/* Bit 19: (0) Beamforming is off, (1) Beamforming is on */ 263/* Bit 19: (0) Beamforming is off, (1) Beamforming is on */
263#define RATE_MCS_BF_POS 19 264#define RATE_MCS_BF_POS 19
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-sta.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-sta.h
index 1b60fdff6a56..d63647867262 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-api-sta.h
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-sta.h
@@ -199,11 +199,14 @@ enum iwl_sta_modify_flag {
199 * @STA_SLEEP_STATE_AWAKE: 199 * @STA_SLEEP_STATE_AWAKE:
200 * @STA_SLEEP_STATE_PS_POLL: 200 * @STA_SLEEP_STATE_PS_POLL:
201 * @STA_SLEEP_STATE_UAPSD: 201 * @STA_SLEEP_STATE_UAPSD:
202 * @STA_SLEEP_STATE_MOREDATA: set more-data bit on
203 * (last) released frame
202 */ 204 */
203enum iwl_sta_sleep_flag { 205enum iwl_sta_sleep_flag {
204 STA_SLEEP_STATE_AWAKE = 0, 206 STA_SLEEP_STATE_AWAKE = 0,
205 STA_SLEEP_STATE_PS_POLL = BIT(0), 207 STA_SLEEP_STATE_PS_POLL = BIT(0),
206 STA_SLEEP_STATE_UAPSD = BIT(1), 208 STA_SLEEP_STATE_UAPSD = BIT(1),
209 STA_SLEEP_STATE_MOREDATA = BIT(2),
207}; 210};
208 211
209/* STA ID and color bits definitions */ 212/* STA ID and color bits definitions */
@@ -318,13 +321,15 @@ struct iwl_mvm_add_sta_cmd_v5 {
318} __packed; /* ADD_STA_CMD_API_S_VER_5 */ 321} __packed; /* ADD_STA_CMD_API_S_VER_5 */
319 322
320/** 323/**
321 * struct iwl_mvm_add_sta_cmd_v6 - Add / modify a station 324 * struct iwl_mvm_add_sta_cmd_v7 - Add / modify a station
322 * VER_6 of this command is quite similar to VER_5 except 325 * VER_7 of this command is quite similar to VER_5 except
323 * exclusion of all fields related to the security key installation. 326 * exclusion of all fields related to the security key installation.
327 * It only differs from VER_6 by the "awake_acs" field that is
328 * reserved and ignored in VER_6.
324 */ 329 */
325struct iwl_mvm_add_sta_cmd_v6 { 330struct iwl_mvm_add_sta_cmd_v7 {
326 u8 add_modify; 331 u8 add_modify;
327 u8 reserved1; 332 u8 awake_acs;
328 __le16 tid_disable_tx; 333 __le16 tid_disable_tx;
329 __le32 mac_id_n_color; 334 __le32 mac_id_n_color;
330 u8 addr[ETH_ALEN]; /* _STA_ID_MODIFY_INFO_API_S_VER_1 */ 335 u8 addr[ETH_ALEN]; /* _STA_ID_MODIFY_INFO_API_S_VER_1 */
@@ -342,7 +347,7 @@ struct iwl_mvm_add_sta_cmd_v6 {
342 __le16 assoc_id; 347 __le16 assoc_id;
343 __le16 beamform_flags; 348 __le16 beamform_flags;
344 __le32 tfd_queue_msk; 349 __le32 tfd_queue_msk;
345} __packed; /* ADD_STA_CMD_API_S_VER_6 */ 350} __packed; /* ADD_STA_CMD_API_S_VER_7 */
346 351
347/** 352/**
348 * struct iwl_mvm_add_sta_key_cmd - add/modify sta key 353 * struct iwl_mvm_add_sta_key_cmd - add/modify sta key
@@ -432,5 +437,15 @@ struct iwl_mvm_wep_key_cmd {
432 struct iwl_mvm_wep_key wep_key[0]; 437 struct iwl_mvm_wep_key wep_key[0];
433} __packed; /* SEC_CURR_WEP_KEY_CMD_API_S_VER_2 */ 438} __packed; /* SEC_CURR_WEP_KEY_CMD_API_S_VER_2 */
434 439
440/**
441 * struct iwl_mvm_eosp_notification - EOSP notification from firmware
442 * @remain_frame_count: # of frames remaining, non-zero if SP was cut
443 * short by GO absence
444 * @sta_id: station ID
445 */
446struct iwl_mvm_eosp_notification {
447 __le32 remain_frame_count;
448 __le32 sta_id;
449} __packed; /* UAPSD_EOSP_NTFY_API_S_VER_1 */
435 450
436#endif /* __fw_api_sta_h__ */ 451#endif /* __fw_api_sta_h__ */
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-tx.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-tx.h
index b674c2a2b51c..8e122f3a7a74 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-api-tx.h
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-tx.h
@@ -76,6 +76,8 @@
76 * @TX_CMD_FLG_VHT_NDPA: mark frame is NDPA for VHT beamformer sequence 76 * @TX_CMD_FLG_VHT_NDPA: mark frame is NDPA for VHT beamformer sequence
77 * @TX_CMD_FLG_HT_NDPA: mark frame is NDPA for HT beamformer sequence 77 * @TX_CMD_FLG_HT_NDPA: mark frame is NDPA for HT beamformer sequence
78 * @TX_CMD_FLG_CSI_FDBK2HOST: mark to send feedback to host (only if good CRC) 78 * @TX_CMD_FLG_CSI_FDBK2HOST: mark to send feedback to host (only if good CRC)
79 * @TX_CMD_FLG_BT_PRIO_POS: the position of the BT priority (bit 11 is ignored
80 * on old firmwares).
79 * @TX_CMD_FLG_BT_DIS: disable BT priority for this frame 81 * @TX_CMD_FLG_BT_DIS: disable BT priority for this frame
80 * @TX_CMD_FLG_SEQ_CTL: set if FW should override the sequence control. 82 * @TX_CMD_FLG_SEQ_CTL: set if FW should override the sequence control.
81 * Should be set for mgmt, non-QOS data, mcast, bcast and in scan command 83 * Should be set for mgmt, non-QOS data, mcast, bcast and in scan command
@@ -107,6 +109,7 @@ enum iwl_tx_flags {
107 TX_CMD_FLG_VHT_NDPA = BIT(8), 109 TX_CMD_FLG_VHT_NDPA = BIT(8),
108 TX_CMD_FLG_HT_NDPA = BIT(9), 110 TX_CMD_FLG_HT_NDPA = BIT(9),
109 TX_CMD_FLG_CSI_FDBK2HOST = BIT(10), 111 TX_CMD_FLG_CSI_FDBK2HOST = BIT(10),
112 TX_CMD_FLG_BT_PRIO_POS = 11,
110 TX_CMD_FLG_BT_DIS = BIT(12), 113 TX_CMD_FLG_BT_DIS = BIT(12),
111 TX_CMD_FLG_SEQ_CTL = BIT(13), 114 TX_CMD_FLG_SEQ_CTL = BIT(13),
112 TX_CMD_FLG_MORE_FRAG = BIT(14), 115 TX_CMD_FLG_MORE_FRAG = BIT(14),
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api.h b/drivers/net/wireless/iwlwifi/mvm/fw-api.h
index 989d7dbdca6c..6e75b52588de 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-api.h
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-api.h
@@ -70,7 +70,7 @@
70#include "fw-api-mac.h" 70#include "fw-api-mac.h"
71#include "fw-api-power.h" 71#include "fw-api-power.h"
72#include "fw-api-d3.h" 72#include "fw-api-d3.h"
73#include "fw-api-bt-coex.h" 73#include "fw-api-coex.h"
74 74
75/* maximal number of Tx queues in any platform */ 75/* maximal number of Tx queues in any platform */
76#define IWL_MVM_MAX_QUEUES 20 76#define IWL_MVM_MAX_QUEUES 20
@@ -95,6 +95,7 @@ enum {
95 /* PHY context commands */ 95 /* PHY context commands */
96 PHY_CONTEXT_CMD = 0x8, 96 PHY_CONTEXT_CMD = 0x8,
97 DBG_CFG = 0x9, 97 DBG_CFG = 0x9,
98 ANTENNA_COUPLING_NOTIFICATION = 0xa,
98 99
99 /* station table */ 100 /* station table */
100 ADD_STA_KEY = 0x17, 101 ADD_STA_KEY = 0x17,
@@ -163,6 +164,7 @@ enum {
163 TX_ANT_CONFIGURATION_CMD = 0x98, 164 TX_ANT_CONFIGURATION_CMD = 0x98,
164 BT_CONFIG = 0x9b, 165 BT_CONFIG = 0x9b,
165 STATISTICS_NOTIFICATION = 0x9d, 166 STATISTICS_NOTIFICATION = 0x9d,
167 EOSP_NOTIFICATION = 0x9e,
166 REDUCE_TX_POWER_CMD = 0x9f, 168 REDUCE_TX_POWER_CMD = 0x9f,
167 169
168 /* RF-KILL commands and notifications */ 170 /* RF-KILL commands and notifications */
@@ -190,6 +192,7 @@ enum {
190 REPLY_DEBUG_CMD = 0xf0, 192 REPLY_DEBUG_CMD = 0xf0,
191 DEBUG_LOG_MSG = 0xf7, 193 DEBUG_LOG_MSG = 0xf7,
192 194
195 BCAST_FILTER_CMD = 0xcf,
193 MCAST_FILTER_CMD = 0xd0, 196 MCAST_FILTER_CMD = 0xd0,
194 197
195 /* D3 commands/notifications */ 198 /* D3 commands/notifications */
@@ -197,6 +200,7 @@ enum {
197 PROT_OFFLOAD_CONFIG_CMD = 0xd4, 200 PROT_OFFLOAD_CONFIG_CMD = 0xd4,
198 OFFLOADS_QUERY_CMD = 0xd5, 201 OFFLOADS_QUERY_CMD = 0xd5,
199 REMOTE_WAKE_CONFIG_CMD = 0xd6, 202 REMOTE_WAKE_CONFIG_CMD = 0xd6,
203 D0I3_END_CMD = 0xed,
200 204
201 /* for WoWLAN in particular */ 205 /* for WoWLAN in particular */
202 WOWLAN_PATTERNS = 0xe0, 206 WOWLAN_PATTERNS = 0xe0,
@@ -313,14 +317,12 @@ enum {
313 317
314/* Section types for NVM_ACCESS_CMD */ 318/* Section types for NVM_ACCESS_CMD */
315enum { 319enum {
316 NVM_SECTION_TYPE_HW = 0, 320 NVM_SECTION_TYPE_SW = 1,
317 NVM_SECTION_TYPE_SW, 321 NVM_SECTION_TYPE_REGULATORY = 3,
318 NVM_SECTION_TYPE_PAPD, 322 NVM_SECTION_TYPE_CALIBRATION = 4,
319 NVM_SECTION_TYPE_BT, 323 NVM_SECTION_TYPE_PRODUCTION = 5,
320 NVM_SECTION_TYPE_CALIBRATION, 324 NVM_SECTION_TYPE_MAC_OVERRIDE = 11,
321 NVM_SECTION_TYPE_PRODUCTION, 325 NVM_MAX_NUM_SECTIONS = 12,
322 NVM_SECTION_TYPE_POST_FCS_CALIB,
323 NVM_NUM_OF_SECTIONS,
324}; 326};
325 327
326/** 328/**
@@ -412,6 +414,35 @@ struct mvm_alive_resp {
412 __le32 scd_base_ptr; /* SRAM address for SCD */ 414 __le32 scd_base_ptr; /* SRAM address for SCD */
413} __packed; /* ALIVE_RES_API_S_VER_1 */ 415} __packed; /* ALIVE_RES_API_S_VER_1 */
414 416
417struct mvm_alive_resp_ver2 {
418 __le16 status;
419 __le16 flags;
420 u8 ucode_minor;
421 u8 ucode_major;
422 __le16 id;
423 u8 api_minor;
424 u8 api_major;
425 u8 ver_subtype;
426 u8 ver_type;
427 u8 mac;
428 u8 opt;
429 __le16 reserved2;
430 __le32 timestamp;
431 __le32 error_event_table_ptr; /* SRAM address for error log */
432 __le32 log_event_table_ptr; /* SRAM address for LMAC event log */
433 __le32 cpu_register_ptr;
434 __le32 dbgm_config_ptr;
435 __le32 alive_counter_ptr;
436 __le32 scd_base_ptr; /* SRAM address for SCD */
437 __le32 st_fwrd_addr; /* pointer to Store and forward */
438 __le32 st_fwrd_size;
439 u8 umac_minor; /* UMAC version: minor */
440 u8 umac_major; /* UMAC version: major */
441 __le16 umac_id; /* UMAC version: id */
442 __le32 error_info_addr; /* SRAM address for UMAC error log */
443 __le32 dbg_print_buff_addr;
444} __packed; /* ALIVE_RES_API_S_VER_2 */
445
415/* Error response/notification */ 446/* Error response/notification */
416enum { 447enum {
417 FW_ERR_UNKNOWN_CMD = 0x0, 448 FW_ERR_UNKNOWN_CMD = 0x0,
@@ -682,6 +713,7 @@ enum {
682 TE_V2_NOTIF_HOST_FRAG_END = BIT(5), 713 TE_V2_NOTIF_HOST_FRAG_END = BIT(5),
683 TE_V2_NOTIF_INTERNAL_FRAG_START = BIT(6), 714 TE_V2_NOTIF_INTERNAL_FRAG_START = BIT(6),
684 TE_V2_NOTIF_INTERNAL_FRAG_END = BIT(7), 715 TE_V2_NOTIF_INTERNAL_FRAG_END = BIT(7),
716 T2_V2_START_IMMEDIATELY = BIT(11),
685 717
686 TE_V2_NOTIF_MSK = 0xff, 718 TE_V2_NOTIF_MSK = 0xff,
687 719
@@ -1159,6 +1191,90 @@ struct iwl_mcast_filter_cmd {
1159 u8 addr_list[0]; 1191 u8 addr_list[0];
1160} __packed; /* MCAST_FILTERING_CMD_API_S_VER_1 */ 1192} __packed; /* MCAST_FILTERING_CMD_API_S_VER_1 */
1161 1193
1194#define MAX_BCAST_FILTERS 8
1195#define MAX_BCAST_FILTER_ATTRS 2
1196
1197/**
1198 * enum iwl_mvm_bcast_filter_attr_offset - written by fw for each Rx packet
1199 * @BCAST_FILTER_OFFSET_PAYLOAD_START: offset is from payload start.
1200 * @BCAST_FILTER_OFFSET_IP_END: offset is from ip header end (i.e.
1201 * start of ip payload).
1202 */
1203enum iwl_mvm_bcast_filter_attr_offset {
1204 BCAST_FILTER_OFFSET_PAYLOAD_START = 0,
1205 BCAST_FILTER_OFFSET_IP_END = 1,
1206};
1207
1208/**
1209 * struct iwl_fw_bcast_filter_attr - broadcast filter attribute
1210 * @offset_type: &enum iwl_mvm_bcast_filter_attr_offset.
1211 * @offset: starting offset of this pattern.
1212 * @val: value to match - big endian (MSB is the first
1213 * byte to match from offset pos).
1214 * @mask: mask to match (big endian).
1215 */
1216struct iwl_fw_bcast_filter_attr {
1217 u8 offset_type;
1218 u8 offset;
1219 __le16 reserved1;
1220 __be32 val;
1221 __be32 mask;
1222} __packed; /* BCAST_FILTER_ATT_S_VER_1 */
1223
1224/**
1225 * enum iwl_mvm_bcast_filter_frame_type - filter frame type
1226 * @BCAST_FILTER_FRAME_TYPE_ALL: consider all frames.
1227 * @BCAST_FILTER_FRAME_TYPE_IPV4: consider only ipv4 frames
1228 */
1229enum iwl_mvm_bcast_filter_frame_type {
1230 BCAST_FILTER_FRAME_TYPE_ALL = 0,
1231 BCAST_FILTER_FRAME_TYPE_IPV4 = 1,
1232};
1233
1234/**
1235 * struct iwl_fw_bcast_filter - broadcast filter
1236 * @discard: discard frame (1) or let it pass (0).
1237 * @frame_type: &enum iwl_mvm_bcast_filter_frame_type.
1238 * @num_attrs: number of valid attributes in this filter.
1239 * @attrs: attributes of this filter. a filter is considered matched
1240 * only when all its attributes are matched (i.e. AND relationship)
1241 */
1242struct iwl_fw_bcast_filter {
1243 u8 discard;
1244 u8 frame_type;
1245 u8 num_attrs;
1246 u8 reserved1;
1247 struct iwl_fw_bcast_filter_attr attrs[MAX_BCAST_FILTER_ATTRS];
1248} __packed; /* BCAST_FILTER_S_VER_1 */
1249
1250/**
1251 * struct iwl_fw_bcast_mac - per-mac broadcast filtering configuration.
1252 * @default_discard: default action for this mac (discard (1) / pass (0)).
1253 * @attached_filters: bitmap of relevant filters for this mac.
1254 */
1255struct iwl_fw_bcast_mac {
1256 u8 default_discard;
1257 u8 reserved1;
1258 __le16 attached_filters;
1259} __packed; /* BCAST_MAC_CONTEXT_S_VER_1 */
1260
1261/**
1262 * struct iwl_bcast_filter_cmd - broadcast filtering configuration
1263 * @disable: enable (0) / disable (1)
1264 * @max_bcast_filters: max number of filters (MAX_BCAST_FILTERS)
1265 * @max_macs: max number of macs (NUM_MAC_INDEX_DRIVER)
1266 * @filters: broadcast filters
1267 * @macs: broadcast filtering configuration per-mac
1268 */
1269struct iwl_bcast_filter_cmd {
1270 u8 disable;
1271 u8 max_bcast_filters;
1272 u8 max_macs;
1273 u8 reserved1;
1274 struct iwl_fw_bcast_filter filters[MAX_BCAST_FILTERS];
1275 struct iwl_fw_bcast_mac macs[NUM_MAC_INDEX_DRIVER];
1276} __packed; /* BCAST_FILTERING_HCMD_API_S_VER_1 */
1277
1162struct mvm_statistics_dbg { 1278struct mvm_statistics_dbg {
1163 __le32 burst_check; 1279 __le32 burst_check;
1164 __le32 burst_count; 1280 __le32 burst_count;
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-error-dump.h b/drivers/net/wireless/iwlwifi/mvm/fw-error-dump.h
new file mode 100644
index 000000000000..58c8941c0d95
--- /dev/null
+++ b/drivers/net/wireless/iwlwifi/mvm/fw-error-dump.h
@@ -0,0 +1,106 @@
1/******************************************************************************
2 *
3 * This file is provided under a dual BSD/GPLv2 license. When using or
4 * redistributing this file, you may do so under either license.
5 *
6 * GPL LICENSE SUMMARY
7 *
8 * Copyright(c) 2014 Intel Corporation. All rights reserved.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of version 2 of the GNU General Public License as
12 * published by the Free Software Foundation.
13 *
14 * This program is distributed in the hope that it will be useful, but
15 * WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110,
22 * USA
23 *
24 * The full GNU General Public License is included in this distribution
25 * in the file called COPYING.
26 *
27 * Contact Information:
28 * Intel Linux Wireless <ilw@linux.intel.com>
29 * Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
30 *
31 * BSD LICENSE
32 *
33 * Copyright(c) 2014 Intel Corporation. All rights reserved.
34 * All rights reserved.
35 *
36 * Redistribution and use in source and binary forms, with or without
37 * modification, are permitted provided that the following conditions
38 * are met:
39 *
40 * * Redistributions of source code must retain the above copyright
41 * notice, this list of conditions and the following disclaimer.
42 * * Redistributions in binary form must reproduce the above copyright
43 * notice, this list of conditions and the following disclaimer in
44 * the documentation and/or other materials provided with the
45 * distribution.
46 * * Neither the name Intel Corporation nor the names of its
47 * contributors may be used to endorse or promote products derived
48 * from this software without specific prior written permission.
49 *
50 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
51 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
52 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
53 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
54 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
55 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
56 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
57 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
58 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
59 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
60 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
61 *****************************************************************************/
62
63#ifndef __fw_error_dump_h__
64#define __fw_error_dump_h__
65
66#include <linux/types.h>
67
68#define IWL_FW_ERROR_DUMP_BARKER 0x14789632
69
70/**
71 * enum iwl_fw_error_dump_type - types of data in the dump file
72 * @IWL_FW_ERROR_DUMP_SRAM:
73 * @IWL_FW_ERROR_DUMP_REG:
74 */
75enum iwl_fw_error_dump_type {
76 IWL_FW_ERROR_DUMP_SRAM = 0,
77 IWL_FW_ERROR_DUMP_REG = 1,
78
79 IWL_FW_ERROR_DUMP_MAX,
80};
81
82/**
83 * struct iwl_fw_error_dump_data - data for one type
84 * @type: %enum iwl_fw_error_dump_type
85 * @len: the length starting from %data - must be a multiplier of 4.
86 * @data: the data itself padded to be a multiplier of 4.
87 */
88struct iwl_fw_error_dump_data {
89 __le32 type;
90 __le32 len;
91 __u8 data[];
92} __packed __aligned(4);
93
94/**
95 * struct iwl_fw_error_dump_file - the layout of the header of the file
96 * @barker: must be %IWL_FW_ERROR_DUMP_BARKER
97 * @file_len: the length of all the file starting from %barker
98 * @data: array of %struct iwl_fw_error_dump_data
99 */
100struct iwl_fw_error_dump_file {
101 __le32 barker;
102 __le32 file_len;
103 u8 data[0];
104} __packed __aligned(4);
105
106#endif /* __fw_error_dump_h__ */
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw.c b/drivers/net/wireless/iwlwifi/mvm/fw.c
index c03d39541f9e..7ce20062f32d 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw.c
+++ b/drivers/net/wireless/iwlwifi/mvm/fw.c
@@ -110,18 +110,48 @@ static bool iwl_alive_fn(struct iwl_notif_wait_data *notif_wait,
110 container_of(notif_wait, struct iwl_mvm, notif_wait); 110 container_of(notif_wait, struct iwl_mvm, notif_wait);
111 struct iwl_mvm_alive_data *alive_data = data; 111 struct iwl_mvm_alive_data *alive_data = data;
112 struct mvm_alive_resp *palive; 112 struct mvm_alive_resp *palive;
113 113 struct mvm_alive_resp_ver2 *palive2;
114 palive = (void *)pkt->data; 114
115 115 if (iwl_rx_packet_payload_len(pkt) == sizeof(*palive)) {
116 mvm->error_event_table = le32_to_cpu(palive->error_event_table_ptr); 116 palive = (void *)pkt->data;
117 mvm->log_event_table = le32_to_cpu(palive->log_event_table_ptr); 117
118 alive_data->scd_base_addr = le32_to_cpu(palive->scd_base_ptr); 118 mvm->support_umac_log = false;
119 119 mvm->error_event_table =
120 alive_data->valid = le16_to_cpu(palive->status) == IWL_ALIVE_STATUS_OK; 120 le32_to_cpu(palive->error_event_table_ptr);
121 IWL_DEBUG_FW(mvm, 121 mvm->log_event_table = le32_to_cpu(palive->log_event_table_ptr);
122 "Alive ucode status 0x%04x revision 0x%01X 0x%01X flags 0x%01X\n", 122 alive_data->scd_base_addr = le32_to_cpu(palive->scd_base_ptr);
123 le16_to_cpu(palive->status), palive->ver_type, 123
124 palive->ver_subtype, palive->flags); 124 alive_data->valid = le16_to_cpu(palive->status) ==
125 IWL_ALIVE_STATUS_OK;
126 IWL_DEBUG_FW(mvm,
127 "Alive VER1 ucode status 0x%04x revision 0x%01X 0x%01X flags 0x%01X\n",
128 le16_to_cpu(palive->status), palive->ver_type,
129 palive->ver_subtype, palive->flags);
130 } else {
131 palive2 = (void *)pkt->data;
132
133 mvm->error_event_table =
134 le32_to_cpu(palive2->error_event_table_ptr);
135 mvm->log_event_table =
136 le32_to_cpu(palive2->log_event_table_ptr);
137 alive_data->scd_base_addr = le32_to_cpu(palive2->scd_base_ptr);
138 mvm->umac_error_event_table =
139 le32_to_cpu(palive2->error_info_addr);
140
141 alive_data->valid = le16_to_cpu(palive2->status) ==
142 IWL_ALIVE_STATUS_OK;
143 if (mvm->umac_error_event_table)
144 mvm->support_umac_log = true;
145
146 IWL_DEBUG_FW(mvm,
147 "Alive VER2 ucode status 0x%04x revision 0x%01X 0x%01X flags 0x%01X\n",
148 le16_to_cpu(palive2->status), palive2->ver_type,
149 palive2->ver_subtype, palive2->flags);
150
151 IWL_DEBUG_FW(mvm,
152 "UMAC version: Major - 0x%x, Minor - 0x%x\n",
153 palive2->umac_major, palive2->umac_minor);
154 }
125 155
126 return true; 156 return true;
127} 157}
@@ -292,7 +322,7 @@ int iwl_run_init_mvm_ucode(struct iwl_mvm *mvm, bool read_nvm)
292 } 322 }
293 323
294 /* Send TX valid antennas before triggering calibrations */ 324 /* Send TX valid antennas before triggering calibrations */
295 ret = iwl_send_tx_ant_cfg(mvm, iwl_fw_valid_tx_ant(mvm->fw)); 325 ret = iwl_send_tx_ant_cfg(mvm, mvm->fw->valid_tx_ant);
296 if (ret) 326 if (ret)
297 goto error; 327 goto error;
298 328
@@ -328,8 +358,6 @@ out:
328 GFP_KERNEL); 358 GFP_KERNEL);
329 if (!mvm->nvm_data) 359 if (!mvm->nvm_data)
330 return -ENOMEM; 360 return -ENOMEM;
331 mvm->nvm_data->valid_rx_ant = 1;
332 mvm->nvm_data->valid_tx_ant = 1;
333 mvm->nvm_data->bands[0].channels = mvm->nvm_data->channels; 361 mvm->nvm_data->bands[0].channels = mvm->nvm_data->channels;
334 mvm->nvm_data->bands[0].n_channels = 1; 362 mvm->nvm_data->bands[0].n_channels = 1;
335 mvm->nvm_data->bands[0].n_bitrates = 1; 363 mvm->nvm_data->bands[0].n_bitrates = 1;
@@ -341,8 +369,6 @@ out:
341 return ret; 369 return ret;
342} 370}
343 371
344#define UCODE_CALIB_TIMEOUT (2*HZ)
345
346int iwl_mvm_up(struct iwl_mvm *mvm) 372int iwl_mvm_up(struct iwl_mvm *mvm)
347{ 373{
348 int ret, i; 374 int ret, i;
@@ -394,7 +420,7 @@ int iwl_mvm_up(struct iwl_mvm *mvm)
394 if (ret) 420 if (ret)
395 IWL_ERR(mvm, "Failed to initialize Smart Fifo\n"); 421 IWL_ERR(mvm, "Failed to initialize Smart Fifo\n");
396 422
397 ret = iwl_send_tx_ant_cfg(mvm, iwl_fw_valid_tx_ant(mvm->fw)); 423 ret = iwl_send_tx_ant_cfg(mvm, mvm->fw->valid_tx_ant);
398 if (ret) 424 if (ret)
399 goto error; 425 goto error;
400 426
@@ -439,10 +465,23 @@ int iwl_mvm_up(struct iwl_mvm *mvm)
439 goto error; 465 goto error;
440 } 466 }
441 467
442 ret = iwl_mvm_power_update_device_mode(mvm); 468 /* Initialize tx backoffs to the minimal possible */
469 iwl_mvm_tt_tx_backoff(mvm, 0);
470
471 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_PM_CMD_SUPPORT)) {
472 ret = iwl_power_legacy_set_cam_mode(mvm);
473 if (ret)
474 goto error;
475 }
476
477 ret = iwl_mvm_power_update_device(mvm);
443 if (ret) 478 if (ret)
444 goto error; 479 goto error;
445 480
481 /* allow FW/transport low power modes if not during restart */
482 if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status))
483 iwl_mvm_unref(mvm, IWL_MVM_REF_UCODE_DOWN);
484
446 IWL_DEBUG_INFO(mvm, "RT uCode started.\n"); 485 IWL_DEBUG_INFO(mvm, "RT uCode started.\n");
447 return 0; 486 return 0;
448 error: 487 error:
@@ -466,7 +505,7 @@ int iwl_mvm_load_d3_fw(struct iwl_mvm *mvm)
466 goto error; 505 goto error;
467 } 506 }
468 507
469 ret = iwl_send_tx_ant_cfg(mvm, iwl_fw_valid_tx_ant(mvm->fw)); 508 ret = iwl_send_tx_ant_cfg(mvm, mvm->fw->valid_tx_ant);
470 if (ret) 509 if (ret)
471 goto error; 510 goto error;
472 511
diff --git a/drivers/net/wireless/iwlwifi/mvm/led.c b/drivers/net/wireless/iwlwifi/mvm/led.c
index 6b4ea6bf8ffe..e3b3cf4dbd77 100644
--- a/drivers/net/wireless/iwlwifi/mvm/led.c
+++ b/drivers/net/wireless/iwlwifi/mvm/led.c
@@ -94,6 +94,8 @@ int iwl_mvm_leds_init(struct iwl_mvm *mvm)
94 int ret; 94 int ret;
95 95
96 switch (mode) { 96 switch (mode) {
97 case IWL_LED_BLINK:
98 IWL_ERR(mvm, "Blink led mode not supported, used default\n");
97 case IWL_LED_DEFAULT: 99 case IWL_LED_DEFAULT:
98 case IWL_LED_RF_STATE: 100 case IWL_LED_RF_STATE:
99 mode = IWL_LED_RF_STATE; 101 mode = IWL_LED_RF_STATE;
diff --git a/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c b/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c
index ba723d50939a..9ccec10bba16 100644
--- a/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c
+++ b/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c
@@ -90,6 +90,7 @@ static void iwl_mvm_mac_tsf_id_iter(void *_data, u8 *mac,
90{ 90{
91 struct iwl_mvm_mac_iface_iterator_data *data = _data; 91 struct iwl_mvm_mac_iface_iterator_data *data = _data;
92 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 92 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
93 u16 min_bi;
93 94
94 /* Skip the interface for which we are trying to assign a tsf_id */ 95 /* Skip the interface for which we are trying to assign a tsf_id */
95 if (vif == data->vif) 96 if (vif == data->vif)
@@ -114,42 +115,57 @@ static void iwl_mvm_mac_tsf_id_iter(void *_data, u8 *mac,
114 switch (data->vif->type) { 115 switch (data->vif->type) {
115 case NL80211_IFTYPE_STATION: 116 case NL80211_IFTYPE_STATION:
116 /* 117 /*
117 * The new interface is client, so if the existing one 118 * The new interface is a client, so if the one we're iterating
118 * we're iterating is an AP, and both interfaces have the 119 * is an AP, and the beacon interval of the AP is a multiple or
119 * same beacon interval, the same TSF should be used to 120 * divisor of the beacon interval of the client, the same TSF
120 * avoid drift between the new client and existing AP, 121 * should be used to avoid drift between the new client and
121 * the existing AP will get drift updates from the new 122 * existing AP. The existing AP will get drift updates from the
122 * client context in this case 123 * new client context in this case.
123 */ 124 */
124 if (vif->type == NL80211_IFTYPE_AP) { 125 if (vif->type != NL80211_IFTYPE_AP ||
125 if (data->preferred_tsf == NUM_TSF_IDS && 126 data->preferred_tsf != NUM_TSF_IDS ||
126 test_bit(mvmvif->tsf_id, data->available_tsf_ids) && 127 !test_bit(mvmvif->tsf_id, data->available_tsf_ids))
127 (vif->bss_conf.beacon_int == 128 break;
128 data->vif->bss_conf.beacon_int)) { 129
129 data->preferred_tsf = mvmvif->tsf_id; 130 min_bi = min(data->vif->bss_conf.beacon_int,
130 return; 131 vif->bss_conf.beacon_int);
131 } 132
133 if (!min_bi)
134 break;
135
136 if ((data->vif->bss_conf.beacon_int -
137 vif->bss_conf.beacon_int) % min_bi == 0) {
138 data->preferred_tsf = mvmvif->tsf_id;
139 return;
132 } 140 }
133 break; 141 break;
142
134 case NL80211_IFTYPE_AP: 143 case NL80211_IFTYPE_AP:
135 /* 144 /*
136 * The new interface is AP/GO, so in case both interfaces 145 * The new interface is AP/GO, so if its beacon interval is a
137 * have the same beacon interval, it should get drift 146 * multiple or a divisor of the beacon interval of an existing
138 * updates from an existing client or use the same 147 * interface, it should get drift updates from an existing
139 * TSF as an existing GO. There's no drift between 148 * client or use the same TSF as an existing GO. There's no
140 * TSFs internally but if they used different TSFs 149 * drift between TSFs internally but if they used different
141 * then a new client MAC could update one of them 150 * TSFs then a new client MAC could update one of them and
142 * and cause drift that way. 151 * cause drift that way.
143 */ 152 */
144 if (vif->type == NL80211_IFTYPE_STATION || 153 if ((vif->type != NL80211_IFTYPE_AP &&
145 vif->type == NL80211_IFTYPE_AP) { 154 vif->type != NL80211_IFTYPE_STATION) ||
146 if (data->preferred_tsf == NUM_TSF_IDS && 155 data->preferred_tsf != NUM_TSF_IDS ||
147 test_bit(mvmvif->tsf_id, data->available_tsf_ids) && 156 !test_bit(mvmvif->tsf_id, data->available_tsf_ids))
148 (vif->bss_conf.beacon_int == 157 break;
149 data->vif->bss_conf.beacon_int)) { 158
150 data->preferred_tsf = mvmvif->tsf_id; 159 min_bi = min(data->vif->bss_conf.beacon_int,
151 return; 160 vif->bss_conf.beacon_int);
152 } 161
162 if (!min_bi)
163 break;
164
165 if ((data->vif->bss_conf.beacon_int -
166 vif->bss_conf.beacon_int) % min_bi == 0) {
167 data->preferred_tsf = mvmvif->tsf_id;
168 return;
153 } 169 }
154 break; 170 break;
155 default: 171 default:
@@ -936,7 +952,7 @@ static int iwl_mvm_mac_ctxt_send_beacon(struct iwl_mvm *mvm,
936 TX_CMD_FLG_TSF); 952 TX_CMD_FLG_TSF);
937 953
938 mvm->mgmt_last_antenna_idx = 954 mvm->mgmt_last_antenna_idx =
939 iwl_mvm_next_antenna(mvm, iwl_fw_valid_tx_ant(mvm->fw), 955 iwl_mvm_next_antenna(mvm, mvm->fw->valid_tx_ant,
940 mvm->mgmt_last_antenna_idx); 956 mvm->mgmt_last_antenna_idx);
941 957
942 beacon_cmd.tx.rate_n_flags = 958 beacon_cmd.tx.rate_n_flags =
diff --git a/drivers/net/wireless/iwlwifi/mvm/mac80211.c b/drivers/net/wireless/iwlwifi/mvm/mac80211.c
index c35b8661b395..4dd9ff43b8b6 100644
--- a/drivers/net/wireless/iwlwifi/mvm/mac80211.c
+++ b/drivers/net/wireless/iwlwifi/mvm/mac80211.c
@@ -66,7 +66,9 @@
66#include <linux/netdevice.h> 66#include <linux/netdevice.h>
67#include <linux/etherdevice.h> 67#include <linux/etherdevice.h>
68#include <linux/ip.h> 68#include <linux/ip.h>
69#include <linux/if_arp.h>
69#include <net/mac80211.h> 70#include <net/mac80211.h>
71#include <net/ieee80211_radiotap.h>
70#include <net/tcp.h> 72#include <net/tcp.h>
71 73
72#include "iwl-op-mode.h" 74#include "iwl-op-mode.h"
@@ -128,6 +130,117 @@ static const struct wiphy_wowlan_tcp_support iwl_mvm_wowlan_tcp_support = {
128}; 130};
129#endif 131#endif
130 132
133#ifdef CONFIG_IWLWIFI_BCAST_FILTERING
134/*
135 * Use the reserved field to indicate magic values.
136 * these values will only be used internally by the driver,
137 * and won't make it to the fw (reserved will be 0).
138 * BC_FILTER_MAGIC_IP - configure the val of this attribute to
139 * be the vif's ip address. in case there is not a single
140 * ip address (0, or more than 1), this attribute will
141 * be skipped.
142 * BC_FILTER_MAGIC_MAC - set the val of this attribute to
143 * the LSB bytes of the vif's mac address
144 */
145enum {
146 BC_FILTER_MAGIC_NONE = 0,
147 BC_FILTER_MAGIC_IP,
148 BC_FILTER_MAGIC_MAC,
149};
150
151static const struct iwl_fw_bcast_filter iwl_mvm_default_bcast_filters[] = {
152 {
153 /* arp */
154 .discard = 0,
155 .frame_type = BCAST_FILTER_FRAME_TYPE_ALL,
156 .attrs = {
157 {
158 /* frame type - arp, hw type - ethernet */
159 .offset_type =
160 BCAST_FILTER_OFFSET_PAYLOAD_START,
161 .offset = sizeof(rfc1042_header),
162 .val = cpu_to_be32(0x08060001),
163 .mask = cpu_to_be32(0xffffffff),
164 },
165 {
166 /* arp dest ip */
167 .offset_type =
168 BCAST_FILTER_OFFSET_PAYLOAD_START,
169 .offset = sizeof(rfc1042_header) + 2 +
170 sizeof(struct arphdr) +
171 ETH_ALEN + sizeof(__be32) +
172 ETH_ALEN,
173 .mask = cpu_to_be32(0xffffffff),
174 /* mark it as special field */
175 .reserved1 = cpu_to_le16(BC_FILTER_MAGIC_IP),
176 },
177 },
178 },
179 {
180 /* dhcp offer bcast */
181 .discard = 0,
182 .frame_type = BCAST_FILTER_FRAME_TYPE_IPV4,
183 .attrs = {
184 {
185 /* udp dest port - 68 (bootp client)*/
186 .offset_type = BCAST_FILTER_OFFSET_IP_END,
187 .offset = offsetof(struct udphdr, dest),
188 .val = cpu_to_be32(0x00440000),
189 .mask = cpu_to_be32(0xffff0000),
190 },
191 {
192 /* dhcp - lsb bytes of client hw address */
193 .offset_type = BCAST_FILTER_OFFSET_IP_END,
194 .offset = 38,
195 .mask = cpu_to_be32(0xffffffff),
196 /* mark it as special field */
197 .reserved1 = cpu_to_le16(BC_FILTER_MAGIC_MAC),
198 },
199 },
200 },
201 /* last filter must be empty */
202 {},
203};
204#endif
205
206void iwl_mvm_ref(struct iwl_mvm *mvm, enum iwl_mvm_ref_type ref_type)
207{
208 if (!iwl_mvm_is_d0i3_supported(mvm))
209 return;
210
211 IWL_DEBUG_RPM(mvm, "Take mvm reference - type %d\n", ref_type);
212 WARN_ON(test_and_set_bit(ref_type, mvm->ref_bitmap));
213 iwl_trans_ref(mvm->trans);
214}
215
216void iwl_mvm_unref(struct iwl_mvm *mvm, enum iwl_mvm_ref_type ref_type)
217{
218 if (!iwl_mvm_is_d0i3_supported(mvm))
219 return;
220
221 IWL_DEBUG_RPM(mvm, "Leave mvm reference - type %d\n", ref_type);
222 WARN_ON(!test_and_clear_bit(ref_type, mvm->ref_bitmap));
223 iwl_trans_unref(mvm->trans);
224}
225
226static void
227iwl_mvm_unref_all_except(struct iwl_mvm *mvm, enum iwl_mvm_ref_type ref)
228{
229 int i;
230
231 if (!iwl_mvm_is_d0i3_supported(mvm))
232 return;
233
234 for_each_set_bit(i, mvm->ref_bitmap, IWL_MVM_REF_COUNT) {
235 if (ref == i)
236 continue;
237
238 IWL_DEBUG_RPM(mvm, "Cleanup: remove mvm ref type %d\n", i);
239 clear_bit(i, mvm->ref_bitmap);
240 iwl_trans_unref(mvm->trans);
241 }
242}
243
131static void iwl_mvm_reset_phy_ctxts(struct iwl_mvm *mvm) 244static void iwl_mvm_reset_phy_ctxts(struct iwl_mvm *mvm)
132{ 245{
133 int i; 246 int i;
@@ -168,6 +281,9 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
168 281
169 hw->queues = mvm->first_agg_queue; 282 hw->queues = mvm->first_agg_queue;
170 hw->offchannel_tx_hw_queue = IWL_MVM_OFFCHANNEL_QUEUE; 283 hw->offchannel_tx_hw_queue = IWL_MVM_OFFCHANNEL_QUEUE;
284 hw->radiotap_mcs_details |= IEEE80211_RADIOTAP_MCS_HAVE_FEC |
285 IEEE80211_RADIOTAP_MCS_HAVE_STBC;
286 hw->radiotap_vht_details |= IEEE80211_RADIOTAP_VHT_KNOWN_STBC;
171 hw->rate_control_algorithm = "iwl-mvm-rs"; 287 hw->rate_control_algorithm = "iwl-mvm-rs";
172 288
173 /* 289 /*
@@ -179,7 +295,7 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
179 !iwlwifi_mod_params.sw_crypto) 295 !iwlwifi_mod_params.sw_crypto)
180 hw->flags |= IEEE80211_HW_MFP_CAPABLE; 296 hw->flags |= IEEE80211_HW_MFP_CAPABLE;
181 297
182 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_UAPSD_SUPPORT) { 298 if (0 && mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_UAPSD_SUPPORT) {
183 hw->flags |= IEEE80211_HW_SUPPORTS_UAPSD; 299 hw->flags |= IEEE80211_HW_SUPPORTS_UAPSD;
184 hw->uapsd_queues = IWL_UAPSD_AC_INFO; 300 hw->uapsd_queues = IWL_UAPSD_AC_INFO;
185 hw->uapsd_max_sp_len = IWL_UAPSD_MAX_SP; 301 hw->uapsd_max_sp_len = IWL_UAPSD_MAX_SP;
@@ -203,6 +319,9 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
203 hw->wiphy->regulatory_flags |= REGULATORY_CUSTOM_REG | 319 hw->wiphy->regulatory_flags |= REGULATORY_CUSTOM_REG |
204 REGULATORY_DISABLE_BEACON_HINTS; 320 REGULATORY_DISABLE_BEACON_HINTS;
205 321
322 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_GO_UAPSD)
323 hw->wiphy->flags |= WIPHY_FLAG_AP_UAPSD;
324
206 hw->wiphy->iface_combinations = iwl_mvm_iface_combinations; 325 hw->wiphy->iface_combinations = iwl_mvm_iface_combinations;
207 hw->wiphy->n_iface_combinations = 326 hw->wiphy->n_iface_combinations =
208 ARRAY_SIZE(iwl_mvm_iface_combinations); 327 ARRAY_SIZE(iwl_mvm_iface_combinations);
@@ -246,7 +365,7 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
246 else 365 else
247 hw->wiphy->flags &= ~WIPHY_FLAG_PS_ON_BY_DEFAULT; 366 hw->wiphy->flags &= ~WIPHY_FLAG_PS_ON_BY_DEFAULT;
248 367
249 if (0 && mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_SCHED_SCAN) { 368 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_SCHED_SCAN) {
250 hw->wiphy->flags |= WIPHY_FLAG_SUPPORTS_SCHED_SCAN; 369 hw->wiphy->flags |= WIPHY_FLAG_SUPPORTS_SCHED_SCAN;
251 hw->wiphy->max_sched_scan_ssids = PROBE_OPTION_MAX; 370 hw->wiphy->max_sched_scan_ssids = PROBE_OPTION_MAX;
252 hw->wiphy->max_match_sets = IWL_SCAN_MAX_PROFILES; 371 hw->wiphy->max_match_sets = IWL_SCAN_MAX_PROFILES;
@@ -256,8 +375,7 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
256 } 375 }
257 376
258 hw->wiphy->features |= NL80211_FEATURE_P2P_GO_CTWIN | 377 hw->wiphy->features |= NL80211_FEATURE_P2P_GO_CTWIN |
259 NL80211_FEATURE_P2P_GO_OPPPS | 378 NL80211_FEATURE_P2P_GO_OPPPS;
260 NL80211_FEATURE_LOW_PRIORITY_SCAN;
261 379
262 mvm->rts_threshold = IEEE80211_MAX_RTS_THRESHOLD; 380 mvm->rts_threshold = IEEE80211_MAX_RTS_THRESHOLD;
263 381
@@ -289,6 +407,11 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
289 } 407 }
290#endif 408#endif
291 409
410#ifdef CONFIG_IWLWIFI_BCAST_FILTERING
411 /* assign default bcast filtering configuration */
412 mvm->bcast_filters = iwl_mvm_default_bcast_filters;
413#endif
414
292 ret = iwl_mvm_leds_init(mvm); 415 ret = iwl_mvm_leds_init(mvm);
293 if (ret) 416 if (ret)
294 return ret; 417 return ret;
@@ -300,11 +423,55 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
300 return ret; 423 return ret;
301} 424}
302 425
426static bool iwl_mvm_defer_tx(struct iwl_mvm *mvm,
427 struct ieee80211_sta *sta,
428 struct sk_buff *skb)
429{
430 struct iwl_mvm_sta *mvmsta;
431 bool defer = false;
432
433 /*
434 * double check the IN_D0I3 flag both before and after
435 * taking the spinlock, in order to prevent taking
436 * the spinlock when not needed.
437 */
438 if (likely(!test_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status)))
439 return false;
440
441 spin_lock(&mvm->d0i3_tx_lock);
442 /*
443 * testing the flag again ensures the skb dequeue
444 * loop (on d0i3 exit) hasn't run yet.
445 */
446 if (!test_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status))
447 goto out;
448
449 mvmsta = iwl_mvm_sta_from_mac80211(sta);
450 if (mvmsta->sta_id == IWL_MVM_STATION_COUNT ||
451 mvmsta->sta_id != mvm->d0i3_ap_sta_id)
452 goto out;
453
454 __skb_queue_tail(&mvm->d0i3_tx, skb);
455 ieee80211_stop_queues(mvm->hw);
456
457 /* trigger wakeup */
458 iwl_mvm_ref(mvm, IWL_MVM_REF_TX);
459 iwl_mvm_unref(mvm, IWL_MVM_REF_TX);
460
461 defer = true;
462out:
463 spin_unlock(&mvm->d0i3_tx_lock);
464 return defer;
465}
466
303static void iwl_mvm_mac_tx(struct ieee80211_hw *hw, 467static void iwl_mvm_mac_tx(struct ieee80211_hw *hw,
304 struct ieee80211_tx_control *control, 468 struct ieee80211_tx_control *control,
305 struct sk_buff *skb) 469 struct sk_buff *skb)
306{ 470{
307 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); 471 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
472 struct ieee80211_sta *sta = control->sta;
473 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
474 struct ieee80211_hdr *hdr = (void *)skb->data;
308 475
309 if (iwl_mvm_is_radio_killed(mvm)) { 476 if (iwl_mvm_is_radio_killed(mvm)) {
310 IWL_DEBUG_DROP(mvm, "Dropping - RF/CT KILL\n"); 477 IWL_DEBUG_DROP(mvm, "Dropping - RF/CT KILL\n");
@@ -315,8 +482,18 @@ static void iwl_mvm_mac_tx(struct ieee80211_hw *hw,
315 !test_bit(IWL_MVM_STATUS_ROC_RUNNING, &mvm->status)) 482 !test_bit(IWL_MVM_STATUS_ROC_RUNNING, &mvm->status))
316 goto drop; 483 goto drop;
317 484
318 if (control->sta) { 485 /* treat non-bufferable MMPDUs as broadcast if sta is sleeping */
319 if (iwl_mvm_tx_skb(mvm, skb, control->sta)) 486 if (unlikely(info->flags & IEEE80211_TX_CTL_NO_PS_BUFFER &&
487 ieee80211_is_mgmt(hdr->frame_control) &&
488 !ieee80211_is_deauth(hdr->frame_control) &&
489 !ieee80211_is_disassoc(hdr->frame_control) &&
490 !ieee80211_is_action(hdr->frame_control)))
491 sta = NULL;
492
493 if (sta) {
494 if (iwl_mvm_defer_tx(mvm, sta, skb))
495 return;
496 if (iwl_mvm_tx_skb(mvm, skb, sta))
320 goto drop; 497 goto drop;
321 return; 498 return;
322 } 499 }
@@ -354,6 +531,7 @@ static int iwl_mvm_mac_ampdu_action(struct ieee80211_hw *hw,
354{ 531{
355 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); 532 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
356 int ret; 533 int ret;
534 bool tx_agg_ref = false;
357 535
358 IWL_DEBUG_HT(mvm, "A-MPDU action on addr %pM tid %d: action %d\n", 536 IWL_DEBUG_HT(mvm, "A-MPDU action on addr %pM tid %d: action %d\n",
359 sta->addr, tid, action); 537 sta->addr, tid, action);
@@ -361,6 +539,23 @@ static int iwl_mvm_mac_ampdu_action(struct ieee80211_hw *hw,
361 if (!(mvm->nvm_data->sku_cap_11n_enable)) 539 if (!(mvm->nvm_data->sku_cap_11n_enable))
362 return -EACCES; 540 return -EACCES;
363 541
542 /* return from D0i3 before starting a new Tx aggregation */
543 if (action == IEEE80211_AMPDU_TX_START) {
544 iwl_mvm_ref(mvm, IWL_MVM_REF_TX_AGG);
545 tx_agg_ref = true;
546
547 /*
548 * wait synchronously until D0i3 exit to get the correct
549 * sequence number for the tid
550 */
551 if (!wait_event_timeout(mvm->d0i3_exit_waitq,
552 !test_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status), HZ)) {
553 WARN_ON_ONCE(1);
554 iwl_mvm_unref(mvm, IWL_MVM_REF_TX_AGG);
555 return -EIO;
556 }
557 }
558
364 mutex_lock(&mvm->mutex); 559 mutex_lock(&mvm->mutex);
365 560
366 switch (action) { 561 switch (action) {
@@ -398,6 +593,13 @@ static int iwl_mvm_mac_ampdu_action(struct ieee80211_hw *hw,
398 } 593 }
399 mutex_unlock(&mvm->mutex); 594 mutex_unlock(&mvm->mutex);
400 595
596 /*
597 * If the tid is marked as started, we won't use it for offloaded
598 * traffic on the next D0i3 entry. It's safe to unref.
599 */
600 if (tx_agg_ref)
601 iwl_mvm_unref(mvm, IWL_MVM_REF_TX_AGG);
602
401 return ret; 603 return ret;
402} 604}
403 605
@@ -422,6 +624,15 @@ static void iwl_mvm_cleanup_iterator(void *data, u8 *mac,
422 624
423static void iwl_mvm_restart_cleanup(struct iwl_mvm *mvm) 625static void iwl_mvm_restart_cleanup(struct iwl_mvm *mvm)
424{ 626{
627#ifdef CONFIG_IWLWIFI_DEBUGFS
628 static char *env[] = { "DRIVER=iwlwifi", "EVENT=error_dump", NULL };
629
630 iwl_mvm_fw_error_dump(mvm);
631
632 /* notify the userspace about the error we had */
633 kobject_uevent_env(&mvm->hw->wiphy->dev.kobj, KOBJ_CHANGE, env);
634#endif
635
425 iwl_trans_stop_device(mvm->trans); 636 iwl_trans_stop_device(mvm->trans);
426 637
427 mvm->scan_status = IWL_MVM_SCAN_NONE; 638 mvm->scan_status = IWL_MVM_SCAN_NONE;
@@ -434,6 +645,7 @@ static void iwl_mvm_restart_cleanup(struct iwl_mvm *mvm)
434 iwl_mvm_cleanup_iterator, mvm); 645 iwl_mvm_cleanup_iterator, mvm);
435 646
436 mvm->p2p_device_vif = NULL; 647 mvm->p2p_device_vif = NULL;
648 mvm->d0i3_ap_sta_id = IWL_MVM_STATION_COUNT;
437 649
438 iwl_mvm_reset_phy_ctxts(mvm); 650 iwl_mvm_reset_phy_ctxts(mvm);
439 memset(mvm->fw_key_table, 0, sizeof(mvm->fw_key_table)); 651 memset(mvm->fw_key_table, 0, sizeof(mvm->fw_key_table));
@@ -441,6 +653,10 @@ static void iwl_mvm_restart_cleanup(struct iwl_mvm *mvm)
441 653
442 ieee80211_wake_queues(mvm->hw); 654 ieee80211_wake_queues(mvm->hw);
443 655
656 /* cleanup all stale references (scan, roc), but keep the
657 * ucode_down ref until reconfig is complete */
658 iwl_mvm_unref_all_except(mvm, IWL_MVM_REF_UCODE_DOWN);
659
444 mvm->vif_count = 0; 660 mvm->vif_count = 0;
445 mvm->rx_ba_sessions = 0; 661 mvm->rx_ba_sessions = 0;
446} 662}
@@ -470,11 +686,15 @@ static void iwl_mvm_mac_restart_complete(struct ieee80211_hw *hw)
470 mutex_lock(&mvm->mutex); 686 mutex_lock(&mvm->mutex);
471 687
472 clear_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status); 688 clear_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status);
689 iwl_mvm_d0i3_enable_tx(mvm, NULL);
473 ret = iwl_mvm_update_quotas(mvm, NULL); 690 ret = iwl_mvm_update_quotas(mvm, NULL);
474 if (ret) 691 if (ret)
475 IWL_ERR(mvm, "Failed to update quotas after restart (%d)\n", 692 IWL_ERR(mvm, "Failed to update quotas after restart (%d)\n",
476 ret); 693 ret);
477 694
695 /* allow transport/FW low power modes */
696 iwl_mvm_unref(mvm, IWL_MVM_REF_UCODE_DOWN);
697
478 mutex_unlock(&mvm->mutex); 698 mutex_unlock(&mvm->mutex);
479} 699}
480 700
@@ -482,9 +702,14 @@ static void iwl_mvm_mac_stop(struct ieee80211_hw *hw)
482{ 702{
483 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); 703 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
484 704
705 flush_work(&mvm->d0i3_exit_work);
485 flush_work(&mvm->async_handlers_wk); 706 flush_work(&mvm->async_handlers_wk);
486 707
487 mutex_lock(&mvm->mutex); 708 mutex_lock(&mvm->mutex);
709
710 /* disallow low power states when the FW is down */
711 iwl_mvm_ref(mvm, IWL_MVM_REF_UCODE_DOWN);
712
488 /* async_handlers_wk is now blocked */ 713 /* async_handlers_wk is now blocked */
489 714
490 /* 715 /*
@@ -510,14 +735,6 @@ static void iwl_mvm_mac_stop(struct ieee80211_hw *hw)
510 cancel_work_sync(&mvm->async_handlers_wk); 735 cancel_work_sync(&mvm->async_handlers_wk);
511} 736}
512 737
513static void iwl_mvm_power_update_iterator(void *data, u8 *mac,
514 struct ieee80211_vif *vif)
515{
516 struct iwl_mvm *mvm = data;
517
518 iwl_mvm_power_update_mode(mvm, vif);
519}
520
521static struct iwl_mvm_phy_ctxt *iwl_mvm_get_free_phy_ctxt(struct iwl_mvm *mvm) 738static struct iwl_mvm_phy_ctxt *iwl_mvm_get_free_phy_ctxt(struct iwl_mvm *mvm)
522{ 739{
523 u16 i; 740 u16 i;
@@ -585,7 +802,8 @@ static int iwl_mvm_mac_add_interface(struct ieee80211_hw *hw,
585 vif->type == NL80211_IFTYPE_ADHOC) { 802 vif->type == NL80211_IFTYPE_ADHOC) {
586 u32 qmask = iwl_mvm_mac_get_queues_mask(mvm, vif); 803 u32 qmask = iwl_mvm_mac_get_queues_mask(mvm, vif);
587 ret = iwl_mvm_allocate_int_sta(mvm, &mvmvif->bcast_sta, 804 ret = iwl_mvm_allocate_int_sta(mvm, &mvmvif->bcast_sta,
588 qmask); 805 qmask,
806 ieee80211_vif_type_p2p(vif));
589 if (ret) { 807 if (ret) {
590 IWL_ERR(mvm, "Failed to allocate bcast sta\n"); 808 IWL_ERR(mvm, "Failed to allocate bcast sta\n");
591 goto out_release; 809 goto out_release;
@@ -599,10 +817,12 @@ static int iwl_mvm_mac_add_interface(struct ieee80211_hw *hw,
599 if (ret) 817 if (ret)
600 goto out_release; 818 goto out_release;
601 819
602 iwl_mvm_power_disable(mvm, vif); 820 ret = iwl_mvm_power_update_mac(mvm, vif);
821 if (ret)
822 goto out_release;
603 823
604 /* beacon filtering */ 824 /* beacon filtering */
605 ret = iwl_mvm_disable_beacon_filter(mvm, vif); 825 ret = iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC);
606 if (ret) 826 if (ret)
607 goto out_remove_mac; 827 goto out_remove_mac;
608 828
@@ -661,11 +881,6 @@ static int iwl_mvm_mac_add_interface(struct ieee80211_hw *hw,
661 if (vif->type != NL80211_IFTYPE_P2P_DEVICE) 881 if (vif->type != NL80211_IFTYPE_P2P_DEVICE)
662 mvm->vif_count--; 882 mvm->vif_count--;
663 883
664 /* TODO: remove this when legacy PM will be discarded */
665 ieee80211_iterate_active_interfaces(
666 mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
667 iwl_mvm_power_update_iterator, mvm);
668
669 iwl_mvm_mac_ctxt_release(mvm, vif); 884 iwl_mvm_mac_ctxt_release(mvm, vif);
670 out_unlock: 885 out_unlock:
671 mutex_unlock(&mvm->mutex); 886 mutex_unlock(&mvm->mutex);
@@ -754,11 +969,7 @@ static void iwl_mvm_mac_remove_interface(struct ieee80211_hw *hw,
754 if (mvm->vif_count && vif->type != NL80211_IFTYPE_P2P_DEVICE) 969 if (mvm->vif_count && vif->type != NL80211_IFTYPE_P2P_DEVICE)
755 mvm->vif_count--; 970 mvm->vif_count--;
756 971
757 /* TODO: remove this when legacy PM will be discarded */ 972 iwl_mvm_power_update_mac(mvm, vif);
758 ieee80211_iterate_active_interfaces(
759 mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
760 iwl_mvm_power_update_iterator, mvm);
761
762 iwl_mvm_mac_ctxt_remove(mvm, vif); 973 iwl_mvm_mac_ctxt_remove(mvm, vif);
763 974
764out_release: 975out_release:
@@ -876,6 +1087,156 @@ out:
876 *total_flags = 0; 1087 *total_flags = 0;
877} 1088}
878 1089
1090#ifdef CONFIG_IWLWIFI_BCAST_FILTERING
1091struct iwl_bcast_iter_data {
1092 struct iwl_mvm *mvm;
1093 struct iwl_bcast_filter_cmd *cmd;
1094 u8 current_filter;
1095};
1096
1097static void
1098iwl_mvm_set_bcast_filter(struct ieee80211_vif *vif,
1099 const struct iwl_fw_bcast_filter *in_filter,
1100 struct iwl_fw_bcast_filter *out_filter)
1101{
1102 struct iwl_fw_bcast_filter_attr *attr;
1103 int i;
1104
1105 memcpy(out_filter, in_filter, sizeof(*out_filter));
1106
1107 for (i = 0; i < ARRAY_SIZE(out_filter->attrs); i++) {
1108 attr = &out_filter->attrs[i];
1109
1110 if (!attr->mask)
1111 break;
1112
1113 switch (attr->reserved1) {
1114 case cpu_to_le16(BC_FILTER_MAGIC_IP):
1115 if (vif->bss_conf.arp_addr_cnt != 1) {
1116 attr->mask = 0;
1117 continue;
1118 }
1119
1120 attr->val = vif->bss_conf.arp_addr_list[0];
1121 break;
1122 case cpu_to_le16(BC_FILTER_MAGIC_MAC):
1123 attr->val = *(__be32 *)&vif->addr[2];
1124 break;
1125 default:
1126 break;
1127 }
1128 attr->reserved1 = 0;
1129 out_filter->num_attrs++;
1130 }
1131}
1132
1133static void iwl_mvm_bcast_filter_iterator(void *_data, u8 *mac,
1134 struct ieee80211_vif *vif)
1135{
1136 struct iwl_bcast_iter_data *data = _data;
1137 struct iwl_mvm *mvm = data->mvm;
1138 struct iwl_bcast_filter_cmd *cmd = data->cmd;
1139 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
1140 struct iwl_fw_bcast_mac *bcast_mac;
1141 int i;
1142
1143 if (WARN_ON(mvmvif->id >= ARRAY_SIZE(cmd->macs)))
1144 return;
1145
1146 bcast_mac = &cmd->macs[mvmvif->id];
1147
1148 /* enable filtering only for associated stations */
1149 if (vif->type != NL80211_IFTYPE_STATION || !vif->bss_conf.assoc)
1150 return;
1151
1152 bcast_mac->default_discard = 1;
1153
1154 /* copy all configured filters */
1155 for (i = 0; mvm->bcast_filters[i].attrs[0].mask; i++) {
1156 /*
1157 * Make sure we don't exceed our filters limit.
1158 * if there is still a valid filter to be configured,
1159 * be on the safe side and just allow bcast for this mac.
1160 */
1161 if (WARN_ON_ONCE(data->current_filter >=
1162 ARRAY_SIZE(cmd->filters))) {
1163 bcast_mac->default_discard = 0;
1164 bcast_mac->attached_filters = 0;
1165 break;
1166 }
1167
1168 iwl_mvm_set_bcast_filter(vif,
1169 &mvm->bcast_filters[i],
1170 &cmd->filters[data->current_filter]);
1171
1172 /* skip current filter if it contains no attributes */
1173 if (!cmd->filters[data->current_filter].num_attrs)
1174 continue;
1175
1176 /* attach the filter to current mac */
1177 bcast_mac->attached_filters |=
1178 cpu_to_le16(BIT(data->current_filter));
1179
1180 data->current_filter++;
1181 }
1182}
1183
1184bool iwl_mvm_bcast_filter_build_cmd(struct iwl_mvm *mvm,
1185 struct iwl_bcast_filter_cmd *cmd)
1186{
1187 struct iwl_bcast_iter_data iter_data = {
1188 .mvm = mvm,
1189 .cmd = cmd,
1190 };
1191
1192 memset(cmd, 0, sizeof(*cmd));
1193 cmd->max_bcast_filters = ARRAY_SIZE(cmd->filters);
1194 cmd->max_macs = ARRAY_SIZE(cmd->macs);
1195
1196#ifdef CONFIG_IWLWIFI_DEBUGFS
1197 /* use debugfs filters/macs if override is configured */
1198 if (mvm->dbgfs_bcast_filtering.override) {
1199 memcpy(cmd->filters, &mvm->dbgfs_bcast_filtering.cmd.filters,
1200 sizeof(cmd->filters));
1201 memcpy(cmd->macs, &mvm->dbgfs_bcast_filtering.cmd.macs,
1202 sizeof(cmd->macs));
1203 return true;
1204 }
1205#endif
1206
1207 /* if no filters are configured, do nothing */
1208 if (!mvm->bcast_filters)
1209 return false;
1210
1211 /* configure and attach these filters for each associated sta vif */
1212 ieee80211_iterate_active_interfaces(
1213 mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
1214 iwl_mvm_bcast_filter_iterator, &iter_data);
1215
1216 return true;
1217}
1218static int iwl_mvm_configure_bcast_filter(struct iwl_mvm *mvm,
1219 struct ieee80211_vif *vif)
1220{
1221 struct iwl_bcast_filter_cmd cmd;
1222
1223 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_BCAST_FILTERING))
1224 return 0;
1225
1226 if (!iwl_mvm_bcast_filter_build_cmd(mvm, &cmd))
1227 return 0;
1228
1229 return iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, CMD_SYNC,
1230 sizeof(cmd), &cmd);
1231}
1232#else
1233static inline int iwl_mvm_configure_bcast_filter(struct iwl_mvm *mvm,
1234 struct ieee80211_vif *vif)
1235{
1236 return 0;
1237}
1238#endif
1239
879static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm, 1240static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
880 struct ieee80211_vif *vif, 1241 struct ieee80211_vif *vif,
881 struct ieee80211_bss_conf *bss_conf, 1242 struct ieee80211_bss_conf *bss_conf,
@@ -928,6 +1289,8 @@ static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
928 1289
929 iwl_mvm_sf_update(mvm, vif, false); 1290 iwl_mvm_sf_update(mvm, vif, false);
930 iwl_mvm_power_vif_assoc(mvm, vif); 1291 iwl_mvm_power_vif_assoc(mvm, vif);
1292 if (vif->p2p)
1293 iwl_mvm_ref(mvm, IWL_MVM_REF_P2P_CLIENT);
931 } else if (mvmvif->ap_sta_id != IWL_MVM_STATION_COUNT) { 1294 } else if (mvmvif->ap_sta_id != IWL_MVM_STATION_COUNT) {
932 /* 1295 /*
933 * If update fails - SF might be running in associated 1296 * If update fails - SF might be running in associated
@@ -940,27 +1303,25 @@ static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
940 ret = iwl_mvm_rm_sta_id(mvm, vif, mvmvif->ap_sta_id); 1303 ret = iwl_mvm_rm_sta_id(mvm, vif, mvmvif->ap_sta_id);
941 if (ret) 1304 if (ret)
942 IWL_ERR(mvm, "failed to remove AP station\n"); 1305 IWL_ERR(mvm, "failed to remove AP station\n");
1306
1307 if (mvm->d0i3_ap_sta_id == mvmvif->ap_sta_id)
1308 mvm->d0i3_ap_sta_id = IWL_MVM_STATION_COUNT;
943 mvmvif->ap_sta_id = IWL_MVM_STATION_COUNT; 1309 mvmvif->ap_sta_id = IWL_MVM_STATION_COUNT;
944 /* remove quota for this interface */ 1310 /* remove quota for this interface */
945 ret = iwl_mvm_update_quotas(mvm, NULL); 1311 ret = iwl_mvm_update_quotas(mvm, NULL);
946 if (ret) 1312 if (ret)
947 IWL_ERR(mvm, "failed to update quotas\n"); 1313 IWL_ERR(mvm, "failed to update quotas\n");
1314
1315 if (vif->p2p)
1316 iwl_mvm_unref(mvm, IWL_MVM_REF_P2P_CLIENT);
948 } 1317 }
949 1318
950 iwl_mvm_recalc_multicast(mvm); 1319 iwl_mvm_recalc_multicast(mvm);
1320 iwl_mvm_configure_bcast_filter(mvm, vif);
951 1321
952 /* reset rssi values */ 1322 /* reset rssi values */
953 mvmvif->bf_data.ave_beacon_signal = 0; 1323 mvmvif->bf_data.ave_beacon_signal = 0;
954 1324
955 if (!(mvm->fw->ucode_capa.flags &
956 IWL_UCODE_TLV_FLAGS_PM_CMD_SUPPORT)) {
957 /* Workaround for FW bug, otherwise FW disables device
958 * power save upon disassociation
959 */
960 ret = iwl_mvm_power_update_mode(mvm, vif);
961 if (ret)
962 IWL_ERR(mvm, "failed to update power mode\n");
963 }
964 iwl_mvm_bt_coex_vif_change(mvm); 1325 iwl_mvm_bt_coex_vif_change(mvm);
965 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_TT, 1326 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_TT,
966 IEEE80211_SMPS_AUTOMATIC); 1327 IEEE80211_SMPS_AUTOMATIC);
@@ -971,9 +1332,10 @@ static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
971 */ 1332 */
972 iwl_mvm_remove_time_event(mvm, mvmvif, 1333 iwl_mvm_remove_time_event(mvm, mvmvif,
973 &mvmvif->time_event_data); 1334 &mvmvif->time_event_data);
1335 WARN_ON(iwl_mvm_enable_beacon_filter(mvm, vif, CMD_SYNC));
974 } else if (changes & (BSS_CHANGED_PS | BSS_CHANGED_P2P_PS | 1336 } else if (changes & (BSS_CHANGED_PS | BSS_CHANGED_P2P_PS |
975 BSS_CHANGED_QOS)) { 1337 BSS_CHANGED_QOS)) {
976 ret = iwl_mvm_power_update_mode(mvm, vif); 1338 ret = iwl_mvm_power_update_mac(mvm, vif);
977 if (ret) 1339 if (ret)
978 IWL_ERR(mvm, "failed to update power mode\n"); 1340 IWL_ERR(mvm, "failed to update power mode\n");
979 } 1341 }
@@ -987,10 +1349,15 @@ static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
987 IWL_DEBUG_MAC80211(mvm, "cqm info_changed"); 1349 IWL_DEBUG_MAC80211(mvm, "cqm info_changed");
988 /* reset cqm events tracking */ 1350 /* reset cqm events tracking */
989 mvmvif->bf_data.last_cqm_event = 0; 1351 mvmvif->bf_data.last_cqm_event = 0;
990 ret = iwl_mvm_update_beacon_filter(mvm, vif); 1352 ret = iwl_mvm_update_beacon_filter(mvm, vif, false, CMD_SYNC);
991 if (ret) 1353 if (ret)
992 IWL_ERR(mvm, "failed to update CQM thresholds\n"); 1354 IWL_ERR(mvm, "failed to update CQM thresholds\n");
993 } 1355 }
1356
1357 if (changes & BSS_CHANGED_ARP_FILTER) {
1358 IWL_DEBUG_MAC80211(mvm, "arp filter changed");
1359 iwl_mvm_configure_bcast_filter(mvm, vif);
1360 }
994} 1361}
995 1362
996static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw, 1363static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw,
@@ -1024,8 +1391,6 @@ static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw,
1024 if (ret) 1391 if (ret)
1025 goto out_remove; 1392 goto out_remove;
1026 1393
1027 mvmvif->ap_ibss_active = true;
1028
1029 /* Send the bcast station. At this stage the TBTT and DTIM time events 1394 /* Send the bcast station. At this stage the TBTT and DTIM time events
1030 * are added and applied to the scheduler */ 1395 * are added and applied to the scheduler */
1031 ret = iwl_mvm_send_bcast_sta(mvm, vif, &mvmvif->bcast_sta); 1396 ret = iwl_mvm_send_bcast_sta(mvm, vif, &mvmvif->bcast_sta);
@@ -1036,8 +1401,7 @@ static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw,
1036 mvmvif->ap_ibss_active = true; 1401 mvmvif->ap_ibss_active = true;
1037 1402
1038 /* power updated needs to be done before quotas */ 1403 /* power updated needs to be done before quotas */
1039 mvm->bound_vif_cnt++; 1404 iwl_mvm_power_update_mac(mvm, vif);
1040 iwl_mvm_power_update_binding(mvm, vif, true);
1041 1405
1042 ret = iwl_mvm_update_quotas(mvm, vif); 1406 ret = iwl_mvm_update_quotas(mvm, vif);
1043 if (ret) 1407 if (ret)
@@ -1047,14 +1411,15 @@ static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw,
1047 if (vif->p2p && mvm->p2p_device_vif) 1411 if (vif->p2p && mvm->p2p_device_vif)
1048 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif); 1412 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif);
1049 1413
1414 iwl_mvm_ref(mvm, IWL_MVM_REF_AP_IBSS);
1415
1050 iwl_mvm_bt_coex_vif_change(mvm); 1416 iwl_mvm_bt_coex_vif_change(mvm);
1051 1417
1052 mutex_unlock(&mvm->mutex); 1418 mutex_unlock(&mvm->mutex);
1053 return 0; 1419 return 0;
1054 1420
1055out_quota_failed: 1421out_quota_failed:
1056 mvm->bound_vif_cnt--; 1422 iwl_mvm_power_update_mac(mvm, vif);
1057 iwl_mvm_power_update_binding(mvm, vif, false);
1058 mvmvif->ap_ibss_active = false; 1423 mvmvif->ap_ibss_active = false;
1059 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta); 1424 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta);
1060out_unbind: 1425out_unbind:
@@ -1080,6 +1445,8 @@ static void iwl_mvm_stop_ap_ibss(struct ieee80211_hw *hw,
1080 1445
1081 iwl_mvm_bt_coex_vif_change(mvm); 1446 iwl_mvm_bt_coex_vif_change(mvm);
1082 1447
1448 iwl_mvm_unref(mvm, IWL_MVM_REF_AP_IBSS);
1449
1083 /* Need to update the P2P Device MAC (only GO, IBSS is single vif) */ 1450 /* Need to update the P2P Device MAC (only GO, IBSS is single vif) */
1084 if (vif->p2p && mvm->p2p_device_vif) 1451 if (vif->p2p && mvm->p2p_device_vif)
1085 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif); 1452 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif);
@@ -1088,8 +1455,7 @@ static void iwl_mvm_stop_ap_ibss(struct ieee80211_hw *hw,
1088 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta); 1455 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta);
1089 iwl_mvm_binding_remove_vif(mvm, vif); 1456 iwl_mvm_binding_remove_vif(mvm, vif);
1090 1457
1091 mvm->bound_vif_cnt--; 1458 iwl_mvm_power_update_mac(mvm, vif);
1092 iwl_mvm_power_update_binding(mvm, vif, false);
1093 1459
1094 iwl_mvm_mac_ctxt_remove(mvm, vif); 1460 iwl_mvm_mac_ctxt_remove(mvm, vif);
1095 1461
@@ -1103,26 +1469,20 @@ iwl_mvm_bss_info_changed_ap_ibss(struct iwl_mvm *mvm,
1103 u32 changes) 1469 u32 changes)
1104{ 1470{
1105 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 1471 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
1106 enum ieee80211_bss_change ht_change = BSS_CHANGED_ERP_CTS_PROT |
1107 BSS_CHANGED_HT |
1108 BSS_CHANGED_BANDWIDTH;
1109 int ret;
1110 1472
1111 /* Changes will be applied when the AP/IBSS is started */ 1473 /* Changes will be applied when the AP/IBSS is started */
1112 if (!mvmvif->ap_ibss_active) 1474 if (!mvmvif->ap_ibss_active)
1113 return; 1475 return;
1114 1476
1115 if (changes & ht_change) { 1477 if (changes & (BSS_CHANGED_ERP_CTS_PROT | BSS_CHANGED_HT |
1116 ret = iwl_mvm_mac_ctxt_changed(mvm, vif); 1478 BSS_CHANGED_BANDWIDTH) &&
1117 if (ret) 1479 iwl_mvm_mac_ctxt_changed(mvm, vif))
1118 IWL_ERR(mvm, "failed to update MAC %pM\n", vif->addr); 1480 IWL_ERR(mvm, "failed to update MAC %pM\n", vif->addr);
1119 }
1120 1481
1121 /* Need to send a new beacon template to the FW */ 1482 /* Need to send a new beacon template to the FW */
1122 if (changes & BSS_CHANGED_BEACON) { 1483 if (changes & BSS_CHANGED_BEACON &&
1123 if (iwl_mvm_mac_ctxt_beacon_changed(mvm, vif)) 1484 iwl_mvm_mac_ctxt_beacon_changed(mvm, vif))
1124 IWL_WARN(mvm, "Failed updating beacon data\n"); 1485 IWL_WARN(mvm, "Failed updating beacon data\n");
1125 }
1126} 1486}
1127 1487
1128static void iwl_mvm_bss_info_changed(struct ieee80211_hw *hw, 1488static void iwl_mvm_bss_info_changed(struct ieee80211_hw *hw,
@@ -1162,13 +1522,30 @@ static int iwl_mvm_mac_hw_scan(struct ieee80211_hw *hw,
1162 1522
1163 mutex_lock(&mvm->mutex); 1523 mutex_lock(&mvm->mutex);
1164 1524
1165 if (mvm->scan_status == IWL_MVM_SCAN_NONE) 1525 switch (mvm->scan_status) {
1166 ret = iwl_mvm_scan_request(mvm, vif, req); 1526 case IWL_MVM_SCAN_SCHED:
1167 else 1527 ret = iwl_mvm_sched_scan_stop(mvm);
1528 if (ret) {
1529 ret = -EBUSY;
1530 goto out;
1531 }
1532 break;
1533 case IWL_MVM_SCAN_NONE:
1534 break;
1535 default:
1168 ret = -EBUSY; 1536 ret = -EBUSY;
1537 goto out;
1538 }
1169 1539
1170 mutex_unlock(&mvm->mutex); 1540 iwl_mvm_ref(mvm, IWL_MVM_REF_SCAN);
1171 1541
1542 ret = iwl_mvm_scan_request(mvm, vif, req);
1543 if (ret)
1544 iwl_mvm_unref(mvm, IWL_MVM_REF_SCAN);
1545out:
1546 mutex_unlock(&mvm->mutex);
1547 /* make sure to flush the Rx handler before the next scan arrives */
1548 iwl_mvm_wait_for_async_handlers(mvm);
1172 return ret; 1549 return ret;
1173} 1550}
1174 1551
@@ -1186,20 +1563,32 @@ static void iwl_mvm_mac_cancel_hw_scan(struct ieee80211_hw *hw,
1186 1563
1187static void 1564static void
1188iwl_mvm_mac_allow_buffered_frames(struct ieee80211_hw *hw, 1565iwl_mvm_mac_allow_buffered_frames(struct ieee80211_hw *hw,
1189 struct ieee80211_sta *sta, u16 tid, 1566 struct ieee80211_sta *sta, u16 tids,
1190 int num_frames, 1567 int num_frames,
1191 enum ieee80211_frame_release_type reason, 1568 enum ieee80211_frame_release_type reason,
1192 bool more_data) 1569 bool more_data)
1193{ 1570{
1194 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); 1571 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
1195 1572
1196 /* TODO: how do we tell the fw to send frames for a specific TID */ 1573 /* Called when we need to transmit (a) frame(s) from mac80211 */
1197 1574
1198 /* 1575 iwl_mvm_sta_modify_sleep_tx_count(mvm, sta, reason, num_frames,
1199 * The fw will send EOSP notification when the last frame will be 1576 tids, more_data, false);
1200 * transmitted. 1577}
1201 */ 1578
1202 iwl_mvm_sta_modify_sleep_tx_count(mvm, sta, reason, num_frames); 1579static void
1580iwl_mvm_mac_release_buffered_frames(struct ieee80211_hw *hw,
1581 struct ieee80211_sta *sta, u16 tids,
1582 int num_frames,
1583 enum ieee80211_frame_release_type reason,
1584 bool more_data)
1585{
1586 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
1587
1588 /* Called when we need to transmit (a) frame(s) from agg queue */
1589
1590 iwl_mvm_sta_modify_sleep_tx_count(mvm, sta, reason, num_frames,
1591 tids, more_data, true);
1203} 1592}
1204 1593
1205static void iwl_mvm_mac_sta_notify(struct ieee80211_hw *hw, 1594static void iwl_mvm_mac_sta_notify(struct ieee80211_hw *hw,
@@ -1209,11 +1598,25 @@ static void iwl_mvm_mac_sta_notify(struct ieee80211_hw *hw,
1209{ 1598{
1210 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); 1599 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
1211 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); 1600 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta);
1601 int tid;
1212 1602
1213 switch (cmd) { 1603 switch (cmd) {
1214 case STA_NOTIFY_SLEEP: 1604 case STA_NOTIFY_SLEEP:
1215 if (atomic_read(&mvm->pending_frames[mvmsta->sta_id]) > 0) 1605 if (atomic_read(&mvm->pending_frames[mvmsta->sta_id]) > 0)
1216 ieee80211_sta_block_awake(hw, sta, true); 1606 ieee80211_sta_block_awake(hw, sta, true);
1607 spin_lock_bh(&mvmsta->lock);
1608 for (tid = 0; tid < IWL_MAX_TID_COUNT; tid++) {
1609 struct iwl_mvm_tid_data *tid_data;
1610
1611 tid_data = &mvmsta->tid_data[tid];
1612 if (tid_data->state != IWL_AGG_ON &&
1613 tid_data->state != IWL_EMPTYING_HW_QUEUE_DELBA)
1614 continue;
1615 if (iwl_mvm_tid_queued(tid_data) == 0)
1616 continue;
1617 ieee80211_sta_set_buffered(sta, tid, true);
1618 }
1619 spin_unlock_bh(&mvmsta->lock);
1217 /* 1620 /*
1218 * The fw updates the STA to be asleep. Tx packets on the Tx 1621 * The fw updates the STA to be asleep. Tx packets on the Tx
1219 * queues to this station will not be transmitted. The fw will 1622 * queues to this station will not be transmitted. The fw will
@@ -1304,12 +1707,14 @@ static int iwl_mvm_mac_sta_state(struct ieee80211_hw *hw,
1304 } else if (old_state == IEEE80211_STA_ASSOC && 1707 } else if (old_state == IEEE80211_STA_ASSOC &&
1305 new_state == IEEE80211_STA_AUTHORIZED) { 1708 new_state == IEEE80211_STA_AUTHORIZED) {
1306 /* enable beacon filtering */ 1709 /* enable beacon filtering */
1307 WARN_ON(iwl_mvm_enable_beacon_filter(mvm, vif)); 1710 if (vif->bss_conf.dtim_period)
1711 WARN_ON(iwl_mvm_enable_beacon_filter(mvm, vif,
1712 CMD_SYNC));
1308 ret = 0; 1713 ret = 0;
1309 } else if (old_state == IEEE80211_STA_AUTHORIZED && 1714 } else if (old_state == IEEE80211_STA_AUTHORIZED &&
1310 new_state == IEEE80211_STA_ASSOC) { 1715 new_state == IEEE80211_STA_ASSOC) {
1311 /* disable beacon filtering */ 1716 /* disable beacon filtering */
1312 WARN_ON(iwl_mvm_disable_beacon_filter(mvm, vif)); 1717 WARN_ON(iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC));
1313 ret = 0; 1718 ret = 0;
1314 } else if (old_state == IEEE80211_STA_ASSOC && 1719 } else if (old_state == IEEE80211_STA_ASSOC &&
1315 new_state == IEEE80211_STA_AUTH) { 1720 new_state == IEEE80211_STA_AUTH) {
@@ -1401,9 +1806,26 @@ static int iwl_mvm_mac_sched_scan_start(struct ieee80211_hw *hw,
1401 1806
1402 mutex_lock(&mvm->mutex); 1807 mutex_lock(&mvm->mutex);
1403 1808
1404 if (mvm->scan_status != IWL_MVM_SCAN_NONE) { 1809 switch (mvm->scan_status) {
1405 IWL_DEBUG_SCAN(mvm, 1810 case IWL_MVM_SCAN_OS:
1406 "SCHED SCAN request during internal scan - abort\n"); 1811 IWL_DEBUG_SCAN(mvm, "Stopping previous scan for sched_scan\n");
1812 ret = iwl_mvm_cancel_scan(mvm);
1813 if (ret) {
1814 ret = -EBUSY;
1815 goto out;
1816 }
1817
1818 /*
1819 * iwl_mvm_rx_scan_complete() will be called soon but will
1820 * not reset the scan status as it won't be IWL_MVM_SCAN_OS
1821 * any more since we queue the next scan immediately (below).
1822 * We make sure it is called before the next scan starts by
1823 * flushing the async-handlers work.
1824 */
1825 break;
1826 case IWL_MVM_SCAN_NONE:
1827 break;
1828 default:
1407 ret = -EBUSY; 1829 ret = -EBUSY;
1408 goto out; 1830 goto out;
1409 } 1831 }
@@ -1425,17 +1847,23 @@ err:
1425 mvm->scan_status = IWL_MVM_SCAN_NONE; 1847 mvm->scan_status = IWL_MVM_SCAN_NONE;
1426out: 1848out:
1427 mutex_unlock(&mvm->mutex); 1849 mutex_unlock(&mvm->mutex);
1850 /* make sure to flush the Rx handler before the next scan arrives */
1851 iwl_mvm_wait_for_async_handlers(mvm);
1428 return ret; 1852 return ret;
1429} 1853}
1430 1854
1431static void iwl_mvm_mac_sched_scan_stop(struct ieee80211_hw *hw, 1855static int iwl_mvm_mac_sched_scan_stop(struct ieee80211_hw *hw,
1432 struct ieee80211_vif *vif) 1856 struct ieee80211_vif *vif)
1433{ 1857{
1434 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); 1858 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
1859 int ret;
1435 1860
1436 mutex_lock(&mvm->mutex); 1861 mutex_lock(&mvm->mutex);
1437 iwl_mvm_sched_scan_stop(mvm); 1862 ret = iwl_mvm_sched_scan_stop(mvm);
1438 mutex_unlock(&mvm->mutex); 1863 mutex_unlock(&mvm->mutex);
1864 iwl_mvm_wait_for_async_handlers(mvm);
1865
1866 return ret;
1439} 1867}
1440 1868
1441static int iwl_mvm_mac_set_key(struct ieee80211_hw *hw, 1869static int iwl_mvm_mac_set_key(struct ieee80211_hw *hw,
@@ -1773,8 +2201,7 @@ static int iwl_mvm_assign_vif_chanctx(struct ieee80211_hw *hw,
1773 * Power state must be updated before quotas, 2201 * Power state must be updated before quotas,
1774 * otherwise fw will complain. 2202 * otherwise fw will complain.
1775 */ 2203 */
1776 mvm->bound_vif_cnt++; 2204 iwl_mvm_power_update_mac(mvm, vif);
1777 iwl_mvm_power_update_binding(mvm, vif, true);
1778 2205
1779 /* Setting the quota at this stage is only required for monitor 2206 /* Setting the quota at this stage is only required for monitor
1780 * interfaces. For the other types, the bss_info changed flow 2207 * interfaces. For the other types, the bss_info changed flow
@@ -1791,8 +2218,7 @@ static int iwl_mvm_assign_vif_chanctx(struct ieee80211_hw *hw,
1791 2218
1792 out_remove_binding: 2219 out_remove_binding:
1793 iwl_mvm_binding_remove_vif(mvm, vif); 2220 iwl_mvm_binding_remove_vif(mvm, vif);
1794 mvm->bound_vif_cnt--; 2221 iwl_mvm_power_update_mac(mvm, vif);
1795 iwl_mvm_power_update_binding(mvm, vif, false);
1796 out_unlock: 2222 out_unlock:
1797 mutex_unlock(&mvm->mutex); 2223 mutex_unlock(&mvm->mutex);
1798 if (ret) 2224 if (ret)
@@ -1824,8 +2250,7 @@ static void iwl_mvm_unassign_vif_chanctx(struct ieee80211_hw *hw,
1824 } 2250 }
1825 2251
1826 iwl_mvm_binding_remove_vif(mvm, vif); 2252 iwl_mvm_binding_remove_vif(mvm, vif);
1827 mvm->bound_vif_cnt--; 2253 iwl_mvm_power_update_mac(mvm, vif);
1828 iwl_mvm_power_update_binding(mvm, vif, false);
1829 2254
1830out_unlock: 2255out_unlock:
1831 mvmvif->phy_ctxt = NULL; 2256 mvmvif->phy_ctxt = NULL;
@@ -1892,8 +2317,9 @@ static int __iwl_mvm_mac_testmode_cmd(struct iwl_mvm *mvm,
1892 return -EINVAL; 2317 return -EINVAL;
1893 2318
1894 if (nla_get_u32(tb[IWL_MVM_TM_ATTR_BEACON_FILTER_STATE])) 2319 if (nla_get_u32(tb[IWL_MVM_TM_ATTR_BEACON_FILTER_STATE]))
1895 return iwl_mvm_enable_beacon_filter(mvm, vif); 2320 return iwl_mvm_enable_beacon_filter(mvm, vif,
1896 return iwl_mvm_disable_beacon_filter(mvm, vif); 2321 CMD_SYNC);
2322 return iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC);
1897 } 2323 }
1898 2324
1899 return -EOPNOTSUPP; 2325 return -EOPNOTSUPP;
@@ -1914,7 +2340,7 @@ static int iwl_mvm_mac_testmode_cmd(struct ieee80211_hw *hw,
1914} 2340}
1915#endif 2341#endif
1916 2342
1917struct ieee80211_ops iwl_mvm_hw_ops = { 2343const struct ieee80211_ops iwl_mvm_hw_ops = {
1918 .tx = iwl_mvm_mac_tx, 2344 .tx = iwl_mvm_mac_tx,
1919 .ampdu_action = iwl_mvm_mac_ampdu_action, 2345 .ampdu_action = iwl_mvm_mac_ampdu_action,
1920 .start = iwl_mvm_mac_start, 2346 .start = iwl_mvm_mac_start,
@@ -1932,6 +2358,7 @@ struct ieee80211_ops iwl_mvm_hw_ops = {
1932 .sta_state = iwl_mvm_mac_sta_state, 2358 .sta_state = iwl_mvm_mac_sta_state,
1933 .sta_notify = iwl_mvm_mac_sta_notify, 2359 .sta_notify = iwl_mvm_mac_sta_notify,
1934 .allow_buffered_frames = iwl_mvm_mac_allow_buffered_frames, 2360 .allow_buffered_frames = iwl_mvm_mac_allow_buffered_frames,
2361 .release_buffered_frames = iwl_mvm_mac_release_buffered_frames,
1935 .set_rts_threshold = iwl_mvm_mac_set_rts_threshold, 2362 .set_rts_threshold = iwl_mvm_mac_set_rts_threshold,
1936 .sta_rc_update = iwl_mvm_sta_rc_update, 2363 .sta_rc_update = iwl_mvm_sta_rc_update,
1937 .conf_tx = iwl_mvm_mac_conf_tx, 2364 .conf_tx = iwl_mvm_mac_conf_tx,
diff --git a/drivers/net/wireless/iwlwifi/mvm/mvm.h b/drivers/net/wireless/iwlwifi/mvm/mvm.h
index 2b0ba1fc3c82..d564233a65da 100644
--- a/drivers/net/wireless/iwlwifi/mvm/mvm.h
+++ b/drivers/net/wireless/iwlwifi/mvm/mvm.h
@@ -91,9 +91,7 @@ enum iwl_mvm_tx_fifo {
91 IWL_MVM_TX_FIFO_MCAST = 5, 91 IWL_MVM_TX_FIFO_MCAST = 5,
92}; 92};
93 93
94extern struct ieee80211_ops iwl_mvm_hw_ops; 94extern const struct ieee80211_ops iwl_mvm_hw_ops;
95extern const struct iwl_mvm_power_ops pm_legacy_ops;
96extern const struct iwl_mvm_power_ops pm_mac_ops;
97 95
98/** 96/**
99 * struct iwl_mvm_mod_params - module parameters for iwlmvm 97 * struct iwl_mvm_mod_params - module parameters for iwlmvm
@@ -159,20 +157,6 @@ enum iwl_power_scheme {
159 IEEE80211_WMM_IE_STA_QOSINFO_AC_BE) 157 IEEE80211_WMM_IE_STA_QOSINFO_AC_BE)
160#define IWL_UAPSD_MAX_SP IEEE80211_WMM_IE_STA_QOSINFO_SP_2 158#define IWL_UAPSD_MAX_SP IEEE80211_WMM_IE_STA_QOSINFO_SP_2
161 159
162struct iwl_mvm_power_ops {
163 int (*power_update_mode)(struct iwl_mvm *mvm,
164 struct ieee80211_vif *vif);
165 int (*power_update_device_mode)(struct iwl_mvm *mvm);
166 int (*power_disable)(struct iwl_mvm *mvm, struct ieee80211_vif *vif);
167 void (*power_update_binding)(struct iwl_mvm *mvm,
168 struct ieee80211_vif *vif, bool assign);
169#ifdef CONFIG_IWLWIFI_DEBUGFS
170 int (*power_dbgfs_read)(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
171 char *buf, int bufsz);
172#endif
173};
174
175
176#ifdef CONFIG_IWLWIFI_DEBUGFS 160#ifdef CONFIG_IWLWIFI_DEBUGFS
177enum iwl_dbgfs_pm_mask { 161enum iwl_dbgfs_pm_mask {
178 MVM_DEBUGFS_PM_KEEP_ALIVE = BIT(0), 162 MVM_DEBUGFS_PM_KEEP_ALIVE = BIT(0),
@@ -239,6 +223,19 @@ enum iwl_mvm_smps_type_request {
239 NUM_IWL_MVM_SMPS_REQ, 223 NUM_IWL_MVM_SMPS_REQ,
240}; 224};
241 225
226enum iwl_mvm_ref_type {
227 IWL_MVM_REF_UCODE_DOWN,
228 IWL_MVM_REF_SCAN,
229 IWL_MVM_REF_ROC,
230 IWL_MVM_REF_P2P_CLIENT,
231 IWL_MVM_REF_AP_IBSS,
232 IWL_MVM_REF_USER,
233 IWL_MVM_REF_TX,
234 IWL_MVM_REF_TX_AGG,
235
236 IWL_MVM_REF_COUNT,
237};
238
242/** 239/**
243* struct iwl_mvm_vif_bf_data - beacon filtering related data 240* struct iwl_mvm_vif_bf_data - beacon filtering related data
244* @bf_enabled: indicates if beacon filtering is enabled 241* @bf_enabled: indicates if beacon filtering is enabled
@@ -269,7 +266,9 @@ struct iwl_mvm_vif_bf_data {
269 * @ap_ibss_active: indicates that AP/IBSS is configured and that the interface 266 * @ap_ibss_active: indicates that AP/IBSS is configured and that the interface
270 * should get quota etc. 267 * should get quota etc.
271 * @monitor_active: indicates that monitor context is configured, and that the 268 * @monitor_active: indicates that monitor context is configured, and that the
272 * interface should get quota etc. 269 * interface should get quota etc.
270 * @low_latency: indicates that this interface is in low-latency mode
271 * (VMACLowLatencyMode)
273 * @queue_params: QoS params for this MAC 272 * @queue_params: QoS params for this MAC
274 * @bcast_sta: station used for broadcast packets. Used by the following 273 * @bcast_sta: station used for broadcast packets. Used by the following
275 * vifs: P2P_DEVICE, GO and AP. 274 * vifs: P2P_DEVICE, GO and AP.
@@ -285,6 +284,7 @@ struct iwl_mvm_vif {
285 bool uploaded; 284 bool uploaded;
286 bool ap_ibss_active; 285 bool ap_ibss_active;
287 bool monitor_active; 286 bool monitor_active;
287 bool low_latency;
288 struct iwl_mvm_vif_bf_data bf_data; 288 struct iwl_mvm_vif_bf_data bf_data;
289 289
290 u32 ap_beacon_time; 290 u32 ap_beacon_time;
@@ -319,13 +319,13 @@ struct iwl_mvm_vif {
319 319
320 bool seqno_valid; 320 bool seqno_valid;
321 u16 seqno; 321 u16 seqno;
322#endif
322 323
323#if IS_ENABLED(CONFIG_IPV6) 324#if IS_ENABLED(CONFIG_IPV6)
324 /* IPv6 addresses for WoWLAN */ 325 /* IPv6 addresses for WoWLAN */
325 struct in6_addr target_ipv6_addrs[IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_MAX]; 326 struct in6_addr target_ipv6_addrs[IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_MAX];
326 int num_target_ipv6_addrs; 327 int num_target_ipv6_addrs;
327#endif 328#endif
328#endif
329 329
330#ifdef CONFIG_IWLWIFI_DEBUGFS 330#ifdef CONFIG_IWLWIFI_DEBUGFS
331 struct iwl_mvm *mvm; 331 struct iwl_mvm *mvm;
@@ -333,14 +333,13 @@ struct iwl_mvm_vif {
333 struct dentry *dbgfs_slink; 333 struct dentry *dbgfs_slink;
334 struct iwl_dbgfs_pm dbgfs_pm; 334 struct iwl_dbgfs_pm dbgfs_pm;
335 struct iwl_dbgfs_bf dbgfs_bf; 335 struct iwl_dbgfs_bf dbgfs_bf;
336 struct iwl_mac_power_cmd mac_pwr_cmd;
336#endif 337#endif
337 338
338 enum ieee80211_smps_mode smps_requests[NUM_IWL_MVM_SMPS_REQ]; 339 enum ieee80211_smps_mode smps_requests[NUM_IWL_MVM_SMPS_REQ];
339 340
340 /* FW identified misbehaving AP */ 341 /* FW identified misbehaving AP */
341 u8 uapsd_misbehaving_bssid[ETH_ALEN]; 342 u8 uapsd_misbehaving_bssid[ETH_ALEN];
342
343 bool pm_prevented;
344}; 343};
345 344
346static inline struct iwl_mvm_vif * 345static inline struct iwl_mvm_vif *
@@ -349,6 +348,8 @@ iwl_mvm_vif_from_mac80211(struct ieee80211_vif *vif)
349 return (void *)vif->drv_priv; 348 return (void *)vif->drv_priv;
350} 349}
351 350
351extern const u8 tid_to_mac80211_ac[];
352
352enum iwl_scan_status { 353enum iwl_scan_status {
353 IWL_MVM_SCAN_NONE, 354 IWL_MVM_SCAN_NONE,
354 IWL_MVM_SCAN_OS, 355 IWL_MVM_SCAN_OS,
@@ -415,6 +416,7 @@ struct iwl_tt_params {
415 * @ct_kill_exit: worker to exit thermal kill 416 * @ct_kill_exit: worker to exit thermal kill
416 * @dynamic_smps: Is thermal throttling enabled dynamic_smps? 417 * @dynamic_smps: Is thermal throttling enabled dynamic_smps?
417 * @tx_backoff: The current thremal throttling tx backoff in uSec. 418 * @tx_backoff: The current thremal throttling tx backoff in uSec.
419 * @min_backoff: The minimal tx backoff due to power restrictions
418 * @params: Parameters to configure the thermal throttling algorithm. 420 * @params: Parameters to configure the thermal throttling algorithm.
419 * @throttle: Is thermal throttling is active? 421 * @throttle: Is thermal throttling is active?
420 */ 422 */
@@ -422,10 +424,33 @@ struct iwl_mvm_tt_mgmt {
422 struct delayed_work ct_kill_exit; 424 struct delayed_work ct_kill_exit;
423 bool dynamic_smps; 425 bool dynamic_smps;
424 u32 tx_backoff; 426 u32 tx_backoff;
427 u32 min_backoff;
425 const struct iwl_tt_params *params; 428 const struct iwl_tt_params *params;
426 bool throttle; 429 bool throttle;
427}; 430};
428 431
432#define IWL_MVM_NUM_LAST_FRAMES_UCODE_RATES 8
433
434struct iwl_mvm_frame_stats {
435 u32 legacy_frames;
436 u32 ht_frames;
437 u32 vht_frames;
438 u32 bw_20_frames;
439 u32 bw_40_frames;
440 u32 bw_80_frames;
441 u32 bw_160_frames;
442 u32 sgi_frames;
443 u32 ngi_frames;
444 u32 siso_frames;
445 u32 mimo2_frames;
446 u32 agg_frames;
447 u32 ampdu_count;
448 u32 success_frames;
449 u32 fail_frames;
450 u32 last_rates[IWL_MVM_NUM_LAST_FRAMES_UCODE_RATES];
451 int last_frame_idx;
452};
453
429struct iwl_mvm { 454struct iwl_mvm {
430 /* for logger access */ 455 /* for logger access */
431 struct device *dev; 456 struct device *dev;
@@ -457,6 +482,8 @@ struct iwl_mvm {
457 bool init_ucode_complete; 482 bool init_ucode_complete;
458 u32 error_event_table; 483 u32 error_event_table;
459 u32 log_event_table; 484 u32 log_event_table;
485 u32 umac_error_event_table;
486 bool support_umac_log;
460 487
461 u32 ampdu_ref; 488 u32 ampdu_ref;
462 489
@@ -470,7 +497,7 @@ struct iwl_mvm {
470 497
471 struct iwl_nvm_data *nvm_data; 498 struct iwl_nvm_data *nvm_data;
472 /* NVM sections */ 499 /* NVM sections */
473 struct iwl_nvm_section nvm_sections[NVM_NUM_OF_SECTIONS]; 500 struct iwl_nvm_section nvm_sections[NVM_MAX_NUM_SECTIONS];
474 501
475 /* EEPROM MAC addresses */ 502 /* EEPROM MAC addresses */
476 struct mac_address addresses[IWL_MVM_MAX_ADDRESSES]; 503 struct mac_address addresses[IWL_MVM_MAX_ADDRESSES];
@@ -494,6 +521,17 @@ struct iwl_mvm {
494 /* rx chain antennas set through debugfs for the scan command */ 521 /* rx chain antennas set through debugfs for the scan command */
495 u8 scan_rx_ant; 522 u8 scan_rx_ant;
496 523
524#ifdef CONFIG_IWLWIFI_BCAST_FILTERING
525 /* broadcast filters to configure for each associated station */
526 const struct iwl_fw_bcast_filter *bcast_filters;
527#ifdef CONFIG_IWLWIFI_DEBUGFS
528 struct {
529 u32 override; /* u32 for debugfs_create_bool */
530 struct iwl_bcast_filter_cmd cmd;
531 } dbgfs_bcast_filtering;
532#endif
533#endif
534
497 /* Internal station */ 535 /* Internal station */
498 struct iwl_mvm_int_sta aux_sta; 536 struct iwl_mvm_int_sta aux_sta;
499 537
@@ -506,6 +544,7 @@ struct iwl_mvm {
506#ifdef CONFIG_IWLWIFI_DEBUGFS 544#ifdef CONFIG_IWLWIFI_DEBUGFS
507 struct dentry *debugfs_dir; 545 struct dentry *debugfs_dir;
508 u32 dbgfs_sram_offset, dbgfs_sram_len; 546 u32 dbgfs_sram_offset, dbgfs_sram_len;
547 u32 dbgfs_prph_reg_addr;
509 bool disable_power_off; 548 bool disable_power_off;
510 bool disable_power_off_d3; 549 bool disable_power_off_d3;
511 550
@@ -513,6 +552,9 @@ struct iwl_mvm {
513 struct debugfs_blob_wrapper nvm_sw_blob; 552 struct debugfs_blob_wrapper nvm_sw_blob;
514 struct debugfs_blob_wrapper nvm_calib_blob; 553 struct debugfs_blob_wrapper nvm_calib_blob;
515 struct debugfs_blob_wrapper nvm_prod_blob; 554 struct debugfs_blob_wrapper nvm_prod_blob;
555
556 struct iwl_mvm_frame_stats drv_rx_stats;
557 spinlock_t drv_stats_lock;
516#endif 558#endif
517 559
518 struct iwl_mvm_phy_ctxt phy_ctxts[NUM_PHY_CTX]; 560 struct iwl_mvm_phy_ctxt phy_ctxts[NUM_PHY_CTX];
@@ -526,10 +568,16 @@ struct iwl_mvm {
526 */ 568 */
527 unsigned long fw_key_table[BITS_TO_LONGS(STA_KEY_MAX_NUM)]; 569 unsigned long fw_key_table[BITS_TO_LONGS(STA_KEY_MAX_NUM)];
528 570
571 /* A bitmap of reference types taken by the driver. */
572 unsigned long ref_bitmap[BITS_TO_LONGS(IWL_MVM_REF_COUNT)];
573
529 u8 vif_count; 574 u8 vif_count;
530 575
531 /* -1 for always, 0 for never, >0 for that many times */ 576 /* -1 for always, 0 for never, >0 for that many times */
532 s8 restart_fw; 577 s8 restart_fw;
578 void *fw_error_dump;
579 void *fw_error_sram;
580 u32 fw_error_sram_len;
533 581
534 struct led_classdev led; 582 struct led_classdev led;
535 583
@@ -548,17 +596,27 @@ struct iwl_mvm {
548#endif 596#endif
549#endif 597#endif
550 598
599 /* d0i3 */
600 u8 d0i3_ap_sta_id;
601 bool d0i3_offloading;
602 struct work_struct d0i3_exit_work;
603 struct sk_buff_head d0i3_tx;
604 /* sync d0i3_tx queue and IWL_MVM_STATUS_IN_D0I3 status flag */
605 spinlock_t d0i3_tx_lock;
606 wait_queue_head_t d0i3_exit_waitq;
607
551 /* BT-Coex */ 608 /* BT-Coex */
552 u8 bt_kill_msk; 609 u8 bt_kill_msk;
553 struct iwl_bt_coex_profile_notif last_bt_notif; 610 struct iwl_bt_coex_profile_notif last_bt_notif;
554 struct iwl_bt_coex_ci_cmd last_bt_ci_cmd; 611 struct iwl_bt_coex_ci_cmd last_bt_ci_cmd;
612 u32 last_ant_isol;
613 u8 last_corun_lut;
614 u8 bt_tx_prio;
555 615
556 /* Thermal Throttling and CTkill */ 616 /* Thermal Throttling and CTkill */
557 struct iwl_mvm_tt_mgmt thermal_throttle; 617 struct iwl_mvm_tt_mgmt thermal_throttle;
558 s32 temperature; /* Celsius */ 618 s32 temperature; /* Celsius */
559 619
560 const struct iwl_mvm_power_ops *pm_ops;
561
562#ifdef CONFIG_NL80211_TESTMODE 620#ifdef CONFIG_NL80211_TESTMODE
563 u32 noa_duration; 621 u32 noa_duration;
564 struct ieee80211_vif *noa_vif; 622 struct ieee80211_vif *noa_vif;
@@ -569,10 +627,10 @@ struct iwl_mvm {
569 u8 first_agg_queue; 627 u8 first_agg_queue;
570 u8 last_agg_queue; 628 u8 last_agg_queue;
571 629
572 u8 bound_vif_cnt;
573
574 /* Indicate if device power save is allowed */ 630 /* Indicate if device power save is allowed */
575 bool ps_prevented; 631 bool ps_disabled;
632 /* Indicate if device power management is allowed */
633 bool pm_disabled;
576}; 634};
577 635
578/* Extract MVM priv from op_mode and _hw */ 636/* Extract MVM priv from op_mode and _hw */
@@ -587,6 +645,7 @@ enum iwl_mvm_status {
587 IWL_MVM_STATUS_HW_CTKILL, 645 IWL_MVM_STATUS_HW_CTKILL,
588 IWL_MVM_STATUS_ROC_RUNNING, 646 IWL_MVM_STATUS_ROC_RUNNING,
589 IWL_MVM_STATUS_IN_HW_RESTART, 647 IWL_MVM_STATUS_IN_HW_RESTART,
648 IWL_MVM_STATUS_IN_D0I3,
590}; 649};
591 650
592static inline bool iwl_mvm_is_radio_killed(struct iwl_mvm *mvm) 651static inline bool iwl_mvm_is_radio_killed(struct iwl_mvm *mvm)
@@ -595,6 +654,30 @@ static inline bool iwl_mvm_is_radio_killed(struct iwl_mvm *mvm)
595 test_bit(IWL_MVM_STATUS_HW_CTKILL, &mvm->status); 654 test_bit(IWL_MVM_STATUS_HW_CTKILL, &mvm->status);
596} 655}
597 656
657static inline struct iwl_mvm_sta *
658iwl_mvm_sta_from_staid_protected(struct iwl_mvm *mvm, u8 sta_id)
659{
660 struct ieee80211_sta *sta;
661
662 if (sta_id >= ARRAY_SIZE(mvm->fw_id_to_mac_id))
663 return NULL;
664
665 sta = rcu_dereference_protected(mvm->fw_id_to_mac_id[sta_id],
666 lockdep_is_held(&mvm->mutex));
667
668 /* This can happen if the station has been removed right now */
669 if (IS_ERR_OR_NULL(sta))
670 return NULL;
671
672 return iwl_mvm_sta_from_mac80211(sta);
673}
674
675static inline bool iwl_mvm_is_d0i3_supported(struct iwl_mvm *mvm)
676{
677 return mvm->trans->cfg->d0i3 &&
678 (mvm->fw->ucode_capa.capa[0] & IWL_UCODE_TLV_CAPA_D0I3_SUPPORT);
679}
680
598extern const u8 iwl_mvm_ac_to_tx_fifo[]; 681extern const u8 iwl_mvm_ac_to_tx_fifo[];
599 682
600struct iwl_rate_info { 683struct iwl_rate_info {
@@ -619,7 +702,10 @@ void iwl_mvm_hwrate_to_tx_rate(u32 rate_n_flags,
619 struct ieee80211_tx_rate *r); 702 struct ieee80211_tx_rate *r);
620u8 iwl_mvm_mac80211_idx_to_hwrate(int rate_idx); 703u8 iwl_mvm_mac80211_idx_to_hwrate(int rate_idx);
621void iwl_mvm_dump_nic_error_log(struct iwl_mvm *mvm); 704void iwl_mvm_dump_nic_error_log(struct iwl_mvm *mvm);
622void iwl_mvm_dump_sram(struct iwl_mvm *mvm); 705#ifdef CONFIG_IWLWIFI_DEBUGFS
706void iwl_mvm_fw_error_dump(struct iwl_mvm *mvm);
707void iwl_mvm_fw_error_sram_dump(struct iwl_mvm *mvm);
708#endif
623u8 first_antenna(u8 mask); 709u8 first_antenna(u8 mask);
624u8 iwl_mvm_next_antenna(struct iwl_mvm *mvm, u8 valid, u8 last_idx); 710u8 iwl_mvm_next_antenna(struct iwl_mvm *mvm, u8 valid, u8 last_idx);
625 711
@@ -645,6 +731,11 @@ static inline const char *iwl_mvm_get_tx_fail_reason(u32 status) { return ""; }
645int iwl_mvm_flush_tx_path(struct iwl_mvm *mvm, u32 tfd_msk, bool sync); 731int iwl_mvm_flush_tx_path(struct iwl_mvm *mvm, u32 tfd_msk, bool sync);
646void iwl_mvm_async_handlers_purge(struct iwl_mvm *mvm); 732void iwl_mvm_async_handlers_purge(struct iwl_mvm *mvm);
647 733
734static inline void iwl_mvm_wait_for_async_handlers(struct iwl_mvm *mvm)
735{
736 flush_work(&mvm->async_handlers_wk);
737}
738
648/* Statistics */ 739/* Statistics */
649int iwl_mvm_rx_reply_statistics(struct iwl_mvm *mvm, 740int iwl_mvm_rx_reply_statistics(struct iwl_mvm *mvm,
650 struct iwl_rx_cmd_buffer *rxb, 741 struct iwl_rx_cmd_buffer *rxb,
@@ -661,6 +752,8 @@ int iwl_mvm_up(struct iwl_mvm *mvm);
661int iwl_mvm_load_d3_fw(struct iwl_mvm *mvm); 752int iwl_mvm_load_d3_fw(struct iwl_mvm *mvm);
662 753
663int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm); 754int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm);
755bool iwl_mvm_bcast_filter_build_cmd(struct iwl_mvm *mvm,
756 struct iwl_bcast_filter_cmd *cmd);
664 757
665/* 758/*
666 * FW notifications / CMD responses handlers 759 * FW notifications / CMD responses handlers
@@ -676,6 +769,9 @@ int iwl_mvm_rx_ba_notif(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
676 struct iwl_device_cmd *cmd); 769 struct iwl_device_cmd *cmd);
677int iwl_mvm_rx_radio_ver(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb, 770int iwl_mvm_rx_radio_ver(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
678 struct iwl_device_cmd *cmd); 771 struct iwl_device_cmd *cmd);
772int iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm,
773 struct iwl_rx_cmd_buffer *rxb,
774 struct iwl_device_cmd *cmd);
679int iwl_mvm_rx_fw_error(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb, 775int iwl_mvm_rx_fw_error(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
680 struct iwl_device_cmd *cmd); 776 struct iwl_device_cmd *cmd);
681int iwl_mvm_rx_card_state_notif(struct iwl_mvm *mvm, 777int iwl_mvm_rx_card_state_notif(struct iwl_mvm *mvm,
@@ -730,7 +826,7 @@ int iwl_mvm_rx_scan_response(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
730 struct iwl_device_cmd *cmd); 826 struct iwl_device_cmd *cmd);
731int iwl_mvm_rx_scan_complete(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb, 827int iwl_mvm_rx_scan_complete(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
732 struct iwl_device_cmd *cmd); 828 struct iwl_device_cmd *cmd);
733void iwl_mvm_cancel_scan(struct iwl_mvm *mvm); 829int iwl_mvm_cancel_scan(struct iwl_mvm *mvm);
734 830
735/* Scheduled scan */ 831/* Scheduled scan */
736int iwl_mvm_rx_scan_offload_complete_notif(struct iwl_mvm *mvm, 832int iwl_mvm_rx_scan_offload_complete_notif(struct iwl_mvm *mvm,
@@ -744,7 +840,7 @@ int iwl_mvm_config_sched_scan_profiles(struct iwl_mvm *mvm,
744 struct cfg80211_sched_scan_request *req); 840 struct cfg80211_sched_scan_request *req);
745int iwl_mvm_sched_scan_start(struct iwl_mvm *mvm, 841int iwl_mvm_sched_scan_start(struct iwl_mvm *mvm,
746 struct cfg80211_sched_scan_request *req); 842 struct cfg80211_sched_scan_request *req);
747void iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm); 843int iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm);
748int iwl_mvm_rx_sched_scan_results(struct iwl_mvm *mvm, 844int iwl_mvm_rx_sched_scan_results(struct iwl_mvm *mvm,
749 struct iwl_rx_cmd_buffer *rxb, 845 struct iwl_rx_cmd_buffer *rxb,
750 struct iwl_device_cmd *cmd); 846 struct iwl_device_cmd *cmd);
@@ -772,49 +868,24 @@ iwl_mvm_vif_dbgfs_clean(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
772 868
773/* rate scaling */ 869/* rate scaling */
774int iwl_mvm_send_lq_cmd(struct iwl_mvm *mvm, struct iwl_lq_cmd *lq, bool init); 870int iwl_mvm_send_lq_cmd(struct iwl_mvm *mvm, struct iwl_lq_cmd *lq, bool init);
871void iwl_mvm_update_frame_stats(struct iwl_mvm *mvm,
872 struct iwl_mvm_frame_stats *stats,
873 u32 rate, bool agg);
874int rs_pretty_print_rate(char *buf, const u32 rate);
775 875
776/* power managment */ 876/* power management */
777static inline int iwl_mvm_power_update_mode(struct iwl_mvm *mvm, 877int iwl_power_legacy_set_cam_mode(struct iwl_mvm *mvm);
778 struct ieee80211_vif *vif)
779{
780 return mvm->pm_ops->power_update_mode(mvm, vif);
781}
782
783static inline int iwl_mvm_power_disable(struct iwl_mvm *mvm,
784 struct ieee80211_vif *vif)
785{
786 return mvm->pm_ops->power_disable(mvm, vif);
787}
788
789static inline int iwl_mvm_power_update_device_mode(struct iwl_mvm *mvm)
790{
791 if (mvm->pm_ops->power_update_device_mode)
792 return mvm->pm_ops->power_update_device_mode(mvm);
793 return 0;
794}
795 878
796static inline void iwl_mvm_power_update_binding(struct iwl_mvm *mvm, 879int iwl_mvm_power_update_device(struct iwl_mvm *mvm);
797 struct ieee80211_vif *vif, 880int iwl_mvm_power_update_mac(struct iwl_mvm *mvm, struct ieee80211_vif *vif);
798 bool assign) 881int iwl_mvm_power_mac_dbgfs_read(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
799{ 882 char *buf, int bufsz);
800 if (mvm->pm_ops->power_update_binding)
801 mvm->pm_ops->power_update_binding(mvm, vif, assign);
802}
803 883
804void iwl_mvm_power_vif_assoc(struct iwl_mvm *mvm, struct ieee80211_vif *vif); 884void iwl_mvm_power_vif_assoc(struct iwl_mvm *mvm, struct ieee80211_vif *vif);
805int iwl_mvm_power_uapsd_misbehaving_ap_notif(struct iwl_mvm *mvm, 885int iwl_mvm_power_uapsd_misbehaving_ap_notif(struct iwl_mvm *mvm,
806 struct iwl_rx_cmd_buffer *rxb, 886 struct iwl_rx_cmd_buffer *rxb,
807 struct iwl_device_cmd *cmd); 887 struct iwl_device_cmd *cmd);
808 888
809#ifdef CONFIG_IWLWIFI_DEBUGFS
810static inline int iwl_mvm_power_dbgfs_read(struct iwl_mvm *mvm,
811 struct ieee80211_vif *vif,
812 char *buf, int bufsz)
813{
814 return mvm->pm_ops->power_dbgfs_read(mvm, vif, buf, bufsz);
815}
816#endif
817
818int iwl_mvm_leds_init(struct iwl_mvm *mvm); 889int iwl_mvm_leds_init(struct iwl_mvm *mvm);
819void iwl_mvm_leds_exit(struct iwl_mvm *mvm); 890void iwl_mvm_leds_exit(struct iwl_mvm *mvm);
820 891
@@ -840,6 +911,17 @@ iwl_mvm_set_last_nonqos_seq(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
840{ 911{
841} 912}
842#endif 913#endif
914void iwl_mvm_set_wowlan_qos_seq(struct iwl_mvm_sta *mvm_ap_sta,
915 struct iwl_wowlan_config_cmd_v2 *cmd);
916int iwl_mvm_send_proto_offload(struct iwl_mvm *mvm,
917 struct ieee80211_vif *vif,
918 bool disable_offloading,
919 u32 cmd_flags);
920
921/* D0i3 */
922void iwl_mvm_ref(struct iwl_mvm *mvm, enum iwl_mvm_ref_type ref_type);
923void iwl_mvm_unref(struct iwl_mvm *mvm, enum iwl_mvm_ref_type ref_type);
924void iwl_mvm_d0i3_enable_tx(struct iwl_mvm *mvm, __le16 *qos_seq);
843 925
844/* BT Coex */ 926/* BT Coex */
845int iwl_send_bt_prio_tbl(struct iwl_mvm *mvm); 927int iwl_send_bt_prio_tbl(struct iwl_mvm *mvm);
@@ -850,10 +932,13 @@ int iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm,
850void iwl_mvm_bt_rssi_event(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 932void iwl_mvm_bt_rssi_event(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
851 enum ieee80211_rssi_event rssi_event); 933 enum ieee80211_rssi_event rssi_event);
852void iwl_mvm_bt_coex_vif_change(struct iwl_mvm *mvm); 934void iwl_mvm_bt_coex_vif_change(struct iwl_mvm *mvm);
853u16 iwl_mvm_bt_coex_agg_time_limit(struct iwl_mvm *mvm, 935u16 iwl_mvm_coex_agg_time_limit(struct iwl_mvm *mvm,
854 struct ieee80211_sta *sta); 936 struct ieee80211_sta *sta);
855bool iwl_mvm_bt_coex_is_mimo_allowed(struct iwl_mvm *mvm, 937bool iwl_mvm_bt_coex_is_mimo_allowed(struct iwl_mvm *mvm,
856 struct ieee80211_sta *sta); 938 struct ieee80211_sta *sta);
939u8 iwl_mvm_bt_coex_tx_prio(struct iwl_mvm *mvm, struct ieee80211_hdr *hdr,
940 struct ieee80211_tx_info *info, u8 ac);
941int iwl_mvm_bt_coex_reduced_txp(struct iwl_mvm *mvm, u8 sta_id, bool enable);
857 942
858enum iwl_bt_kill_msk { 943enum iwl_bt_kill_msk {
859 BT_KILL_MSK_DEFAULT, 944 BT_KILL_MSK_DEFAULT,
@@ -875,25 +960,53 @@ iwl_mvm_beacon_filter_debugfs_parameters(struct ieee80211_vif *vif,
875 struct iwl_beacon_filter_cmd *cmd) 960 struct iwl_beacon_filter_cmd *cmd)
876{} 961{}
877#endif 962#endif
963int iwl_mvm_update_d0i3_power_mode(struct iwl_mvm *mvm,
964 struct ieee80211_vif *vif,
965 bool enable, u32 flags);
878int iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm, 966int iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm,
879 struct ieee80211_vif *vif); 967 struct ieee80211_vif *vif,
968 u32 flags);
880int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm, 969int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm,
881 struct ieee80211_vif *vif); 970 struct ieee80211_vif *vif,
882int iwl_mvm_beacon_filter_send_cmd(struct iwl_mvm *mvm, 971 u32 flags);
883 struct iwl_beacon_filter_cmd *cmd);
884int iwl_mvm_update_beacon_abort(struct iwl_mvm *mvm, 972int iwl_mvm_update_beacon_abort(struct iwl_mvm *mvm,
885 struct ieee80211_vif *vif, bool enable); 973 struct ieee80211_vif *vif, bool enable);
886int iwl_mvm_update_beacon_filter(struct iwl_mvm *mvm, 974int iwl_mvm_update_beacon_filter(struct iwl_mvm *mvm,
887 struct ieee80211_vif *vif); 975 struct ieee80211_vif *vif,
976 bool force,
977 u32 flags);
888 978
889/* SMPS */ 979/* SMPS */
890void iwl_mvm_update_smps(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 980void iwl_mvm_update_smps(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
891 enum iwl_mvm_smps_type_request req_type, 981 enum iwl_mvm_smps_type_request req_type,
892 enum ieee80211_smps_mode smps_request); 982 enum ieee80211_smps_mode smps_request);
893 983
984/* Low latency */
985int iwl_mvm_update_low_latency(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
986 bool value);
987/* get SystemLowLatencyMode - only needed for beacon threshold? */
988bool iwl_mvm_low_latency(struct iwl_mvm *mvm);
989/* get VMACLowLatencyMode */
990static inline bool iwl_mvm_vif_low_latency(struct iwl_mvm_vif *mvmvif)
991{
992 /*
993 * should this consider associated/active/... state?
994 *
995 * Normally low-latency should only be active on interfaces
996 * that are active, but at least with debugfs it can also be
997 * enabled on interfaces that aren't active. However, when
998 * interface aren't active then they aren't added into the
999 * binding, so this has no real impact. For now, just return
1000 * the current desired low-latency state.
1001 */
1002
1003 return mvmvif->low_latency;
1004}
1005
894/* Thermal management and CT-kill */ 1006/* Thermal management and CT-kill */
1007void iwl_mvm_tt_tx_backoff(struct iwl_mvm *mvm, u32 backoff);
895void iwl_mvm_tt_handler(struct iwl_mvm *mvm); 1008void iwl_mvm_tt_handler(struct iwl_mvm *mvm);
896void iwl_mvm_tt_initialize(struct iwl_mvm *mvm); 1009void iwl_mvm_tt_initialize(struct iwl_mvm *mvm, u32 min_backoff);
897void iwl_mvm_tt_exit(struct iwl_mvm *mvm); 1010void iwl_mvm_tt_exit(struct iwl_mvm *mvm);
898void iwl_mvm_set_hw_ctkill_state(struct iwl_mvm *mvm, bool state); 1011void iwl_mvm_set_hw_ctkill_state(struct iwl_mvm *mvm, bool state);
899 1012
diff --git a/drivers/net/wireless/iwlwifi/mvm/nvm.c b/drivers/net/wireless/iwlwifi/mvm/nvm.c
index 35b71af78d02..cf2d09f53782 100644
--- a/drivers/net/wireless/iwlwifi/mvm/nvm.c
+++ b/drivers/net/wireless/iwlwifi/mvm/nvm.c
@@ -67,14 +67,6 @@
67#include "iwl-eeprom-read.h" 67#include "iwl-eeprom-read.h"
68#include "iwl-nvm-parse.h" 68#include "iwl-nvm-parse.h"
69 69
70/* list of NVM sections we are allowed/need to read */
71static const int nvm_to_read[] = {
72 NVM_SECTION_TYPE_HW,
73 NVM_SECTION_TYPE_SW,
74 NVM_SECTION_TYPE_CALIBRATION,
75 NVM_SECTION_TYPE_PRODUCTION,
76};
77
78/* Default NVM size to read */ 70/* Default NVM size to read */
79#define IWL_NVM_DEFAULT_CHUNK_SIZE (2*1024) 71#define IWL_NVM_DEFAULT_CHUNK_SIZE (2*1024)
80#define IWL_MAX_NVM_SECTION_SIZE 7000 72#define IWL_MAX_NVM_SECTION_SIZE 7000
@@ -236,24 +228,39 @@ static struct iwl_nvm_data *
236iwl_parse_nvm_sections(struct iwl_mvm *mvm) 228iwl_parse_nvm_sections(struct iwl_mvm *mvm)
237{ 229{
238 struct iwl_nvm_section *sections = mvm->nvm_sections; 230 struct iwl_nvm_section *sections = mvm->nvm_sections;
239 const __le16 *hw, *sw, *calib; 231 const __le16 *hw, *sw, *calib, *regulatory, *mac_override;
240 232
241 /* Checking for required sections */ 233 /* Checking for required sections */
242 if (!mvm->nvm_sections[NVM_SECTION_TYPE_SW].data || 234 if (mvm->trans->cfg->device_family != IWL_DEVICE_FAMILY_8000) {
243 !mvm->nvm_sections[NVM_SECTION_TYPE_HW].data) { 235 if (!mvm->nvm_sections[NVM_SECTION_TYPE_SW].data ||
244 IWL_ERR(mvm, "Can't parse empty NVM sections\n"); 236 !mvm->nvm_sections[mvm->cfg->nvm_hw_section_num].data) {
245 return NULL; 237 IWL_ERR(mvm, "Can't parse empty NVM sections\n");
238 return NULL;
239 }
240 } else {
241 if (!mvm->nvm_sections[NVM_SECTION_TYPE_SW].data ||
242 !mvm->nvm_sections[NVM_SECTION_TYPE_MAC_OVERRIDE].data ||
243 !mvm->nvm_sections[NVM_SECTION_TYPE_REGULATORY].data) {
244 IWL_ERR(mvm,
245 "Can't parse empty family 8000 NVM sections\n");
246 return NULL;
247 }
246 } 248 }
247 249
248 if (WARN_ON(!mvm->cfg)) 250 if (WARN_ON(!mvm->cfg))
249 return NULL; 251 return NULL;
250 252
251 hw = (const __le16 *)sections[NVM_SECTION_TYPE_HW].data; 253 hw = (const __le16 *)sections[mvm->cfg->nvm_hw_section_num].data;
252 sw = (const __le16 *)sections[NVM_SECTION_TYPE_SW].data; 254 sw = (const __le16 *)sections[NVM_SECTION_TYPE_SW].data;
253 calib = (const __le16 *)sections[NVM_SECTION_TYPE_CALIBRATION].data; 255 calib = (const __le16 *)sections[NVM_SECTION_TYPE_CALIBRATION].data;
256 regulatory = (const __le16 *)sections[NVM_SECTION_TYPE_REGULATORY].data;
257 mac_override =
258 (const __le16 *)sections[NVM_SECTION_TYPE_MAC_OVERRIDE].data;
259
254 return iwl_parse_nvm_data(mvm->trans->dev, mvm->cfg, hw, sw, calib, 260 return iwl_parse_nvm_data(mvm->trans->dev, mvm->cfg, hw, sw, calib,
255 iwl_fw_valid_tx_ant(mvm->fw), 261 regulatory, mac_override,
256 iwl_fw_valid_rx_ant(mvm->fw)); 262 mvm->fw->valid_tx_ant,
263 mvm->fw->valid_rx_ant);
257} 264}
258 265
259#define MAX_NVM_FILE_LEN 16384 266#define MAX_NVM_FILE_LEN 16384
@@ -293,6 +300,8 @@ static int iwl_mvm_read_external_nvm(struct iwl_mvm *mvm)
293 300
294#define NVM_WORD1_LEN(x) (8 * (x & 0x03FF)) 301#define NVM_WORD1_LEN(x) (8 * (x & 0x03FF))
295#define NVM_WORD2_ID(x) (x >> 12) 302#define NVM_WORD2_ID(x) (x >> 12)
303#define NVM_WORD2_LEN_FAMILY_8000(x) (2 * ((x & 0xFF) << 8 | x >> 8))
304#define NVM_WORD1_ID_FAMILY_8000(x) (x >> 4)
296 305
297 IWL_DEBUG_EEPROM(mvm->trans->dev, "Read from external NVM\n"); 306 IWL_DEBUG_EEPROM(mvm->trans->dev, "Read from external NVM\n");
298 307
@@ -343,8 +352,16 @@ static int iwl_mvm_read_external_nvm(struct iwl_mvm *mvm)
343 break; 352 break;
344 } 353 }
345 354
346 section_size = 2 * NVM_WORD1_LEN(le16_to_cpu(file_sec->word1)); 355 if (mvm->trans->cfg->device_family != IWL_DEVICE_FAMILY_8000) {
347 section_id = NVM_WORD2_ID(le16_to_cpu(file_sec->word2)); 356 section_size =
357 2 * NVM_WORD1_LEN(le16_to_cpu(file_sec->word1));
358 section_id = NVM_WORD2_ID(le16_to_cpu(file_sec->word2));
359 } else {
360 section_size = 2 * NVM_WORD2_LEN_FAMILY_8000(
361 le16_to_cpu(file_sec->word2));
362 section_id = NVM_WORD1_ID_FAMILY_8000(
363 le16_to_cpu(file_sec->word1));
364 }
348 365
349 if (section_size > IWL_MAX_NVM_SECTION_SIZE) { 366 if (section_size > IWL_MAX_NVM_SECTION_SIZE) {
350 IWL_ERR(mvm, "ERROR - section too large (%d)\n", 367 IWL_ERR(mvm, "ERROR - section too large (%d)\n",
@@ -367,7 +384,7 @@ static int iwl_mvm_read_external_nvm(struct iwl_mvm *mvm)
367 break; 384 break;
368 } 385 }
369 386
370 if (WARN(section_id >= NVM_NUM_OF_SECTIONS, 387 if (WARN(section_id >= NVM_MAX_NUM_SECTIONS,
371 "Invalid NVM section ID %d\n", section_id)) { 388 "Invalid NVM section ID %d\n", section_id)) {
372 ret = -EINVAL; 389 ret = -EINVAL;
373 break; 390 break;
@@ -414,6 +431,11 @@ int iwl_nvm_init(struct iwl_mvm *mvm)
414{ 431{
415 int ret, i, section; 432 int ret, i, section;
416 u8 *nvm_buffer, *temp; 433 u8 *nvm_buffer, *temp;
434 int nvm_to_read[NVM_MAX_NUM_SECTIONS];
435 int num_of_sections_to_read;
436
437 if (WARN_ON_ONCE(mvm->cfg->nvm_hw_section_num >= NVM_MAX_NUM_SECTIONS))
438 return -EINVAL;
417 439
418 /* load external NVM if configured */ 440 /* load external NVM if configured */
419 if (iwlwifi_mod_params.nvm_file) { 441 if (iwlwifi_mod_params.nvm_file) {
@@ -422,6 +444,22 @@ int iwl_nvm_init(struct iwl_mvm *mvm)
422 if (ret) 444 if (ret)
423 return ret; 445 return ret;
424 } else { 446 } else {
447 /* list of NVM sections we are allowed/need to read */
448 if (mvm->trans->cfg->device_family != IWL_DEVICE_FAMILY_8000) {
449 nvm_to_read[0] = mvm->cfg->nvm_hw_section_num;
450 nvm_to_read[1] = NVM_SECTION_TYPE_SW;
451 nvm_to_read[2] = NVM_SECTION_TYPE_CALIBRATION;
452 nvm_to_read[3] = NVM_SECTION_TYPE_PRODUCTION;
453 num_of_sections_to_read = 4;
454 } else {
455 nvm_to_read[0] = NVM_SECTION_TYPE_SW;
456 nvm_to_read[1] = NVM_SECTION_TYPE_CALIBRATION;
457 nvm_to_read[2] = NVM_SECTION_TYPE_PRODUCTION;
458 nvm_to_read[3] = NVM_SECTION_TYPE_REGULATORY;
459 nvm_to_read[4] = NVM_SECTION_TYPE_MAC_OVERRIDE;
460 num_of_sections_to_read = 5;
461 }
462
425 /* Read From FW NVM */ 463 /* Read From FW NVM */
426 IWL_DEBUG_EEPROM(mvm->trans->dev, "Read from NVM\n"); 464 IWL_DEBUG_EEPROM(mvm->trans->dev, "Read from NVM\n");
427 465
@@ -430,7 +468,7 @@ int iwl_nvm_init(struct iwl_mvm *mvm)
430 GFP_KERNEL); 468 GFP_KERNEL);
431 if (!nvm_buffer) 469 if (!nvm_buffer)
432 return -ENOMEM; 470 return -ENOMEM;
433 for (i = 0; i < ARRAY_SIZE(nvm_to_read); i++) { 471 for (i = 0; i < num_of_sections_to_read; i++) {
434 section = nvm_to_read[i]; 472 section = nvm_to_read[i];
435 /* we override the constness for initial read */ 473 /* we override the constness for initial read */
436 ret = iwl_nvm_read_section(mvm, section, nvm_buffer); 474 ret = iwl_nvm_read_section(mvm, section, nvm_buffer);
@@ -446,10 +484,6 @@ int iwl_nvm_init(struct iwl_mvm *mvm)
446 484
447#ifdef CONFIG_IWLWIFI_DEBUGFS 485#ifdef CONFIG_IWLWIFI_DEBUGFS
448 switch (section) { 486 switch (section) {
449 case NVM_SECTION_TYPE_HW:
450 mvm->nvm_hw_blob.data = temp;
451 mvm->nvm_hw_blob.size = ret;
452 break;
453 case NVM_SECTION_TYPE_SW: 487 case NVM_SECTION_TYPE_SW:
454 mvm->nvm_sw_blob.data = temp; 488 mvm->nvm_sw_blob.data = temp;
455 mvm->nvm_sw_blob.size = ret; 489 mvm->nvm_sw_blob.size = ret;
@@ -463,6 +497,11 @@ int iwl_nvm_init(struct iwl_mvm *mvm)
463 mvm->nvm_prod_blob.size = ret; 497 mvm->nvm_prod_blob.size = ret;
464 break; 498 break;
465 default: 499 default:
500 if (section == mvm->cfg->nvm_hw_section_num) {
501 mvm->nvm_hw_blob.data = temp;
502 mvm->nvm_hw_blob.size = ret;
503 break;
504 }
466 WARN(1, "section: %d", section); 505 WARN(1, "section: %d", section);
467 } 506 }
468#endif 507#endif
diff --git a/drivers/net/wireless/iwlwifi/mvm/offloading.c b/drivers/net/wireless/iwlwifi/mvm/offloading.c
new file mode 100644
index 000000000000..9bfb95e89cfb
--- /dev/null
+++ b/drivers/net/wireless/iwlwifi/mvm/offloading.c
@@ -0,0 +1,215 @@
1/******************************************************************************
2 *
3 * This file is provided under a dual BSD/GPLv2 license. When using or
4 * redistributing this file, you may do so under either license.
5 *
6 * GPL LICENSE SUMMARY
7 *
8 * Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of version 2 of the GNU General Public License as
12 * published by the Free Software Foundation.
13 *
14 * This program is distributed in the hope that it will be useful, but
15 * WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110,
22 * USA
23 *
24 * The full GNU General Public License is included in this distribution
25 * in the file called COPYING.
26 *
27 * Contact Information:
28 * Intel Linux Wireless <ilw@linux.intel.com>
29 * Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
30 *
31 * BSD LICENSE
32 *
33 * Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
34 * All rights reserved.
35 *
36 * Redistribution and use in source and binary forms, with or without
37 * modification, are permitted provided that the following conditions
38 * are met:
39 *
40 * * Redistributions of source code must retain the above copyright
41 * notice, this list of conditions and the following disclaimer.
42 * * Redistributions in binary form must reproduce the above copyright
43 * notice, this list of conditions and the following disclaimer in
44 * the documentation and/or other materials provided with the
45 * distribution.
46 * * Neither the name Intel Corporation nor the names of its
47 * contributors may be used to endorse or promote products derived
48 * from this software without specific prior written permission.
49 *
50 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
51 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
52 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
53 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
54 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
55 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
56 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
57 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
58 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
59 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
60 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
61 *
62 *****************************************************************************/
63#include <net/ipv6.h>
64#include <net/addrconf.h>
65#include "mvm.h"
66
67void iwl_mvm_set_wowlan_qos_seq(struct iwl_mvm_sta *mvm_ap_sta,
68 struct iwl_wowlan_config_cmd_v2 *cmd)
69{
70 int i;
71
72 /*
73 * For QoS counters, we store the one to use next, so subtract 0x10
74 * since the uCode will add 0x10 *before* using the value while we
75 * increment after using the value (i.e. store the next value to use).
76 */
77 for (i = 0; i < IWL_MAX_TID_COUNT; i++) {
78 u16 seq = mvm_ap_sta->tid_data[i].seq_number;
79 seq -= 0x10;
80 cmd->qos_seq[i] = cpu_to_le16(seq);
81 }
82}
83
84int iwl_mvm_send_proto_offload(struct iwl_mvm *mvm,
85 struct ieee80211_vif *vif,
86 bool disable_offloading,
87 u32 cmd_flags)
88{
89 union {
90 struct iwl_proto_offload_cmd_v1 v1;
91 struct iwl_proto_offload_cmd_v2 v2;
92 struct iwl_proto_offload_cmd_v3_small v3s;
93 struct iwl_proto_offload_cmd_v3_large v3l;
94 } cmd = {};
95 struct iwl_host_cmd hcmd = {
96 .id = PROT_OFFLOAD_CONFIG_CMD,
97 .flags = cmd_flags,
98 .data[0] = &cmd,
99 .dataflags[0] = IWL_HCMD_DFL_DUP,
100 };
101 struct iwl_proto_offload_cmd_common *common;
102 u32 enabled = 0, size;
103 u32 capa_flags = mvm->fw->ucode_capa.flags;
104#if IS_ENABLED(CONFIG_IPV6)
105 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
106 int i;
107
108 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL ||
109 capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_LARGE) {
110 struct iwl_ns_config *nsc;
111 struct iwl_targ_addr *addrs;
112 int n_nsc, n_addrs;
113 int c;
114
115 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL) {
116 nsc = cmd.v3s.ns_config;
117 n_nsc = IWL_PROTO_OFFLOAD_NUM_NS_CONFIG_V3S;
118 addrs = cmd.v3s.targ_addrs;
119 n_addrs = IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V3S;
120 } else {
121 nsc = cmd.v3l.ns_config;
122 n_nsc = IWL_PROTO_OFFLOAD_NUM_NS_CONFIG_V3L;
123 addrs = cmd.v3l.targ_addrs;
124 n_addrs = IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V3L;
125 }
126
127 if (mvmvif->num_target_ipv6_addrs)
128 enabled |= IWL_D3_PROTO_OFFLOAD_NS;
129
130 /*
131 * For each address we have (and that will fit) fill a target
132 * address struct and combine for NS offload structs with the
133 * solicited node addresses.
134 */
135 for (i = 0, c = 0;
136 i < mvmvif->num_target_ipv6_addrs &&
137 i < n_addrs && c < n_nsc; i++) {
138 struct in6_addr solicited_addr;
139 int j;
140
141 addrconf_addr_solict_mult(&mvmvif->target_ipv6_addrs[i],
142 &solicited_addr);
143 for (j = 0; j < c; j++)
144 if (ipv6_addr_cmp(&nsc[j].dest_ipv6_addr,
145 &solicited_addr) == 0)
146 break;
147 if (j == c)
148 c++;
149 addrs[i].addr = mvmvif->target_ipv6_addrs[i];
150 addrs[i].config_num = cpu_to_le32(j);
151 nsc[j].dest_ipv6_addr = solicited_addr;
152 memcpy(nsc[j].target_mac_addr, vif->addr, ETH_ALEN);
153 }
154
155 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL)
156 cmd.v3s.num_valid_ipv6_addrs = cpu_to_le32(i);
157 else
158 cmd.v3l.num_valid_ipv6_addrs = cpu_to_le32(i);
159 } else if (capa_flags & IWL_UCODE_TLV_FLAGS_D3_6_IPV6_ADDRS) {
160 if (mvmvif->num_target_ipv6_addrs) {
161 enabled |= IWL_D3_PROTO_OFFLOAD_NS;
162 memcpy(cmd.v2.ndp_mac_addr, vif->addr, ETH_ALEN);
163 }
164
165 BUILD_BUG_ON(sizeof(cmd.v2.target_ipv6_addr[0]) !=
166 sizeof(mvmvif->target_ipv6_addrs[0]));
167
168 for (i = 0; i < min(mvmvif->num_target_ipv6_addrs,
169 IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V2); i++)
170 memcpy(cmd.v2.target_ipv6_addr[i],
171 &mvmvif->target_ipv6_addrs[i],
172 sizeof(cmd.v2.target_ipv6_addr[i]));
173 } else {
174 if (mvmvif->num_target_ipv6_addrs) {
175 enabled |= IWL_D3_PROTO_OFFLOAD_NS;
176 memcpy(cmd.v1.ndp_mac_addr, vif->addr, ETH_ALEN);
177 }
178
179 BUILD_BUG_ON(sizeof(cmd.v1.target_ipv6_addr[0]) !=
180 sizeof(mvmvif->target_ipv6_addrs[0]));
181
182 for (i = 0; i < min(mvmvif->num_target_ipv6_addrs,
183 IWL_PROTO_OFFLOAD_NUM_IPV6_ADDRS_V1); i++)
184 memcpy(cmd.v1.target_ipv6_addr[i],
185 &mvmvif->target_ipv6_addrs[i],
186 sizeof(cmd.v1.target_ipv6_addr[i]));
187 }
188#endif
189
190 if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_SMALL) {
191 common = &cmd.v3s.common;
192 size = sizeof(cmd.v3s);
193 } else if (capa_flags & IWL_UCODE_TLV_FLAGS_NEW_NSOFFL_LARGE) {
194 common = &cmd.v3l.common;
195 size = sizeof(cmd.v3l);
196 } else if (capa_flags & IWL_UCODE_TLV_FLAGS_D3_6_IPV6_ADDRS) {
197 common = &cmd.v2.common;
198 size = sizeof(cmd.v2);
199 } else {
200 common = &cmd.v1.common;
201 size = sizeof(cmd.v1);
202 }
203
204 if (vif->bss_conf.arp_addr_cnt) {
205 enabled |= IWL_D3_PROTO_OFFLOAD_ARP;
206 common->host_ipv4_addr = vif->bss_conf.arp_addr_list[0];
207 memcpy(common->arp_mac_addr, vif->addr, ETH_ALEN);
208 }
209
210 if (!disable_offloading)
211 common->enabled = cpu_to_le32(enabled);
212
213 hcmd.len[0] = size;
214 return iwl_mvm_send_cmd(mvm, &hcmd);
215}
diff --git a/drivers/net/wireless/iwlwifi/mvm/ops.c b/drivers/net/wireless/iwlwifi/mvm/ops.c
index a3d43de342d7..9545d7fdd4bf 100644
--- a/drivers/net/wireless/iwlwifi/mvm/ops.c
+++ b/drivers/net/wireless/iwlwifi/mvm/ops.c
@@ -61,6 +61,7 @@
61 * 61 *
62 *****************************************************************************/ 62 *****************************************************************************/
63#include <linux/module.h> 63#include <linux/module.h>
64#include <linux/vmalloc.h>
64#include <net/mac80211.h> 65#include <net/mac80211.h>
65 66
66#include "iwl-notif-wait.h" 67#include "iwl-notif-wait.h"
@@ -78,6 +79,7 @@
78#include "iwl-prph.h" 79#include "iwl-prph.h"
79#include "rs.h" 80#include "rs.h"
80#include "fw-api-scan.h" 81#include "fw-api-scan.h"
82#include "fw-error-dump.h"
81#include "time-event.h" 83#include "time-event.h"
82 84
83/* 85/*
@@ -185,9 +187,10 @@ static void iwl_mvm_nic_config(struct iwl_op_mode *op_mode)
185 * (PCIe power is lost before PERST# is asserted), causing ME FW 187 * (PCIe power is lost before PERST# is asserted), causing ME FW
186 * to lose ownership and not being able to obtain it back. 188 * to lose ownership and not being able to obtain it back.
187 */ 189 */
188 iwl_set_bits_mask_prph(mvm->trans, APMG_PS_CTRL_REG, 190 if (mvm->trans->cfg->device_family != IWL_DEVICE_FAMILY_8000)
189 APMG_PS_CTRL_EARLY_PWR_OFF_RESET_DIS, 191 iwl_set_bits_mask_prph(mvm->trans, APMG_PS_CTRL_REG,
190 ~APMG_PS_CTRL_EARLY_PWR_OFF_RESET_DIS); 192 APMG_PS_CTRL_EARLY_PWR_OFF_RESET_DIS,
193 ~APMG_PS_CTRL_EARLY_PWR_OFF_RESET_DIS);
191} 194}
192 195
193struct iwl_rx_handlers { 196struct iwl_rx_handlers {
@@ -219,13 +222,17 @@ static const struct iwl_rx_handlers iwl_mvm_rx_handlers[] = {
219 RX_HANDLER(BT_PROFILE_NOTIFICATION, iwl_mvm_rx_bt_coex_notif, true), 222 RX_HANDLER(BT_PROFILE_NOTIFICATION, iwl_mvm_rx_bt_coex_notif, true),
220 RX_HANDLER(BEACON_NOTIFICATION, iwl_mvm_rx_beacon_notif, false), 223 RX_HANDLER(BEACON_NOTIFICATION, iwl_mvm_rx_beacon_notif, false),
221 RX_HANDLER(STATISTICS_NOTIFICATION, iwl_mvm_rx_statistics, true), 224 RX_HANDLER(STATISTICS_NOTIFICATION, iwl_mvm_rx_statistics, true),
225 RX_HANDLER(ANTENNA_COUPLING_NOTIFICATION,
226 iwl_mvm_rx_ant_coupling_notif, true),
222 227
223 RX_HANDLER(TIME_EVENT_NOTIFICATION, iwl_mvm_rx_time_event_notif, false), 228 RX_HANDLER(TIME_EVENT_NOTIFICATION, iwl_mvm_rx_time_event_notif, false),
224 229
230 RX_HANDLER(EOSP_NOTIFICATION, iwl_mvm_rx_eosp_notif, false),
231
225 RX_HANDLER(SCAN_REQUEST_CMD, iwl_mvm_rx_scan_response, false), 232 RX_HANDLER(SCAN_REQUEST_CMD, iwl_mvm_rx_scan_response, false),
226 RX_HANDLER(SCAN_COMPLETE_NOTIFICATION, iwl_mvm_rx_scan_complete, false), 233 RX_HANDLER(SCAN_COMPLETE_NOTIFICATION, iwl_mvm_rx_scan_complete, true),
227 RX_HANDLER(SCAN_OFFLOAD_COMPLETE, 234 RX_HANDLER(SCAN_OFFLOAD_COMPLETE,
228 iwl_mvm_rx_scan_offload_complete_notif, false), 235 iwl_mvm_rx_scan_offload_complete_notif, true),
229 RX_HANDLER(MATCH_FOUND_NOTIFICATION, iwl_mvm_rx_sched_scan_results, 236 RX_HANDLER(MATCH_FOUND_NOTIFICATION, iwl_mvm_rx_sched_scan_results,
230 false), 237 false),
231 238
@@ -242,7 +249,7 @@ static const struct iwl_rx_handlers iwl_mvm_rx_handlers[] = {
242#undef RX_HANDLER 249#undef RX_HANDLER
243#define CMD(x) [x] = #x 250#define CMD(x) [x] = #x
244 251
245static const char *iwl_mvm_cmd_strings[REPLY_MAX] = { 252static const char *const iwl_mvm_cmd_strings[REPLY_MAX] = {
246 CMD(MVM_ALIVE), 253 CMD(MVM_ALIVE),
247 CMD(REPLY_ERROR), 254 CMD(REPLY_ERROR),
248 CMD(INIT_COMPLETE_NOTIF), 255 CMD(INIT_COMPLETE_NOTIF),
@@ -284,9 +291,11 @@ static const char *iwl_mvm_cmd_strings[REPLY_MAX] = {
284 CMD(BEACON_NOTIFICATION), 291 CMD(BEACON_NOTIFICATION),
285 CMD(BEACON_TEMPLATE_CMD), 292 CMD(BEACON_TEMPLATE_CMD),
286 CMD(STATISTICS_NOTIFICATION), 293 CMD(STATISTICS_NOTIFICATION),
294 CMD(EOSP_NOTIFICATION),
287 CMD(REDUCE_TX_POWER_CMD), 295 CMD(REDUCE_TX_POWER_CMD),
288 CMD(TX_ANT_CONFIGURATION_CMD), 296 CMD(TX_ANT_CONFIGURATION_CMD),
289 CMD(D3_CONFIG_CMD), 297 CMD(D3_CONFIG_CMD),
298 CMD(D0I3_END_CMD),
290 CMD(PROT_OFFLOAD_CONFIG_CMD), 299 CMD(PROT_OFFLOAD_CONFIG_CMD),
291 CMD(OFFLOADS_QUERY_CMD), 300 CMD(OFFLOADS_QUERY_CMD),
292 CMD(REMOTE_WAKE_CONFIG_CMD), 301 CMD(REMOTE_WAKE_CONFIG_CMD),
@@ -309,17 +318,37 @@ static const char *iwl_mvm_cmd_strings[REPLY_MAX] = {
309 CMD(BT_PROFILE_NOTIFICATION), 318 CMD(BT_PROFILE_NOTIFICATION),
310 CMD(BT_CONFIG), 319 CMD(BT_CONFIG),
311 CMD(MCAST_FILTER_CMD), 320 CMD(MCAST_FILTER_CMD),
321 CMD(BCAST_FILTER_CMD),
312 CMD(REPLY_SF_CFG_CMD), 322 CMD(REPLY_SF_CFG_CMD),
313 CMD(REPLY_BEACON_FILTERING_CMD), 323 CMD(REPLY_BEACON_FILTERING_CMD),
314 CMD(REPLY_THERMAL_MNG_BACKOFF), 324 CMD(REPLY_THERMAL_MNG_BACKOFF),
315 CMD(MAC_PM_POWER_TABLE), 325 CMD(MAC_PM_POWER_TABLE),
316 CMD(BT_COEX_CI), 326 CMD(BT_COEX_CI),
317 CMD(PSM_UAPSD_AP_MISBEHAVING_NOTIFICATION), 327 CMD(PSM_UAPSD_AP_MISBEHAVING_NOTIFICATION),
328 CMD(ANTENNA_COUPLING_NOTIFICATION),
318}; 329};
319#undef CMD 330#undef CMD
320 331
321/* this forward declaration can avoid to export the function */ 332/* this forward declaration can avoid to export the function */
322static void iwl_mvm_async_handlers_wk(struct work_struct *wk); 333static void iwl_mvm_async_handlers_wk(struct work_struct *wk);
334static void iwl_mvm_d0i3_exit_work(struct work_struct *wk);
335
336static u32 calc_min_backoff(struct iwl_trans *trans, const struct iwl_cfg *cfg)
337{
338 const struct iwl_pwr_tx_backoff *pwr_tx_backoff = cfg->pwr_tx_backoffs;
339
340 if (!pwr_tx_backoff)
341 return 0;
342
343 while (pwr_tx_backoff->pwr) {
344 if (trans->dflt_pwr_limit >= pwr_tx_backoff->pwr)
345 return pwr_tx_backoff->backoff;
346
347 pwr_tx_backoff++;
348 }
349
350 return 0;
351}
323 352
324static struct iwl_op_mode * 353static struct iwl_op_mode *
325iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg, 354iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
@@ -333,6 +362,14 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
333 TX_CMD, 362 TX_CMD,
334 }; 363 };
335 int err, scan_size; 364 int err, scan_size;
365 u32 min_backoff;
366
367 /*
368 * We use IWL_MVM_STATION_COUNT to check the validity of the station
369 * index all over the driver - check that its value corresponds to the
370 * array size.
371 */
372 BUILD_BUG_ON(ARRAY_SIZE(mvm->fw_id_to_mac_id) != IWL_MVM_STATION_COUNT);
336 373
337 /******************************** 374 /********************************
338 * 1. Allocating and configuring HW data 375 * 1. Allocating and configuring HW data
@@ -373,6 +410,11 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
373 INIT_WORK(&mvm->async_handlers_wk, iwl_mvm_async_handlers_wk); 410 INIT_WORK(&mvm->async_handlers_wk, iwl_mvm_async_handlers_wk);
374 INIT_WORK(&mvm->roc_done_wk, iwl_mvm_roc_done_wk); 411 INIT_WORK(&mvm->roc_done_wk, iwl_mvm_roc_done_wk);
375 INIT_WORK(&mvm->sta_drained_wk, iwl_mvm_sta_drained_wk); 412 INIT_WORK(&mvm->sta_drained_wk, iwl_mvm_sta_drained_wk);
413 INIT_WORK(&mvm->d0i3_exit_work, iwl_mvm_d0i3_exit_work);
414
415 spin_lock_init(&mvm->d0i3_tx_lock);
416 skb_queue_head_init(&mvm->d0i3_tx);
417 init_waitqueue_head(&mvm->d0i3_exit_waitq);
376 418
377 SET_IEEE80211_DEV(mvm->hw, mvm->trans->dev); 419 SET_IEEE80211_DEV(mvm->hw, mvm->trans->dev);
378 420
@@ -421,7 +463,8 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
421 IWL_INFO(mvm, "Detected %s, REV=0x%X\n", 463 IWL_INFO(mvm, "Detected %s, REV=0x%X\n",
422 mvm->cfg->name, mvm->trans->hw_rev); 464 mvm->cfg->name, mvm->trans->hw_rev);
423 465
424 iwl_mvm_tt_initialize(mvm); 466 min_backoff = calc_min_backoff(trans, cfg);
467 iwl_mvm_tt_initialize(mvm, min_backoff);
425 468
426 /* 469 /*
427 * If the NVM exists in an external file, 470 * If the NVM exists in an external file,
@@ -462,13 +505,11 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
462 if (err) 505 if (err)
463 goto out_unregister; 506 goto out_unregister;
464 507
465 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_PM_CMD_SUPPORT)
466 mvm->pm_ops = &pm_mac_ops;
467 else
468 mvm->pm_ops = &pm_legacy_ops;
469
470 memset(&mvm->rx_stats, 0, sizeof(struct mvm_statistics_rx)); 508 memset(&mvm->rx_stats, 0, sizeof(struct mvm_statistics_rx));
471 509
510 /* rpm starts with a taken ref. only set the appropriate bit here. */
511 set_bit(IWL_MVM_REF_UCODE_DOWN, mvm->ref_bitmap);
512
472 return op_mode; 513 return op_mode;
473 514
474 out_unregister: 515 out_unregister:
@@ -495,6 +536,8 @@ static void iwl_op_mode_mvm_stop(struct iwl_op_mode *op_mode)
495 ieee80211_unregister_hw(mvm->hw); 536 ieee80211_unregister_hw(mvm->hw);
496 537
497 kfree(mvm->scan_cmd); 538 kfree(mvm->scan_cmd);
539 vfree(mvm->fw_error_dump);
540 kfree(mvm->fw_error_sram);
498 kfree(mvm->mcast_filter_cmd); 541 kfree(mvm->mcast_filter_cmd);
499 mvm->mcast_filter_cmd = NULL; 542 mvm->mcast_filter_cmd = NULL;
500 543
@@ -508,7 +551,7 @@ static void iwl_op_mode_mvm_stop(struct iwl_op_mode *op_mode)
508 mvm->phy_db = NULL; 551 mvm->phy_db = NULL;
509 552
510 iwl_free_nvm_data(mvm->nvm_data); 553 iwl_free_nvm_data(mvm->nvm_data);
511 for (i = 0; i < NVM_NUM_OF_SECTIONS; i++) 554 for (i = 0; i < NVM_MAX_NUM_SECTIONS; i++)
512 kfree(mvm->nvm_sections[i].data); 555 kfree(mvm->nvm_sections[i].data);
513 556
514 ieee80211_free_hw(mvm->hw); 557 ieee80211_free_hw(mvm->hw);
@@ -658,7 +701,7 @@ void iwl_mvm_set_hw_ctkill_state(struct iwl_mvm *mvm, bool state)
658 wiphy_rfkill_set_hw_state(mvm->hw->wiphy, iwl_mvm_is_radio_killed(mvm)); 701 wiphy_rfkill_set_hw_state(mvm->hw->wiphy, iwl_mvm_is_radio_killed(mvm));
659} 702}
660 703
661static void iwl_mvm_set_hw_rfkill_state(struct iwl_op_mode *op_mode, bool state) 704static bool iwl_mvm_set_hw_rfkill_state(struct iwl_op_mode *op_mode, bool state)
662{ 705{
663 struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode); 706 struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
664 707
@@ -667,9 +710,9 @@ static void iwl_mvm_set_hw_rfkill_state(struct iwl_op_mode *op_mode, bool state)
667 else 710 else
668 clear_bit(IWL_MVM_STATUS_HW_RFKILL, &mvm->status); 711 clear_bit(IWL_MVM_STATUS_HW_RFKILL, &mvm->status);
669 712
670 if (state && mvm->cur_ucode != IWL_UCODE_INIT)
671 iwl_trans_stop_device(mvm->trans);
672 wiphy_rfkill_set_hw_state(mvm->hw->wiphy, iwl_mvm_is_radio_killed(mvm)); 713 wiphy_rfkill_set_hw_state(mvm->hw->wiphy, iwl_mvm_is_radio_killed(mvm));
714
715 return state && mvm->cur_ucode != IWL_UCODE_INIT;
673} 716}
674 717
675static void iwl_mvm_free_skb(struct iwl_op_mode *op_mode, struct sk_buff *skb) 718static void iwl_mvm_free_skb(struct iwl_op_mode *op_mode, struct sk_buff *skb)
@@ -703,6 +746,29 @@ static void iwl_mvm_nic_restart(struct iwl_mvm *mvm)
703 iwl_abort_notification_waits(&mvm->notif_wait); 746 iwl_abort_notification_waits(&mvm->notif_wait);
704 747
705 /* 748 /*
749 * This is a bit racy, but worst case we tell mac80211 about
750 * a stopped/aborted scan when that was already done which
751 * is not a problem. It is necessary to abort any os scan
752 * here because mac80211 requires having the scan cleared
753 * before restarting.
754 * We'll reset the scan_status to NONE in restart cleanup in
755 * the next start() call from mac80211. If restart isn't called
756 * (no fw restart) scan status will stay busy.
757 */
758 switch (mvm->scan_status) {
759 case IWL_MVM_SCAN_NONE:
760 break;
761 case IWL_MVM_SCAN_OS:
762 ieee80211_scan_completed(mvm->hw, true);
763 break;
764 case IWL_MVM_SCAN_SCHED:
765 /* Sched scan will be restarted by mac80211 in restart_hw. */
766 if (!mvm->restart_fw)
767 ieee80211_sched_scan_stopped(mvm->hw);
768 break;
769 }
770
771 /*
706 * If we're restarting already, don't cycle restarts. 772 * If we're restarting already, don't cycle restarts.
707 * If INIT fw asserted, it will likely fail again. 773 * If INIT fw asserted, it will likely fail again.
708 * If WoWLAN fw asserted, don't restart either, mac80211 774 * If WoWLAN fw asserted, don't restart either, mac80211
@@ -733,25 +799,8 @@ static void iwl_mvm_nic_restart(struct iwl_mvm *mvm)
733 INIT_WORK(&reprobe->work, iwl_mvm_reprobe_wk); 799 INIT_WORK(&reprobe->work, iwl_mvm_reprobe_wk);
734 schedule_work(&reprobe->work); 800 schedule_work(&reprobe->work);
735 } else if (mvm->cur_ucode == IWL_UCODE_REGULAR && mvm->restart_fw) { 801 } else if (mvm->cur_ucode == IWL_UCODE_REGULAR && mvm->restart_fw) {
736 /* 802 /* don't let the transport/FW power down */
737 * This is a bit racy, but worst case we tell mac80211 about 803 iwl_mvm_ref(mvm, IWL_MVM_REF_UCODE_DOWN);
738 * a stopped/aborted (sched) scan when that was already done
739 * which is not a problem. It is necessary to abort any scan
740 * here because mac80211 requires having the scan cleared
741 * before restarting.
742 * We'll reset the scan_status to NONE in restart cleanup in
743 * the next start() call from mac80211.
744 */
745 switch (mvm->scan_status) {
746 case IWL_MVM_SCAN_NONE:
747 break;
748 case IWL_MVM_SCAN_OS:
749 ieee80211_scan_completed(mvm->hw, true);
750 break;
751 case IWL_MVM_SCAN_SCHED:
752 ieee80211_sched_scan_stopped(mvm->hw);
753 break;
754 }
755 804
756 if (mvm->restart_fw > 0) 805 if (mvm->restart_fw > 0)
757 mvm->restart_fw--; 806 mvm->restart_fw--;
@@ -759,13 +808,52 @@ static void iwl_mvm_nic_restart(struct iwl_mvm *mvm)
759 } 808 }
760} 809}
761 810
811#ifdef CONFIG_IWLWIFI_DEBUGFS
812void iwl_mvm_fw_error_dump(struct iwl_mvm *mvm)
813{
814 struct iwl_fw_error_dump_file *dump_file;
815 struct iwl_fw_error_dump_data *dump_data;
816 u32 file_len;
817
818 lockdep_assert_held(&mvm->mutex);
819
820 if (mvm->fw_error_dump)
821 return;
822
823 file_len = mvm->fw_error_sram_len +
824 sizeof(*dump_file) +
825 sizeof(*dump_data);
826
827 dump_file = vmalloc(file_len);
828 if (!dump_file)
829 return;
830
831 mvm->fw_error_dump = dump_file;
832
833 dump_file->barker = cpu_to_le32(IWL_FW_ERROR_DUMP_BARKER);
834 dump_file->file_len = cpu_to_le32(file_len);
835 dump_data = (void *)dump_file->data;
836 dump_data->type = IWL_FW_ERROR_DUMP_SRAM;
837 dump_data->len = cpu_to_le32(mvm->fw_error_sram_len);
838
839 /*
840 * No need for lock since at the stage the FW isn't loaded. So it
841 * can't assert - we are the only one who can possibly be accessing
842 * mvm->fw_error_sram right now.
843 */
844 memcpy(dump_data->data, mvm->fw_error_sram, mvm->fw_error_sram_len);
845}
846#endif
847
762static void iwl_mvm_nic_error(struct iwl_op_mode *op_mode) 848static void iwl_mvm_nic_error(struct iwl_op_mode *op_mode)
763{ 849{
764 struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode); 850 struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
765 851
766 iwl_mvm_dump_nic_error_log(mvm); 852 iwl_mvm_dump_nic_error_log(mvm);
767 if (!mvm->restart_fw) 853
768 iwl_mvm_dump_sram(mvm); 854#ifdef CONFIG_IWLWIFI_DEBUGFS
855 iwl_mvm_fw_error_sram_dump(mvm);
856#endif
769 857
770 iwl_mvm_nic_restart(mvm); 858 iwl_mvm_nic_restart(mvm);
771} 859}
@@ -778,6 +866,323 @@ static void iwl_mvm_cmd_queue_full(struct iwl_op_mode *op_mode)
778 iwl_mvm_nic_restart(mvm); 866 iwl_mvm_nic_restart(mvm);
779} 867}
780 868
869struct iwl_d0i3_iter_data {
870 struct iwl_mvm *mvm;
871 u8 ap_sta_id;
872 u8 vif_count;
873 u8 offloading_tid;
874 bool disable_offloading;
875};
876
877static bool iwl_mvm_disallow_offloading(struct iwl_mvm *mvm,
878 struct ieee80211_vif *vif,
879 struct iwl_d0i3_iter_data *iter_data)
880{
881 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
882 struct ieee80211_sta *ap_sta;
883 struct iwl_mvm_sta *mvmsta;
884 u32 available_tids = 0;
885 u8 tid;
886
887 if (WARN_ON(vif->type != NL80211_IFTYPE_STATION ||
888 mvmvif->ap_sta_id == IWL_MVM_STATION_COUNT))
889 return false;
890
891 ap_sta = rcu_dereference(mvm->fw_id_to_mac_id[mvmvif->ap_sta_id]);
892 if (IS_ERR_OR_NULL(ap_sta))
893 return false;
894
895 mvmsta = iwl_mvm_sta_from_mac80211(ap_sta);
896 spin_lock_bh(&mvmsta->lock);
897 for (tid = 0; tid < IWL_MAX_TID_COUNT; tid++) {
898 struct iwl_mvm_tid_data *tid_data = &mvmsta->tid_data[tid];
899
900 /*
901 * in case of pending tx packets, don't use this tid
902 * for offloading in order to prevent reuse of the same
903 * qos seq counters.
904 */
905 if (iwl_mvm_tid_queued(tid_data))
906 continue;
907
908 if (tid_data->state != IWL_AGG_OFF)
909 continue;
910
911 available_tids |= BIT(tid);
912 }
913 spin_unlock_bh(&mvmsta->lock);
914
915 /*
916 * disallow protocol offloading if we have no available tid
917 * (with no pending frames and no active aggregation,
918 * as we don't handle "holes" properly - the scheduler needs the
919 * frame's seq number and TFD index to match)
920 */
921 if (!available_tids)
922 return true;
923
924 /* for simplicity, just use the first available tid */
925 iter_data->offloading_tid = ffs(available_tids) - 1;
926 return false;
927}
928
929static void iwl_mvm_enter_d0i3_iterator(void *_data, u8 *mac,
930 struct ieee80211_vif *vif)
931{
932 struct iwl_d0i3_iter_data *data = _data;
933 struct iwl_mvm *mvm = data->mvm;
934 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
935 u32 flags = CMD_ASYNC | CMD_HIGH_PRIO | CMD_SEND_IN_IDLE;
936
937 IWL_DEBUG_RPM(mvm, "entering D0i3 - vif %pM\n", vif->addr);
938 if (vif->type != NL80211_IFTYPE_STATION ||
939 !vif->bss_conf.assoc)
940 return;
941
942 /*
943 * in case of pending tx packets or active aggregations,
944 * avoid offloading features in order to prevent reuse of
945 * the same qos seq counters.
946 */
947 if (iwl_mvm_disallow_offloading(mvm, vif, data))
948 data->disable_offloading = true;
949
950 iwl_mvm_update_d0i3_power_mode(mvm, vif, true, flags);
951 iwl_mvm_send_proto_offload(mvm, vif, data->disable_offloading, flags);
952
953 /*
954 * on init/association, mvm already configures POWER_TABLE_CMD
955 * and REPLY_MCAST_FILTER_CMD, so currently don't
956 * reconfigure them (we might want to use different
957 * params later on, though).
958 */
959 data->ap_sta_id = mvmvif->ap_sta_id;
960 data->vif_count++;
961}
962
963static void iwl_mvm_set_wowlan_data(struct iwl_mvm *mvm,
964 struct iwl_wowlan_config_cmd_v3 *cmd,
965 struct iwl_d0i3_iter_data *iter_data)
966{
967 struct ieee80211_sta *ap_sta;
968 struct iwl_mvm_sta *mvm_ap_sta;
969
970 if (iter_data->ap_sta_id == IWL_MVM_STATION_COUNT)
971 return;
972
973 rcu_read_lock();
974
975 ap_sta = rcu_dereference(mvm->fw_id_to_mac_id[iter_data->ap_sta_id]);
976 if (IS_ERR_OR_NULL(ap_sta))
977 goto out;
978
979 mvm_ap_sta = iwl_mvm_sta_from_mac80211(ap_sta);
980 cmd->common.is_11n_connection = ap_sta->ht_cap.ht_supported;
981 cmd->offloading_tid = iter_data->offloading_tid;
982
983 /*
984 * The d0i3 uCode takes care of the nonqos counters,
985 * so configure only the qos seq ones.
986 */
987 iwl_mvm_set_wowlan_qos_seq(mvm_ap_sta, &cmd->common);
988out:
989 rcu_read_unlock();
990}
991static int iwl_mvm_enter_d0i3(struct iwl_op_mode *op_mode)
992{
993 struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
994 u32 flags = CMD_ASYNC | CMD_HIGH_PRIO | CMD_SEND_IN_IDLE;
995 int ret;
996 struct iwl_d0i3_iter_data d0i3_iter_data = {
997 .mvm = mvm,
998 };
999 struct iwl_wowlan_config_cmd_v3 wowlan_config_cmd = {
1000 .common = {
1001 .wakeup_filter =
1002 cpu_to_le32(IWL_WOWLAN_WAKEUP_RX_FRAME |
1003 IWL_WOWLAN_WAKEUP_BEACON_MISS |
1004 IWL_WOWLAN_WAKEUP_LINK_CHANGE |
1005 IWL_WOWLAN_WAKEUP_BCN_FILTERING),
1006 },
1007 };
1008 struct iwl_d3_manager_config d3_cfg_cmd = {
1009 .min_sleep_time = cpu_to_le32(1000),
1010 };
1011
1012 IWL_DEBUG_RPM(mvm, "MVM entering D0i3\n");
1013
1014 /* make sure we have no running tx while configuring the qos */
1015 set_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status);
1016 synchronize_net();
1017
1018 ieee80211_iterate_active_interfaces_atomic(mvm->hw,
1019 IEEE80211_IFACE_ITER_NORMAL,
1020 iwl_mvm_enter_d0i3_iterator,
1021 &d0i3_iter_data);
1022 if (d0i3_iter_data.vif_count == 1) {
1023 mvm->d0i3_ap_sta_id = d0i3_iter_data.ap_sta_id;
1024 mvm->d0i3_offloading = !d0i3_iter_data.disable_offloading;
1025 } else {
1026 WARN_ON_ONCE(d0i3_iter_data.vif_count > 1);
1027 mvm->d0i3_ap_sta_id = IWL_MVM_STATION_COUNT;
1028 mvm->d0i3_offloading = false;
1029 }
1030
1031 iwl_mvm_set_wowlan_data(mvm, &wowlan_config_cmd, &d0i3_iter_data);
1032 ret = iwl_mvm_send_cmd_pdu(mvm, WOWLAN_CONFIGURATION, flags,
1033 sizeof(wowlan_config_cmd),
1034 &wowlan_config_cmd);
1035 if (ret)
1036 return ret;
1037
1038 return iwl_mvm_send_cmd_pdu(mvm, D3_CONFIG_CMD,
1039 flags | CMD_MAKE_TRANS_IDLE,
1040 sizeof(d3_cfg_cmd), &d3_cfg_cmd);
1041}
1042
1043static void iwl_mvm_exit_d0i3_iterator(void *_data, u8 *mac,
1044 struct ieee80211_vif *vif)
1045{
1046 struct iwl_mvm *mvm = _data;
1047 u32 flags = CMD_ASYNC | CMD_HIGH_PRIO;
1048
1049 IWL_DEBUG_RPM(mvm, "exiting D0i3 - vif %pM\n", vif->addr);
1050 if (vif->type != NL80211_IFTYPE_STATION ||
1051 !vif->bss_conf.assoc)
1052 return;
1053
1054 iwl_mvm_update_d0i3_power_mode(mvm, vif, false, flags);
1055}
1056
1057static void iwl_mvm_d0i3_disconnect_iter(void *data, u8 *mac,
1058 struct ieee80211_vif *vif)
1059{
1060 struct iwl_mvm *mvm = data;
1061 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
1062
1063 if (vif->type == NL80211_IFTYPE_STATION && vif->bss_conf.assoc &&
1064 mvm->d0i3_ap_sta_id == mvmvif->ap_sta_id)
1065 ieee80211_connection_loss(vif);
1066}
1067
1068void iwl_mvm_d0i3_enable_tx(struct iwl_mvm *mvm, __le16 *qos_seq)
1069{
1070 struct ieee80211_sta *sta = NULL;
1071 struct iwl_mvm_sta *mvm_ap_sta;
1072 int i;
1073 bool wake_queues = false;
1074
1075 lockdep_assert_held(&mvm->mutex);
1076
1077 spin_lock_bh(&mvm->d0i3_tx_lock);
1078
1079 if (mvm->d0i3_ap_sta_id == IWL_MVM_STATION_COUNT)
1080 goto out;
1081
1082 IWL_DEBUG_RPM(mvm, "re-enqueue packets\n");
1083
1084 /* get the sta in order to update seq numbers and re-enqueue skbs */
1085 sta = rcu_dereference_protected(
1086 mvm->fw_id_to_mac_id[mvm->d0i3_ap_sta_id],
1087 lockdep_is_held(&mvm->mutex));
1088
1089 if (IS_ERR_OR_NULL(sta)) {
1090 sta = NULL;
1091 goto out;
1092 }
1093
1094 if (mvm->d0i3_offloading && qos_seq) {
1095 /* update qos seq numbers if offloading was enabled */
1096 mvm_ap_sta = (struct iwl_mvm_sta *)sta->drv_priv;
1097 for (i = 0; i < IWL_MAX_TID_COUNT; i++) {
1098 u16 seq = le16_to_cpu(qos_seq[i]);
1099 /* firmware stores last-used one, we store next one */
1100 seq += 0x10;
1101 mvm_ap_sta->tid_data[i].seq_number = seq;
1102 }
1103 }
1104out:
1105 /* re-enqueue (or drop) all packets */
1106 while (!skb_queue_empty(&mvm->d0i3_tx)) {
1107 struct sk_buff *skb = __skb_dequeue(&mvm->d0i3_tx);
1108
1109 if (!sta || iwl_mvm_tx_skb(mvm, skb, sta))
1110 ieee80211_free_txskb(mvm->hw, skb);
1111
1112 /* if the skb_queue is not empty, we need to wake queues */
1113 wake_queues = true;
1114 }
1115 clear_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status);
1116 wake_up(&mvm->d0i3_exit_waitq);
1117 mvm->d0i3_ap_sta_id = IWL_MVM_STATION_COUNT;
1118 if (wake_queues)
1119 ieee80211_wake_queues(mvm->hw);
1120
1121 spin_unlock_bh(&mvm->d0i3_tx_lock);
1122}
1123
1124static void iwl_mvm_d0i3_exit_work(struct work_struct *wk)
1125{
1126 struct iwl_mvm *mvm = container_of(wk, struct iwl_mvm, d0i3_exit_work);
1127 struct iwl_host_cmd get_status_cmd = {
1128 .id = WOWLAN_GET_STATUSES,
1129 .flags = CMD_SYNC | CMD_HIGH_PRIO | CMD_WANT_SKB,
1130 };
1131 struct iwl_wowlan_status_v6 *status;
1132 int ret;
1133 u32 disconnection_reasons, wakeup_reasons;
1134 __le16 *qos_seq = NULL;
1135
1136 mutex_lock(&mvm->mutex);
1137 ret = iwl_mvm_send_cmd(mvm, &get_status_cmd);
1138 if (ret)
1139 goto out;
1140
1141 if (!get_status_cmd.resp_pkt)
1142 goto out;
1143
1144 status = (void *)get_status_cmd.resp_pkt->data;
1145 wakeup_reasons = le32_to_cpu(status->wakeup_reasons);
1146 qos_seq = status->qos_seq_ctr;
1147
1148 IWL_DEBUG_RPM(mvm, "wakeup reasons: 0x%x\n", wakeup_reasons);
1149
1150 disconnection_reasons =
1151 IWL_WOWLAN_WAKEUP_BY_DISCONNECTION_ON_MISSED_BEACON |
1152 IWL_WOWLAN_WAKEUP_BY_DISCONNECTION_ON_DEAUTH;
1153 if (wakeup_reasons & disconnection_reasons)
1154 ieee80211_iterate_active_interfaces(
1155 mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
1156 iwl_mvm_d0i3_disconnect_iter, mvm);
1157
1158 iwl_free_resp(&get_status_cmd);
1159out:
1160 iwl_mvm_d0i3_enable_tx(mvm, qos_seq);
1161 mutex_unlock(&mvm->mutex);
1162}
1163
1164static int iwl_mvm_exit_d0i3(struct iwl_op_mode *op_mode)
1165{
1166 struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode);
1167 u32 flags = CMD_ASYNC | CMD_HIGH_PRIO | CMD_SEND_IN_IDLE |
1168 CMD_WAKE_UP_TRANS;
1169 int ret;
1170
1171 IWL_DEBUG_RPM(mvm, "MVM exiting D0i3\n");
1172
1173 ret = iwl_mvm_send_cmd_pdu(mvm, D0I3_END_CMD, flags, 0, NULL);
1174 if (ret)
1175 goto out;
1176
1177 ieee80211_iterate_active_interfaces_atomic(mvm->hw,
1178 IEEE80211_IFACE_ITER_NORMAL,
1179 iwl_mvm_exit_d0i3_iterator,
1180 mvm);
1181out:
1182 schedule_work(&mvm->d0i3_exit_work);
1183 return ret;
1184}
1185
781static const struct iwl_op_mode_ops iwl_mvm_ops = { 1186static const struct iwl_op_mode_ops iwl_mvm_ops = {
782 .start = iwl_op_mode_mvm_start, 1187 .start = iwl_op_mode_mvm_start,
783 .stop = iwl_op_mode_mvm_stop, 1188 .stop = iwl_op_mode_mvm_stop,
@@ -789,4 +1194,6 @@ static const struct iwl_op_mode_ops iwl_mvm_ops = {
789 .nic_error = iwl_mvm_nic_error, 1194 .nic_error = iwl_mvm_nic_error,
790 .cmd_queue_full = iwl_mvm_cmd_queue_full, 1195 .cmd_queue_full = iwl_mvm_cmd_queue_full,
791 .nic_config = iwl_mvm_nic_config, 1196 .nic_config = iwl_mvm_nic_config,
1197 .enter_d0i3 = iwl_mvm_enter_d0i3,
1198 .exit_d0i3 = iwl_mvm_exit_d0i3,
792}; 1199};
diff --git a/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c b/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c
index b7268c0b3333..237efe0ac1c4 100644
--- a/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c
+++ b/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c
@@ -156,13 +156,13 @@ static void iwl_mvm_phy_ctxt_cmd_data(struct iwl_mvm *mvm,
156 idle_cnt = chains_static; 156 idle_cnt = chains_static;
157 active_cnt = chains_dynamic; 157 active_cnt = chains_dynamic;
158 158
159 cmd->rxchain_info = cpu_to_le32(iwl_fw_valid_rx_ant(mvm->fw) << 159 cmd->rxchain_info = cpu_to_le32(mvm->fw->valid_rx_ant <<
160 PHY_RX_CHAIN_VALID_POS); 160 PHY_RX_CHAIN_VALID_POS);
161 cmd->rxchain_info |= cpu_to_le32(idle_cnt << PHY_RX_CHAIN_CNT_POS); 161 cmd->rxchain_info |= cpu_to_le32(idle_cnt << PHY_RX_CHAIN_CNT_POS);
162 cmd->rxchain_info |= cpu_to_le32(active_cnt << 162 cmd->rxchain_info |= cpu_to_le32(active_cnt <<
163 PHY_RX_CHAIN_MIMO_CNT_POS); 163 PHY_RX_CHAIN_MIMO_CNT_POS);
164 164
165 cmd->txchain_info = cpu_to_le32(iwl_fw_valid_tx_ant(mvm->fw)); 165 cmd->txchain_info = cpu_to_le32(mvm->fw->valid_tx_ant);
166} 166}
167 167
168/* 168/*
diff --git a/drivers/net/wireless/iwlwifi/mvm/power.c b/drivers/net/wireless/iwlwifi/mvm/power.c
index d9eab3b7bb9f..6b636eab3339 100644
--- a/drivers/net/wireless/iwlwifi/mvm/power.c
+++ b/drivers/net/wireless/iwlwifi/mvm/power.c
@@ -74,39 +74,36 @@
74 74
75#define POWER_KEEP_ALIVE_PERIOD_SEC 25 75#define POWER_KEEP_ALIVE_PERIOD_SEC 25
76 76
77static
77int iwl_mvm_beacon_filter_send_cmd(struct iwl_mvm *mvm, 78int iwl_mvm_beacon_filter_send_cmd(struct iwl_mvm *mvm,
78 struct iwl_beacon_filter_cmd *cmd) 79 struct iwl_beacon_filter_cmd *cmd,
80 u32 flags)
79{ 81{
80 int ret; 82 IWL_DEBUG_POWER(mvm, "ba_enable_beacon_abort is: %d\n",
81 83 le32_to_cpu(cmd->ba_enable_beacon_abort));
82 ret = iwl_mvm_send_cmd_pdu(mvm, REPLY_BEACON_FILTERING_CMD, CMD_SYNC, 84 IWL_DEBUG_POWER(mvm, "ba_escape_timer is: %d\n",
83 sizeof(struct iwl_beacon_filter_cmd), cmd); 85 le32_to_cpu(cmd->ba_escape_timer));
84 86 IWL_DEBUG_POWER(mvm, "bf_debug_flag is: %d\n",
85 if (!ret) { 87 le32_to_cpu(cmd->bf_debug_flag));
86 IWL_DEBUG_POWER(mvm, "ba_enable_beacon_abort is: %d\n", 88 IWL_DEBUG_POWER(mvm, "bf_enable_beacon_filter is: %d\n",
87 le32_to_cpu(cmd->ba_enable_beacon_abort)); 89 le32_to_cpu(cmd->bf_enable_beacon_filter));
88 IWL_DEBUG_POWER(mvm, "ba_escape_timer is: %d\n", 90 IWL_DEBUG_POWER(mvm, "bf_energy_delta is: %d\n",
89 le32_to_cpu(cmd->ba_escape_timer)); 91 le32_to_cpu(cmd->bf_energy_delta));
90 IWL_DEBUG_POWER(mvm, "bf_debug_flag is: %d\n", 92 IWL_DEBUG_POWER(mvm, "bf_escape_timer is: %d\n",
91 le32_to_cpu(cmd->bf_debug_flag)); 93 le32_to_cpu(cmd->bf_escape_timer));
92 IWL_DEBUG_POWER(mvm, "bf_enable_beacon_filter is: %d\n", 94 IWL_DEBUG_POWER(mvm, "bf_roaming_energy_delta is: %d\n",
93 le32_to_cpu(cmd->bf_enable_beacon_filter)); 95 le32_to_cpu(cmd->bf_roaming_energy_delta));
94 IWL_DEBUG_POWER(mvm, "bf_energy_delta is: %d\n", 96 IWL_DEBUG_POWER(mvm, "bf_roaming_state is: %d\n",
95 le32_to_cpu(cmd->bf_energy_delta)); 97 le32_to_cpu(cmd->bf_roaming_state));
96 IWL_DEBUG_POWER(mvm, "bf_escape_timer is: %d\n", 98 IWL_DEBUG_POWER(mvm, "bf_temp_threshold is: %d\n",
97 le32_to_cpu(cmd->bf_escape_timer)); 99 le32_to_cpu(cmd->bf_temp_threshold));
98 IWL_DEBUG_POWER(mvm, "bf_roaming_energy_delta is: %d\n", 100 IWL_DEBUG_POWER(mvm, "bf_temp_fast_filter is: %d\n",
99 le32_to_cpu(cmd->bf_roaming_energy_delta)); 101 le32_to_cpu(cmd->bf_temp_fast_filter));
100 IWL_DEBUG_POWER(mvm, "bf_roaming_state is: %d\n", 102 IWL_DEBUG_POWER(mvm, "bf_temp_slow_filter is: %d\n",
101 le32_to_cpu(cmd->bf_roaming_state)); 103 le32_to_cpu(cmd->bf_temp_slow_filter));
102 IWL_DEBUG_POWER(mvm, "bf_temp_threshold is: %d\n", 104
103 le32_to_cpu(cmd->bf_temp_threshold)); 105 return iwl_mvm_send_cmd_pdu(mvm, REPLY_BEACON_FILTERING_CMD, flags,
104 IWL_DEBUG_POWER(mvm, "bf_temp_fast_filter is: %d\n", 106 sizeof(struct iwl_beacon_filter_cmd), cmd);
105 le32_to_cpu(cmd->bf_temp_fast_filter));
106 IWL_DEBUG_POWER(mvm, "bf_temp_slow_filter is: %d\n",
107 le32_to_cpu(cmd->bf_temp_slow_filter));
108 }
109 return ret;
110} 107}
111 108
112static 109static
@@ -145,7 +142,7 @@ int iwl_mvm_update_beacon_abort(struct iwl_mvm *mvm,
145 mvmvif->bf_data.ba_enabled = enable; 142 mvmvif->bf_data.ba_enabled = enable;
146 iwl_mvm_beacon_filter_set_cqm_params(mvm, vif, &cmd); 143 iwl_mvm_beacon_filter_set_cqm_params(mvm, vif, &cmd);
147 iwl_mvm_beacon_filter_debugfs_parameters(vif, &cmd); 144 iwl_mvm_beacon_filter_debugfs_parameters(vif, &cmd);
148 return iwl_mvm_beacon_filter_send_cmd(mvm, &cmd); 145 return iwl_mvm_beacon_filter_send_cmd(mvm, &cmd, CMD_SYNC);
149} 146}
150 147
151static void iwl_mvm_power_log(struct iwl_mvm *mvm, 148static void iwl_mvm_power_log(struct iwl_mvm *mvm,
@@ -301,8 +298,7 @@ static void iwl_mvm_power_build_cmd(struct iwl_mvm *mvm,
301 keep_alive = DIV_ROUND_UP(keep_alive, MSEC_PER_SEC); 298 keep_alive = DIV_ROUND_UP(keep_alive, MSEC_PER_SEC);
302 cmd->keep_alive_seconds = cpu_to_le16(keep_alive); 299 cmd->keep_alive_seconds = cpu_to_le16(keep_alive);
303 300
304 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM || 301 if (mvm->ps_disabled)
305 mvm->ps_prevented)
306 return; 302 return;
307 303
308 cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_SAVE_ENA_MSK); 304 cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_SAVE_ENA_MSK);
@@ -312,7 +308,8 @@ static void iwl_mvm_power_build_cmd(struct iwl_mvm *mvm,
312 mvmvif->dbgfs_pm.disable_power_off) 308 mvmvif->dbgfs_pm.disable_power_off)
313 cmd->flags &= cpu_to_le16(~POWER_FLAGS_POWER_SAVE_ENA_MSK); 309 cmd->flags &= cpu_to_le16(~POWER_FLAGS_POWER_SAVE_ENA_MSK);
314#endif 310#endif
315 if (!vif->bss_conf.ps || mvmvif->pm_prevented) 311 if (!vif->bss_conf.ps || iwl_mvm_vif_low_latency(mvmvif) ||
312 mvm->pm_disabled)
316 return; 313 return;
317 314
318 cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK); 315 cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK);
@@ -419,72 +416,44 @@ static void iwl_mvm_power_build_cmd(struct iwl_mvm *mvm,
419#endif /* CONFIG_IWLWIFI_DEBUGFS */ 416#endif /* CONFIG_IWLWIFI_DEBUGFS */
420} 417}
421 418
422static int iwl_mvm_power_mac_update_mode(struct iwl_mvm *mvm, 419static int iwl_mvm_power_send_cmd(struct iwl_mvm *mvm,
423 struct ieee80211_vif *vif) 420 struct ieee80211_vif *vif)
424{ 421{
425 int ret;
426 bool ba_enable;
427 struct iwl_mac_power_cmd cmd = {}; 422 struct iwl_mac_power_cmd cmd = {};
428 423
429 if (vif->type != NL80211_IFTYPE_STATION) 424 if (vif->type != NL80211_IFTYPE_STATION)
430 return 0; 425 return 0;
431 426
432 if (vif->p2p && 427 if (vif->p2p &&
433 !(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_P2P_PS)) 428 !(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM))
434 return 0; 429 return 0;
435 430
436 iwl_mvm_power_build_cmd(mvm, vif, &cmd); 431 iwl_mvm_power_build_cmd(mvm, vif, &cmd);
437 iwl_mvm_power_log(mvm, &cmd); 432 iwl_mvm_power_log(mvm, &cmd);
438
439 ret = iwl_mvm_send_cmd_pdu(mvm, MAC_PM_POWER_TABLE, CMD_SYNC,
440 sizeof(cmd), &cmd);
441 if (ret)
442 return ret;
443
444 ba_enable = !!(cmd.flags &
445 cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK));
446
447 return iwl_mvm_update_beacon_abort(mvm, vif, ba_enable);
448}
449
450static int iwl_mvm_power_mac_disable(struct iwl_mvm *mvm,
451 struct ieee80211_vif *vif)
452{
453 struct iwl_mac_power_cmd cmd = {};
454 struct iwl_mvm_vif *mvmvif __maybe_unused =
455 iwl_mvm_vif_from_mac80211(vif);
456
457 if (vif->type != NL80211_IFTYPE_STATION || vif->p2p)
458 return 0;
459
460 cmd.id_and_color = cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id,
461 mvmvif->color));
462
463 if (iwlmvm_mod_params.power_scheme != IWL_POWER_SCHEME_CAM)
464 cmd.flags |= cpu_to_le16(POWER_FLAGS_POWER_SAVE_ENA_MSK);
465
466#ifdef CONFIG_IWLWIFI_DEBUGFS 433#ifdef CONFIG_IWLWIFI_DEBUGFS
467 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_DISABLE_POWER_OFF && 434 memcpy(&iwl_mvm_vif_from_mac80211(vif)->mac_pwr_cmd, &cmd, sizeof(cmd));
468 mvmvif->dbgfs_pm.disable_power_off)
469 cmd.flags &= cpu_to_le16(~POWER_FLAGS_POWER_SAVE_ENA_MSK);
470#endif 435#endif
471 iwl_mvm_power_log(mvm, &cmd);
472 436
473 return iwl_mvm_send_cmd_pdu(mvm, MAC_PM_POWER_TABLE, CMD_ASYNC, 437 return iwl_mvm_send_cmd_pdu(mvm, MAC_PM_POWER_TABLE, CMD_SYNC,
474 sizeof(cmd), &cmd); 438 sizeof(cmd), &cmd);
475} 439}
476 440
477static int _iwl_mvm_power_update_device(struct iwl_mvm *mvm, bool force_disable) 441int iwl_mvm_power_update_device(struct iwl_mvm *mvm)
478{ 442{
479 struct iwl_device_power_cmd cmd = { 443 struct iwl_device_power_cmd cmd = {
480 .flags = cpu_to_le16(DEVICE_POWER_FLAGS_POWER_SAVE_ENA_MSK), 444 .flags = cpu_to_le16(DEVICE_POWER_FLAGS_POWER_SAVE_ENA_MSK),
481 }; 445 };
482 446
447 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_PM_CMD_SUPPORT))
448 return 0;
449
483 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_DEVICE_PS_CMD)) 450 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_DEVICE_PS_CMD))
484 return 0; 451 return 0;
485 452
486 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM || 453 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM)
487 force_disable) 454 mvm->ps_disabled = true;
455
456 if (mvm->ps_disabled)
488 cmd.flags |= cpu_to_le16(DEVICE_POWER_FLAGS_CAM_MSK); 457 cmd.flags |= cpu_to_le16(DEVICE_POWER_FLAGS_CAM_MSK);
489 458
490#ifdef CONFIG_IWLWIFI_DEBUGFS 459#ifdef CONFIG_IWLWIFI_DEBUGFS
@@ -501,11 +470,6 @@ static int _iwl_mvm_power_update_device(struct iwl_mvm *mvm, bool force_disable)
501 &cmd); 470 &cmd);
502} 471}
503 472
504static int iwl_mvm_power_update_device(struct iwl_mvm *mvm)
505{
506 return _iwl_mvm_power_update_device(mvm, false);
507}
508
509void iwl_mvm_power_vif_assoc(struct iwl_mvm *mvm, struct ieee80211_vif *vif) 473void iwl_mvm_power_vif_assoc(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
510{ 474{
511 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 475 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
@@ -544,44 +508,176 @@ int iwl_mvm_power_uapsd_misbehaving_ap_notif(struct iwl_mvm *mvm,
544 return 0; 508 return 0;
545} 509}
546 510
547static void iwl_mvm_power_binding_iterator(void *_data, u8 *mac, 511struct iwl_power_constraint {
548 struct ieee80211_vif *vif) 512 struct ieee80211_vif *bf_vif;
513 struct ieee80211_vif *bss_vif;
514 struct ieee80211_vif *p2p_vif;
515 u16 bss_phyctx_id;
516 u16 p2p_phyctx_id;
517 bool pm_disabled;
518 bool ps_disabled;
519 struct iwl_mvm *mvm;
520};
521
522static void iwl_mvm_power_iterator(void *_data, u8 *mac,
523 struct ieee80211_vif *vif)
549{ 524{
550 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 525 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
551 struct iwl_mvm *mvm = _data; 526 struct iwl_power_constraint *power_iterator = _data;
552 int ret; 527 struct iwl_mvm *mvm = power_iterator->mvm;
528
529 switch (ieee80211_vif_type_p2p(vif)) {
530 case NL80211_IFTYPE_P2P_DEVICE:
531 break;
532
533 case NL80211_IFTYPE_P2P_GO:
534 case NL80211_IFTYPE_AP:
535 /* no BSS power mgmt if we have an active AP */
536 if (mvmvif->ap_ibss_active)
537 power_iterator->pm_disabled = true;
538 break;
539
540 case NL80211_IFTYPE_MONITOR:
541 /* no BSS power mgmt and no device power save */
542 power_iterator->pm_disabled = true;
543 power_iterator->ps_disabled = true;
544 break;
545
546 case NL80211_IFTYPE_P2P_CLIENT:
547 if (mvmvif->phy_ctxt)
548 power_iterator->p2p_phyctx_id = mvmvif->phy_ctxt->id;
549
550 /* we should have only one P2P vif */
551 WARN_ON(power_iterator->p2p_vif);
552 power_iterator->p2p_vif = vif;
553
554 IWL_DEBUG_POWER(mvm, "p2p: p2p_id=%d, bss_id=%d\n",
555 power_iterator->p2p_phyctx_id,
556 power_iterator->bss_phyctx_id);
557 if (!(mvm->fw->ucode_capa.flags &
558 IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM)) {
559 /* no BSS power mgmt if we have a P2P client*/
560 power_iterator->pm_disabled = true;
561 } else if (power_iterator->p2p_phyctx_id < MAX_PHYS &&
562 power_iterator->bss_phyctx_id < MAX_PHYS &&
563 power_iterator->p2p_phyctx_id ==
564 power_iterator->bss_phyctx_id) {
565 power_iterator->pm_disabled = true;
566 }
567 break;
568
569 case NL80211_IFTYPE_STATION:
570 if (mvmvif->phy_ctxt)
571 power_iterator->bss_phyctx_id = mvmvif->phy_ctxt->id;
572
573 /* we should have only one BSS vif */
574 WARN_ON(power_iterator->bss_vif);
575 power_iterator->bss_vif = vif;
576
577 if (mvmvif->bf_data.bf_enabled &&
578 !WARN_ON(power_iterator->bf_vif))
579 power_iterator->bf_vif = vif;
580
581 IWL_DEBUG_POWER(mvm, "bss: p2p_id=%d, bss_id=%d\n",
582 power_iterator->p2p_phyctx_id,
583 power_iterator->bss_phyctx_id);
584 if (mvm->fw->ucode_capa.flags &
585 IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM &&
586 (power_iterator->p2p_phyctx_id < MAX_PHYS &&
587 power_iterator->bss_phyctx_id < MAX_PHYS &&
588 power_iterator->p2p_phyctx_id ==
589 power_iterator->bss_phyctx_id))
590 power_iterator->pm_disabled = true;
591 break;
592
593 default:
594 break;
595 }
596}
553 597
554 mvmvif->pm_prevented = (mvm->bound_vif_cnt <= 1) ? false : true; 598static void
599iwl_mvm_power_get_global_constraint(struct iwl_mvm *mvm,
600 struct iwl_power_constraint *constraint)
601{
602 lockdep_assert_held(&mvm->mutex);
603
604 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM) {
605 constraint->pm_disabled = true;
606 constraint->ps_disabled = true;
607 }
555 608
556 ret = iwl_mvm_power_mac_update_mode(mvm, vif); 609 ieee80211_iterate_active_interfaces_atomic(mvm->hw,
557 WARN_ONCE(ret, "Failed to update power parameters on a specific vif\n"); 610 IEEE80211_IFACE_ITER_NORMAL,
611 iwl_mvm_power_iterator, constraint);
558} 612}
559 613
560static void _iwl_mvm_power_update_binding(struct iwl_mvm *mvm, 614int iwl_mvm_power_update_mac(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
561 struct ieee80211_vif *vif,
562 bool assign)
563{ 615{
616 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
617 struct iwl_power_constraint constraint = {
618 .p2p_phyctx_id = MAX_PHYS,
619 .bss_phyctx_id = MAX_PHYS,
620 .mvm = mvm,
621 };
622 bool ba_enable;
623 int ret;
624
625 lockdep_assert_held(&mvm->mutex);
626
627 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_PM_CMD_SUPPORT))
628 return 0;
629
630 iwl_mvm_power_get_global_constraint(mvm, &constraint);
631 mvm->ps_disabled = constraint.ps_disabled;
632 mvm->pm_disabled = constraint.pm_disabled;
633
634 /* don't update device power state unless we add / remove monitor */
564 if (vif->type == NL80211_IFTYPE_MONITOR) { 635 if (vif->type == NL80211_IFTYPE_MONITOR) {
565 int ret = _iwl_mvm_power_update_device(mvm, assign); 636 ret = iwl_mvm_power_update_device(mvm);
566 mvm->ps_prevented = assign; 637 if (ret)
567 WARN_ONCE(ret, "Failed to update power device state\n"); 638 return ret;
568 } 639 }
569 640
570 ieee80211_iterate_active_interfaces(mvm->hw, 641 if (constraint.bss_vif) {
571 IEEE80211_IFACE_ITER_NORMAL, 642 ret = iwl_mvm_power_send_cmd(mvm, constraint.bss_vif);
572 iwl_mvm_power_binding_iterator, 643 if (ret)
573 mvm); 644 return ret;
645 }
646
647 if (constraint.p2p_vif) {
648 ret = iwl_mvm_power_send_cmd(mvm, constraint.p2p_vif);
649 if (ret)
650 return ret;
651 }
652
653 if (!constraint.bf_vif)
654 return 0;
655
656 vif = constraint.bf_vif;
657 mvmvif = iwl_mvm_vif_from_mac80211(vif);
658
659 ba_enable = !(constraint.pm_disabled || constraint.ps_disabled ||
660 !vif->bss_conf.ps || iwl_mvm_vif_low_latency(mvmvif));
661
662 return iwl_mvm_update_beacon_abort(mvm, constraint.bf_vif, ba_enable);
574} 663}
575 664
576#ifdef CONFIG_IWLWIFI_DEBUGFS 665#ifdef CONFIG_IWLWIFI_DEBUGFS
577static int iwl_mvm_power_mac_dbgfs_read(struct iwl_mvm *mvm, 666int iwl_mvm_power_mac_dbgfs_read(struct iwl_mvm *mvm,
578 struct ieee80211_vif *vif, char *buf, 667 struct ieee80211_vif *vif, char *buf,
579 int bufsz) 668 int bufsz)
580{ 669{
670 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
581 struct iwl_mac_power_cmd cmd = {}; 671 struct iwl_mac_power_cmd cmd = {};
582 int pos = 0; 672 int pos = 0;
583 673
584 iwl_mvm_power_build_cmd(mvm, vif, &cmd); 674 if (WARN_ON(!(mvm->fw->ucode_capa.flags &
675 IWL_UCODE_TLV_FLAGS_PM_CMD_SUPPORT)))
676 return 0;
677
678 mutex_lock(&mvm->mutex);
679 memcpy(&cmd, &mvmvif->mac_pwr_cmd, sizeof(cmd));
680 mutex_unlock(&mvm->mutex);
585 681
586 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_DEVICE_PS_CMD)) 682 if (!(mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_DEVICE_PS_CMD))
587 pos += scnprintf(buf+pos, bufsz-pos, "disable_power_off = %d\n", 683 pos += scnprintf(buf+pos, bufsz-pos, "disable_power_off = %d\n",
@@ -685,32 +781,46 @@ iwl_mvm_beacon_filter_debugfs_parameters(struct ieee80211_vif *vif,
685} 781}
686#endif 782#endif
687 783
688int iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm, 784static int _iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm,
689 struct ieee80211_vif *vif) 785 struct ieee80211_vif *vif,
786 struct iwl_beacon_filter_cmd *cmd,
787 u32 cmd_flags,
788 bool d0i3)
690{ 789{
691 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 790 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
692 struct iwl_beacon_filter_cmd cmd = {
693 IWL_BF_CMD_CONFIG_DEFAULTS,
694 .bf_enable_beacon_filter = cpu_to_le32(1),
695 };
696 int ret; 791 int ret;
697 792
698 if (mvmvif != mvm->bf_allowed_vif || 793 if (mvmvif != mvm->bf_allowed_vif ||
699 vif->type != NL80211_IFTYPE_STATION || vif->p2p) 794 vif->type != NL80211_IFTYPE_STATION || vif->p2p)
700 return 0; 795 return 0;
701 796
702 iwl_mvm_beacon_filter_set_cqm_params(mvm, vif, &cmd); 797 iwl_mvm_beacon_filter_set_cqm_params(mvm, vif, cmd);
703 iwl_mvm_beacon_filter_debugfs_parameters(vif, &cmd); 798 if (!d0i3)
704 ret = iwl_mvm_beacon_filter_send_cmd(mvm, &cmd); 799 iwl_mvm_beacon_filter_debugfs_parameters(vif, cmd);
800 ret = iwl_mvm_beacon_filter_send_cmd(mvm, cmd, cmd_flags);
705 801
706 if (!ret) 802 /* don't change bf_enabled in case of temporary d0i3 configuration */
803 if (!ret && !d0i3)
707 mvmvif->bf_data.bf_enabled = true; 804 mvmvif->bf_data.bf_enabled = true;
708 805
709 return ret; 806 return ret;
710} 807}
711 808
809int iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm,
810 struct ieee80211_vif *vif,
811 u32 flags)
812{
813 struct iwl_beacon_filter_cmd cmd = {
814 IWL_BF_CMD_CONFIG_DEFAULTS,
815 .bf_enable_beacon_filter = cpu_to_le32(1),
816 };
817
818 return _iwl_mvm_enable_beacon_filter(mvm, vif, &cmd, flags, false);
819}
820
712int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm, 821int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm,
713 struct ieee80211_vif *vif) 822 struct ieee80211_vif *vif,
823 u32 flags)
714{ 824{
715 struct iwl_beacon_filter_cmd cmd = {}; 825 struct iwl_beacon_filter_cmd cmd = {};
716 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 826 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
@@ -720,7 +830,7 @@ int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm,
720 vif->type != NL80211_IFTYPE_STATION || vif->p2p) 830 vif->type != NL80211_IFTYPE_STATION || vif->p2p)
721 return 0; 831 return 0;
722 832
723 ret = iwl_mvm_beacon_filter_send_cmd(mvm, &cmd); 833 ret = iwl_mvm_beacon_filter_send_cmd(mvm, &cmd, flags);
724 834
725 if (!ret) 835 if (!ret)
726 mvmvif->bf_data.bf_enabled = false; 836 mvmvif->bf_data.bf_enabled = false;
@@ -728,23 +838,89 @@ int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm,
728 return ret; 838 return ret;
729} 839}
730 840
731int iwl_mvm_update_beacon_filter(struct iwl_mvm *mvm, 841int iwl_mvm_update_d0i3_power_mode(struct iwl_mvm *mvm,
732 struct ieee80211_vif *vif) 842 struct ieee80211_vif *vif,
843 bool enable, u32 flags)
733{ 844{
845 int ret;
734 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 846 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
847 struct iwl_mac_power_cmd cmd = {};
735 848
736 if (!mvmvif->bf_data.bf_enabled) 849 if (vif->type != NL80211_IFTYPE_STATION || vif->p2p)
737 return 0; 850 return 0;
738 851
739 return iwl_mvm_enable_beacon_filter(mvm, vif); 852 if (!vif->bss_conf.assoc)
740} 853 return 0;
741 854
742const struct iwl_mvm_power_ops pm_mac_ops = { 855 iwl_mvm_power_build_cmd(mvm, vif, &cmd);
743 .power_update_mode = iwl_mvm_power_mac_update_mode, 856 if (enable) {
744 .power_update_device_mode = iwl_mvm_power_update_device, 857 /* configure skip over dtim up to 300 msec */
745 .power_disable = iwl_mvm_power_mac_disable, 858 int dtimper = mvm->hw->conf.ps_dtim_period ?: 1;
746 .power_update_binding = _iwl_mvm_power_update_binding, 859 int dtimper_msec = dtimper * vif->bss_conf.beacon_int;
860
861 if (WARN_ON(!dtimper_msec))
862 return 0;
863
864 cmd.flags |=
865 cpu_to_le16(POWER_FLAGS_SKIP_OVER_DTIM_MSK);
866 cmd.skip_dtim_periods = 300 / dtimper_msec;
867 }
868 iwl_mvm_power_log(mvm, &cmd);
747#ifdef CONFIG_IWLWIFI_DEBUGFS 869#ifdef CONFIG_IWLWIFI_DEBUGFS
748 .power_dbgfs_read = iwl_mvm_power_mac_dbgfs_read, 870 memcpy(&mvmvif->mac_pwr_cmd, &cmd, sizeof(cmd));
749#endif 871#endif
750}; 872 ret = iwl_mvm_send_cmd_pdu(mvm, MAC_PM_POWER_TABLE, flags,
873 sizeof(cmd), &cmd);
874 if (ret)
875 return ret;
876
877 /* configure beacon filtering */
878 if (mvmvif != mvm->bf_allowed_vif)
879 return 0;
880
881 if (enable) {
882 struct iwl_beacon_filter_cmd cmd_bf = {
883 IWL_BF_CMD_CONFIG_D0I3,
884 .bf_enable_beacon_filter = cpu_to_le32(1),
885 };
886 ret = _iwl_mvm_enable_beacon_filter(mvm, vif, &cmd_bf,
887 flags, true);
888 } else {
889 if (mvmvif->bf_data.bf_enabled)
890 ret = iwl_mvm_enable_beacon_filter(mvm, vif, flags);
891 else
892 ret = iwl_mvm_disable_beacon_filter(mvm, vif, flags);
893 }
894
895 return ret;
896}
897
898int iwl_mvm_update_beacon_filter(struct iwl_mvm *mvm,
899 struct ieee80211_vif *vif,
900 bool force,
901 u32 flags)
902{
903 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
904
905 if (mvmvif != mvm->bf_allowed_vif)
906 return 0;
907
908 if (!mvmvif->bf_data.bf_enabled) {
909 /* disable beacon filtering explicitly if force is true */
910 if (force)
911 return iwl_mvm_disable_beacon_filter(mvm, vif, flags);
912 return 0;
913 }
914
915 return iwl_mvm_enable_beacon_filter(mvm, vif, flags);
916}
917
918int iwl_power_legacy_set_cam_mode(struct iwl_mvm *mvm)
919{
920 struct iwl_powertable_cmd cmd = {
921 .keep_alive_seconds = POWER_KEEP_ALIVE_PERIOD_SEC,
922 };
923
924 return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_SYNC,
925 sizeof(cmd), &cmd);
926}
diff --git a/drivers/net/wireless/iwlwifi/mvm/power_legacy.c b/drivers/net/wireless/iwlwifi/mvm/power_legacy.c
deleted file mode 100644
index ef712ae5bc62..000000000000
--- a/drivers/net/wireless/iwlwifi/mvm/power_legacy.c
+++ /dev/null
@@ -1,319 +0,0 @@
1/******************************************************************************
2 *
3 * This file is provided under a dual BSD/GPLv2 license. When using or
4 * redistributing this file, you may do so under either license.
5 *
6 * GPL LICENSE SUMMARY
7 *
8 * Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of version 2 of the GNU General Public License as
12 * published by the Free Software Foundation.
13 *
14 * This program is distributed in the hope that it will be useful, but
15 * WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110,
22 * USA
23 *
24 * The full GNU General Public License is included in this distribution
25 * in the file called COPYING.
26 *
27 * Contact Information:
28 * Intel Linux Wireless <ilw@linux.intel.com>
29 * Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
30 *
31 * BSD LICENSE
32 *
33 * Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
34 * All rights reserved.
35 *
36 * Redistribution and use in source and binary forms, with or without
37 * modification, are permitted provided that the following conditions
38 * are met:
39 *
40 * * Redistributions of source code must retain the above copyright
41 * notice, this list of conditions and the following disclaimer.
42 * * Redistributions in binary form must reproduce the above copyright
43 * notice, this list of conditions and the following disclaimer in
44 * the documentation and/or other materials provided with the
45 * distribution.
46 * * Neither the name Intel Corporation nor the names of its
47 * contributors may be used to endorse or promote products derived
48 * from this software without specific prior written permission.
49 *
50 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
51 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
52 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
53 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
54 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
55 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
56 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
57 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
58 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
59 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
60 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
61 *
62 *****************************************************************************/
63
64#include <linux/kernel.h>
65#include <linux/module.h>
66#include <linux/slab.h>
67#include <linux/init.h>
68
69#include <net/mac80211.h>
70
71#include "iwl-debug.h"
72#include "mvm.h"
73#include "iwl-modparams.h"
74#include "fw-api-power.h"
75
76#define POWER_KEEP_ALIVE_PERIOD_SEC 25
77
78static void iwl_mvm_power_log(struct iwl_mvm *mvm,
79 struct iwl_powertable_cmd *cmd)
80{
81 IWL_DEBUG_POWER(mvm,
82 "Sending power table command for power level %d, flags = 0x%X\n",
83 iwlmvm_mod_params.power_scheme,
84 le16_to_cpu(cmd->flags));
85 IWL_DEBUG_POWER(mvm, "Keep alive = %u sec\n", cmd->keep_alive_seconds);
86
87 if (cmd->flags & cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK)) {
88 IWL_DEBUG_POWER(mvm, "Rx timeout = %u usec\n",
89 le32_to_cpu(cmd->rx_data_timeout));
90 IWL_DEBUG_POWER(mvm, "Tx timeout = %u usec\n",
91 le32_to_cpu(cmd->tx_data_timeout));
92 if (cmd->flags & cpu_to_le16(POWER_FLAGS_SKIP_OVER_DTIM_MSK))
93 IWL_DEBUG_POWER(mvm, "DTIM periods to skip = %u\n",
94 le32_to_cpu(cmd->skip_dtim_periods));
95 if (cmd->flags & cpu_to_le16(POWER_FLAGS_LPRX_ENA_MSK))
96 IWL_DEBUG_POWER(mvm, "LP RX RSSI threshold = %u\n",
97 le32_to_cpu(cmd->lprx_rssi_threshold));
98 }
99}
100
101static void iwl_mvm_power_build_cmd(struct iwl_mvm *mvm,
102 struct ieee80211_vif *vif,
103 struct iwl_powertable_cmd *cmd)
104{
105 struct ieee80211_hw *hw = mvm->hw;
106 struct ieee80211_chanctx_conf *chanctx_conf;
107 struct ieee80211_channel *chan;
108 int dtimper, dtimper_msec;
109 int keep_alive;
110 bool radar_detect = false;
111 struct iwl_mvm_vif *mvmvif __maybe_unused =
112 iwl_mvm_vif_from_mac80211(vif);
113
114 /*
115 * Regardless of power management state the driver must set
116 * keep alive period. FW will use it for sending keep alive NDPs
117 * immediately after association.
118 */
119 cmd->keep_alive_seconds = POWER_KEEP_ALIVE_PERIOD_SEC;
120
121 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM)
122 return;
123
124 cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_SAVE_ENA_MSK);
125 if (!vif->bss_conf.assoc)
126 cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK);
127
128#ifdef CONFIG_IWLWIFI_DEBUGFS
129 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_DISABLE_POWER_OFF &&
130 mvmvif->dbgfs_pm.disable_power_off)
131 cmd->flags &= cpu_to_le16(~POWER_FLAGS_POWER_SAVE_ENA_MSK);
132#endif
133 if (!vif->bss_conf.ps)
134 return;
135
136 cmd->flags |= cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK);
137
138 if (vif->bss_conf.beacon_rate &&
139 (vif->bss_conf.beacon_rate->bitrate == 10 ||
140 vif->bss_conf.beacon_rate->bitrate == 60)) {
141 cmd->flags |= cpu_to_le16(POWER_FLAGS_LPRX_ENA_MSK);
142 cmd->lprx_rssi_threshold =
143 cpu_to_le32(POWER_LPRX_RSSI_THRESHOLD);
144 }
145
146 dtimper = hw->conf.ps_dtim_period ?: 1;
147
148 /* Check if radar detection is required on current channel */
149 rcu_read_lock();
150 chanctx_conf = rcu_dereference(vif->chanctx_conf);
151 WARN_ON(!chanctx_conf);
152 if (chanctx_conf) {
153 chan = chanctx_conf->def.chan;
154 radar_detect = chan->flags & IEEE80211_CHAN_RADAR;
155 }
156 rcu_read_unlock();
157
158 /* Check skip over DTIM conditions */
159 if (!radar_detect && (dtimper <= 10) &&
160 (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_LP ||
161 mvm->cur_ucode == IWL_UCODE_WOWLAN)) {
162 cmd->flags |= cpu_to_le16(POWER_FLAGS_SKIP_OVER_DTIM_MSK);
163 cmd->skip_dtim_periods = cpu_to_le32(3);
164 }
165
166 /* Check that keep alive period is at least 3 * DTIM */
167 dtimper_msec = dtimper * vif->bss_conf.beacon_int;
168 keep_alive = max_t(int, 3 * dtimper_msec,
169 MSEC_PER_SEC * cmd->keep_alive_seconds);
170 keep_alive = DIV_ROUND_UP(keep_alive, MSEC_PER_SEC);
171 cmd->keep_alive_seconds = keep_alive;
172
173 if (mvm->cur_ucode != IWL_UCODE_WOWLAN) {
174 cmd->rx_data_timeout = cpu_to_le32(100 * USEC_PER_MSEC);
175 cmd->tx_data_timeout = cpu_to_le32(100 * USEC_PER_MSEC);
176 } else {
177 cmd->rx_data_timeout = cpu_to_le32(10 * USEC_PER_MSEC);
178 cmd->tx_data_timeout = cpu_to_le32(10 * USEC_PER_MSEC);
179 }
180
181#ifdef CONFIG_IWLWIFI_DEBUGFS
182 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_KEEP_ALIVE)
183 cmd->keep_alive_seconds = mvmvif->dbgfs_pm.keep_alive_seconds;
184 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_SKIP_OVER_DTIM) {
185 if (mvmvif->dbgfs_pm.skip_over_dtim)
186 cmd->flags |=
187 cpu_to_le16(POWER_FLAGS_SKIP_OVER_DTIM_MSK);
188 else
189 cmd->flags &=
190 cpu_to_le16(~POWER_FLAGS_SKIP_OVER_DTIM_MSK);
191 }
192 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_RX_DATA_TIMEOUT)
193 cmd->rx_data_timeout =
194 cpu_to_le32(mvmvif->dbgfs_pm.rx_data_timeout);
195 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_TX_DATA_TIMEOUT)
196 cmd->tx_data_timeout =
197 cpu_to_le32(mvmvif->dbgfs_pm.tx_data_timeout);
198 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_SKIP_DTIM_PERIODS)
199 cmd->skip_dtim_periods =
200 cpu_to_le32(mvmvif->dbgfs_pm.skip_dtim_periods);
201 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_LPRX_ENA) {
202 if (mvmvif->dbgfs_pm.lprx_ena)
203 cmd->flags |= cpu_to_le16(POWER_FLAGS_LPRX_ENA_MSK);
204 else
205 cmd->flags &= cpu_to_le16(~POWER_FLAGS_LPRX_ENA_MSK);
206 }
207 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_LPRX_RSSI_THRESHOLD)
208 cmd->lprx_rssi_threshold =
209 cpu_to_le32(mvmvif->dbgfs_pm.lprx_rssi_threshold);
210#endif /* CONFIG_IWLWIFI_DEBUGFS */
211}
212
213static int iwl_mvm_power_legacy_update_mode(struct iwl_mvm *mvm,
214 struct ieee80211_vif *vif)
215{
216 int ret;
217 bool ba_enable;
218 struct iwl_powertable_cmd cmd = {};
219
220 if (vif->type != NL80211_IFTYPE_STATION || vif->p2p)
221 return 0;
222
223 /*
224 * TODO: The following vif_count verification is temporary condition.
225 * Avoid power mode update if more than one interface is currently
226 * active. Remove this condition when FW will support power management
227 * on multiple MACs.
228 */
229 IWL_DEBUG_POWER(mvm, "Currently %d interfaces active\n",
230 mvm->vif_count);
231 if (mvm->vif_count > 1)
232 return 0;
233
234 iwl_mvm_power_build_cmd(mvm, vif, &cmd);
235 iwl_mvm_power_log(mvm, &cmd);
236
237 ret = iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_SYNC,
238 sizeof(cmd), &cmd);
239 if (ret)
240 return ret;
241
242 ba_enable = !!(cmd.flags &
243 cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK));
244
245 return iwl_mvm_update_beacon_abort(mvm, vif, ba_enable);
246}
247
248static int iwl_mvm_power_legacy_disable(struct iwl_mvm *mvm,
249 struct ieee80211_vif *vif)
250{
251 struct iwl_powertable_cmd cmd = {};
252 struct iwl_mvm_vif *mvmvif __maybe_unused =
253 iwl_mvm_vif_from_mac80211(vif);
254
255 if (vif->type != NL80211_IFTYPE_STATION || vif->p2p)
256 return 0;
257
258 if (iwlmvm_mod_params.power_scheme != IWL_POWER_SCHEME_CAM)
259 cmd.flags |= cpu_to_le16(POWER_FLAGS_POWER_SAVE_ENA_MSK);
260
261#ifdef CONFIG_IWLWIFI_DEBUGFS
262 if (mvmvif->dbgfs_pm.mask & MVM_DEBUGFS_PM_DISABLE_POWER_OFF &&
263 mvmvif->dbgfs_pm.disable_power_off)
264 cmd.flags &= cpu_to_le16(~POWER_FLAGS_POWER_SAVE_ENA_MSK);
265#endif
266 iwl_mvm_power_log(mvm, &cmd);
267
268 return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_ASYNC,
269 sizeof(cmd), &cmd);
270}
271
272#ifdef CONFIG_IWLWIFI_DEBUGFS
273static int iwl_mvm_power_legacy_dbgfs_read(struct iwl_mvm *mvm,
274 struct ieee80211_vif *vif, char *buf,
275 int bufsz)
276{
277 struct iwl_powertable_cmd cmd = {};
278 int pos = 0;
279
280 iwl_mvm_power_build_cmd(mvm, vif, &cmd);
281
282 pos += scnprintf(buf+pos, bufsz-pos, "disable_power_off = %d\n",
283 (cmd.flags &
284 cpu_to_le16(POWER_FLAGS_POWER_SAVE_ENA_MSK)) ?
285 0 : 1);
286 pos += scnprintf(buf+pos, bufsz-pos, "skip_dtim_periods = %d\n",
287 le32_to_cpu(cmd.skip_dtim_periods));
288 pos += scnprintf(buf+pos, bufsz-pos, "power_scheme = %d\n",
289 iwlmvm_mod_params.power_scheme);
290 pos += scnprintf(buf+pos, bufsz-pos, "flags = 0x%x\n",
291 le16_to_cpu(cmd.flags));
292 pos += scnprintf(buf+pos, bufsz-pos, "keep_alive = %d\n",
293 cmd.keep_alive_seconds);
294
295 if (cmd.flags & cpu_to_le16(POWER_FLAGS_POWER_MANAGEMENT_ENA_MSK)) {
296 pos += scnprintf(buf+pos, bufsz-pos, "skip_over_dtim = %d\n",
297 (cmd.flags &
298 cpu_to_le16(POWER_FLAGS_SKIP_OVER_DTIM_MSK)) ?
299 1 : 0);
300 pos += scnprintf(buf+pos, bufsz-pos, "rx_data_timeout = %d\n",
301 le32_to_cpu(cmd.rx_data_timeout));
302 pos += scnprintf(buf+pos, bufsz-pos, "tx_data_timeout = %d\n",
303 le32_to_cpu(cmd.tx_data_timeout));
304 if (cmd.flags & cpu_to_le16(POWER_FLAGS_LPRX_ENA_MSK))
305 pos += scnprintf(buf+pos, bufsz-pos,
306 "lprx_rssi_threshold = %d\n",
307 le32_to_cpu(cmd.lprx_rssi_threshold));
308 }
309 return pos;
310}
311#endif
312
313const struct iwl_mvm_power_ops pm_legacy_ops = {
314 .power_update_mode = iwl_mvm_power_legacy_update_mode,
315 .power_disable = iwl_mvm_power_legacy_disable,
316#ifdef CONFIG_IWLWIFI_DEBUGFS
317 .power_dbgfs_read = iwl_mvm_power_legacy_dbgfs_read,
318#endif
319};
diff --git a/drivers/net/wireless/iwlwifi/mvm/quota.c b/drivers/net/wireless/iwlwifi/mvm/quota.c
index ce5db6c4ef7e..35e86e06dffd 100644
--- a/drivers/net/wireless/iwlwifi/mvm/quota.c
+++ b/drivers/net/wireless/iwlwifi/mvm/quota.c
@@ -65,9 +65,14 @@
65#include "fw-api.h" 65#include "fw-api.h"
66#include "mvm.h" 66#include "mvm.h"
67 67
68#define QUOTA_100 IWL_MVM_MAX_QUOTA
69#define QUOTA_LOWLAT_MIN ((QUOTA_100 * IWL_MVM_LOWLAT_QUOTA_MIN_PERCENT) / 100)
70
68struct iwl_mvm_quota_iterator_data { 71struct iwl_mvm_quota_iterator_data {
69 int n_interfaces[MAX_BINDINGS]; 72 int n_interfaces[MAX_BINDINGS];
70 int colors[MAX_BINDINGS]; 73 int colors[MAX_BINDINGS];
74 int low_latency[MAX_BINDINGS];
75 int n_low_latency_bindings;
71 struct ieee80211_vif *new_vif; 76 struct ieee80211_vif *new_vif;
72}; 77};
73 78
@@ -107,22 +112,29 @@ static void iwl_mvm_quota_iterator(void *_data, u8 *mac,
107 switch (vif->type) { 112 switch (vif->type) {
108 case NL80211_IFTYPE_STATION: 113 case NL80211_IFTYPE_STATION:
109 if (vif->bss_conf.assoc) 114 if (vif->bss_conf.assoc)
110 data->n_interfaces[id]++; 115 break;
111 break; 116 return;
112 case NL80211_IFTYPE_AP: 117 case NL80211_IFTYPE_AP:
113 case NL80211_IFTYPE_ADHOC: 118 case NL80211_IFTYPE_ADHOC:
114 if (mvmvif->ap_ibss_active) 119 if (mvmvif->ap_ibss_active)
115 data->n_interfaces[id]++; 120 break;
116 break; 121 return;
117 case NL80211_IFTYPE_MONITOR: 122 case NL80211_IFTYPE_MONITOR:
118 if (mvmvif->monitor_active) 123 if (mvmvif->monitor_active)
119 data->n_interfaces[id]++; 124 break;
120 break; 125 return;
121 case NL80211_IFTYPE_P2P_DEVICE: 126 case NL80211_IFTYPE_P2P_DEVICE:
122 break; 127 return;
123 default: 128 default:
124 WARN_ON_ONCE(1); 129 WARN_ON_ONCE(1);
125 break; 130 return;
131 }
132
133 data->n_interfaces[id]++;
134
135 if (iwl_mvm_vif_low_latency(mvmvif) && !data->low_latency[id]) {
136 data->n_low_latency_bindings++;
137 data->low_latency[id] = true;
126 } 138 }
127} 139}
128 140
@@ -162,7 +174,7 @@ static void iwl_mvm_adjust_quota_for_noa(struct iwl_mvm *mvm,
162int iwl_mvm_update_quotas(struct iwl_mvm *mvm, struct ieee80211_vif *newvif) 174int iwl_mvm_update_quotas(struct iwl_mvm *mvm, struct ieee80211_vif *newvif)
163{ 175{
164 struct iwl_time_quota_cmd cmd = {}; 176 struct iwl_time_quota_cmd cmd = {};
165 int i, idx, ret, num_active_macs, quota, quota_rem; 177 int i, idx, ret, num_active_macs, quota, quota_rem, n_non_lowlat;
166 struct iwl_mvm_quota_iterator_data data = { 178 struct iwl_mvm_quota_iterator_data data = {
167 .n_interfaces = {}, 179 .n_interfaces = {},
168 .colors = { -1, -1, -1, -1 }, 180 .colors = { -1, -1, -1, -1 },
@@ -197,11 +209,39 @@ int iwl_mvm_update_quotas(struct iwl_mvm *mvm, struct ieee80211_vif *newvif)
197 num_active_macs += data.n_interfaces[i]; 209 num_active_macs += data.n_interfaces[i];
198 } 210 }
199 211
200 quota = 0; 212 n_non_lowlat = num_active_macs;
201 quota_rem = 0; 213
202 if (num_active_macs) { 214 if (data.n_low_latency_bindings == 1) {
203 quota = IWL_MVM_MAX_QUOTA / num_active_macs; 215 for (i = 0; i < MAX_BINDINGS; i++) {
204 quota_rem = IWL_MVM_MAX_QUOTA % num_active_macs; 216 if (data.low_latency[i]) {
217 n_non_lowlat -= data.n_interfaces[i];
218 break;
219 }
220 }
221 }
222
223 if (data.n_low_latency_bindings == 1 && n_non_lowlat) {
224 /*
225 * Reserve quota for the low latency binding in case that
226 * there are several data bindings but only a single
227 * low latency one. Split the rest of the quota equally
228 * between the other data interfaces.
229 */
230 quota = (QUOTA_100 - QUOTA_LOWLAT_MIN) / n_non_lowlat;
231 quota_rem = QUOTA_100 - n_non_lowlat * quota -
232 QUOTA_LOWLAT_MIN;
233 } else if (num_active_macs) {
234 /*
235 * There are 0 or more than 1 low latency bindings, or all the
236 * data interfaces belong to the single low latency binding.
237 * Split the quota equally between the data interfaces.
238 */
239 quota = QUOTA_100 / num_active_macs;
240 quota_rem = QUOTA_100 % num_active_macs;
241 } else {
242 /* values don't really matter - won't be used */
243 quota = 0;
244 quota_rem = 0;
205 } 245 }
206 246
207 for (idx = 0, i = 0; i < MAX_BINDINGS; i++) { 247 for (idx = 0, i = 0; i < MAX_BINDINGS; i++) {
@@ -211,19 +251,37 @@ int iwl_mvm_update_quotas(struct iwl_mvm *mvm, struct ieee80211_vif *newvif)
211 cmd.quotas[idx].id_and_color = 251 cmd.quotas[idx].id_and_color =
212 cpu_to_le32(FW_CMD_ID_AND_COLOR(i, data.colors[i])); 252 cpu_to_le32(FW_CMD_ID_AND_COLOR(i, data.colors[i]));
213 253
214 if (data.n_interfaces[i] <= 0) { 254 if (data.n_interfaces[i] <= 0)
215 cmd.quotas[idx].quota = cpu_to_le32(0); 255 cmd.quotas[idx].quota = cpu_to_le32(0);
216 cmd.quotas[idx].max_duration = cpu_to_le32(0); 256 else if (data.n_low_latency_bindings == 1 && n_non_lowlat &&
217 } else { 257 data.low_latency[i])
258 /*
259 * There is more than one binding, but only one of the
260 * bindings is in low latency. For this case, allocate
261 * the minimal required quota for the low latency
262 * binding.
263 */
264 cmd.quotas[idx].quota = cpu_to_le32(QUOTA_LOWLAT_MIN);
265 else
218 cmd.quotas[idx].quota = 266 cmd.quotas[idx].quota =
219 cpu_to_le32(quota * data.n_interfaces[i]); 267 cpu_to_le32(quota * data.n_interfaces[i]);
220 cmd.quotas[idx].max_duration = cpu_to_le32(0); 268
221 } 269 WARN_ONCE(le32_to_cpu(cmd.quotas[idx].quota) > QUOTA_100,
270 "Binding=%d, quota=%u > max=%u\n",
271 idx, le32_to_cpu(cmd.quotas[idx].quota), QUOTA_100);
272
273 cmd.quotas[idx].max_duration = cpu_to_le32(0);
274
222 idx++; 275 idx++;
223 } 276 }
224 277
225 /* Give the remainder of the session to the first binding */ 278 /* Give the remainder of the session to the first data binding */
226 le32_add_cpu(&cmd.quotas[0].quota, quota_rem); 279 for (i = 0; i < MAX_BINDINGS; i++) {
280 if (le32_to_cpu(cmd.quotas[i].quota) != 0) {
281 le32_add_cpu(&cmd.quotas[i].quota, quota_rem);
282 break;
283 }
284 }
227 285
228 iwl_mvm_adjust_quota_for_noa(mvm, &cmd); 286 iwl_mvm_adjust_quota_for_noa(mvm, &cmd);
229 287
diff --git a/drivers/net/wireless/iwlwifi/mvm/rs.c b/drivers/net/wireless/iwlwifi/mvm/rs.c
index 6abf74e1351f..568abd61b14f 100644
--- a/drivers/net/wireless/iwlwifi/mvm/rs.c
+++ b/drivers/net/wireless/iwlwifi/mvm/rs.c
@@ -166,7 +166,7 @@ static bool rs_mimo_allow(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
166 if (sta->smps_mode == IEEE80211_SMPS_STATIC) 166 if (sta->smps_mode == IEEE80211_SMPS_STATIC)
167 return false; 167 return false;
168 168
169 if (num_of_ant(iwl_fw_valid_tx_ant(mvm->fw)) < 2) 169 if (num_of_ant(mvm->fw->valid_tx_ant) < 2)
170 return false; 170 return false;
171 171
172 if (!iwl_mvm_bt_coex_is_mimo_allowed(mvm, sta)) 172 if (!iwl_mvm_bt_coex_is_mimo_allowed(mvm, sta))
@@ -211,9 +211,9 @@ static const struct rs_tx_column rs_tx_columns[] = {
211 .next_columns = { 211 .next_columns = {
212 RS_COLUMN_LEGACY_ANT_B, 212 RS_COLUMN_LEGACY_ANT_B,
213 RS_COLUMN_SISO_ANT_A, 213 RS_COLUMN_SISO_ANT_A,
214 RS_COLUMN_SISO_ANT_B,
214 RS_COLUMN_MIMO2, 215 RS_COLUMN_MIMO2,
215 RS_COLUMN_INVALID, 216 RS_COLUMN_MIMO2_SGI,
216 RS_COLUMN_INVALID,
217 }, 217 },
218 }, 218 },
219 [RS_COLUMN_LEGACY_ANT_B] = { 219 [RS_COLUMN_LEGACY_ANT_B] = {
@@ -221,10 +221,10 @@ static const struct rs_tx_column rs_tx_columns[] = {
221 .ant = ANT_B, 221 .ant = ANT_B,
222 .next_columns = { 222 .next_columns = {
223 RS_COLUMN_LEGACY_ANT_A, 223 RS_COLUMN_LEGACY_ANT_A,
224 RS_COLUMN_SISO_ANT_A,
224 RS_COLUMN_SISO_ANT_B, 225 RS_COLUMN_SISO_ANT_B,
225 RS_COLUMN_MIMO2, 226 RS_COLUMN_MIMO2,
226 RS_COLUMN_INVALID, 227 RS_COLUMN_MIMO2_SGI,
227 RS_COLUMN_INVALID,
228 }, 228 },
229 }, 229 },
230 [RS_COLUMN_SISO_ANT_A] = { 230 [RS_COLUMN_SISO_ANT_A] = {
@@ -234,8 +234,8 @@ static const struct rs_tx_column rs_tx_columns[] = {
234 RS_COLUMN_SISO_ANT_B, 234 RS_COLUMN_SISO_ANT_B,
235 RS_COLUMN_MIMO2, 235 RS_COLUMN_MIMO2,
236 RS_COLUMN_SISO_ANT_A_SGI, 236 RS_COLUMN_SISO_ANT_A_SGI,
237 RS_COLUMN_INVALID, 237 RS_COLUMN_SISO_ANT_B_SGI,
238 RS_COLUMN_INVALID, 238 RS_COLUMN_MIMO2_SGI,
239 }, 239 },
240 .checks = { 240 .checks = {
241 rs_siso_allow, 241 rs_siso_allow,
@@ -248,8 +248,8 @@ static const struct rs_tx_column rs_tx_columns[] = {
248 RS_COLUMN_SISO_ANT_A, 248 RS_COLUMN_SISO_ANT_A,
249 RS_COLUMN_MIMO2, 249 RS_COLUMN_MIMO2,
250 RS_COLUMN_SISO_ANT_B_SGI, 250 RS_COLUMN_SISO_ANT_B_SGI,
251 RS_COLUMN_INVALID, 251 RS_COLUMN_SISO_ANT_A_SGI,
252 RS_COLUMN_INVALID, 252 RS_COLUMN_MIMO2_SGI,
253 }, 253 },
254 .checks = { 254 .checks = {
255 rs_siso_allow, 255 rs_siso_allow,
@@ -263,8 +263,8 @@ static const struct rs_tx_column rs_tx_columns[] = {
263 RS_COLUMN_SISO_ANT_B_SGI, 263 RS_COLUMN_SISO_ANT_B_SGI,
264 RS_COLUMN_MIMO2_SGI, 264 RS_COLUMN_MIMO2_SGI,
265 RS_COLUMN_SISO_ANT_A, 265 RS_COLUMN_SISO_ANT_A,
266 RS_COLUMN_INVALID, 266 RS_COLUMN_SISO_ANT_B,
267 RS_COLUMN_INVALID, 267 RS_COLUMN_MIMO2,
268 }, 268 },
269 .checks = { 269 .checks = {
270 rs_siso_allow, 270 rs_siso_allow,
@@ -279,8 +279,8 @@ static const struct rs_tx_column rs_tx_columns[] = {
279 RS_COLUMN_SISO_ANT_A_SGI, 279 RS_COLUMN_SISO_ANT_A_SGI,
280 RS_COLUMN_MIMO2_SGI, 280 RS_COLUMN_MIMO2_SGI,
281 RS_COLUMN_SISO_ANT_B, 281 RS_COLUMN_SISO_ANT_B,
282 RS_COLUMN_INVALID, 282 RS_COLUMN_SISO_ANT_A,
283 RS_COLUMN_INVALID, 283 RS_COLUMN_MIMO2,
284 }, 284 },
285 .checks = { 285 .checks = {
286 rs_siso_allow, 286 rs_siso_allow,
@@ -292,10 +292,10 @@ static const struct rs_tx_column rs_tx_columns[] = {
292 .ant = ANT_AB, 292 .ant = ANT_AB,
293 .next_columns = { 293 .next_columns = {
294 RS_COLUMN_SISO_ANT_A, 294 RS_COLUMN_SISO_ANT_A,
295 RS_COLUMN_SISO_ANT_B,
296 RS_COLUMN_SISO_ANT_A_SGI,
297 RS_COLUMN_SISO_ANT_B_SGI,
295 RS_COLUMN_MIMO2_SGI, 298 RS_COLUMN_MIMO2_SGI,
296 RS_COLUMN_INVALID,
297 RS_COLUMN_INVALID,
298 RS_COLUMN_INVALID,
299 }, 299 },
300 .checks = { 300 .checks = {
301 rs_mimo_allow, 301 rs_mimo_allow,
@@ -307,10 +307,10 @@ static const struct rs_tx_column rs_tx_columns[] = {
307 .sgi = true, 307 .sgi = true,
308 .next_columns = { 308 .next_columns = {
309 RS_COLUMN_SISO_ANT_A_SGI, 309 RS_COLUMN_SISO_ANT_A_SGI,
310 RS_COLUMN_SISO_ANT_B_SGI,
311 RS_COLUMN_SISO_ANT_A,
312 RS_COLUMN_SISO_ANT_B,
310 RS_COLUMN_MIMO2, 313 RS_COLUMN_MIMO2,
311 RS_COLUMN_INVALID,
312 RS_COLUMN_INVALID,
313 RS_COLUMN_INVALID,
314 }, 314 },
315 .checks = { 315 .checks = {
316 rs_mimo_allow, 316 rs_mimo_allow,
@@ -380,49 +380,49 @@ static void rs_stay_in_table(struct iwl_lq_sta *lq_sta, bool force_search);
380 * (2.4 GHz) band. 380 * (2.4 GHz) band.
381 */ 381 */
382 382
383static s32 expected_tpt_legacy[IWL_RATE_COUNT] = { 383static const u16 expected_tpt_legacy[IWL_RATE_COUNT] = {
384 7, 13, 35, 58, 40, 57, 72, 98, 121, 154, 177, 186, 0, 0, 0 384 7, 13, 35, 58, 40, 57, 72, 98, 121, 154, 177, 186, 0, 0, 0
385}; 385};
386 386
387/* Expected TpT tables. 4 indexes: 387/* Expected TpT tables. 4 indexes:
388 * 0 - NGI, 1 - SGI, 2 - AGG+NGI, 3 - AGG+SGI 388 * 0 - NGI, 1 - SGI, 2 - AGG+NGI, 3 - AGG+SGI
389 */ 389 */
390static s32 expected_tpt_siso_20MHz[4][IWL_RATE_COUNT] = { 390static const u16 expected_tpt_siso_20MHz[4][IWL_RATE_COUNT] = {
391 {0, 0, 0, 0, 42, 0, 76, 102, 124, 159, 183, 193, 202, 216, 0}, 391 {0, 0, 0, 0, 42, 0, 76, 102, 124, 159, 183, 193, 202, 216, 0},
392 {0, 0, 0, 0, 46, 0, 82, 110, 132, 168, 192, 202, 210, 225, 0}, 392 {0, 0, 0, 0, 46, 0, 82, 110, 132, 168, 192, 202, 210, 225, 0},
393 {0, 0, 0, 0, 49, 0, 97, 145, 192, 285, 375, 420, 464, 551, 0}, 393 {0, 0, 0, 0, 49, 0, 97, 145, 192, 285, 375, 420, 464, 551, 0},
394 {0, 0, 0, 0, 54, 0, 108, 160, 213, 315, 415, 465, 513, 608, 0}, 394 {0, 0, 0, 0, 54, 0, 108, 160, 213, 315, 415, 465, 513, 608, 0},
395}; 395};
396 396
397static s32 expected_tpt_siso_40MHz[4][IWL_RATE_COUNT] = { 397static const u16 expected_tpt_siso_40MHz[4][IWL_RATE_COUNT] = {
398 {0, 0, 0, 0, 77, 0, 127, 160, 184, 220, 242, 250, 257, 269, 275}, 398 {0, 0, 0, 0, 77, 0, 127, 160, 184, 220, 242, 250, 257, 269, 275},
399 {0, 0, 0, 0, 83, 0, 135, 169, 193, 229, 250, 257, 264, 275, 280}, 399 {0, 0, 0, 0, 83, 0, 135, 169, 193, 229, 250, 257, 264, 275, 280},
400 {0, 0, 0, 0, 101, 0, 199, 295, 389, 570, 744, 828, 911, 1070, 1173}, 400 {0, 0, 0, 0, 101, 0, 199, 295, 389, 570, 744, 828, 911, 1070, 1173},
401 {0, 0, 0, 0, 112, 0, 220, 326, 429, 629, 819, 912, 1000, 1173, 1284}, 401 {0, 0, 0, 0, 112, 0, 220, 326, 429, 629, 819, 912, 1000, 1173, 1284},
402}; 402};
403 403
404static s32 expected_tpt_siso_80MHz[4][IWL_RATE_COUNT] = { 404static const u16 expected_tpt_siso_80MHz[4][IWL_RATE_COUNT] = {
405 {0, 0, 0, 0, 130, 0, 191, 223, 244, 273, 288, 294, 298, 305, 308}, 405 {0, 0, 0, 0, 130, 0, 191, 223, 244, 273, 288, 294, 298, 305, 308},
406 {0, 0, 0, 0, 138, 0, 200, 231, 251, 279, 293, 298, 302, 308, 312}, 406 {0, 0, 0, 0, 138, 0, 200, 231, 251, 279, 293, 298, 302, 308, 312},
407 {0, 0, 0, 0, 217, 0, 429, 634, 834, 1220, 1585, 1760, 1931, 2258, 2466}, 407 {0, 0, 0, 0, 217, 0, 429, 634, 834, 1220, 1585, 1760, 1931, 2258, 2466},
408 {0, 0, 0, 0, 241, 0, 475, 701, 921, 1343, 1741, 1931, 2117, 2468, 2691}, 408 {0, 0, 0, 0, 241, 0, 475, 701, 921, 1343, 1741, 1931, 2117, 2468, 2691},
409}; 409};
410 410
411static s32 expected_tpt_mimo2_20MHz[4][IWL_RATE_COUNT] = { 411static const u16 expected_tpt_mimo2_20MHz[4][IWL_RATE_COUNT] = {
412 {0, 0, 0, 0, 74, 0, 123, 155, 179, 213, 235, 243, 250, 261, 0}, 412 {0, 0, 0, 0, 74, 0, 123, 155, 179, 213, 235, 243, 250, 261, 0},
413 {0, 0, 0, 0, 81, 0, 131, 164, 187, 221, 242, 250, 256, 267, 0}, 413 {0, 0, 0, 0, 81, 0, 131, 164, 187, 221, 242, 250, 256, 267, 0},
414 {0, 0, 0, 0, 98, 0, 193, 286, 375, 550, 718, 799, 878, 1032, 0}, 414 {0, 0, 0, 0, 98, 0, 193, 286, 375, 550, 718, 799, 878, 1032, 0},
415 {0, 0, 0, 0, 109, 0, 214, 316, 414, 607, 790, 879, 965, 1132, 0}, 415 {0, 0, 0, 0, 109, 0, 214, 316, 414, 607, 790, 879, 965, 1132, 0},
416}; 416};
417 417
418static s32 expected_tpt_mimo2_40MHz[4][IWL_RATE_COUNT] = { 418static const u16 expected_tpt_mimo2_40MHz[4][IWL_RATE_COUNT] = {
419 {0, 0, 0, 0, 123, 0, 182, 214, 235, 264, 279, 285, 289, 296, 300}, 419 {0, 0, 0, 0, 123, 0, 182, 214, 235, 264, 279, 285, 289, 296, 300},
420 {0, 0, 0, 0, 131, 0, 191, 222, 242, 270, 284, 289, 293, 300, 303}, 420 {0, 0, 0, 0, 131, 0, 191, 222, 242, 270, 284, 289, 293, 300, 303},
421 {0, 0, 0, 0, 200, 0, 390, 571, 741, 1067, 1365, 1505, 1640, 1894, 2053}, 421 {0, 0, 0, 0, 200, 0, 390, 571, 741, 1067, 1365, 1505, 1640, 1894, 2053},
422 {0, 0, 0, 0, 221, 0, 430, 630, 816, 1169, 1490, 1641, 1784, 2053, 2221}, 422 {0, 0, 0, 0, 221, 0, 430, 630, 816, 1169, 1490, 1641, 1784, 2053, 2221},
423}; 423};
424 424
425static s32 expected_tpt_mimo2_80MHz[4][IWL_RATE_COUNT] = { 425static const u16 expected_tpt_mimo2_80MHz[4][IWL_RATE_COUNT] = {
426 {0, 0, 0, 0, 182, 0, 240, 264, 278, 299, 308, 311, 313, 317, 319}, 426 {0, 0, 0, 0, 182, 0, 240, 264, 278, 299, 308, 311, 313, 317, 319},
427 {0, 0, 0, 0, 190, 0, 247, 269, 282, 302, 310, 313, 315, 319, 320}, 427 {0, 0, 0, 0, 190, 0, 247, 269, 282, 302, 310, 313, 315, 319, 320},
428 {0, 0, 0, 0, 428, 0, 833, 1215, 1577, 2254, 2863, 3147, 3418, 3913, 4219}, 428 {0, 0, 0, 0, 428, 0, 833, 1215, 1577, 2254, 2863, 3147, 3418, 3913, 4219},
@@ -503,6 +503,14 @@ static void rs_rate_scale_clear_window(struct iwl_rate_scale_data *window)
503 window->average_tpt = IWL_INVALID_VALUE; 503 window->average_tpt = IWL_INVALID_VALUE;
504} 504}
505 505
506static void rs_rate_scale_clear_tbl_windows(struct iwl_scale_tbl_info *tbl)
507{
508 int i;
509
510 for (i = 0; i < IWL_RATE_COUNT; i++)
511 rs_rate_scale_clear_window(&tbl->win[i]);
512}
513
506static inline u8 rs_is_valid_ant(u8 valid_antenna, u8 ant_type) 514static inline u8 rs_is_valid_ant(u8 valid_antenna, u8 ant_type)
507{ 515{
508 return (ant_type & valid_antenna) == ant_type; 516 return (ant_type & valid_antenna) == ant_type;
@@ -566,19 +574,13 @@ static s32 get_expected_tpt(struct iwl_scale_tbl_info *tbl, int rs_index)
566 * at this rate. window->data contains the bitmask of successful 574 * at this rate. window->data contains the bitmask of successful
567 * packets. 575 * packets.
568 */ 576 */
569static int rs_collect_tx_data(struct iwl_scale_tbl_info *tbl, 577static int _rs_collect_tx_data(struct iwl_scale_tbl_info *tbl,
570 int scale_index, int attempts, int successes) 578 int scale_index, int attempts, int successes,
579 struct iwl_rate_scale_data *window)
571{ 580{
572 struct iwl_rate_scale_data *window = NULL;
573 static const u64 mask = (((u64)1) << (IWL_RATE_MAX_WINDOW - 1)); 581 static const u64 mask = (((u64)1) << (IWL_RATE_MAX_WINDOW - 1));
574 s32 fail_count, tpt; 582 s32 fail_count, tpt;
575 583
576 if (scale_index < 0 || scale_index >= IWL_RATE_COUNT)
577 return -EINVAL;
578
579 /* Select window for current tx bit rate */
580 window = &(tbl->win[scale_index]);
581
582 /* Get expected throughput */ 584 /* Get expected throughput */
583 tpt = get_expected_tpt(tbl, scale_index); 585 tpt = get_expected_tpt(tbl, scale_index);
584 586
@@ -636,6 +638,21 @@ static int rs_collect_tx_data(struct iwl_scale_tbl_info *tbl,
636 return 0; 638 return 0;
637} 639}
638 640
641static int rs_collect_tx_data(struct iwl_scale_tbl_info *tbl,
642 int scale_index, int attempts, int successes)
643{
644 struct iwl_rate_scale_data *window = NULL;
645
646 if (scale_index < 0 || scale_index >= IWL_RATE_COUNT)
647 return -EINVAL;
648
649 /* Select window for current tx bit rate */
650 window = &(tbl->win[scale_index]);
651
652 return _rs_collect_tx_data(tbl, scale_index, attempts, successes,
653 window);
654}
655
639/* Convert rs_rate object into ucode rate bitmask */ 656/* Convert rs_rate object into ucode rate bitmask */
640static u32 ucode_rate_from_rs_rate(struct iwl_mvm *mvm, 657static u32 ucode_rate_from_rs_rate(struct iwl_mvm *mvm,
641 struct rs_rate *rate) 658 struct rs_rate *rate)
@@ -905,7 +922,7 @@ static void rs_get_lower_rate_down_column(struct iwl_lq_sta *lq_sta,
905 922
906 rate->bw = RATE_MCS_CHAN_WIDTH_20; 923 rate->bw = RATE_MCS_CHAN_WIDTH_20;
907 924
908 WARN_ON_ONCE(rate->index < IWL_RATE_MCS_0_INDEX && 925 WARN_ON_ONCE(rate->index < IWL_RATE_MCS_0_INDEX ||
909 rate->index > IWL_RATE_MCS_9_INDEX); 926 rate->index > IWL_RATE_MCS_9_INDEX);
910 927
911 rate->index = rs_ht_to_legacy[rate->index]; 928 rate->index = rs_ht_to_legacy[rate->index];
@@ -917,7 +934,7 @@ static void rs_get_lower_rate_down_column(struct iwl_lq_sta *lq_sta,
917 934
918 935
919 if (num_of_ant(rate->ant) > 1) 936 if (num_of_ant(rate->ant) > 1)
920 rate->ant = first_antenna(iwl_fw_valid_tx_ant(mvm->fw)); 937 rate->ant = first_antenna(mvm->fw->valid_tx_ant);
921 938
922 /* Relevant in both switching to SISO or Legacy */ 939 /* Relevant in both switching to SISO or Legacy */
923 rate->sgi = false; 940 rate->sgi = false;
@@ -1169,12 +1186,12 @@ static void rs_set_stay_in_table(struct iwl_mvm *mvm, u8 is_legacy,
1169 lq_sta->visited_columns = 0; 1186 lq_sta->visited_columns = 0;
1170} 1187}
1171 1188
1172static s32 *rs_get_expected_tpt_table(struct iwl_lq_sta *lq_sta, 1189static const u16 *rs_get_expected_tpt_table(struct iwl_lq_sta *lq_sta,
1173 const struct rs_tx_column *column, 1190 const struct rs_tx_column *column,
1174 u32 bw) 1191 u32 bw)
1175{ 1192{
1176 /* Used to choose among HT tables */ 1193 /* Used to choose among HT tables */
1177 s32 (*ht_tbl_pointer)[IWL_RATE_COUNT]; 1194 const u16 (*ht_tbl_pointer)[IWL_RATE_COUNT];
1178 1195
1179 if (WARN_ON_ONCE(column->mode != RS_LEGACY && 1196 if (WARN_ON_ONCE(column->mode != RS_LEGACY &&
1180 column->mode != RS_SISO && 1197 column->mode != RS_SISO &&
@@ -1262,9 +1279,8 @@ static s32 rs_get_best_rate(struct iwl_mvm *mvm,
1262 &(lq_sta->lq_info[lq_sta->active_tbl]); 1279 &(lq_sta->lq_info[lq_sta->active_tbl]);
1263 s32 active_sr = active_tbl->win[index].success_ratio; 1280 s32 active_sr = active_tbl->win[index].success_ratio;
1264 s32 active_tpt = active_tbl->expected_tpt[index]; 1281 s32 active_tpt = active_tbl->expected_tpt[index];
1265
1266 /* expected "search" throughput */ 1282 /* expected "search" throughput */
1267 s32 *tpt_tbl = tbl->expected_tpt; 1283 const u16 *tpt_tbl = tbl->expected_tpt;
1268 1284
1269 s32 new_rate, high, low, start_hi; 1285 s32 new_rate, high, low, start_hi;
1270 u16 high_low; 1286 u16 high_low;
@@ -1362,7 +1378,6 @@ static u32 rs_bw_from_sta_bw(struct ieee80211_sta *sta)
1362static void rs_stay_in_table(struct iwl_lq_sta *lq_sta, bool force_search) 1378static void rs_stay_in_table(struct iwl_lq_sta *lq_sta, bool force_search)
1363{ 1379{
1364 struct iwl_scale_tbl_info *tbl; 1380 struct iwl_scale_tbl_info *tbl;
1365 int i;
1366 int active_tbl; 1381 int active_tbl;
1367 int flush_interval_passed = 0; 1382 int flush_interval_passed = 0;
1368 struct iwl_mvm *mvm; 1383 struct iwl_mvm *mvm;
@@ -1423,9 +1438,7 @@ static void rs_stay_in_table(struct iwl_lq_sta *lq_sta, bool force_search)
1423 1438
1424 IWL_DEBUG_RATE(mvm, 1439 IWL_DEBUG_RATE(mvm,
1425 "LQ: stay in table clear win\n"); 1440 "LQ: stay in table clear win\n");
1426 for (i = 0; i < IWL_RATE_COUNT; i++) 1441 rs_rate_scale_clear_tbl_windows(tbl);
1427 rs_rate_scale_clear_window(
1428 &(tbl->win[i]));
1429 } 1442 }
1430 } 1443 }
1431 1444
@@ -1434,8 +1447,7 @@ static void rs_stay_in_table(struct iwl_lq_sta *lq_sta, bool force_search)
1434 * "search" table). */ 1447 * "search" table). */
1435 if (lq_sta->rs_state == RS_STATE_SEARCH_CYCLE_STARTED) { 1448 if (lq_sta->rs_state == RS_STATE_SEARCH_CYCLE_STARTED) {
1436 IWL_DEBUG_RATE(mvm, "Clearing up window stats\n"); 1449 IWL_DEBUG_RATE(mvm, "Clearing up window stats\n");
1437 for (i = 0; i < IWL_RATE_COUNT; i++) 1450 rs_rate_scale_clear_tbl_windows(tbl);
1438 rs_rate_scale_clear_window(&(tbl->win[i]));
1439 } 1451 }
1440 } 1452 }
1441} 1453}
@@ -1478,8 +1490,8 @@ static enum rs_column rs_get_next_column(struct iwl_mvm *mvm,
1478 const struct rs_tx_column *curr_col = &rs_tx_columns[tbl->column]; 1490 const struct rs_tx_column *curr_col = &rs_tx_columns[tbl->column];
1479 const struct rs_tx_column *next_col; 1491 const struct rs_tx_column *next_col;
1480 allow_column_func_t allow_func; 1492 allow_column_func_t allow_func;
1481 u8 valid_ants = iwl_fw_valid_tx_ant(mvm->fw); 1493 u8 valid_ants = mvm->fw->valid_tx_ant;
1482 s32 *expected_tpt_tbl; 1494 const u16 *expected_tpt_tbl;
1483 s32 tpt, max_expected_tpt; 1495 s32 tpt, max_expected_tpt;
1484 1496
1485 for (i = 0; i < MAX_NEXT_COLUMNS; i++) { 1497 for (i = 0; i < MAX_NEXT_COLUMNS; i++) {
@@ -1725,7 +1737,6 @@ static void rs_rate_scale_perform(struct iwl_mvm *mvm,
1725 int low = IWL_RATE_INVALID; 1737 int low = IWL_RATE_INVALID;
1726 int high = IWL_RATE_INVALID; 1738 int high = IWL_RATE_INVALID;
1727 int index; 1739 int index;
1728 int i;
1729 struct iwl_rate_scale_data *window = NULL; 1740 struct iwl_rate_scale_data *window = NULL;
1730 int current_tpt = IWL_INVALID_VALUE; 1741 int current_tpt = IWL_INVALID_VALUE;
1731 int low_tpt = IWL_INVALID_VALUE; 1742 int low_tpt = IWL_INVALID_VALUE;
@@ -2010,8 +2021,7 @@ lq_update:
2010 if (lq_sta->search_better_tbl) { 2021 if (lq_sta->search_better_tbl) {
2011 /* Access the "search" table, clear its history. */ 2022 /* Access the "search" table, clear its history. */
2012 tbl = &(lq_sta->lq_info[(1 - lq_sta->active_tbl)]); 2023 tbl = &(lq_sta->lq_info[(1 - lq_sta->active_tbl)]);
2013 for (i = 0; i < IWL_RATE_COUNT; i++) 2024 rs_rate_scale_clear_tbl_windows(tbl);
2014 rs_rate_scale_clear_window(&(tbl->win[i]));
2015 2025
2016 /* Use new "search" start rate */ 2026 /* Use new "search" start rate */
2017 index = tbl->rate.index; 2027 index = tbl->rate.index;
@@ -2090,7 +2100,7 @@ static void rs_initialize_lq(struct iwl_mvm *mvm,
2090 2100
2091 i = lq_sta->last_txrate_idx; 2101 i = lq_sta->last_txrate_idx;
2092 2102
2093 valid_tx_ant = iwl_fw_valid_tx_ant(mvm->fw); 2103 valid_tx_ant = mvm->fw->valid_tx_ant;
2094 2104
2095 if (!lq_sta->search_better_tbl) 2105 if (!lq_sta->search_better_tbl)
2096 active_tbl = lq_sta->active_tbl; 2106 active_tbl = lq_sta->active_tbl;
@@ -2241,6 +2251,73 @@ static void rs_vht_set_enabled_rates(struct ieee80211_sta *sta,
2241 } 2251 }
2242} 2252}
2243 2253
2254#ifdef CONFIG_IWLWIFI_DEBUGFS
2255static void iwl_mvm_reset_frame_stats(struct iwl_mvm *mvm,
2256 struct iwl_mvm_frame_stats *stats)
2257{
2258 spin_lock_bh(&mvm->drv_stats_lock);
2259 memset(stats, 0, sizeof(*stats));
2260 spin_unlock_bh(&mvm->drv_stats_lock);
2261}
2262
2263void iwl_mvm_update_frame_stats(struct iwl_mvm *mvm,
2264 struct iwl_mvm_frame_stats *stats,
2265 u32 rate, bool agg)
2266{
2267 u8 nss = 0, mcs = 0;
2268
2269 spin_lock(&mvm->drv_stats_lock);
2270
2271 if (agg)
2272 stats->agg_frames++;
2273
2274 stats->success_frames++;
2275
2276 switch (rate & RATE_MCS_CHAN_WIDTH_MSK) {
2277 case RATE_MCS_CHAN_WIDTH_20:
2278 stats->bw_20_frames++;
2279 break;
2280 case RATE_MCS_CHAN_WIDTH_40:
2281 stats->bw_40_frames++;
2282 break;
2283 case RATE_MCS_CHAN_WIDTH_80:
2284 stats->bw_80_frames++;
2285 break;
2286 default:
2287 WARN_ONCE(1, "bad BW. rate 0x%x", rate);
2288 }
2289
2290 if (rate & RATE_MCS_HT_MSK) {
2291 stats->ht_frames++;
2292 mcs = rate & RATE_HT_MCS_RATE_CODE_MSK;
2293 nss = ((rate & RATE_HT_MCS_NSS_MSK) >> RATE_HT_MCS_NSS_POS) + 1;
2294 } else if (rate & RATE_MCS_VHT_MSK) {
2295 stats->vht_frames++;
2296 mcs = rate & RATE_VHT_MCS_RATE_CODE_MSK;
2297 nss = ((rate & RATE_VHT_MCS_NSS_MSK) >>
2298 RATE_VHT_MCS_NSS_POS) + 1;
2299 } else {
2300 stats->legacy_frames++;
2301 }
2302
2303 if (nss == 1)
2304 stats->siso_frames++;
2305 else if (nss == 2)
2306 stats->mimo2_frames++;
2307
2308 if (rate & RATE_MCS_SGI_MSK)
2309 stats->sgi_frames++;
2310 else
2311 stats->ngi_frames++;
2312
2313 stats->last_rates[stats->last_frame_idx] = rate;
2314 stats->last_frame_idx = (stats->last_frame_idx + 1) %
2315 ARRAY_SIZE(stats->last_rates);
2316
2317 spin_unlock(&mvm->drv_stats_lock);
2318}
2319#endif
2320
2244/* 2321/*
2245 * Called after adding a new station to initialize rate scaling 2322 * Called after adding a new station to initialize rate scaling
2246 */ 2323 */
@@ -2265,8 +2342,7 @@ void iwl_mvm_rs_rate_init(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
2265 lq_sta->lq.sta_id = sta_priv->sta_id; 2342 lq_sta->lq.sta_id = sta_priv->sta_id;
2266 2343
2267 for (j = 0; j < LQ_SIZE; j++) 2344 for (j = 0; j < LQ_SIZE; j++)
2268 for (i = 0; i < IWL_RATE_COUNT; i++) 2345 rs_rate_scale_clear_tbl_windows(&lq_sta->lq_info[j]);
2269 rs_rate_scale_clear_window(&lq_sta->lq_info[j].win[i]);
2270 2346
2271 lq_sta->flush_timer = 0; 2347 lq_sta->flush_timer = 0;
2272 2348
@@ -2320,7 +2396,7 @@ void iwl_mvm_rs_rate_init(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
2320 2396
2321 /* These values will be overridden later */ 2397 /* These values will be overridden later */
2322 lq_sta->lq.single_stream_ant_msk = 2398 lq_sta->lq.single_stream_ant_msk =
2323 first_antenna(iwl_fw_valid_tx_ant(mvm->fw)); 2399 first_antenna(mvm->fw->valid_tx_ant);
2324 lq_sta->lq.dual_stream_ant_msk = ANT_AB; 2400 lq_sta->lq.dual_stream_ant_msk = ANT_AB;
2325 2401
2326 /* as default allow aggregation for all tids */ 2402 /* as default allow aggregation for all tids */
@@ -2335,7 +2411,9 @@ void iwl_mvm_rs_rate_init(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
2335#ifdef CONFIG_MAC80211_DEBUGFS 2411#ifdef CONFIG_MAC80211_DEBUGFS
2336 lq_sta->dbg_fixed_rate = 0; 2412 lq_sta->dbg_fixed_rate = 0;
2337#endif 2413#endif
2338 2414#ifdef CONFIG_IWLWIFI_DEBUGFS
2415 iwl_mvm_reset_frame_stats(mvm, &mvm->drv_rx_stats);
2416#endif
2339 rs_initialize_lq(mvm, sta, lq_sta, band, init); 2417 rs_initialize_lq(mvm, sta, lq_sta, band, init);
2340} 2418}
2341 2419
@@ -2446,7 +2524,7 @@ static void rs_build_rates_table(struct iwl_mvm *mvm,
2446 2524
2447 memcpy(&rate, initial_rate, sizeof(rate)); 2525 memcpy(&rate, initial_rate, sizeof(rate));
2448 2526
2449 valid_tx_ant = iwl_fw_valid_tx_ant(mvm->fw); 2527 valid_tx_ant = mvm->fw->valid_tx_ant;
2450 2528
2451 if (is_siso(&rate)) { 2529 if (is_siso(&rate)) {
2452 num_rates = RS_INITIAL_SISO_NUM_RATES; 2530 num_rates = RS_INITIAL_SISO_NUM_RATES;
@@ -2523,7 +2601,7 @@ static void rs_fill_lq_cmd(struct iwl_mvm *mvm,
2523 2601
2524 if (sta) 2602 if (sta)
2525 lq_cmd->agg_time_limit = 2603 lq_cmd->agg_time_limit =
2526 cpu_to_le16(iwl_mvm_bt_coex_agg_time_limit(mvm, sta)); 2604 cpu_to_le16(iwl_mvm_coex_agg_time_limit(mvm, sta));
2527} 2605}
2528 2606
2529static void *rs_alloc(struct ieee80211_hw *hw, struct dentry *debugfsdir) 2607static void *rs_alloc(struct ieee80211_hw *hw, struct dentry *debugfsdir)
@@ -2547,7 +2625,7 @@ static void rs_free_sta(void *mvm_r, struct ieee80211_sta *sta,
2547} 2625}
2548 2626
2549#ifdef CONFIG_MAC80211_DEBUGFS 2627#ifdef CONFIG_MAC80211_DEBUGFS
2550static int rs_pretty_print_rate(char *buf, const u32 rate) 2628int rs_pretty_print_rate(char *buf, const u32 rate)
2551{ 2629{
2552 2630
2553 char *type, *bw; 2631 char *type, *bw;
@@ -2596,7 +2674,7 @@ static int rs_pretty_print_rate(char *buf, const u32 rate)
2596 return sprintf(buf, "%s | ANT: %s BW: %s MCS: %d NSS: %d %s%s%s%s%s\n", 2674 return sprintf(buf, "%s | ANT: %s BW: %s MCS: %d NSS: %d %s%s%s%s%s\n",
2597 type, rs_pretty_ant(ant), bw, mcs, nss, 2675 type, rs_pretty_ant(ant), bw, mcs, nss,
2598 (rate & RATE_MCS_SGI_MSK) ? "SGI " : "NGI ", 2676 (rate & RATE_MCS_SGI_MSK) ? "SGI " : "NGI ",
2599 (rate & RATE_MCS_STBC_MSK) ? "STBC " : "", 2677 (rate & RATE_MCS_HT_STBC_MSK) ? "STBC " : "",
2600 (rate & RATE_MCS_LDPC_MSK) ? "LDPC " : "", 2678 (rate & RATE_MCS_LDPC_MSK) ? "LDPC " : "",
2601 (rate & RATE_MCS_BF_MSK) ? "BF " : "", 2679 (rate & RATE_MCS_BF_MSK) ? "BF " : "",
2602 (rate & RATE_MCS_ZLF_MSK) ? "ZLF " : ""); 2680 (rate & RATE_MCS_ZLF_MSK) ? "ZLF " : "");
@@ -2677,9 +2755,9 @@ static ssize_t rs_sta_dbgfs_scale_table_read(struct file *file,
2677 desc += sprintf(buff+desc, "fixed rate 0x%X\n", 2755 desc += sprintf(buff+desc, "fixed rate 0x%X\n",
2678 lq_sta->dbg_fixed_rate); 2756 lq_sta->dbg_fixed_rate);
2679 desc += sprintf(buff+desc, "valid_tx_ant %s%s%s\n", 2757 desc += sprintf(buff+desc, "valid_tx_ant %s%s%s\n",
2680 (iwl_fw_valid_tx_ant(mvm->fw) & ANT_A) ? "ANT_A," : "", 2758 (mvm->fw->valid_tx_ant & ANT_A) ? "ANT_A," : "",
2681 (iwl_fw_valid_tx_ant(mvm->fw) & ANT_B) ? "ANT_B," : "", 2759 (mvm->fw->valid_tx_ant & ANT_B) ? "ANT_B," : "",
2682 (iwl_fw_valid_tx_ant(mvm->fw) & ANT_C) ? "ANT_C" : ""); 2760 (mvm->fw->valid_tx_ant & ANT_C) ? "ANT_C" : "");
2683 desc += sprintf(buff+desc, "lq type %s\n", 2761 desc += sprintf(buff+desc, "lq type %s\n",
2684 (is_legacy(rate)) ? "legacy" : 2762 (is_legacy(rate)) ? "legacy" :
2685 is_vht(rate) ? "VHT" : "HT"); 2763 is_vht(rate) ? "VHT" : "HT");
@@ -2815,8 +2893,8 @@ static void rs_rate_init_stub(void *mvm_r,
2815 struct ieee80211_sta *sta, void *mvm_sta) 2893 struct ieee80211_sta *sta, void *mvm_sta)
2816{ 2894{
2817} 2895}
2818static struct rate_control_ops rs_mvm_ops = { 2896
2819 .module = NULL, 2897static const struct rate_control_ops rs_mvm_ops = {
2820 .name = RS_NAME, 2898 .name = RS_NAME,
2821 .tx_status = rs_tx_status, 2899 .tx_status = rs_tx_status,
2822 .get_rate = rs_get_rate, 2900 .get_rate = rs_get_rate,
diff --git a/drivers/net/wireless/iwlwifi/mvm/rs.h b/drivers/net/wireless/iwlwifi/mvm/rs.h
index 7bc6404f6986..3332b396011e 100644
--- a/drivers/net/wireless/iwlwifi/mvm/rs.h
+++ b/drivers/net/wireless/iwlwifi/mvm/rs.h
@@ -277,7 +277,7 @@ enum rs_column {
277struct iwl_scale_tbl_info { 277struct iwl_scale_tbl_info {
278 struct rs_rate rate; 278 struct rs_rate rate;
279 enum rs_column column; 279 enum rs_column column;
280 s32 *expected_tpt; /* throughput metrics; expected_tpt_G, etc. */ 280 const u16 *expected_tpt; /* throughput metrics; expected_tpt_G, etc. */
281 struct iwl_rate_scale_data win[IWL_RATE_COUNT]; /* rate histories */ 281 struct iwl_rate_scale_data win[IWL_RATE_COUNT]; /* rate histories */
282}; 282};
283 283
diff --git a/drivers/net/wireless/iwlwifi/mvm/rx.c b/drivers/net/wireless/iwlwifi/mvm/rx.c
index a85b60f7e67e..6061553a5e44 100644
--- a/drivers/net/wireless/iwlwifi/mvm/rx.c
+++ b/drivers/net/wireless/iwlwifi/mvm/rx.c
@@ -77,6 +77,15 @@ int iwl_mvm_rx_rx_phy_cmd(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
77 77
78 memcpy(&mvm->last_phy_info, pkt->data, sizeof(mvm->last_phy_info)); 78 memcpy(&mvm->last_phy_info, pkt->data, sizeof(mvm->last_phy_info));
79 mvm->ampdu_ref++; 79 mvm->ampdu_ref++;
80
81#ifdef CONFIG_IWLWIFI_DEBUGFS
82 if (mvm->last_phy_info.phy_flags & cpu_to_le16(RX_RES_PHY_FLAGS_AGG)) {
83 spin_lock(&mvm->drv_stats_lock);
84 mvm->drv_rx_stats.ampdu_count++;
85 spin_unlock(&mvm->drv_stats_lock);
86 }
87#endif
88
80 return 0; 89 return 0;
81} 90}
82 91
@@ -129,22 +138,16 @@ static void iwl_mvm_calc_rssi(struct iwl_mvm *mvm,
129 struct ieee80211_rx_status *rx_status) 138 struct ieee80211_rx_status *rx_status)
130{ 139{
131 int rssi_a, rssi_b, rssi_a_dbm, rssi_b_dbm, max_rssi_dbm; 140 int rssi_a, rssi_b, rssi_a_dbm, rssi_b_dbm, max_rssi_dbm;
132 int rssi_all_band_a, rssi_all_band_b; 141 u32 agc_a, agc_b;
133 u32 agc_a, agc_b, max_agc;
134 u32 val; 142 u32 val;
135 143
136 val = le32_to_cpu(phy_info->non_cfg_phy[IWL_RX_INFO_AGC_IDX]); 144 val = le32_to_cpu(phy_info->non_cfg_phy[IWL_RX_INFO_AGC_IDX]);
137 agc_a = (val & IWL_OFDM_AGC_A_MSK) >> IWL_OFDM_AGC_A_POS; 145 agc_a = (val & IWL_OFDM_AGC_A_MSK) >> IWL_OFDM_AGC_A_POS;
138 agc_b = (val & IWL_OFDM_AGC_B_MSK) >> IWL_OFDM_AGC_B_POS; 146 agc_b = (val & IWL_OFDM_AGC_B_MSK) >> IWL_OFDM_AGC_B_POS;
139 max_agc = max_t(u32, agc_a, agc_b);
140 147
141 val = le32_to_cpu(phy_info->non_cfg_phy[IWL_RX_INFO_RSSI_AB_IDX]); 148 val = le32_to_cpu(phy_info->non_cfg_phy[IWL_RX_INFO_RSSI_AB_IDX]);
142 rssi_a = (val & IWL_OFDM_RSSI_INBAND_A_MSK) >> IWL_OFDM_RSSI_A_POS; 149 rssi_a = (val & IWL_OFDM_RSSI_INBAND_A_MSK) >> IWL_OFDM_RSSI_A_POS;
143 rssi_b = (val & IWL_OFDM_RSSI_INBAND_B_MSK) >> IWL_OFDM_RSSI_B_POS; 150 rssi_b = (val & IWL_OFDM_RSSI_INBAND_B_MSK) >> IWL_OFDM_RSSI_B_POS;
144 rssi_all_band_a = (val & IWL_OFDM_RSSI_ALLBAND_A_MSK) >>
145 IWL_OFDM_RSSI_ALLBAND_A_POS;
146 rssi_all_band_b = (val & IWL_OFDM_RSSI_ALLBAND_B_MSK) >>
147 IWL_OFDM_RSSI_ALLBAND_B_POS;
148 151
149 /* 152 /*
150 * dBm = rssi dB - agc dB - constant. 153 * dBm = rssi dB - agc dB - constant.
@@ -364,31 +367,43 @@ int iwl_mvm_rx_rx_mpdu(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
364 rx_status.flag |= RX_FLAG_40MHZ; 367 rx_status.flag |= RX_FLAG_40MHZ;
365 break; 368 break;
366 case RATE_MCS_CHAN_WIDTH_80: 369 case RATE_MCS_CHAN_WIDTH_80:
367 rx_status.flag |= RX_FLAG_80MHZ; 370 rx_status.vht_flag |= RX_VHT_FLAG_80MHZ;
368 break; 371 break;
369 case RATE_MCS_CHAN_WIDTH_160: 372 case RATE_MCS_CHAN_WIDTH_160:
370 rx_status.flag |= RX_FLAG_160MHZ; 373 rx_status.vht_flag |= RX_VHT_FLAG_160MHZ;
371 break; 374 break;
372 } 375 }
373 if (rate_n_flags & RATE_MCS_SGI_MSK) 376 if (rate_n_flags & RATE_MCS_SGI_MSK)
374 rx_status.flag |= RX_FLAG_SHORT_GI; 377 rx_status.flag |= RX_FLAG_SHORT_GI;
375 if (rate_n_flags & RATE_HT_MCS_GF_MSK) 378 if (rate_n_flags & RATE_HT_MCS_GF_MSK)
376 rx_status.flag |= RX_FLAG_HT_GF; 379 rx_status.flag |= RX_FLAG_HT_GF;
380 if (rate_n_flags & RATE_MCS_LDPC_MSK)
381 rx_status.flag |= RX_FLAG_LDPC;
377 if (rate_n_flags & RATE_MCS_HT_MSK) { 382 if (rate_n_flags & RATE_MCS_HT_MSK) {
383 u8 stbc = (rate_n_flags & RATE_MCS_HT_STBC_MSK) >>
384 RATE_MCS_STBC_POS;
378 rx_status.flag |= RX_FLAG_HT; 385 rx_status.flag |= RX_FLAG_HT;
379 rx_status.rate_idx = rate_n_flags & RATE_HT_MCS_INDEX_MSK; 386 rx_status.rate_idx = rate_n_flags & RATE_HT_MCS_INDEX_MSK;
387 rx_status.flag |= stbc << RX_FLAG_STBC_SHIFT;
380 } else if (rate_n_flags & RATE_MCS_VHT_MSK) { 388 } else if (rate_n_flags & RATE_MCS_VHT_MSK) {
389 u8 stbc = (rate_n_flags & RATE_MCS_VHT_STBC_MSK) >>
390 RATE_MCS_STBC_POS;
381 rx_status.vht_nss = 391 rx_status.vht_nss =
382 ((rate_n_flags & RATE_VHT_MCS_NSS_MSK) >> 392 ((rate_n_flags & RATE_VHT_MCS_NSS_MSK) >>
383 RATE_VHT_MCS_NSS_POS) + 1; 393 RATE_VHT_MCS_NSS_POS) + 1;
384 rx_status.rate_idx = rate_n_flags & RATE_VHT_MCS_RATE_CODE_MSK; 394 rx_status.rate_idx = rate_n_flags & RATE_VHT_MCS_RATE_CODE_MSK;
385 rx_status.flag |= RX_FLAG_VHT; 395 rx_status.flag |= RX_FLAG_VHT;
396 rx_status.flag |= stbc << RX_FLAG_STBC_SHIFT;
386 } else { 397 } else {
387 rx_status.rate_idx = 398 rx_status.rate_idx =
388 iwl_mvm_legacy_rate_to_mac80211_idx(rate_n_flags, 399 iwl_mvm_legacy_rate_to_mac80211_idx(rate_n_flags,
389 rx_status.band); 400 rx_status.band);
390 } 401 }
391 402
403#ifdef CONFIG_IWLWIFI_DEBUGFS
404 iwl_mvm_update_frame_stats(mvm, &mvm->drv_rx_stats, rate_n_flags,
405 rx_status.flag & RX_FLAG_AMPDU_DETAILS);
406#endif
392 iwl_mvm_pass_packet_to_mac80211(mvm, hdr, len, ampdu_status, 407 iwl_mvm_pass_packet_to_mac80211(mvm, hdr, len, ampdu_status,
393 rxb, &rx_status); 408 rxb, &rx_status);
394 return 0; 409 return 0;
diff --git a/drivers/net/wireless/iwlwifi/mvm/scan.c b/drivers/net/wireless/iwlwifi/mvm/scan.c
index 742afc429c94..c91dc8498852 100644
--- a/drivers/net/wireless/iwlwifi/mvm/scan.c
+++ b/drivers/net/wireless/iwlwifi/mvm/scan.c
@@ -70,9 +70,16 @@
70 70
71#define IWL_PLCP_QUIET_THRESH 1 71#define IWL_PLCP_QUIET_THRESH 1
72#define IWL_ACTIVE_QUIET_TIME 10 72#define IWL_ACTIVE_QUIET_TIME 10
73#define LONG_OUT_TIME_PERIOD 600 73
74#define SHORT_OUT_TIME_PERIOD 200 74struct iwl_mvm_scan_params {
75#define SUSPEND_TIME_PERIOD 100 75 u32 max_out_time;
76 u32 suspend_time;
77 bool passive_fragmented;
78 struct _dwell {
79 u16 passive;
80 u16 active;
81 } dwell[IEEE80211_NUM_BANDS];
82};
76 83
77static inline __le16 iwl_mvm_scan_rx_chain(struct iwl_mvm *mvm) 84static inline __le16 iwl_mvm_scan_rx_chain(struct iwl_mvm *mvm)
78{ 85{
@@ -82,7 +89,7 @@ static inline __le16 iwl_mvm_scan_rx_chain(struct iwl_mvm *mvm)
82 if (mvm->scan_rx_ant != ANT_NONE) 89 if (mvm->scan_rx_ant != ANT_NONE)
83 rx_ant = mvm->scan_rx_ant; 90 rx_ant = mvm->scan_rx_ant;
84 else 91 else
85 rx_ant = iwl_fw_valid_rx_ant(mvm->fw); 92 rx_ant = mvm->fw->valid_rx_ant;
86 rx_chain = rx_ant << PHY_RX_CHAIN_VALID_POS; 93 rx_chain = rx_ant << PHY_RX_CHAIN_VALID_POS;
87 rx_chain |= rx_ant << PHY_RX_CHAIN_FORCE_MIMO_SEL_POS; 94 rx_chain |= rx_ant << PHY_RX_CHAIN_FORCE_MIMO_SEL_POS;
88 rx_chain |= rx_ant << PHY_RX_CHAIN_FORCE_SEL_POS; 95 rx_chain |= rx_ant << PHY_RX_CHAIN_FORCE_SEL_POS;
@@ -90,24 +97,6 @@ static inline __le16 iwl_mvm_scan_rx_chain(struct iwl_mvm *mvm)
90 return cpu_to_le16(rx_chain); 97 return cpu_to_le16(rx_chain);
91} 98}
92 99
93static inline __le32 iwl_mvm_scan_max_out_time(struct ieee80211_vif *vif,
94 u32 flags, bool is_assoc)
95{
96 if (!is_assoc)
97 return 0;
98 if (flags & NL80211_SCAN_FLAG_LOW_PRIORITY)
99 return cpu_to_le32(ieee80211_tu_to_usec(SHORT_OUT_TIME_PERIOD));
100 return cpu_to_le32(ieee80211_tu_to_usec(LONG_OUT_TIME_PERIOD));
101}
102
103static inline __le32 iwl_mvm_scan_suspend_time(struct ieee80211_vif *vif,
104 bool is_assoc)
105{
106 if (!is_assoc)
107 return 0;
108 return cpu_to_le32(ieee80211_tu_to_usec(SUSPEND_TIME_PERIOD));
109}
110
111static inline __le32 100static inline __le32
112iwl_mvm_scan_rxon_flags(struct cfg80211_scan_request *req) 101iwl_mvm_scan_rxon_flags(struct cfg80211_scan_request *req)
113{ 102{
@@ -124,7 +113,7 @@ iwl_mvm_scan_rate_n_flags(struct iwl_mvm *mvm, enum ieee80211_band band,
124 u32 tx_ant; 113 u32 tx_ant;
125 114
126 mvm->scan_last_antenna_idx = 115 mvm->scan_last_antenna_idx =
127 iwl_mvm_next_antenna(mvm, iwl_fw_valid_tx_ant(mvm->fw), 116 iwl_mvm_next_antenna(mvm, mvm->fw->valid_tx_ant,
128 mvm->scan_last_antenna_idx); 117 mvm->scan_last_antenna_idx);
129 tx_ant = BIT(mvm->scan_last_antenna_idx) << RATE_MCS_ANT_POS; 118 tx_ant = BIT(mvm->scan_last_antenna_idx) << RATE_MCS_ANT_POS;
130 119
@@ -181,15 +170,14 @@ static u16 iwl_mvm_get_passive_dwell(enum ieee80211_band band)
181 170
182static void iwl_mvm_scan_fill_channels(struct iwl_scan_cmd *cmd, 171static void iwl_mvm_scan_fill_channels(struct iwl_scan_cmd *cmd,
183 struct cfg80211_scan_request *req, 172 struct cfg80211_scan_request *req,
184 bool basic_ssid) 173 bool basic_ssid,
174 struct iwl_mvm_scan_params *params)
185{ 175{
186 u16 passive_dwell = iwl_mvm_get_passive_dwell(req->channels[0]->band);
187 u16 active_dwell = iwl_mvm_get_active_dwell(req->channels[0]->band,
188 req->n_ssids);
189 struct iwl_scan_channel *chan = (struct iwl_scan_channel *) 176 struct iwl_scan_channel *chan = (struct iwl_scan_channel *)
190 (cmd->data + le16_to_cpu(cmd->tx_cmd.len)); 177 (cmd->data + le16_to_cpu(cmd->tx_cmd.len));
191 int i; 178 int i;
192 int type = BIT(req->n_ssids) - 1; 179 int type = BIT(req->n_ssids) - 1;
180 enum ieee80211_band band = req->channels[0]->band;
193 181
194 if (!basic_ssid) 182 if (!basic_ssid)
195 type |= BIT(req->n_ssids); 183 type |= BIT(req->n_ssids);
@@ -199,8 +187,8 @@ static void iwl_mvm_scan_fill_channels(struct iwl_scan_cmd *cmd,
199 chan->type = cpu_to_le32(type); 187 chan->type = cpu_to_le32(type);
200 if (req->channels[i]->flags & IEEE80211_CHAN_NO_IR) 188 if (req->channels[i]->flags & IEEE80211_CHAN_NO_IR)
201 chan->type &= cpu_to_le32(~SCAN_CHANNEL_TYPE_ACTIVE); 189 chan->type &= cpu_to_le32(~SCAN_CHANNEL_TYPE_ACTIVE);
202 chan->active_dwell = cpu_to_le16(active_dwell); 190 chan->active_dwell = cpu_to_le16(params->dwell[band].active);
203 chan->passive_dwell = cpu_to_le16(passive_dwell); 191 chan->passive_dwell = cpu_to_le16(params->dwell[band].passive);
204 chan->iteration_count = cpu_to_le16(1); 192 chan->iteration_count = cpu_to_le16(1);
205 chan++; 193 chan++;
206 } 194 }
@@ -267,13 +255,76 @@ static u16 iwl_mvm_fill_probe_req(struct ieee80211_mgmt *frame, const u8 *ta,
267 return (u16)len; 255 return (u16)len;
268} 256}
269 257
270static void iwl_mvm_vif_assoc_iterator(void *data, u8 *mac, 258static void iwl_mvm_scan_condition_iterator(void *data, u8 *mac,
271 struct ieee80211_vif *vif) 259 struct ieee80211_vif *vif)
272{ 260{
273 bool *is_assoc = data; 261 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
262 bool *global_bound = data;
263
264 if (mvmvif->phy_ctxt && mvmvif->phy_ctxt->id < MAX_PHYS)
265 *global_bound = true;
266}
267
268static void iwl_mvm_scan_calc_params(struct iwl_mvm *mvm,
269 struct ieee80211_vif *vif,
270 int n_ssids,
271 struct iwl_mvm_scan_params *params)
272{
273 bool global_bound = false;
274 enum ieee80211_band band;
275
276 ieee80211_iterate_active_interfaces_atomic(mvm->hw,
277 IEEE80211_IFACE_ITER_NORMAL,
278 iwl_mvm_scan_condition_iterator,
279 &global_bound);
280 /*
281 * Under low latency traffic passive scan is fragmented meaning
282 * that dwell on a particular channel will be fragmented. Each fragment
283 * dwell time is 20ms and fragments period is 105ms. Skipping to next
284 * channel will be delayed by the same period - 105ms. So suspend_time
285 * parameter describing both fragments and channels skipping periods is
286 * set to 105ms. This value is chosen so that overall passive scan
287 * duration will not be too long. Max_out_time in this case is set to
288 * 70ms, so for active scanning operating channel will be left for 70ms
289 * while for passive still for 20ms (fragment dwell).
290 */
291 if (global_bound) {
292 if (!iwl_mvm_low_latency(mvm)) {
293 params->suspend_time = ieee80211_tu_to_usec(100);
294 params->max_out_time = ieee80211_tu_to_usec(600);
295 } else {
296 params->suspend_time = ieee80211_tu_to_usec(105);
297 /* P2P doesn't support fragmented passive scan, so
298 * configure max_out_time to be at least longest dwell
299 * time for passive scan.
300 */
301 if (vif->type == NL80211_IFTYPE_STATION && !vif->p2p) {
302 params->max_out_time = ieee80211_tu_to_usec(70);
303 params->passive_fragmented = true;
304 } else {
305 u32 passive_dwell;
274 306
275 if (vif->bss_conf.assoc) 307 /*
276 *is_assoc = true; 308 * Use band G so that passive channel dwell time
309 * will be assigned with maximum value.
310 */
311 band = IEEE80211_BAND_2GHZ;
312 passive_dwell = iwl_mvm_get_passive_dwell(band);
313 params->max_out_time =
314 ieee80211_tu_to_usec(passive_dwell);
315 }
316 }
317 }
318
319 for (band = IEEE80211_BAND_2GHZ; band < IEEE80211_NUM_BANDS; band++) {
320 if (params->passive_fragmented)
321 params->dwell[band].passive = 20;
322 else
323 params->dwell[band].passive =
324 iwl_mvm_get_passive_dwell(band);
325 params->dwell[band].active = iwl_mvm_get_active_dwell(band,
326 n_ssids);
327 }
277} 328}
278 329
279int iwl_mvm_scan_request(struct iwl_mvm *mvm, 330int iwl_mvm_scan_request(struct iwl_mvm *mvm,
@@ -288,13 +339,13 @@ int iwl_mvm_scan_request(struct iwl_mvm *mvm,
288 .dataflags = { IWL_HCMD_DFL_NOCOPY, }, 339 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
289 }; 340 };
290 struct iwl_scan_cmd *cmd = mvm->scan_cmd; 341 struct iwl_scan_cmd *cmd = mvm->scan_cmd;
291 bool is_assoc = false;
292 int ret; 342 int ret;
293 u32 status; 343 u32 status;
294 int ssid_len = 0; 344 int ssid_len = 0;
295 u8 *ssid = NULL; 345 u8 *ssid = NULL;
296 bool basic_ssid = !(mvm->fw->ucode_capa.flags & 346 bool basic_ssid = !(mvm->fw->ucode_capa.flags &
297 IWL_UCODE_TLV_FLAGS_NO_BASIC_SSID); 347 IWL_UCODE_TLV_FLAGS_NO_BASIC_SSID);
348 struct iwl_mvm_scan_params params = {};
298 349
299 lockdep_assert_held(&mvm->mutex); 350 lockdep_assert_held(&mvm->mutex);
300 BUG_ON(mvm->scan_cmd == NULL); 351 BUG_ON(mvm->scan_cmd == NULL);
@@ -304,17 +355,18 @@ int iwl_mvm_scan_request(struct iwl_mvm *mvm,
304 memset(cmd, 0, sizeof(struct iwl_scan_cmd) + 355 memset(cmd, 0, sizeof(struct iwl_scan_cmd) +
305 mvm->fw->ucode_capa.max_probe_length + 356 mvm->fw->ucode_capa.max_probe_length +
306 (MAX_NUM_SCAN_CHANNELS * sizeof(struct iwl_scan_channel))); 357 (MAX_NUM_SCAN_CHANNELS * sizeof(struct iwl_scan_channel)));
307 ieee80211_iterate_active_interfaces_atomic(mvm->hw, 358
308 IEEE80211_IFACE_ITER_NORMAL,
309 iwl_mvm_vif_assoc_iterator,
310 &is_assoc);
311 cmd->channel_count = (u8)req->n_channels; 359 cmd->channel_count = (u8)req->n_channels;
312 cmd->quiet_time = cpu_to_le16(IWL_ACTIVE_QUIET_TIME); 360 cmd->quiet_time = cpu_to_le16(IWL_ACTIVE_QUIET_TIME);
313 cmd->quiet_plcp_th = cpu_to_le16(IWL_PLCP_QUIET_THRESH); 361 cmd->quiet_plcp_th = cpu_to_le16(IWL_PLCP_QUIET_THRESH);
314 cmd->rxchain_sel_flags = iwl_mvm_scan_rx_chain(mvm); 362 cmd->rxchain_sel_flags = iwl_mvm_scan_rx_chain(mvm);
315 cmd->max_out_time = iwl_mvm_scan_max_out_time(vif, req->flags, 363
316 is_assoc); 364 iwl_mvm_scan_calc_params(mvm, vif, req->n_ssids, &params);
317 cmd->suspend_time = iwl_mvm_scan_suspend_time(vif, is_assoc); 365 cmd->max_out_time = cpu_to_le32(params.max_out_time);
366 cmd->suspend_time = cpu_to_le32(params.suspend_time);
367 if (params.passive_fragmented)
368 cmd->scan_flags |= SCAN_FLAGS_FRAGMENTED_SCAN;
369
318 cmd->rxon_flags = iwl_mvm_scan_rxon_flags(req); 370 cmd->rxon_flags = iwl_mvm_scan_rxon_flags(req);
319 cmd->filter_flags = cpu_to_le32(MAC_FILTER_ACCEPT_GRP | 371 cmd->filter_flags = cpu_to_le32(MAC_FILTER_ACCEPT_GRP |
320 MAC_FILTER_IN_BEACON); 372 MAC_FILTER_IN_BEACON);
@@ -360,7 +412,7 @@ int iwl_mvm_scan_request(struct iwl_mvm *mvm,
360 req->ie, req->ie_len, 412 req->ie, req->ie_len,
361 mvm->fw->ucode_capa.max_probe_length)); 413 mvm->fw->ucode_capa.max_probe_length));
362 414
363 iwl_mvm_scan_fill_channels(cmd, req, basic_ssid); 415 iwl_mvm_scan_fill_channels(cmd, req, basic_ssid, &params);
364 416
365 cmd->len = cpu_to_le16(sizeof(struct iwl_scan_cmd) + 417 cmd->len = cpu_to_le16(sizeof(struct iwl_scan_cmd) +
366 le16_to_cpu(cmd->tx_cmd.len) + 418 le16_to_cpu(cmd->tx_cmd.len) +
@@ -402,12 +454,17 @@ int iwl_mvm_rx_scan_complete(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb,
402 struct iwl_rx_packet *pkt = rxb_addr(rxb); 454 struct iwl_rx_packet *pkt = rxb_addr(rxb);
403 struct iwl_scan_complete_notif *notif = (void *)pkt->data; 455 struct iwl_scan_complete_notif *notif = (void *)pkt->data;
404 456
457 lockdep_assert_held(&mvm->mutex);
458
405 IWL_DEBUG_SCAN(mvm, "Scan complete: status=0x%x scanned channels=%d\n", 459 IWL_DEBUG_SCAN(mvm, "Scan complete: status=0x%x scanned channels=%d\n",
406 notif->status, notif->scanned_channels); 460 notif->status, notif->scanned_channels);
407 461
408 mvm->scan_status = IWL_MVM_SCAN_NONE; 462 if (mvm->scan_status == IWL_MVM_SCAN_OS)
463 mvm->scan_status = IWL_MVM_SCAN_NONE;
409 ieee80211_scan_completed(mvm->hw, notif->status != SCAN_COMP_STATUS_OK); 464 ieee80211_scan_completed(mvm->hw, notif->status != SCAN_COMP_STATUS_OK);
410 465
466 iwl_mvm_unref(mvm, IWL_MVM_REF_SCAN);
467
411 return 0; 468 return 0;
412} 469}
413 470
@@ -464,7 +521,7 @@ static bool iwl_mvm_scan_abort_notif(struct iwl_notif_wait_data *notif_wait,
464 }; 521 };
465} 522}
466 523
467void iwl_mvm_cancel_scan(struct iwl_mvm *mvm) 524int iwl_mvm_cancel_scan(struct iwl_mvm *mvm)
468{ 525{
469 struct iwl_notification_wait wait_scan_abort; 526 struct iwl_notification_wait wait_scan_abort;
470 static const u8 scan_abort_notif[] = { SCAN_ABORT_CMD, 527 static const u8 scan_abort_notif[] = { SCAN_ABORT_CMD,
@@ -472,12 +529,13 @@ void iwl_mvm_cancel_scan(struct iwl_mvm *mvm)
472 int ret; 529 int ret;
473 530
474 if (mvm->scan_status == IWL_MVM_SCAN_NONE) 531 if (mvm->scan_status == IWL_MVM_SCAN_NONE)
475 return; 532 return 0;
476 533
477 if (iwl_mvm_is_radio_killed(mvm)) { 534 if (iwl_mvm_is_radio_killed(mvm)) {
478 ieee80211_scan_completed(mvm->hw, true); 535 ieee80211_scan_completed(mvm->hw, true);
536 iwl_mvm_unref(mvm, IWL_MVM_REF_SCAN);
479 mvm->scan_status = IWL_MVM_SCAN_NONE; 537 mvm->scan_status = IWL_MVM_SCAN_NONE;
480 return; 538 return 0;
481 } 539 }
482 540
483 iwl_init_notification_wait(&mvm->notif_wait, &wait_scan_abort, 541 iwl_init_notification_wait(&mvm->notif_wait, &wait_scan_abort,
@@ -488,18 +546,15 @@ void iwl_mvm_cancel_scan(struct iwl_mvm *mvm)
488 ret = iwl_mvm_send_cmd_pdu(mvm, SCAN_ABORT_CMD, CMD_SYNC, 0, NULL); 546 ret = iwl_mvm_send_cmd_pdu(mvm, SCAN_ABORT_CMD, CMD_SYNC, 0, NULL);
489 if (ret) { 547 if (ret) {
490 IWL_ERR(mvm, "Couldn't send SCAN_ABORT_CMD: %d\n", ret); 548 IWL_ERR(mvm, "Couldn't send SCAN_ABORT_CMD: %d\n", ret);
491 /* mac80211's state will be cleaned in the fw_restart flow */ 549 /* mac80211's state will be cleaned in the nic_restart flow */
492 goto out_remove_notif; 550 goto out_remove_notif;
493 } 551 }
494 552
495 ret = iwl_wait_notification(&mvm->notif_wait, &wait_scan_abort, 1 * HZ); 553 return iwl_wait_notification(&mvm->notif_wait, &wait_scan_abort, HZ);
496 if (ret)
497 IWL_ERR(mvm, "%s - failed on timeout\n", __func__);
498
499 return;
500 554
501out_remove_notif: 555out_remove_notif:
502 iwl_remove_notification(&mvm->notif_wait, &wait_scan_abort); 556 iwl_remove_notification(&mvm->notif_wait, &wait_scan_abort);
557 return ret;
503} 558}
504 559
505int iwl_mvm_rx_scan_offload_complete_notif(struct iwl_mvm *mvm, 560int iwl_mvm_rx_scan_offload_complete_notif(struct iwl_mvm *mvm,
@@ -509,12 +564,18 @@ int iwl_mvm_rx_scan_offload_complete_notif(struct iwl_mvm *mvm,
509 struct iwl_rx_packet *pkt = rxb_addr(rxb); 564 struct iwl_rx_packet *pkt = rxb_addr(rxb);
510 struct iwl_scan_offload_complete *scan_notif = (void *)pkt->data; 565 struct iwl_scan_offload_complete *scan_notif = (void *)pkt->data;
511 566
567 /* scan status must be locked for proper checking */
568 lockdep_assert_held(&mvm->mutex);
569
512 IWL_DEBUG_SCAN(mvm, "Scheduled scan completed, status %s\n", 570 IWL_DEBUG_SCAN(mvm, "Scheduled scan completed, status %s\n",
513 scan_notif->status == IWL_SCAN_OFFLOAD_COMPLETED ? 571 scan_notif->status == IWL_SCAN_OFFLOAD_COMPLETED ?
514 "completed" : "aborted"); 572 "completed" : "aborted");
515 573
516 mvm->scan_status = IWL_MVM_SCAN_NONE; 574 /* only call mac80211 completion if the stop was initiated by FW */
517 ieee80211_sched_scan_stopped(mvm->hw); 575 if (mvm->scan_status == IWL_MVM_SCAN_SCHED) {
576 mvm->scan_status = IWL_MVM_SCAN_NONE;
577 ieee80211_sched_scan_stopped(mvm->hw);
578 }
518 579
519 return 0; 580 return 0;
520} 581}
@@ -545,14 +606,9 @@ static void iwl_scan_offload_build_tx_cmd(struct iwl_mvm *mvm,
545static void iwl_build_scan_cmd(struct iwl_mvm *mvm, 606static void iwl_build_scan_cmd(struct iwl_mvm *mvm,
546 struct ieee80211_vif *vif, 607 struct ieee80211_vif *vif,
547 struct cfg80211_sched_scan_request *req, 608 struct cfg80211_sched_scan_request *req,
548 struct iwl_scan_offload_cmd *scan) 609 struct iwl_scan_offload_cmd *scan,
610 struct iwl_mvm_scan_params *params)
549{ 611{
550 bool is_assoc = false;
551
552 ieee80211_iterate_active_interfaces_atomic(mvm->hw,
553 IEEE80211_IFACE_ITER_NORMAL,
554 iwl_mvm_vif_assoc_iterator,
555 &is_assoc);
556 scan->channel_count = 612 scan->channel_count =
557 mvm->nvm_data->bands[IEEE80211_BAND_2GHZ].n_channels + 613 mvm->nvm_data->bands[IEEE80211_BAND_2GHZ].n_channels +
558 mvm->nvm_data->bands[IEEE80211_BAND_5GHZ].n_channels; 614 mvm->nvm_data->bands[IEEE80211_BAND_5GHZ].n_channels;
@@ -560,13 +616,17 @@ static void iwl_build_scan_cmd(struct iwl_mvm *mvm,
560 scan->quiet_plcp_th = cpu_to_le16(IWL_PLCP_QUIET_THRESH); 616 scan->quiet_plcp_th = cpu_to_le16(IWL_PLCP_QUIET_THRESH);
561 scan->good_CRC_th = IWL_GOOD_CRC_TH_DEFAULT; 617 scan->good_CRC_th = IWL_GOOD_CRC_TH_DEFAULT;
562 scan->rx_chain = iwl_mvm_scan_rx_chain(mvm); 618 scan->rx_chain = iwl_mvm_scan_rx_chain(mvm);
563 scan->max_out_time = iwl_mvm_scan_max_out_time(vif, req->flags, 619
564 is_assoc); 620 scan->max_out_time = cpu_to_le32(params->max_out_time);
565 scan->suspend_time = iwl_mvm_scan_suspend_time(vif, is_assoc); 621 scan->suspend_time = cpu_to_le32(params->suspend_time);
622
566 scan->filter_flags |= cpu_to_le32(MAC_FILTER_ACCEPT_GRP | 623 scan->filter_flags |= cpu_to_le32(MAC_FILTER_ACCEPT_GRP |
567 MAC_FILTER_IN_BEACON); 624 MAC_FILTER_IN_BEACON);
568 scan->scan_type = cpu_to_le32(SCAN_TYPE_BACKGROUND); 625 scan->scan_type = cpu_to_le32(SCAN_TYPE_BACKGROUND);
569 scan->rep_count = cpu_to_le32(1); 626 scan->rep_count = cpu_to_le32(1);
627
628 if (params->passive_fragmented)
629 scan->scan_flags |= SCAN_FLAGS_FRAGMENTED_SCAN;
570} 630}
571 631
572static int iwl_ssid_exist(u8 *ssid, u8 ssid_len, struct iwl_ssid_ie *ssid_list) 632static int iwl_ssid_exist(u8 *ssid, u8 ssid_len, struct iwl_ssid_ie *ssid_list)
@@ -596,6 +656,9 @@ static void iwl_scan_offload_build_ssid(struct cfg80211_sched_scan_request *req,
596 * config match list. 656 * config match list.
597 */ 657 */
598 for (i = 0; i < req->n_match_sets && i < PROBE_OPTION_MAX; i++) { 658 for (i = 0; i < req->n_match_sets && i < PROBE_OPTION_MAX; i++) {
659 /* skip empty SSID matchsets */
660 if (!req->match_sets[i].ssid.ssid_len)
661 continue;
599 scan->direct_scan[i].id = WLAN_EID_SSID; 662 scan->direct_scan[i].id = WLAN_EID_SSID;
600 scan->direct_scan[i].len = req->match_sets[i].ssid.ssid_len; 663 scan->direct_scan[i].len = req->match_sets[i].ssid.ssid_len;
601 memcpy(scan->direct_scan[i].ssid, req->match_sets[i].ssid.ssid, 664 memcpy(scan->direct_scan[i].ssid, req->match_sets[i].ssid.ssid,
@@ -628,12 +691,11 @@ static void iwl_build_channel_cfg(struct iwl_mvm *mvm,
628 struct iwl_scan_channel_cfg *channels, 691 struct iwl_scan_channel_cfg *channels,
629 enum ieee80211_band band, 692 enum ieee80211_band band,
630 int *head, int *tail, 693 int *head, int *tail,
631 u32 ssid_bitmap) 694 u32 ssid_bitmap,
695 struct iwl_mvm_scan_params *params)
632{ 696{
633 struct ieee80211_supported_band *s_band; 697 struct ieee80211_supported_band *s_band;
634 int n_probes = req->n_ssids;
635 int n_channels = req->n_channels; 698 int n_channels = req->n_channels;
636 u8 active_dwell, passive_dwell;
637 int i, j, index = 0; 699 int i, j, index = 0;
638 bool partial; 700 bool partial;
639 701
@@ -643,8 +705,6 @@ static void iwl_build_channel_cfg(struct iwl_mvm *mvm,
643 * to scan. So add requested channels to head of the list and others to 705 * to scan. So add requested channels to head of the list and others to
644 * the end. 706 * the end.
645 */ 707 */
646 active_dwell = iwl_mvm_get_active_dwell(band, n_probes);
647 passive_dwell = iwl_mvm_get_passive_dwell(band);
648 s_band = &mvm->nvm_data->bands[band]; 708 s_band = &mvm->nvm_data->bands[band];
649 709
650 for (i = 0; i < s_band->n_channels && *head <= *tail; i++) { 710 for (i = 0; i < s_band->n_channels && *head <= *tail; i++) {
@@ -668,8 +728,8 @@ static void iwl_build_channel_cfg(struct iwl_mvm *mvm,
668 channels->channel_number[index] = 728 channels->channel_number[index] =
669 cpu_to_le16(ieee80211_frequency_to_channel( 729 cpu_to_le16(ieee80211_frequency_to_channel(
670 s_band->channels[i].center_freq)); 730 s_band->channels[i].center_freq));
671 channels->dwell_time[index][0] = active_dwell; 731 channels->dwell_time[index][0] = params->dwell[band].active;
672 channels->dwell_time[index][1] = passive_dwell; 732 channels->dwell_time[index][1] = params->dwell[band].passive;
673 733
674 channels->iter_count[index] = cpu_to_le16(1); 734 channels->iter_count[index] = cpu_to_le16(1);
675 channels->iter_interval[index] = 0; 735 channels->iter_interval[index] = 0;
@@ -698,7 +758,6 @@ int iwl_mvm_config_sched_scan(struct iwl_mvm *mvm,
698 struct cfg80211_sched_scan_request *req, 758 struct cfg80211_sched_scan_request *req,
699 struct ieee80211_sched_scan_ies *ies) 759 struct ieee80211_sched_scan_ies *ies)
700{ 760{
701 int supported_bands = 0;
702 int band_2ghz = mvm->nvm_data->bands[IEEE80211_BAND_2GHZ].n_channels; 761 int band_2ghz = mvm->nvm_data->bands[IEEE80211_BAND_2GHZ].n_channels;
703 int band_5ghz = mvm->nvm_data->bands[IEEE80211_BAND_5GHZ].n_channels; 762 int band_5ghz = mvm->nvm_data->bands[IEEE80211_BAND_5GHZ].n_channels;
704 int head = 0; 763 int head = 0;
@@ -712,22 +771,19 @@ int iwl_mvm_config_sched_scan(struct iwl_mvm *mvm,
712 .id = SCAN_OFFLOAD_CONFIG_CMD, 771 .id = SCAN_OFFLOAD_CONFIG_CMD,
713 .flags = CMD_SYNC, 772 .flags = CMD_SYNC,
714 }; 773 };
774 struct iwl_mvm_scan_params params = {};
715 775
716 lockdep_assert_held(&mvm->mutex); 776 lockdep_assert_held(&mvm->mutex);
717 777
718 if (band_2ghz)
719 supported_bands++;
720 if (band_5ghz)
721 supported_bands++;
722
723 cmd_len = sizeof(struct iwl_scan_offload_cfg) + 778 cmd_len = sizeof(struct iwl_scan_offload_cfg) +
724 supported_bands * SCAN_OFFLOAD_PROBE_REQ_SIZE; 779 2 * SCAN_OFFLOAD_PROBE_REQ_SIZE;
725 780
726 scan_cfg = kzalloc(cmd_len, GFP_KERNEL); 781 scan_cfg = kzalloc(cmd_len, GFP_KERNEL);
727 if (!scan_cfg) 782 if (!scan_cfg)
728 return -ENOMEM; 783 return -ENOMEM;
729 784
730 iwl_build_scan_cmd(mvm, vif, req, &scan_cfg->scan_cmd); 785 iwl_mvm_scan_calc_params(mvm, vif, req->n_ssids, &params);
786 iwl_build_scan_cmd(mvm, vif, req, &scan_cfg->scan_cmd, &params);
731 scan_cfg->scan_cmd.len = cpu_to_le16(cmd_len); 787 scan_cfg->scan_cmd.len = cpu_to_le16(cmd_len);
732 788
733 iwl_scan_offload_build_ssid(req, &scan_cfg->scan_cmd, &ssid_bitmap); 789 iwl_scan_offload_build_ssid(req, &scan_cfg->scan_cmd, &ssid_bitmap);
@@ -739,7 +795,7 @@ int iwl_mvm_config_sched_scan(struct iwl_mvm *mvm,
739 scan_cfg->data); 795 scan_cfg->data);
740 iwl_build_channel_cfg(mvm, req, &scan_cfg->channel_cfg, 796 iwl_build_channel_cfg(mvm, req, &scan_cfg->channel_cfg,
741 IEEE80211_BAND_2GHZ, &head, &tail, 797 IEEE80211_BAND_2GHZ, &head, &tail,
742 ssid_bitmap); 798 ssid_bitmap, &params);
743 } 799 }
744 if (band_5ghz) { 800 if (band_5ghz) {
745 iwl_scan_offload_build_tx_cmd(mvm, vif, ies, 801 iwl_scan_offload_build_tx_cmd(mvm, vif, ies,
@@ -749,7 +805,7 @@ int iwl_mvm_config_sched_scan(struct iwl_mvm *mvm,
749 SCAN_OFFLOAD_PROBE_REQ_SIZE); 805 SCAN_OFFLOAD_PROBE_REQ_SIZE);
750 iwl_build_channel_cfg(mvm, req, &scan_cfg->channel_cfg, 806 iwl_build_channel_cfg(mvm, req, &scan_cfg->channel_cfg,
751 IEEE80211_BAND_5GHZ, &head, &tail, 807 IEEE80211_BAND_5GHZ, &head, &tail,
752 ssid_bitmap); 808 ssid_bitmap, &params);
753 } 809 }
754 810
755 cmd.data[0] = scan_cfg; 811 cmd.data[0] = scan_cfg;
@@ -889,26 +945,49 @@ static int iwl_mvm_send_sched_scan_abort(struct iwl_mvm *mvm)
889 * microcode has notified us that a scan is completed. 945 * microcode has notified us that a scan is completed.
890 */ 946 */
891 IWL_DEBUG_SCAN(mvm, "SCAN OFFLOAD ABORT ret %d.\n", status); 947 IWL_DEBUG_SCAN(mvm, "SCAN OFFLOAD ABORT ret %d.\n", status);
892 ret = -EIO; 948 ret = -ENOENT;
893 } 949 }
894 950
895 return ret; 951 return ret;
896} 952}
897 953
898void iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm) 954int iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm)
899{ 955{
900 int ret; 956 int ret;
957 struct iwl_notification_wait wait_scan_done;
958 static const u8 scan_done_notif[] = { SCAN_OFFLOAD_COMPLETE, };
901 959
902 lockdep_assert_held(&mvm->mutex); 960 lockdep_assert_held(&mvm->mutex);
903 961
904 if (mvm->scan_status != IWL_MVM_SCAN_SCHED) { 962 if (mvm->scan_status != IWL_MVM_SCAN_SCHED) {
905 IWL_DEBUG_SCAN(mvm, "No offloaded scan to stop\n"); 963 IWL_DEBUG_SCAN(mvm, "No offloaded scan to stop\n");
906 return; 964 return 0;
907 } 965 }
908 966
967 iwl_init_notification_wait(&mvm->notif_wait, &wait_scan_done,
968 scan_done_notif,
969 ARRAY_SIZE(scan_done_notif),
970 NULL, NULL);
971
909 ret = iwl_mvm_send_sched_scan_abort(mvm); 972 ret = iwl_mvm_send_sched_scan_abort(mvm);
910 if (ret) 973 if (ret) {
911 IWL_DEBUG_SCAN(mvm, "Send stop offload scan failed %d\n", ret); 974 IWL_DEBUG_SCAN(mvm, "Send stop offload scan failed %d\n", ret);
912 else 975 iwl_remove_notification(&mvm->notif_wait, &wait_scan_done);
913 IWL_DEBUG_SCAN(mvm, "Successfully sent stop offload scan\n"); 976 return ret;
977 }
978
979 IWL_DEBUG_SCAN(mvm, "Successfully sent stop offload scan\n");
980
981 ret = iwl_wait_notification(&mvm->notif_wait, &wait_scan_done, 1 * HZ);
982 if (ret)
983 return ret;
984
985 /*
986 * Clear the scan status so the next scan requests will succeed. This
987 * also ensures the Rx handler doesn't do anything, as the scan was
988 * stopped from above.
989 */
990 mvm->scan_status = IWL_MVM_SCAN_NONE;
991
992 return 0;
914} 993}
diff --git a/drivers/net/wireless/iwlwifi/mvm/sta.c b/drivers/net/wireless/iwlwifi/mvm/sta.c
index 3397f59cd4e4..f339ef884250 100644
--- a/drivers/net/wireless/iwlwifi/mvm/sta.c
+++ b/drivers/net/wireless/iwlwifi/mvm/sta.c
@@ -66,27 +66,27 @@
66#include "sta.h" 66#include "sta.h"
67#include "rs.h" 67#include "rs.h"
68 68
69static void iwl_mvm_add_sta_cmd_v6_to_v5(struct iwl_mvm_add_sta_cmd_v6 *cmd_v6, 69static void iwl_mvm_add_sta_cmd_v7_to_v5(struct iwl_mvm_add_sta_cmd_v7 *cmd_v7,
70 struct iwl_mvm_add_sta_cmd_v5 *cmd_v5) 70 struct iwl_mvm_add_sta_cmd_v5 *cmd_v5)
71{ 71{
72 memset(cmd_v5, 0, sizeof(*cmd_v5)); 72 memset(cmd_v5, 0, sizeof(*cmd_v5));
73 73
74 cmd_v5->add_modify = cmd_v6->add_modify; 74 cmd_v5->add_modify = cmd_v7->add_modify;
75 cmd_v5->tid_disable_tx = cmd_v6->tid_disable_tx; 75 cmd_v5->tid_disable_tx = cmd_v7->tid_disable_tx;
76 cmd_v5->mac_id_n_color = cmd_v6->mac_id_n_color; 76 cmd_v5->mac_id_n_color = cmd_v7->mac_id_n_color;
77 memcpy(cmd_v5->addr, cmd_v6->addr, ETH_ALEN); 77 memcpy(cmd_v5->addr, cmd_v7->addr, ETH_ALEN);
78 cmd_v5->sta_id = cmd_v6->sta_id; 78 cmd_v5->sta_id = cmd_v7->sta_id;
79 cmd_v5->modify_mask = cmd_v6->modify_mask; 79 cmd_v5->modify_mask = cmd_v7->modify_mask;
80 cmd_v5->station_flags = cmd_v6->station_flags; 80 cmd_v5->station_flags = cmd_v7->station_flags;
81 cmd_v5->station_flags_msk = cmd_v6->station_flags_msk; 81 cmd_v5->station_flags_msk = cmd_v7->station_flags_msk;
82 cmd_v5->add_immediate_ba_tid = cmd_v6->add_immediate_ba_tid; 82 cmd_v5->add_immediate_ba_tid = cmd_v7->add_immediate_ba_tid;
83 cmd_v5->remove_immediate_ba_tid = cmd_v6->remove_immediate_ba_tid; 83 cmd_v5->remove_immediate_ba_tid = cmd_v7->remove_immediate_ba_tid;
84 cmd_v5->add_immediate_ba_ssn = cmd_v6->add_immediate_ba_ssn; 84 cmd_v5->add_immediate_ba_ssn = cmd_v7->add_immediate_ba_ssn;
85 cmd_v5->sleep_tx_count = cmd_v6->sleep_tx_count; 85 cmd_v5->sleep_tx_count = cmd_v7->sleep_tx_count;
86 cmd_v5->sleep_state_flags = cmd_v6->sleep_state_flags; 86 cmd_v5->sleep_state_flags = cmd_v7->sleep_state_flags;
87 cmd_v5->assoc_id = cmd_v6->assoc_id; 87 cmd_v5->assoc_id = cmd_v7->assoc_id;
88 cmd_v5->beamform_flags = cmd_v6->beamform_flags; 88 cmd_v5->beamform_flags = cmd_v7->beamform_flags;
89 cmd_v5->tfd_queue_msk = cmd_v6->tfd_queue_msk; 89 cmd_v5->tfd_queue_msk = cmd_v7->tfd_queue_msk;
90} 90}
91 91
92static void 92static void
@@ -110,7 +110,7 @@ iwl_mvm_add_sta_key_to_add_sta_cmd_v5(struct iwl_mvm_add_sta_key_cmd *key_cmd,
110} 110}
111 111
112static int iwl_mvm_send_add_sta_cmd_status(struct iwl_mvm *mvm, 112static int iwl_mvm_send_add_sta_cmd_status(struct iwl_mvm *mvm,
113 struct iwl_mvm_add_sta_cmd_v6 *cmd, 113 struct iwl_mvm_add_sta_cmd_v7 *cmd,
114 int *status) 114 int *status)
115{ 115{
116 struct iwl_mvm_add_sta_cmd_v5 cmd_v5; 116 struct iwl_mvm_add_sta_cmd_v5 cmd_v5;
@@ -119,14 +119,14 @@ static int iwl_mvm_send_add_sta_cmd_status(struct iwl_mvm *mvm,
119 return iwl_mvm_send_cmd_pdu_status(mvm, ADD_STA, sizeof(*cmd), 119 return iwl_mvm_send_cmd_pdu_status(mvm, ADD_STA, sizeof(*cmd),
120 cmd, status); 120 cmd, status);
121 121
122 iwl_mvm_add_sta_cmd_v6_to_v5(cmd, &cmd_v5); 122 iwl_mvm_add_sta_cmd_v7_to_v5(cmd, &cmd_v5);
123 123
124 return iwl_mvm_send_cmd_pdu_status(mvm, ADD_STA, sizeof(cmd_v5), 124 return iwl_mvm_send_cmd_pdu_status(mvm, ADD_STA, sizeof(cmd_v5),
125 &cmd_v5, status); 125 &cmd_v5, status);
126} 126}
127 127
128static int iwl_mvm_send_add_sta_cmd(struct iwl_mvm *mvm, u32 flags, 128static int iwl_mvm_send_add_sta_cmd(struct iwl_mvm *mvm, u32 flags,
129 struct iwl_mvm_add_sta_cmd_v6 *cmd) 129 struct iwl_mvm_add_sta_cmd_v7 *cmd)
130{ 130{
131 struct iwl_mvm_add_sta_cmd_v5 cmd_v5; 131 struct iwl_mvm_add_sta_cmd_v5 cmd_v5;
132 132
@@ -134,7 +134,7 @@ static int iwl_mvm_send_add_sta_cmd(struct iwl_mvm *mvm, u32 flags,
134 return iwl_mvm_send_cmd_pdu(mvm, ADD_STA, flags, 134 return iwl_mvm_send_cmd_pdu(mvm, ADD_STA, flags,
135 sizeof(*cmd), cmd); 135 sizeof(*cmd), cmd);
136 136
137 iwl_mvm_add_sta_cmd_v6_to_v5(cmd, &cmd_v5); 137 iwl_mvm_add_sta_cmd_v7_to_v5(cmd, &cmd_v5);
138 138
139 return iwl_mvm_send_cmd_pdu(mvm, ADD_STA, flags, sizeof(cmd_v5), 139 return iwl_mvm_send_cmd_pdu(mvm, ADD_STA, flags, sizeof(cmd_v5),
140 &cmd_v5); 140 &cmd_v5);
@@ -175,19 +175,30 @@ static int iwl_mvm_send_add_sta_key_cmd(struct iwl_mvm *mvm,
175 &sta_cmd); 175 &sta_cmd);
176} 176}
177 177
178static int iwl_mvm_find_free_sta_id(struct iwl_mvm *mvm) 178static int iwl_mvm_find_free_sta_id(struct iwl_mvm *mvm,
179 enum nl80211_iftype iftype)
179{ 180{
180 int sta_id; 181 int sta_id;
182 u32 reserved_ids = 0;
181 183
184 BUILD_BUG_ON(IWL_MVM_STATION_COUNT > 32);
182 WARN_ON_ONCE(test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status)); 185 WARN_ON_ONCE(test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status));
183 186
184 lockdep_assert_held(&mvm->mutex); 187 lockdep_assert_held(&mvm->mutex);
185 188
189 /* d0i3/d3 assumes the AP's sta_id (of sta vif) is 0. reserve it. */
190 if (iftype != NL80211_IFTYPE_STATION)
191 reserved_ids = BIT(0);
192
186 /* Don't take rcu_read_lock() since we are protected by mvm->mutex */ 193 /* Don't take rcu_read_lock() since we are protected by mvm->mutex */
187 for (sta_id = 0; sta_id < IWL_MVM_STATION_COUNT; sta_id++) 194 for (sta_id = 0; sta_id < IWL_MVM_STATION_COUNT; sta_id++) {
195 if (BIT(sta_id) & reserved_ids)
196 continue;
197
188 if (!rcu_dereference_protected(mvm->fw_id_to_mac_id[sta_id], 198 if (!rcu_dereference_protected(mvm->fw_id_to_mac_id[sta_id],
189 lockdep_is_held(&mvm->mutex))) 199 lockdep_is_held(&mvm->mutex)))
190 return sta_id; 200 return sta_id;
201 }
191 return IWL_MVM_STATION_COUNT; 202 return IWL_MVM_STATION_COUNT;
192} 203}
193 204
@@ -196,7 +207,7 @@ int iwl_mvm_sta_send_to_fw(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
196 bool update) 207 bool update)
197{ 208{
198 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv; 209 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv;
199 struct iwl_mvm_add_sta_cmd_v6 add_sta_cmd; 210 struct iwl_mvm_add_sta_cmd_v7 add_sta_cmd;
200 int ret; 211 int ret;
201 u32 status; 212 u32 status;
202 u32 agg_size = 0, mpdu_dens = 0; 213 u32 agg_size = 0, mpdu_dens = 0;
@@ -312,7 +323,8 @@ int iwl_mvm_add_sta(struct iwl_mvm *mvm,
312 lockdep_assert_held(&mvm->mutex); 323 lockdep_assert_held(&mvm->mutex);
313 324
314 if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status)) 325 if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status))
315 sta_id = iwl_mvm_find_free_sta_id(mvm); 326 sta_id = iwl_mvm_find_free_sta_id(mvm,
327 ieee80211_vif_type_p2p(vif));
316 else 328 else
317 sta_id = mvm_sta->sta_id; 329 sta_id = mvm_sta->sta_id;
318 330
@@ -368,7 +380,7 @@ int iwl_mvm_update_sta(struct iwl_mvm *mvm,
368int iwl_mvm_drain_sta(struct iwl_mvm *mvm, struct iwl_mvm_sta *mvmsta, 380int iwl_mvm_drain_sta(struct iwl_mvm *mvm, struct iwl_mvm_sta *mvmsta,
369 bool drain) 381 bool drain)
370{ 382{
371 struct iwl_mvm_add_sta_cmd_v6 cmd = {}; 383 struct iwl_mvm_add_sta_cmd_v7 cmd = {};
372 int ret; 384 int ret;
373 u32 status; 385 u32 status;
374 386
@@ -522,6 +534,10 @@ int iwl_mvm_rm_sta(struct iwl_mvm *mvm,
522 534
523 /* unassoc - go ahead - remove the AP STA now */ 535 /* unassoc - go ahead - remove the AP STA now */
524 mvmvif->ap_sta_id = IWL_MVM_STATION_COUNT; 536 mvmvif->ap_sta_id = IWL_MVM_STATION_COUNT;
537
538 /* clear d0i3_ap_sta_id if no longer relevant */
539 if (mvm->d0i3_ap_sta_id == mvm_sta->sta_id)
540 mvm->d0i3_ap_sta_id = IWL_MVM_STATION_COUNT;
525 } 541 }
526 542
527 /* 543 /*
@@ -560,10 +576,10 @@ int iwl_mvm_rm_sta_id(struct iwl_mvm *mvm,
560} 576}
561 577
562int iwl_mvm_allocate_int_sta(struct iwl_mvm *mvm, struct iwl_mvm_int_sta *sta, 578int iwl_mvm_allocate_int_sta(struct iwl_mvm *mvm, struct iwl_mvm_int_sta *sta,
563 u32 qmask) 579 u32 qmask, enum nl80211_iftype iftype)
564{ 580{
565 if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status)) { 581 if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status)) {
566 sta->sta_id = iwl_mvm_find_free_sta_id(mvm); 582 sta->sta_id = iwl_mvm_find_free_sta_id(mvm, iftype);
567 if (WARN_ON_ONCE(sta->sta_id == IWL_MVM_STATION_COUNT)) 583 if (WARN_ON_ONCE(sta->sta_id == IWL_MVM_STATION_COUNT))
568 return -ENOSPC; 584 return -ENOSPC;
569 } 585 }
@@ -587,13 +603,13 @@ static int iwl_mvm_add_int_sta_common(struct iwl_mvm *mvm,
587 const u8 *addr, 603 const u8 *addr,
588 u16 mac_id, u16 color) 604 u16 mac_id, u16 color)
589{ 605{
590 struct iwl_mvm_add_sta_cmd_v6 cmd; 606 struct iwl_mvm_add_sta_cmd_v7 cmd;
591 int ret; 607 int ret;
592 u32 status; 608 u32 status;
593 609
594 lockdep_assert_held(&mvm->mutex); 610 lockdep_assert_held(&mvm->mutex);
595 611
596 memset(&cmd, 0, sizeof(struct iwl_mvm_add_sta_cmd_v6)); 612 memset(&cmd, 0, sizeof(struct iwl_mvm_add_sta_cmd_v7));
597 cmd.sta_id = sta->sta_id; 613 cmd.sta_id = sta->sta_id;
598 cmd.mac_id_n_color = cpu_to_le32(FW_CMD_ID_AND_COLOR(mac_id, 614 cmd.mac_id_n_color = cpu_to_le32(FW_CMD_ID_AND_COLOR(mac_id,
599 color)); 615 color));
@@ -627,7 +643,8 @@ int iwl_mvm_add_aux_sta(struct iwl_mvm *mvm)
627 lockdep_assert_held(&mvm->mutex); 643 lockdep_assert_held(&mvm->mutex);
628 644
629 /* Add the aux station, but without any queues */ 645 /* Add the aux station, but without any queues */
630 ret = iwl_mvm_allocate_int_sta(mvm, &mvm->aux_sta, 0); 646 ret = iwl_mvm_allocate_int_sta(mvm, &mvm->aux_sta, 0,
647 NL80211_IFTYPE_UNSPECIFIED);
631 if (ret) 648 if (ret)
632 return ret; 649 return ret;
633 650
@@ -699,7 +716,8 @@ int iwl_mvm_add_bcast_sta(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
699 lockdep_assert_held(&mvm->mutex); 716 lockdep_assert_held(&mvm->mutex);
700 717
701 qmask = iwl_mvm_mac_get_queues_mask(mvm, vif); 718 qmask = iwl_mvm_mac_get_queues_mask(mvm, vif);
702 ret = iwl_mvm_allocate_int_sta(mvm, bsta, qmask); 719 ret = iwl_mvm_allocate_int_sta(mvm, bsta, qmask,
720 ieee80211_vif_type_p2p(vif));
703 if (ret) 721 if (ret)
704 return ret; 722 return ret;
705 723
@@ -735,7 +753,7 @@ int iwl_mvm_sta_rx_agg(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
735 int tid, u16 ssn, bool start) 753 int tid, u16 ssn, bool start)
736{ 754{
737 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv; 755 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv;
738 struct iwl_mvm_add_sta_cmd_v6 cmd = {}; 756 struct iwl_mvm_add_sta_cmd_v7 cmd = {};
739 int ret; 757 int ret;
740 u32 status; 758 u32 status;
741 759
@@ -794,7 +812,7 @@ static int iwl_mvm_sta_tx_agg(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
794 int tid, u8 queue, bool start) 812 int tid, u8 queue, bool start)
795{ 813{
796 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv; 814 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv;
797 struct iwl_mvm_add_sta_cmd_v6 cmd = {}; 815 struct iwl_mvm_add_sta_cmd_v7 cmd = {};
798 int ret; 816 int ret;
799 u32 status; 817 u32 status;
800 818
@@ -833,7 +851,7 @@ static int iwl_mvm_sta_tx_agg(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
833 return ret; 851 return ret;
834} 852}
835 853
836static const u8 tid_to_ac[] = { 854const u8 tid_to_mac80211_ac[] = {
837 IEEE80211_AC_BE, 855 IEEE80211_AC_BE,
838 IEEE80211_AC_BK, 856 IEEE80211_AC_BK,
839 IEEE80211_AC_BK, 857 IEEE80211_AC_BK,
@@ -844,6 +862,17 @@ static const u8 tid_to_ac[] = {
844 IEEE80211_AC_VO, 862 IEEE80211_AC_VO,
845}; 863};
846 864
865static const u8 tid_to_ucode_ac[] = {
866 AC_BE,
867 AC_BK,
868 AC_BK,
869 AC_BE,
870 AC_VI,
871 AC_VI,
872 AC_VO,
873 AC_VO,
874};
875
847int iwl_mvm_sta_tx_agg_start(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 876int iwl_mvm_sta_tx_agg_start(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
848 struct ieee80211_sta *sta, u16 tid, u16 *ssn) 877 struct ieee80211_sta *sta, u16 tid, u16 *ssn)
849{ 878{
@@ -873,10 +902,18 @@ int iwl_mvm_sta_tx_agg_start(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
873 return -EIO; 902 return -EIO;
874 } 903 }
875 904
905 spin_lock_bh(&mvmsta->lock);
906
907 /* possible race condition - we entered D0i3 while starting agg */
908 if (test_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status)) {
909 spin_unlock_bh(&mvmsta->lock);
910 IWL_ERR(mvm, "Entered D0i3 while starting Tx agg\n");
911 return -EIO;
912 }
913
876 /* the new tx queue is still connected to the same mac80211 queue */ 914 /* the new tx queue is still connected to the same mac80211 queue */
877 mvm->queue_to_mac80211[txq_id] = vif->hw_queue[tid_to_ac[tid]]; 915 mvm->queue_to_mac80211[txq_id] = vif->hw_queue[tid_to_mac80211_ac[tid]];
878 916
879 spin_lock_bh(&mvmsta->lock);
880 tid_data = &mvmsta->tid_data[tid]; 917 tid_data = &mvmsta->tid_data[tid];
881 tid_data->ssn = IEEE80211_SEQ_TO_SN(tid_data->seq_number); 918 tid_data->ssn = IEEE80211_SEQ_TO_SN(tid_data->seq_number);
882 tid_data->txq_id = txq_id; 919 tid_data->txq_id = txq_id;
@@ -916,7 +953,7 @@ int iwl_mvm_sta_tx_agg_oper(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
916 tid_data->ssn = 0xffff; 953 tid_data->ssn = 0xffff;
917 spin_unlock_bh(&mvmsta->lock); 954 spin_unlock_bh(&mvmsta->lock);
918 955
919 fifo = iwl_mvm_ac_to_tx_fifo[tid_to_ac[tid]]; 956 fifo = iwl_mvm_ac_to_tx_fifo[tid_to_mac80211_ac[tid]];
920 957
921 ret = iwl_mvm_sta_tx_agg(mvm, sta, tid, queue, true); 958 ret = iwl_mvm_sta_tx_agg(mvm, sta, tid, queue, true);
922 if (ret) 959 if (ret)
@@ -1411,7 +1448,7 @@ void iwl_mvm_sta_modify_ps_wake(struct iwl_mvm *mvm,
1411 struct ieee80211_sta *sta) 1448 struct ieee80211_sta *sta)
1412{ 1449{
1413 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); 1450 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta);
1414 struct iwl_mvm_add_sta_cmd_v6 cmd = { 1451 struct iwl_mvm_add_sta_cmd_v7 cmd = {
1415 .add_modify = STA_MODE_MODIFY, 1452 .add_modify = STA_MODE_MODIFY,
1416 .sta_id = mvmsta->sta_id, 1453 .sta_id = mvmsta->sta_id,
1417 .station_flags_msk = cpu_to_le32(STA_FLG_PS), 1454 .station_flags_msk = cpu_to_le32(STA_FLG_PS),
@@ -1427,28 +1464,102 @@ void iwl_mvm_sta_modify_ps_wake(struct iwl_mvm *mvm,
1427void iwl_mvm_sta_modify_sleep_tx_count(struct iwl_mvm *mvm, 1464void iwl_mvm_sta_modify_sleep_tx_count(struct iwl_mvm *mvm,
1428 struct ieee80211_sta *sta, 1465 struct ieee80211_sta *sta,
1429 enum ieee80211_frame_release_type reason, 1466 enum ieee80211_frame_release_type reason,
1430 u16 cnt) 1467 u16 cnt, u16 tids, bool more_data,
1468 bool agg)
1431{ 1469{
1432 u16 sleep_state_flags =
1433 (reason == IEEE80211_FRAME_RELEASE_UAPSD) ?
1434 STA_SLEEP_STATE_UAPSD : STA_SLEEP_STATE_PS_POLL;
1435 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); 1470 struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta);
1436 struct iwl_mvm_add_sta_cmd_v6 cmd = { 1471 struct iwl_mvm_add_sta_cmd_v7 cmd = {
1437 .add_modify = STA_MODE_MODIFY, 1472 .add_modify = STA_MODE_MODIFY,
1438 .sta_id = mvmsta->sta_id, 1473 .sta_id = mvmsta->sta_id,
1439 .modify_mask = STA_MODIFY_SLEEPING_STA_TX_COUNT, 1474 .modify_mask = STA_MODIFY_SLEEPING_STA_TX_COUNT,
1440 .sleep_tx_count = cpu_to_le16(cnt), 1475 .sleep_tx_count = cpu_to_le16(cnt),
1441 .mac_id_n_color = cpu_to_le32(mvmsta->mac_id_n_color), 1476 .mac_id_n_color = cpu_to_le32(mvmsta->mac_id_n_color),
1442 /*
1443 * Same modify mask for sleep_tx_count and sleep_state_flags so
1444 * we must set the sleep_state_flags too.
1445 */
1446 .sleep_state_flags = cpu_to_le16(sleep_state_flags),
1447 }; 1477 };
1448 int ret; 1478 int tid, ret;
1479 unsigned long _tids = tids;
1480
1481 /* convert TIDs to ACs - we don't support TSPEC so that's OK
1482 * Note that this field is reserved and unused by firmware not
1483 * supporting GO uAPSD, so it's safe to always do this.
1484 */
1485 for_each_set_bit(tid, &_tids, IWL_MAX_TID_COUNT)
1486 cmd.awake_acs |= BIT(tid_to_ucode_ac[tid]);
1487
1488 /* If we're releasing frames from aggregation queues then check if the
1489 * all queues combined that we're releasing frames from have
1490 * - more frames than the service period, in which case more_data
1491 * needs to be set
1492 * - fewer than 'cnt' frames, in which case we need to adjust the
1493 * firmware command (but do that unconditionally)
1494 */
1495 if (agg) {
1496 int remaining = cnt;
1497
1498 spin_lock_bh(&mvmsta->lock);
1499 for_each_set_bit(tid, &_tids, IWL_MAX_TID_COUNT) {
1500 struct iwl_mvm_tid_data *tid_data;
1501 u16 n_queued;
1502
1503 tid_data = &mvmsta->tid_data[tid];
1504 if (WARN(tid_data->state != IWL_AGG_ON &&
1505 tid_data->state != IWL_EMPTYING_HW_QUEUE_DELBA,
1506 "TID %d state is %d\n",
1507 tid, tid_data->state)) {
1508 spin_unlock_bh(&mvmsta->lock);
1509 ieee80211_sta_eosp(sta);
1510 return;
1511 }
1512
1513 n_queued = iwl_mvm_tid_queued(tid_data);
1514 if (n_queued > remaining) {
1515 more_data = true;
1516 remaining = 0;
1517 break;
1518 }
1519 remaining -= n_queued;
1520 }
1521 spin_unlock_bh(&mvmsta->lock);
1522
1523 cmd.sleep_tx_count = cpu_to_le16(cnt - remaining);
1524 if (WARN_ON(cnt - remaining == 0)) {
1525 ieee80211_sta_eosp(sta);
1526 return;
1527 }
1528 }
1529
1530 /* Note: this is ignored by firmware not supporting GO uAPSD */
1531 if (more_data)
1532 cmd.sleep_state_flags |= cpu_to_le16(STA_SLEEP_STATE_MOREDATA);
1533
1534 if (reason == IEEE80211_FRAME_RELEASE_PSPOLL) {
1535 mvmsta->next_status_eosp = true;
1536 cmd.sleep_state_flags |= cpu_to_le16(STA_SLEEP_STATE_PS_POLL);
1537 } else {
1538 cmd.sleep_state_flags |= cpu_to_le16(STA_SLEEP_STATE_UAPSD);
1539 }
1449 1540
1450 /* TODO: somehow the fw doesn't seem to take PS_POLL into account */
1451 ret = iwl_mvm_send_add_sta_cmd(mvm, CMD_ASYNC, &cmd); 1541 ret = iwl_mvm_send_add_sta_cmd(mvm, CMD_ASYNC, &cmd);
1452 if (ret) 1542 if (ret)
1453 IWL_ERR(mvm, "Failed to send ADD_STA command (%d)\n", ret); 1543 IWL_ERR(mvm, "Failed to send ADD_STA command (%d)\n", ret);
1454} 1544}
1545
1546int iwl_mvm_rx_eosp_notif(struct iwl_mvm *mvm,
1547 struct iwl_rx_cmd_buffer *rxb,
1548 struct iwl_device_cmd *cmd)
1549{
1550 struct iwl_rx_packet *pkt = rxb_addr(rxb);
1551 struct iwl_mvm_eosp_notification *notif = (void *)pkt->data;
1552 struct ieee80211_sta *sta;
1553 u32 sta_id = le32_to_cpu(notif->sta_id);
1554
1555 if (WARN_ON_ONCE(sta_id >= IWL_MVM_STATION_COUNT))
1556 return 0;
1557
1558 rcu_read_lock();
1559 sta = rcu_dereference(mvm->fw_id_to_mac_id[sta_id]);
1560 if (!IS_ERR_OR_NULL(sta))
1561 ieee80211_sta_eosp(sta);
1562 rcu_read_unlock();
1563
1564 return 0;
1565}
diff --git a/drivers/net/wireless/iwlwifi/mvm/sta.h b/drivers/net/wireless/iwlwifi/mvm/sta.h
index 4968d0237dc5..2ed84c421481 100644
--- a/drivers/net/wireless/iwlwifi/mvm/sta.h
+++ b/drivers/net/wireless/iwlwifi/mvm/sta.h
@@ -195,24 +195,33 @@ struct iwl_mvm;
195/** 195/**
196 * DOC: AP mode - PS 196 * DOC: AP mode - PS
197 * 197 *
198 * When a station is asleep, the fw will set it as "asleep". All the 198 * When a station is asleep, the fw will set it as "asleep". All frames on
199 * non-aggregation frames to that station will be dropped by the fw 199 * shared queues (i.e. non-aggregation queues) to that station will be dropped
200 * (%TX_STATUS_FAIL_DEST_PS failure code). 200 * by the fw (%TX_STATUS_FAIL_DEST_PS failure code).
201 *
201 * AMPDUs are in a separate queue that is stopped by the fw. We just need to 202 * AMPDUs are in a separate queue that is stopped by the fw. We just need to
202 * let mac80211 know how many frames we have in these queues so that it can 203 * let mac80211 know when there are frames in these queues so that it can
203 * properly handle trigger frames. 204 * properly handle trigger frames.
204 * When the a trigger frame is received, mac80211 tells the driver to send 205 *
205 * frames from the AMPDU queues or AC queue depending on which queue are 206 * When a trigger frame is received, mac80211 tells the driver to send frames
206 * delivery-enabled and what TID has frames to transmit (Note that mac80211 has 207 * from the AMPDU queues or sends frames to non-aggregation queues itself,
207 * all the knowledege since all the non-agg frames are buffered / filtered, and 208 * depending on which ACs are delivery-enabled and what TID has frames to
208 * the driver tells mac80211 about agg frames). The driver needs to tell the fw 209 * transmit. Note that mac80211 has all the knowledege since all the non-agg
209 * to let frames out even if the station is asleep. This is done by 210 * frames are buffered / filtered, and the driver tells mac80211 about agg
210 * %iwl_mvm_sta_modify_sleep_tx_count. 211 * frames). The driver needs to tell the fw to let frames out even if the
211 * When we receive a frame from that station with PM bit unset, the 212 * station is asleep. This is done by %iwl_mvm_sta_modify_sleep_tx_count.
212 * driver needs to let the fw know that this station isn't alseep any more. 213 *
213 * This is done by %iwl_mvm_sta_modify_ps_wake. 214 * When we receive a frame from that station with PM bit unset, the driver
214 * 215 * needs to let the fw know that this station isn't asleep any more. This is
215 * TODO - EOSP handling 216 * done by %iwl_mvm_sta_modify_ps_wake in response to mac80211 signalling the
217 * station's wakeup.
218 *
219 * For a GO, the Service Period might be cut short due to an absence period
220 * of the GO. In this (and all other cases) the firmware notifies us with the
221 * EOSP_NOTIFICATION, and we notify mac80211 of that. Further frames that we
222 * already sent to the device will be rejected again.
223 *
224 * See also "AP support for powersaving clients" in mac80211.h.
216 */ 225 */
217 226
218/** 227/**
@@ -261,6 +270,12 @@ struct iwl_mvm_tid_data {
261 u16 ssn; 270 u16 ssn;
262}; 271};
263 272
273static inline u16 iwl_mvm_tid_queued(struct iwl_mvm_tid_data *tid_data)
274{
275 return ieee80211_sn_sub(IEEE80211_SEQ_TO_SN(tid_data->seq_number),
276 tid_data->next_reclaimed);
277}
278
264/** 279/**
265 * struct iwl_mvm_sta - representation of a station in the driver 280 * struct iwl_mvm_sta - representation of a station in the driver
266 * @sta_id: the index of the station in the fw (will be replaced by id_n_color) 281 * @sta_id: the index of the station in the fw (will be replaced by id_n_color)
@@ -269,7 +284,11 @@ struct iwl_mvm_tid_data {
269 * @tid_disable_agg: bitmap: if bit(tid) is set, the fw won't send ampdus for 284 * @tid_disable_agg: bitmap: if bit(tid) is set, the fw won't send ampdus for
270 * tid. 285 * tid.
271 * @max_agg_bufsize: the maximal size of the AGG buffer for this station 286 * @max_agg_bufsize: the maximal size of the AGG buffer for this station
287 * @bt_reduced_txpower_dbg: debug mode in which %bt_reduced_txpower is forced
288 * by debugfs.
272 * @bt_reduced_txpower: is reduced tx power enabled for this station 289 * @bt_reduced_txpower: is reduced tx power enabled for this station
290 * @next_status_eosp: the next reclaimed packet is a PS-Poll response and
291 * we need to signal the EOSP
273 * @lock: lock to protect the whole struct. Since %tid_data is access from Tx 292 * @lock: lock to protect the whole struct. Since %tid_data is access from Tx
274 * and from Tx response flow, it needs a spinlock. 293 * and from Tx response flow, it needs a spinlock.
275 * @tid_data: per tid data. Look at %iwl_mvm_tid_data. 294 * @tid_data: per tid data. Look at %iwl_mvm_tid_data.
@@ -287,7 +306,9 @@ struct iwl_mvm_sta {
287 u32 mac_id_n_color; 306 u32 mac_id_n_color;
288 u16 tid_disable_agg; 307 u16 tid_disable_agg;
289 u8 max_agg_bufsize; 308 u8 max_agg_bufsize;
309 bool bt_reduced_txpower_dbg;
290 bool bt_reduced_txpower; 310 bool bt_reduced_txpower;
311 bool next_status_eosp;
291 spinlock_t lock; 312 spinlock_t lock;
292 struct iwl_mvm_tid_data tid_data[IWL_MAX_TID_COUNT]; 313 struct iwl_mvm_tid_data tid_data[IWL_MAX_TID_COUNT];
293 struct iwl_lq_sta lq_sta; 314 struct iwl_lq_sta lq_sta;
@@ -345,6 +366,10 @@ void iwl_mvm_update_tkip_key(struct iwl_mvm *mvm,
345 struct ieee80211_sta *sta, u32 iv32, 366 struct ieee80211_sta *sta, u32 iv32,
346 u16 *phase1key); 367 u16 *phase1key);
347 368
369int iwl_mvm_rx_eosp_notif(struct iwl_mvm *mvm,
370 struct iwl_rx_cmd_buffer *rxb,
371 struct iwl_device_cmd *cmd);
372
348/* AMPDU */ 373/* AMPDU */
349int iwl_mvm_sta_rx_agg(struct iwl_mvm *mvm, struct ieee80211_sta *sta, 374int iwl_mvm_sta_rx_agg(struct iwl_mvm *mvm, struct ieee80211_sta *sta,
350 int tid, u16 ssn, bool start); 375 int tid, u16 ssn, bool start);
@@ -359,7 +384,7 @@ int iwl_mvm_sta_tx_agg_flush(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
359 384
360int iwl_mvm_add_aux_sta(struct iwl_mvm *mvm); 385int iwl_mvm_add_aux_sta(struct iwl_mvm *mvm);
361int iwl_mvm_allocate_int_sta(struct iwl_mvm *mvm, struct iwl_mvm_int_sta *sta, 386int iwl_mvm_allocate_int_sta(struct iwl_mvm *mvm, struct iwl_mvm_int_sta *sta,
362 u32 qmask); 387 u32 qmask, enum nl80211_iftype iftype);
363void iwl_mvm_dealloc_int_sta(struct iwl_mvm *mvm, 388void iwl_mvm_dealloc_int_sta(struct iwl_mvm *mvm,
364 struct iwl_mvm_int_sta *sta); 389 struct iwl_mvm_int_sta *sta);
365int iwl_mvm_send_bcast_sta(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 390int iwl_mvm_send_bcast_sta(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
@@ -375,7 +400,8 @@ void iwl_mvm_sta_modify_ps_wake(struct iwl_mvm *mvm,
375void iwl_mvm_sta_modify_sleep_tx_count(struct iwl_mvm *mvm, 400void iwl_mvm_sta_modify_sleep_tx_count(struct iwl_mvm *mvm,
376 struct ieee80211_sta *sta, 401 struct ieee80211_sta *sta,
377 enum ieee80211_frame_release_type reason, 402 enum ieee80211_frame_release_type reason,
378 u16 cnt); 403 u16 cnt, u16 tids, bool more_data,
404 bool agg);
379int iwl_mvm_drain_sta(struct iwl_mvm *mvm, struct iwl_mvm_sta *mvmsta, 405int iwl_mvm_drain_sta(struct iwl_mvm *mvm, struct iwl_mvm_sta *mvmsta,
380 bool drain); 406 bool drain);
381 407
diff --git a/drivers/net/wireless/iwlwifi/mvm/time-event.c b/drivers/net/wireless/iwlwifi/mvm/time-event.c
index b4c2abaa297b..61331245ad93 100644
--- a/drivers/net/wireless/iwlwifi/mvm/time-event.c
+++ b/drivers/net/wireless/iwlwifi/mvm/time-event.c
@@ -126,6 +126,7 @@ static void iwl_mvm_roc_finished(struct iwl_mvm *mvm)
126 * in iwl_mvm_te_handle_notif). 126 * in iwl_mvm_te_handle_notif).
127 */ 127 */
128 clear_bit(IWL_MVM_STATUS_ROC_RUNNING, &mvm->status); 128 clear_bit(IWL_MVM_STATUS_ROC_RUNNING, &mvm->status);
129 iwl_mvm_unref(mvm, IWL_MVM_REF_ROC);
129 130
130 /* 131 /*
131 * Of course, our status bit is just as racy as mac80211, so in 132 * Of course, our status bit is just as racy as mac80211, so in
@@ -210,6 +211,7 @@ static void iwl_mvm_te_handle_notif(struct iwl_mvm *mvm,
210 211
211 if (te_data->vif->type == NL80211_IFTYPE_P2P_DEVICE) { 212 if (te_data->vif->type == NL80211_IFTYPE_P2P_DEVICE) {
212 set_bit(IWL_MVM_STATUS_ROC_RUNNING, &mvm->status); 213 set_bit(IWL_MVM_STATUS_ROC_RUNNING, &mvm->status);
214 iwl_mvm_ref(mvm, IWL_MVM_REF_ROC);
213 ieee80211_ready_on_channel(mvm->hw); 215 ieee80211_ready_on_channel(mvm->hw);
214 } 216 }
215 } else { 217 } else {
@@ -436,7 +438,8 @@ void iwl_mvm_protect_session(struct iwl_mvm *mvm,
436 time_cmd.duration = cpu_to_le32(duration); 438 time_cmd.duration = cpu_to_le32(duration);
437 time_cmd.repeat = 1; 439 time_cmd.repeat = 1;
438 time_cmd.policy = cpu_to_le16(TE_V2_NOTIF_HOST_EVENT_START | 440 time_cmd.policy = cpu_to_le16(TE_V2_NOTIF_HOST_EVENT_START |
439 TE_V2_NOTIF_HOST_EVENT_END); 441 TE_V2_NOTIF_HOST_EVENT_END |
442 T2_V2_START_IMMEDIATELY);
440 443
441 iwl_mvm_time_event_send_add(mvm, vif, te_data, &time_cmd); 444 iwl_mvm_time_event_send_add(mvm, vif, te_data, &time_cmd);
442} 445}
@@ -551,7 +554,8 @@ int iwl_mvm_start_p2p_roc(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
551 time_cmd.duration = cpu_to_le32(MSEC_TO_TU(duration)); 554 time_cmd.duration = cpu_to_le32(MSEC_TO_TU(duration));
552 time_cmd.repeat = 1; 555 time_cmd.repeat = 1;
553 time_cmd.policy = cpu_to_le16(TE_V2_NOTIF_HOST_EVENT_START | 556 time_cmd.policy = cpu_to_le16(TE_V2_NOTIF_HOST_EVENT_START |
554 TE_V2_NOTIF_HOST_EVENT_END); 557 TE_V2_NOTIF_HOST_EVENT_END |
558 T2_V2_START_IMMEDIATELY);
555 559
556 return iwl_mvm_time_event_send_add(mvm, vif, te_data, &time_cmd); 560 return iwl_mvm_time_event_send_add(mvm, vif, te_data, &time_cmd);
557} 561}
diff --git a/drivers/net/wireless/iwlwifi/mvm/tt.c b/drivers/net/wireless/iwlwifi/mvm/tt.c
index 3afa6b6bf835..7a99fa361954 100644
--- a/drivers/net/wireless/iwlwifi/mvm/tt.c
+++ b/drivers/net/wireless/iwlwifi/mvm/tt.c
@@ -403,7 +403,7 @@ static void iwl_mvm_tt_tx_protection(struct iwl_mvm *mvm, bool enable)
403 } 403 }
404} 404}
405 405
406static void iwl_mvm_tt_tx_backoff(struct iwl_mvm *mvm, u32 backoff) 406void iwl_mvm_tt_tx_backoff(struct iwl_mvm *mvm, u32 backoff)
407{ 407{
408 struct iwl_host_cmd cmd = { 408 struct iwl_host_cmd cmd = {
409 .id = REPLY_THERMAL_MNG_BACKOFF, 409 .id = REPLY_THERMAL_MNG_BACKOFF,
@@ -412,6 +412,8 @@ static void iwl_mvm_tt_tx_backoff(struct iwl_mvm *mvm, u32 backoff)
412 .flags = CMD_SYNC, 412 .flags = CMD_SYNC,
413 }; 413 };
414 414
415 backoff = max(backoff, mvm->thermal_throttle.min_backoff);
416
415 if (iwl_mvm_send_cmd(mvm, &cmd) == 0) { 417 if (iwl_mvm_send_cmd(mvm, &cmd) == 0) {
416 IWL_DEBUG_TEMP(mvm, "Set Thermal Tx backoff to: %u\n", 418 IWL_DEBUG_TEMP(mvm, "Set Thermal Tx backoff to: %u\n",
417 backoff); 419 backoff);
@@ -534,7 +536,7 @@ static const struct iwl_tt_params iwl7000_high_temp_tt_params = {
534 .support_tx_backoff = true, 536 .support_tx_backoff = true,
535}; 537};
536 538
537void iwl_mvm_tt_initialize(struct iwl_mvm *mvm) 539void iwl_mvm_tt_initialize(struct iwl_mvm *mvm, u32 min_backoff)
538{ 540{
539 struct iwl_mvm_tt_mgmt *tt = &mvm->thermal_throttle; 541 struct iwl_mvm_tt_mgmt *tt = &mvm->thermal_throttle;
540 542
@@ -546,6 +548,7 @@ void iwl_mvm_tt_initialize(struct iwl_mvm *mvm)
546 tt->params = &iwl7000_tt_params; 548 tt->params = &iwl7000_tt_params;
547 549
548 tt->throttle = false; 550 tt->throttle = false;
551 tt->min_backoff = min_backoff;
549 INIT_DELAYED_WORK(&tt->ct_kill_exit, check_exit_ctkill); 552 INIT_DELAYED_WORK(&tt->ct_kill_exit, check_exit_ctkill);
550} 553}
551 554
diff --git a/drivers/net/wireless/iwlwifi/mvm/tx.c b/drivers/net/wireless/iwlwifi/mvm/tx.c
index 76ee486039d7..879aeac46cc1 100644
--- a/drivers/net/wireless/iwlwifi/mvm/tx.c
+++ b/drivers/net/wireless/iwlwifi/mvm/tx.c
@@ -79,6 +79,7 @@ static void iwl_mvm_set_tx_cmd(struct iwl_mvm *mvm, struct sk_buff *skb,
79 __le16 fc = hdr->frame_control; 79 __le16 fc = hdr->frame_control;
80 u32 tx_flags = le32_to_cpu(tx_cmd->tx_flags); 80 u32 tx_flags = le32_to_cpu(tx_cmd->tx_flags);
81 u32 len = skb->len + FCS_LEN; 81 u32 len = skb->len + FCS_LEN;
82 u8 ac;
82 83
83 if (!(info->flags & IEEE80211_TX_CTL_NO_ACK)) 84 if (!(info->flags & IEEE80211_TX_CTL_NO_ACK))
84 tx_flags |= TX_CMD_FLG_ACK; 85 tx_flags |= TX_CMD_FLG_ACK;
@@ -90,13 +91,6 @@ static void iwl_mvm_set_tx_cmd(struct iwl_mvm *mvm, struct sk_buff *skb,
90 else if (ieee80211_is_back_req(fc)) 91 else if (ieee80211_is_back_req(fc))
91 tx_flags |= TX_CMD_FLG_ACK | TX_CMD_FLG_BAR; 92 tx_flags |= TX_CMD_FLG_ACK | TX_CMD_FLG_BAR;
92 93
93 /* High prio packet (wrt. BT coex) if it is EAPOL, MCAST or MGMT */
94 if (info->band == IEEE80211_BAND_2GHZ &&
95 (info->control.flags & IEEE80211_TX_CTRL_PORT_CTRL_PROTO ||
96 is_multicast_ether_addr(hdr->addr1) ||
97 ieee80211_is_back_req(fc) || ieee80211_is_mgmt(fc)))
98 tx_flags |= TX_CMD_FLG_BT_DIS;
99
100 if (ieee80211_has_morefrags(fc)) 94 if (ieee80211_has_morefrags(fc))
101 tx_flags |= TX_CMD_FLG_MORE_FRAG; 95 tx_flags |= TX_CMD_FLG_MORE_FRAG;
102 96
@@ -112,6 +106,11 @@ static void iwl_mvm_set_tx_cmd(struct iwl_mvm *mvm, struct sk_buff *skb,
112 tx_flags &= ~TX_CMD_FLG_SEQ_CTL; 106 tx_flags &= ~TX_CMD_FLG_SEQ_CTL;
113 } 107 }
114 108
109 /* tid_tspec will default to 0 = BE when QOS isn't enabled */
110 ac = tid_to_mac80211_ac[tx_cmd->tid_tspec];
111 tx_flags |= iwl_mvm_bt_coex_tx_prio(mvm, hdr, info, ac) <<
112 TX_CMD_FLG_BT_PRIO_POS;
113
115 if (ieee80211_is_mgmt(fc)) { 114 if (ieee80211_is_mgmt(fc)) {
116 if (ieee80211_is_assoc_req(fc) || ieee80211_is_reassoc_req(fc)) 115 if (ieee80211_is_assoc_req(fc) || ieee80211_is_reassoc_req(fc))
117 tx_cmd->pm_frame_timeout = cpu_to_le16(3); 116 tx_cmd->pm_frame_timeout = cpu_to_le16(3);
@@ -122,15 +121,12 @@ static void iwl_mvm_set_tx_cmd(struct iwl_mvm *mvm, struct sk_buff *skb,
122 * it 121 * it
123 */ 122 */
124 WARN_ON_ONCE(info->flags & IEEE80211_TX_CTL_AMPDU); 123 WARN_ON_ONCE(info->flags & IEEE80211_TX_CTL_AMPDU);
125 } else if (skb->protocol == cpu_to_be16(ETH_P_PAE)) { 124 } else if (info->control.flags & IEEE80211_TX_CTRL_PORT_CTRL_PROTO) {
126 tx_cmd->pm_frame_timeout = cpu_to_le16(2); 125 tx_cmd->pm_frame_timeout = cpu_to_le16(2);
127 } else { 126 } else {
128 tx_cmd->pm_frame_timeout = 0; 127 tx_cmd->pm_frame_timeout = 0;
129 } 128 }
130 129
131 if (info->flags & IEEE80211_TX_CTL_AMPDU)
132 tx_flags |= TX_CMD_FLG_PROT_REQUIRE;
133
134 if (ieee80211_is_data(fc) && len > mvm->rts_threshold && 130 if (ieee80211_is_data(fc) && len > mvm->rts_threshold &&
135 !is_multicast_ether_addr(ieee80211_get_DA(hdr))) 131 !is_multicast_ether_addr(ieee80211_get_DA(hdr)))
136 tx_flags |= TX_CMD_FLG_PROT_REQUIRE; 132 tx_flags |= TX_CMD_FLG_PROT_REQUIRE;
@@ -207,7 +203,7 @@ static void iwl_mvm_set_tx_cmd_rate(struct iwl_mvm *mvm,
207 rate_plcp = iwl_mvm_mac80211_idx_to_hwrate(rate_idx); 203 rate_plcp = iwl_mvm_mac80211_idx_to_hwrate(rate_idx);
208 204
209 mvm->mgmt_last_antenna_idx = 205 mvm->mgmt_last_antenna_idx =
210 iwl_mvm_next_antenna(mvm, iwl_fw_valid_tx_ant(mvm->fw), 206 iwl_mvm_next_antenna(mvm, mvm->fw->valid_tx_ant,
211 mvm->mgmt_last_antenna_idx); 207 mvm->mgmt_last_antenna_idx);
212 rate_flags = BIT(mvm->mgmt_last_antenna_idx) << RATE_MCS_ANT_POS; 208 rate_flags = BIT(mvm->mgmt_last_antenna_idx) << RATE_MCS_ANT_POS;
213 209
@@ -377,6 +373,13 @@ int iwl_mvm_tx_skb(struct iwl_mvm *mvm, struct sk_buff *skb,
377 tx_cmd = (struct iwl_tx_cmd *)dev_cmd->payload; 373 tx_cmd = (struct iwl_tx_cmd *)dev_cmd->payload;
378 /* From now on, we cannot access info->control */ 374 /* From now on, we cannot access info->control */
379 375
376 /*
377 * we handle that entirely ourselves -- for uAPSD the firmware
378 * will always send a notification, and for PS-Poll responses
379 * we'll notify mac80211 when getting frame status
380 */
381 info->flags &= ~IEEE80211_TX_STATUS_EOSP;
382
380 spin_lock(&mvmsta->lock); 383 spin_lock(&mvmsta->lock);
381 384
382 if (ieee80211_is_data_qos(fc) && !ieee80211_is_qos_nullfunc(fc)) { 385 if (ieee80211_is_data_qos(fc) && !ieee80211_is_qos_nullfunc(fc)) {
@@ -437,6 +440,17 @@ static void iwl_mvm_check_ratid_empty(struct iwl_mvm *mvm,
437 440
438 lockdep_assert_held(&mvmsta->lock); 441 lockdep_assert_held(&mvmsta->lock);
439 442
443 if ((tid_data->state == IWL_AGG_ON ||
444 tid_data->state == IWL_EMPTYING_HW_QUEUE_DELBA) &&
445 iwl_mvm_tid_queued(tid_data) == 0) {
446 /*
447 * Now that this aggregation queue is empty tell mac80211 so it
448 * knows we no longer have frames buffered for the station on
449 * this TID (for the TIM bitmap calculation.)
450 */
451 ieee80211_sta_set_buffered(sta, tid, false);
452 }
453
440 if (tid_data->ssn != tid_data->next_reclaimed) 454 if (tid_data->ssn != tid_data->next_reclaimed)
441 return; 455 return;
442 456
@@ -680,6 +694,11 @@ static void iwl_mvm_rx_tx_cmd_single(struct iwl_mvm *mvm,
680 iwl_mvm_check_ratid_empty(mvm, sta, tid); 694 iwl_mvm_check_ratid_empty(mvm, sta, tid);
681 spin_unlock_bh(&mvmsta->lock); 695 spin_unlock_bh(&mvmsta->lock);
682 } 696 }
697
698 if (mvmsta->next_status_eosp) {
699 mvmsta->next_status_eosp = false;
700 ieee80211_sta_eosp(sta);
701 }
683 } else { 702 } else {
684 mvmsta = NULL; 703 mvmsta = NULL;
685 } 704 }
diff --git a/drivers/net/wireless/iwlwifi/mvm/utils.c b/drivers/net/wireless/iwlwifi/mvm/utils.c
index 86989df69356..d619851745a1 100644
--- a/drivers/net/wireless/iwlwifi/mvm/utils.c
+++ b/drivers/net/wireless/iwlwifi/mvm/utils.c
@@ -289,8 +289,8 @@ u8 iwl_mvm_next_antenna(struct iwl_mvm *mvm, u8 valid, u8 last_idx)
289 return last_idx; 289 return last_idx;
290} 290}
291 291
292static struct { 292static const struct {
293 char *name; 293 const char *name;
294 u8 num; 294 u8 num;
295} advanced_lookup[] = { 295} advanced_lookup[] = {
296 { "NMI_INTERRUPT_WDG", 0x34 }, 296 { "NMI_INTERRUPT_WDG", 0x34 },
@@ -376,9 +376,67 @@ struct iwl_error_event_table {
376 u32 flow_handler; /* FH read/write pointers, RX credit */ 376 u32 flow_handler; /* FH read/write pointers, RX credit */
377} __packed; 377} __packed;
378 378
379/*
380 * UMAC error struct - relevant starting from family 8000 chip.
381 * Note: This structure is read from the device with IO accesses,
382 * and the reading already does the endian conversion. As it is
383 * read with u32-sized accesses, any members with a different size
384 * need to be ordered correctly though!
385 */
386struct iwl_umac_error_event_table {
387 u32 valid; /* (nonzero) valid, (0) log is empty */
388 u32 error_id; /* type of error */
389 u32 pc; /* program counter */
390 u32 blink1; /* branch link */
391 u32 blink2; /* branch link */
392 u32 ilink1; /* interrupt link */
393 u32 ilink2; /* interrupt link */
394 u32 data1; /* error-specific data */
395 u32 data2; /* error-specific data */
396 u32 line; /* source code line of error */
397 u32 umac_ver; /* umac version */
398} __packed;
399
379#define ERROR_START_OFFSET (1 * sizeof(u32)) 400#define ERROR_START_OFFSET (1 * sizeof(u32))
380#define ERROR_ELEM_SIZE (7 * sizeof(u32)) 401#define ERROR_ELEM_SIZE (7 * sizeof(u32))
381 402
403static void iwl_mvm_dump_umac_error_log(struct iwl_mvm *mvm)
404{
405 struct iwl_trans *trans = mvm->trans;
406 struct iwl_umac_error_event_table table;
407 u32 base;
408
409 base = mvm->umac_error_event_table;
410
411 if (base < 0x800000 || base >= 0x80C000) {
412 IWL_ERR(mvm,
413 "Not valid error log pointer 0x%08X for %s uCode\n",
414 base,
415 (mvm->cur_ucode == IWL_UCODE_INIT)
416 ? "Init" : "RT");
417 return;
418 }
419
420 iwl_trans_read_mem_bytes(trans, base, &table, sizeof(table));
421
422 if (ERROR_START_OFFSET <= table.valid * ERROR_ELEM_SIZE) {
423 IWL_ERR(trans, "Start IWL Error Log Dump:\n");
424 IWL_ERR(trans, "Status: 0x%08lX, count: %d\n",
425 mvm->status, table.valid);
426 }
427
428 IWL_ERR(mvm, "0x%08X | %-28s\n", table.error_id,
429 desc_lookup(table.error_id));
430 IWL_ERR(mvm, "0x%08X | umac uPc\n", table.pc);
431 IWL_ERR(mvm, "0x%08X | umac branchlink1\n", table.blink1);
432 IWL_ERR(mvm, "0x%08X | umac branchlink2\n", table.blink2);
433 IWL_ERR(mvm, "0x%08X | umac interruptlink1\n", table.ilink1);
434 IWL_ERR(mvm, "0x%08X | umac interruptlink2\n", table.ilink2);
435 IWL_ERR(mvm, "0x%08X | umac data1\n", table.data1);
436 IWL_ERR(mvm, "0x%08X | umac data2\n", table.data2);
437 IWL_ERR(mvm, "0x%08X | umac version\n", table.umac_ver);
438}
439
382void iwl_mvm_dump_nic_error_log(struct iwl_mvm *mvm) 440void iwl_mvm_dump_nic_error_log(struct iwl_mvm *mvm)
383{ 441{
384 struct iwl_trans *trans = mvm->trans; 442 struct iwl_trans *trans = mvm->trans;
@@ -394,7 +452,7 @@ void iwl_mvm_dump_nic_error_log(struct iwl_mvm *mvm)
394 base = mvm->fw->inst_errlog_ptr; 452 base = mvm->fw->inst_errlog_ptr;
395 } 453 }
396 454
397 if (base < 0x800000 || base >= 0x80C000) { 455 if (base < 0x800000) {
398 IWL_ERR(mvm, 456 IWL_ERR(mvm,
399 "Not valid error log pointer 0x%08X for %s uCode\n", 457 "Not valid error log pointer 0x%08X for %s uCode\n",
400 base, 458 base,
@@ -453,29 +511,31 @@ void iwl_mvm_dump_nic_error_log(struct iwl_mvm *mvm)
453 IWL_ERR(mvm, "0x%08X | lmpm_pmg_sel\n", table.lmpm_pmg_sel); 511 IWL_ERR(mvm, "0x%08X | lmpm_pmg_sel\n", table.lmpm_pmg_sel);
454 IWL_ERR(mvm, "0x%08X | timestamp\n", table.u_timestamp); 512 IWL_ERR(mvm, "0x%08X | timestamp\n", table.u_timestamp);
455 IWL_ERR(mvm, "0x%08X | flow_handler\n", table.flow_handler); 513 IWL_ERR(mvm, "0x%08X | flow_handler\n", table.flow_handler);
514
515 if (mvm->support_umac_log)
516 iwl_mvm_dump_umac_error_log(mvm);
456} 517}
457 518
458void iwl_mvm_dump_sram(struct iwl_mvm *mvm) 519void iwl_mvm_fw_error_sram_dump(struct iwl_mvm *mvm)
459{ 520{
460 const struct fw_img *img; 521 const struct fw_img *img;
461 int ofs, len = 0; 522 u32 ofs, sram_len;
462 u8 *buf; 523 void *sram;
463 524
464 if (!mvm->ucode_loaded) 525 if (!mvm->ucode_loaded || mvm->fw_error_sram)
465 return; 526 return;
466 527
467 img = &mvm->fw->img[mvm->cur_ucode]; 528 img = &mvm->fw->img[mvm->cur_ucode];
468 ofs = img->sec[IWL_UCODE_SECTION_DATA].offset; 529 ofs = img->sec[IWL_UCODE_SECTION_DATA].offset;
469 len = img->sec[IWL_UCODE_SECTION_DATA].len; 530 sram_len = img->sec[IWL_UCODE_SECTION_DATA].len;
470 531
471 buf = kzalloc(len, GFP_ATOMIC); 532 sram = kzalloc(sram_len, GFP_ATOMIC);
472 if (!buf) 533 if (!sram)
473 return; 534 return;
474 535
475 iwl_trans_read_mem_bytes(mvm->trans, ofs, buf, len); 536 iwl_trans_read_mem_bytes(mvm->trans, ofs, sram, sram_len);
476 iwl_print_hex_error(mvm->trans, buf, len); 537 mvm->fw_error_sram = sram;
477 538 mvm->fw_error_sram_len = sram_len;
478 kfree(buf);
479} 539}
480 540
481/** 541/**
@@ -516,15 +576,20 @@ void iwl_mvm_update_smps(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
516 enum ieee80211_smps_mode smps_request) 576 enum ieee80211_smps_mode smps_request)
517{ 577{
518 struct iwl_mvm_vif *mvmvif; 578 struct iwl_mvm_vif *mvmvif;
519 enum ieee80211_smps_mode smps_mode = IEEE80211_SMPS_AUTOMATIC; 579 enum ieee80211_smps_mode smps_mode;
520 int i; 580 int i;
521 581
522 lockdep_assert_held(&mvm->mutex); 582 lockdep_assert_held(&mvm->mutex);
523 583
524 /* SMPS is irrelevant for NICs that don't have at least 2 RX antenna */ 584 /* SMPS is irrelevant for NICs that don't have at least 2 RX antenna */
525 if (num_of_ant(iwl_fw_valid_rx_ant(mvm->fw)) == 1) 585 if (num_of_ant(mvm->fw->valid_rx_ant) == 1)
526 return; 586 return;
527 587
588 if (vif->type == NL80211_IFTYPE_AP)
589 smps_mode = IEEE80211_SMPS_OFF;
590 else
591 smps_mode = IEEE80211_SMPS_AUTOMATIC;
592
528 mvmvif = iwl_mvm_vif_from_mac80211(vif); 593 mvmvif = iwl_mvm_vif_from_mac80211(vif);
529 mvmvif->smps_requests[req_type] = smps_request; 594 mvmvif->smps_requests[req_type] = smps_request;
530 for (i = 0; i < NUM_IWL_MVM_SMPS_REQ; i++) { 595 for (i = 0; i < NUM_IWL_MVM_SMPS_REQ; i++) {
@@ -538,3 +603,44 @@ void iwl_mvm_update_smps(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
538 603
539 ieee80211_request_smps(vif, smps_mode); 604 ieee80211_request_smps(vif, smps_mode);
540} 605}
606
607int iwl_mvm_update_low_latency(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
608 bool value)
609{
610 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
611 int res;
612
613 lockdep_assert_held(&mvm->mutex);
614
615 if (mvmvif->low_latency == value)
616 return 0;
617
618 mvmvif->low_latency = value;
619
620 res = iwl_mvm_update_quotas(mvm, NULL);
621 if (res)
622 return res;
623
624 iwl_mvm_bt_coex_vif_change(mvm);
625
626 return iwl_mvm_power_update_mac(mvm, vif);
627}
628
629static void iwl_mvm_ll_iter(void *_data, u8 *mac, struct ieee80211_vif *vif)
630{
631 bool *result = _data;
632
633 if (iwl_mvm_vif_low_latency(iwl_mvm_vif_from_mac80211(vif)))
634 *result = true;
635}
636
637bool iwl_mvm_low_latency(struct iwl_mvm *mvm)
638{
639 bool result = false;
640
641 ieee80211_iterate_active_interfaces_atomic(
642 mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
643 iwl_mvm_ll_iter, &result);
644
645 return result;
646}