aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJohn W. Linville <linville@tuxdriver.com>2014-05-27 13:51:31 -0400
committerJohn W. Linville <linville@tuxdriver.com>2014-05-27 13:51:31 -0400
commit9db7cb6901740453a442e598563b576987dd471b (patch)
treee38911285b5cd9980280a92ea0e0260f6c1ef2ad
parent3bea8eddfebe1c61ea824dd2880d4368791edc1f (diff)
parent03c4444650969431b3a5effde4995de767e3013a (diff)
Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/linville/wireless-next into for-davem
-rw-r--r--Documentation/devicetree/bindings/net/nfc/pn544.txt35
-rw-r--r--Documentation/devicetree/bindings/net/nfc/st21nfca.txt33
-rw-r--r--Documentation/devicetree/bindings/net/nfc/trf7970a.txt2
-rw-r--r--arch/arm/mach-tegra/board-paz00.c4
-rw-r--r--arch/mips/bcm47xx/sprom.c1
-rw-r--r--drivers/mmc/host/mmc_spi.c18
-rw-r--r--drivers/net/wireless/ath/ath10k/core.c6
-rw-r--r--drivers/net/wireless/ath/ath10k/mac.c16
-rw-r--r--drivers/net/wireless/ath/ath10k/pci.c18
-rw-r--r--drivers/net/wireless/ath/ath10k/wmi.c2
-rw-r--r--drivers/net/wireless/ath/ath6kl/cfg80211.c7
-rw-r--r--drivers/net/wireless/ath/ath6kl/wmi.c2
-rw-r--r--drivers/net/wireless/ath/ath6kl/wmi.h2
-rw-r--r--drivers/net/wireless/ath/ath9k/Makefile3
-rw-r--r--drivers/net/wireless/ath/ath9k/ath9k.h3
-rw-r--r--drivers/net/wireless/ath/ath9k/beacon.c5
-rw-r--r--drivers/net/wireless/ath/ath9k/common-debug.c253
-rw-r--r--drivers/net/wireless/ath/ath9k/common-debug.h72
-rw-r--r--drivers/net/wireless/ath/ath9k/common.h1
-rw-r--r--drivers/net/wireless/ath/ath9k/debug.c214
-rw-r--r--drivers/net/wireless/ath/ath9k/debug.h44
-rw-r--r--drivers/net/wireless/ath/ath9k/dfs.c8
-rw-r--r--drivers/net/wireless/ath/ath9k/dfs_debug.h1
-rw-r--r--drivers/net/wireless/ath/ath9k/htc.h19
-rw-r--r--drivers/net/wireless/ath/ath9k/htc_drv_debug.c555
-rw-r--r--drivers/net/wireless/ath/ath9k/htc_drv_txrx.c3
-rw-r--r--drivers/net/wireless/ath/ath9k/hw.c3
-rw-r--r--drivers/net/wireless/ath/ath9k/init.c5
-rw-r--r--drivers/net/wireless/ath/ath9k/mac.c22
-rw-r--r--drivers/net/wireless/ath/ath9k/mac.h1
-rw-r--r--drivers/net/wireless/ath/ath9k/main.c47
-rw-r--r--drivers/net/wireless/ath/ath9k/pci.c3
-rw-r--r--drivers/net/wireless/ath/ath9k/recv.c4
-rw-r--r--drivers/net/wireless/ath/ath9k/reg.h3
-rw-r--r--drivers/net/wireless/ath/carl9170/usb.c8
-rw-r--r--drivers/net/wireless/ath/dfs_pattern_detector.c45
-rw-r--r--drivers/net/wireless/ath/wil6210/cfg80211.c4
-rw-r--r--drivers/net/wireless/ath/wil6210/main.c4
-rw-r--r--drivers/net/wireless/ath/wil6210/wil6210.h2
-rw-r--r--drivers/net/wireless/b43/Kconfig42
-rw-r--r--drivers/net/wireless/b43/bus.h10
-rw-r--r--drivers/net/wireless/b43/main.c412
-rw-r--r--drivers/net/wireless/b43/phy_common.c85
-rw-r--r--drivers/net/wireless/b43/phy_common.h5
-rw-r--r--drivers/net/wireless/b43/radio_2056.c918
-rw-r--r--drivers/net/wireless/b43/xmit.c2
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd.h2
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd_bus.h1
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c18
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c32
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/fwil_types.h24
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/fwsignal.c80
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/nvram.c220
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/usb.c1
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c206
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/main.c13
-rw-r--r--drivers/net/wireless/brcm80211/brcmutil/d11.c93
-rw-r--r--drivers/net/wireless/brcm80211/include/brcmu_d11.h14
-rw-r--r--drivers/net/wireless/brcm80211/include/brcmu_wifi.h1
-rw-r--r--drivers/net/wireless/iwlwifi/Kconfig13
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/Makefile3
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/calib.c1
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/debugfs.c7
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/dev.h2
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/devices.c2
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/led.h12
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/lib.c17
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/main.c27
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/power.c4
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/rs.c10
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/rx.c2
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/rxon.c18
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/scan.c3
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/sta.c29
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/tt.c2
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/tx.c24
-rw-r--r--drivers/net/wireless/iwlwifi/dvm/ucode.c6
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-7000.c2
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-8000.c5
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-agn-hw.h4
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-config.h7
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-debug.c6
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-debug.h41
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-drv.c5
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-fw-error-dump.h (renamed from drivers/net/wireless/iwlwifi/mvm/fw-error-dump.h)26
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-fw.h10
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-io.c18
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-io.h1
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-modparams.h1
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-nvm-parse.c50
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-phy-db.c9
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-prph.h3
-rw-r--r--drivers/net/wireless/iwlwifi/iwl-trans.h50
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/Makefile3
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/coex.c80
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/d3.c35
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c48
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/debugfs.c11
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/fw.c19
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c114
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/mac80211.c173
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/mvm.h34
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/nvm.c102
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/ops.c43
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c23
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/power.c208
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/quota.c2
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/rs.c179
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/scan.c13
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/sta.c18
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/sta.h3
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/time-event.c4
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/tt.c1
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/tx.c2
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/utils.c41
-rw-r--r--drivers/net/wireless/iwlwifi/pcie/drv.c14
-rw-r--r--drivers/net/wireless/iwlwifi/pcie/internal.h24
-rw-r--r--drivers/net/wireless/iwlwifi/pcie/rx.c2
-rw-r--r--drivers/net/wireless/iwlwifi/pcie/trans.c90
-rw-r--r--drivers/net/wireless/iwlwifi/pcie/tx.c139
-rw-r--r--drivers/net/wireless/libertas/cfg.c7
-rw-r--r--drivers/net/wireless/libertas/defs.h3
-rw-r--r--drivers/net/wireless/libertas/rx.c8
-rw-r--r--drivers/net/wireless/mwifiex/11n.c42
-rw-r--r--drivers/net/wireless/mwifiex/11n.h3
-rw-r--r--drivers/net/wireless/mwifiex/11n_aggr.c7
-rw-r--r--drivers/net/wireless/mwifiex/cfg80211.c19
-rw-r--r--drivers/net/wireless/mwifiex/fw.h23
-rw-r--r--drivers/net/wireless/mwifiex/main.h22
-rw-r--r--drivers/net/wireless/mwifiex/pcie.c1
-rw-r--r--drivers/net/wireless/mwifiex/sdio.c6
-rw-r--r--drivers/net/wireless/mwifiex/sta_cmd.c7
-rw-r--r--drivers/net/wireless/mwifiex/sta_cmdresp.c18
-rw-r--r--drivers/net/wireless/mwifiex/sta_event.c44
-rw-r--r--drivers/net/wireless/mwifiex/sta_rx.c16
-rw-r--r--drivers/net/wireless/mwifiex/sta_tx.c4
-rw-r--r--drivers/net/wireless/mwifiex/tdls.c97
-rw-r--r--drivers/net/wireless/mwifiex/util.c6
-rw-r--r--drivers/net/wireless/mwifiex/wmm.c12
-rw-r--r--drivers/net/wireless/mwifiex/wmm.h5
-rw-r--r--drivers/net/wireless/orinoco/hw.c4
-rw-r--r--drivers/net/wireless/orinoco/hw.h4
-rw-r--r--drivers/net/wireless/orinoco/orinoco_usb.c2
-rw-r--r--drivers/net/wireless/orinoco/wext.c4
-rw-r--r--drivers/net/wireless/rndis_wlan.c4
-rw-r--r--drivers/net/wireless/rsi/rsi_91x_mac80211.c1
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00usb.c6
-rw-r--r--drivers/net/wireless/rtl818x/rtl8180/dev.c17
-rw-r--r--drivers/net/wireless/rtl818x/rtl8187/dev.c11
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8188ee/hw.c20
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8188ee/hw.h2
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8188ee/sw.c5
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192ce/hw.c21
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192ce/hw.h2
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192ce/sw.c1
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192cu/hw.c2
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192se/hw.c20
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192se/hw.h2
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192se/sw.c1
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8723ae/hw.c21
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8723ae/hw.h2
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8723ae/sw.c1
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8723be/hw.c20
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8723be/hw.h2
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8723be/sw.c5
-rw-r--r--drivers/net/wireless/rtlwifi/wifi.h6
-rw-r--r--drivers/net/wireless/ti/wl1251/acx.c1
-rw-r--r--drivers/net/wireless/ti/wl1251/cmd.c1
-rw-r--r--drivers/net/wireless/ti/wl1251/event.c5
-rw-r--r--drivers/net/wireless/ti/wl1251/main.c68
-rw-r--r--drivers/net/wireless/ti/wl1251/spi.c44
-rw-r--r--drivers/net/wireless/ti/wlcore/debugfs.h4
-rw-r--r--drivers/net/wireless/ti/wlcore/main.c2
-rw-r--r--drivers/net/wireless/ti/wlcore/spi.c46
-rw-r--r--drivers/net/wireless/ti/wlcore/wlcore_i.h4
-rw-r--r--drivers/nfc/Kconfig1
-rw-r--r--drivers/nfc/Makefile1
-rw-r--r--drivers/nfc/pn544/i2c.c154
-rw-r--r--drivers/nfc/st21nfca/Kconfig23
-rw-r--r--drivers/nfc/st21nfca/Makefile8
-rw-r--r--drivers/nfc/st21nfca/i2c.c724
-rw-r--r--drivers/nfc/st21nfca/st21nfca.c698
-rw-r--r--drivers/nfc/st21nfca/st21nfca.h87
-rw-r--r--drivers/nfc/trf7970a.c252
-rw-r--r--drivers/staging/wlan-ng/cfg80211.c4
-rw-r--r--include/linux/ath9k_platform.h2
-rw-r--r--include/linux/crc7.h8
-rw-r--r--include/linux/platform_data/st21nfca.h32
-rw-r--r--include/linux/rfkill-gpio.h10
-rw-r--r--include/linux/ssb/ssb.h1
-rw-r--r--include/net/cfg80211.h191
-rw-r--r--include/net/mac80211.h78
-rw-r--r--include/net/nfc/digital.h4
-rw-r--r--include/net/nfc/hci.h1
-rw-r--r--include/net/nfc/nfc.h3
-rw-r--r--include/uapi/linux/nfc.h16
-rw-r--r--include/uapi/linux/nl80211.h25
-rw-r--r--lib/crc7.c84
-rw-r--r--net/bluetooth/l2cap_core.c4
-rw-r--r--net/mac80211/Makefile3
-rw-r--r--net/mac80211/cfg.c538
-rw-r--r--net/mac80211/chan.c4
-rw-r--r--net/mac80211/driver-ops.h121
-rw-r--r--net/mac80211/ibss.c2
-rw-r--r--net/mac80211/ieee80211_i.h17
-rw-r--r--net/mac80211/iface.c7
-rw-r--r--net/mac80211/key.c7
-rw-r--r--net/mac80211/main.c2
-rw-r--r--net/mac80211/mesh.c2
-rw-r--r--net/mac80211/mesh_pathtbl.c6
-rw-r--r--net/mac80211/mesh_sync.c2
-rw-r--r--net/mac80211/mlme.c46
-rw-r--r--net/mac80211/rc80211_minstrel.c12
-rw-r--r--net/mac80211/rc80211_minstrel_ht.c22
-rw-r--r--net/mac80211/scan.c15
-rw-r--r--net/mac80211/tdls.c325
-rw-r--r--net/mac80211/trace.h32
-rw-r--r--net/mac80211/tx.c189
-rw-r--r--net/mac80211/util.c46
-rw-r--r--net/nfc/digital.h1
-rw-r--r--net/nfc/digital_core.c20
-rw-r--r--net/nfc/digital_technology.c230
-rw-r--r--net/nfc/hci/command.c6
-rw-r--r--net/nfc/hci/core.c47
-rw-r--r--net/nfc/llcp_commands.c2
-rw-r--r--net/nfc/llcp_core.c11
-rw-r--r--net/nfc/nci/core.c9
-rw-r--r--net/nfc/nci/ntf.c7
-rw-r--r--net/nfc/nfc.h6
-rw-r--r--net/nfc/rawsock.c94
-rw-r--r--net/rfkill/rfkill-gpio.c59
-rw-r--r--net/wireless/ap.c4
-rw-r--r--net/wireless/chan.c5
-rw-r--r--net/wireless/core.c67
-rw-r--r--net/wireless/core.h7
-rw-r--r--net/wireless/ibss.c2
-rw-r--r--net/wireless/mesh.c4
-rw-r--r--net/wireless/nl80211.c140
-rw-r--r--net/wireless/rdev-ops.h2
-rw-r--r--net/wireless/reg.c3
-rw-r--r--net/wireless/scan.c12
-rw-r--r--net/wireless/sme.c8
-rw-r--r--net/wireless/trace.h37
-rw-r--r--net/wireless/util.c38
244 files changed, 7662 insertions, 3181 deletions
diff --git a/Documentation/devicetree/bindings/net/nfc/pn544.txt b/Documentation/devicetree/bindings/net/nfc/pn544.txt
new file mode 100644
index 000000000000..dab69f36167c
--- /dev/null
+++ b/Documentation/devicetree/bindings/net/nfc/pn544.txt
@@ -0,0 +1,35 @@
1* NXP Semiconductors PN544 NFC Controller
2
3Required properties:
4- compatible: Should be "nxp,pn544-i2c".
5- clock-frequency: I²C work frequency.
6- reg: address on the bus
7- interrupt-parent: phandle for the interrupt gpio controller
8- interrupts: GPIO interrupt to which the chip is connected
9- enable-gpios: Output GPIO pin used for enabling/disabling the PN544
10- firmware-gpios: Output GPIO pin used to enter firmware download mode
11
12Optional SoC Specific Properties:
13- pinctrl-names: Contains only one value - "default".
14- pintctrl-0: Specifies the pin control groups used for this controller.
15
16Example (for ARM-based BeagleBone with PN544 on I2C2):
17
18&i2c2 {
19
20 status = "okay";
21
22 pn544: pn544@28 {
23
24 compatible = "nxp,pn544-i2c";
25
26 reg = <0x28>;
27 clock-frequency = <400000>;
28
29 interrupt-parent = <&gpio1>;
30 interrupts = <17 GPIO_ACTIVE_HIGH>;
31
32 enable-gpios = <&gpio3 21 GPIO_ACTIVE_HIGH>;
33 firmware-gpios = <&gpio3 19 GPIO_ACTIVE_HIGH>;
34 };
35};
diff --git a/Documentation/devicetree/bindings/net/nfc/st21nfca.txt b/Documentation/devicetree/bindings/net/nfc/st21nfca.txt
new file mode 100644
index 000000000000..4724fe669172
--- /dev/null
+++ b/Documentation/devicetree/bindings/net/nfc/st21nfca.txt
@@ -0,0 +1,33 @@
1* STMicroelectronics SAS. ST21NFCA NFC Controller
2
3Required properties:
4- compatible: Should be "st,st21nfca-i2c".
5- clock-frequency: I²C work frequency.
6- reg: address on the bus
7- interrupt-parent: phandle for the interrupt gpio controller
8- interrupts: GPIO interrupt to which the chip is connected
9- enable-gpios: Output GPIO pin used for enabling/disabling the ST21NFCA
10
11Optional SoC Specific Properties:
12- pinctrl-names: Contains only one value - "default".
13- pintctrl-0: Specifies the pin control groups used for this controller.
14
15Example (for ARM-based BeagleBoard xM with ST21NFCA on I2C2):
16
17&i2c2 {
18
19 status = "okay";
20
21 st21nfca: st21nfca@1 {
22
23 compatible = "st,st21nfca_i2c";
24
25 reg = <0x01>;
26 clock-frequency = <400000>;
27
28 interrupt-parent = <&gpio5>;
29 interrupts = <2 IRQ_TYPE_LEVEL_LOW>;
30
31 enable-gpios = <&gpio5 29 GPIO_ACTIVE_HIGH>;
32 };
33};
diff --git a/Documentation/devicetree/bindings/net/nfc/trf7970a.txt b/Documentation/devicetree/bindings/net/nfc/trf7970a.txt
index 8dd3ef7bc56b..1e436133685f 100644
--- a/Documentation/devicetree/bindings/net/nfc/trf7970a.txt
+++ b/Documentation/devicetree/bindings/net/nfc/trf7970a.txt
@@ -12,6 +12,7 @@ Required properties:
12Optional SoC Specific Properties: 12Optional SoC Specific Properties:
13- pinctrl-names: Contains only one value - "default". 13- pinctrl-names: Contains only one value - "default".
14- pintctrl-0: Specifies the pin control groups used for this controller. 14- pintctrl-0: Specifies the pin control groups used for this controller.
15- autosuspend-delay: Specify autosuspend delay in milliseconds.
15 16
16Example (for ARM-based BeagleBone with TRF7970A on SPI1): 17Example (for ARM-based BeagleBone with TRF7970A on SPI1):
17 18
@@ -29,6 +30,7 @@ Example (for ARM-based BeagleBone with TRF7970A on SPI1):
29 ti,enable-gpios = <&gpio2 2 GPIO_ACTIVE_LOW>, 30 ti,enable-gpios = <&gpio2 2 GPIO_ACTIVE_LOW>,
30 <&gpio2 5 GPIO_ACTIVE_LOW>; 31 <&gpio2 5 GPIO_ACTIVE_LOW>;
31 vin-supply = <&ldo3_reg>; 32 vin-supply = <&ldo3_reg>;
33 autosuspend-delay = <30000>;
32 status = "okay"; 34 status = "okay";
33 }; 35 };
34}; 36};
diff --git a/arch/arm/mach-tegra/board-paz00.c b/arch/arm/mach-tegra/board-paz00.c
index e4dec9fcb084..9c6029ba526f 100644
--- a/arch/arm/mach-tegra/board-paz00.c
+++ b/arch/arm/mach-tegra/board-paz00.c
@@ -23,9 +23,7 @@
23#include "board.h" 23#include "board.h"
24 24
25static struct rfkill_gpio_platform_data wifi_rfkill_platform_data = { 25static struct rfkill_gpio_platform_data wifi_rfkill_platform_data = {
26 .name = "wifi_rfkill", 26 .name = "wifi_rfkill",
27 .reset_gpio = 25, /* PD1 */
28 .shutdown_gpio = 85, /* PK5 */
29 .type = RFKILL_TYPE_WLAN, 27 .type = RFKILL_TYPE_WLAN,
30}; 28};
31 29
diff --git a/arch/mips/bcm47xx/sprom.c b/arch/mips/bcm47xx/sprom.c
index a8b5408dd349..da4cdb16844e 100644
--- a/arch/mips/bcm47xx/sprom.c
+++ b/arch/mips/bcm47xx/sprom.c
@@ -168,6 +168,7 @@ static void nvram_read_alpha2(const char *prefix, const char *name,
168static void bcm47xx_fill_sprom_r1234589(struct ssb_sprom *sprom, 168static void bcm47xx_fill_sprom_r1234589(struct ssb_sprom *sprom,
169 const char *prefix, bool fallback) 169 const char *prefix, bool fallback)
170{ 170{
171 nvram_read_u16(prefix, NULL, "devid", &sprom->dev_id, 0, fallback);
171 nvram_read_u8(prefix, NULL, "ledbh0", &sprom->gpio0, 0xff, fallback); 172 nvram_read_u8(prefix, NULL, "ledbh0", &sprom->gpio0, 0xff, fallback);
172 nvram_read_u8(prefix, NULL, "ledbh1", &sprom->gpio1, 0xff, fallback); 173 nvram_read_u8(prefix, NULL, "ledbh1", &sprom->gpio1, 0xff, fallback);
173 nvram_read_u8(prefix, NULL, "ledbh2", &sprom->gpio2, 0xff, fallback); 174 nvram_read_u8(prefix, NULL, "ledbh2", &sprom->gpio2, 0xff, fallback);
diff --git a/drivers/mmc/host/mmc_spi.c b/drivers/mmc/host/mmc_spi.c
index 0a87e5691341..cc8d4a6099cd 100644
--- a/drivers/mmc/host/mmc_spi.c
+++ b/drivers/mmc/host/mmc_spi.c
@@ -448,7 +448,6 @@ mmc_spi_command_send(struct mmc_spi_host *host,
448{ 448{
449 struct scratch *data = host->data; 449 struct scratch *data = host->data;
450 u8 *cp = data->status; 450 u8 *cp = data->status;
451 u32 arg = cmd->arg;
452 int status; 451 int status;
453 struct spi_transfer *t; 452 struct spi_transfer *t;
454 453
@@ -465,14 +464,12 @@ mmc_spi_command_send(struct mmc_spi_host *host,
465 * We init the whole buffer to all-ones, which is what we need 464 * We init the whole buffer to all-ones, which is what we need
466 * to write while we're reading (later) response data. 465 * to write while we're reading (later) response data.
467 */ 466 */
468 memset(cp++, 0xff, sizeof(data->status)); 467 memset(cp, 0xff, sizeof(data->status));
469 468
470 *cp++ = 0x40 | cmd->opcode; 469 cp[1] = 0x40 | cmd->opcode;
471 *cp++ = (u8)(arg >> 24); 470 put_unaligned_be32(cmd->arg, cp+2);
472 *cp++ = (u8)(arg >> 16); 471 cp[6] = crc7_be(0, cp+1, 5) | 0x01;
473 *cp++ = (u8)(arg >> 8); 472 cp += 7;
474 *cp++ = (u8)arg;
475 *cp++ = (crc7(0, &data->status[1], 5) << 1) | 0x01;
476 473
477 /* Then, read up to 13 bytes (while writing all-ones): 474 /* Then, read up to 13 bytes (while writing all-ones):
478 * - N(CR) (== 1..8) bytes of all-ones 475 * - N(CR) (== 1..8) bytes of all-ones
@@ -711,10 +708,7 @@ mmc_spi_writeblock(struct mmc_spi_host *host, struct spi_transfer *t,
711 * so we have to cope with this situation and check the response 708 * so we have to cope with this situation and check the response
712 * bit-by-bit. Arggh!!! 709 * bit-by-bit. Arggh!!!
713 */ 710 */
714 pattern = scratch->status[0] << 24; 711 pattern = get_unaligned_be32(scratch->status);
715 pattern |= scratch->status[1] << 16;
716 pattern |= scratch->status[2] << 8;
717 pattern |= scratch->status[3];
718 712
719 /* First 3 bit of pattern are undefined */ 713 /* First 3 bit of pattern are undefined */
720 pattern |= 0xE0000000; 714 pattern |= 0xE0000000;
diff --git a/drivers/net/wireless/ath/ath10k/core.c b/drivers/net/wireless/ath/ath10k/core.c
index 6abde37fb339..75b3dfbd6509 100644
--- a/drivers/net/wireless/ath/ath10k/core.c
+++ b/drivers/net/wireless/ath/ath10k/core.c
@@ -680,8 +680,8 @@ static void ath10k_core_restart(struct work_struct *work)
680 680
681 switch (ar->state) { 681 switch (ar->state) {
682 case ATH10K_STATE_ON: 682 case ATH10K_STATE_ON:
683 ath10k_halt(ar);
684 ar->state = ATH10K_STATE_RESTARTING; 683 ar->state = ATH10K_STATE_RESTARTING;
684 ath10k_halt(ar);
685 ieee80211_restart_hw(ar->hw); 685 ieee80211_restart_hw(ar->hw);
686 break; 686 break;
687 case ATH10K_STATE_OFF: 687 case ATH10K_STATE_OFF:
@@ -908,7 +908,9 @@ void ath10k_core_stop(struct ath10k *ar)
908 lockdep_assert_held(&ar->conf_mutex); 908 lockdep_assert_held(&ar->conf_mutex);
909 909
910 /* try to suspend target */ 910 /* try to suspend target */
911 ath10k_wait_for_suspend(ar, WMI_PDEV_SUSPEND_AND_DISABLE_INTR); 911 if (ar->state != ATH10K_STATE_RESTARTING)
912 ath10k_wait_for_suspend(ar, WMI_PDEV_SUSPEND_AND_DISABLE_INTR);
913
912 ath10k_debug_stop(ar); 914 ath10k_debug_stop(ar);
913 ath10k_htc_stop(&ar->htc); 915 ath10k_htc_stop(&ar->htc);
914 ath10k_htt_detach(&ar->htt); 916 ath10k_htt_detach(&ar->htt);
diff --git a/drivers/net/wireless/ath/ath10k/mac.c b/drivers/net/wireless/ath/ath10k/mac.c
index 0ac5437492fd..7026f021ccbb 100644
--- a/drivers/net/wireless/ath/ath10k/mac.c
+++ b/drivers/net/wireless/ath/ath10k/mac.c
@@ -2291,6 +2291,8 @@ static void ath10k_tx(struct ieee80211_hw *hw,
2291 */ 2291 */
2292void ath10k_halt(struct ath10k *ar) 2292void ath10k_halt(struct ath10k *ar)
2293{ 2293{
2294 struct ath10k_vif *arvif;
2295
2294 lockdep_assert_held(&ar->conf_mutex); 2296 lockdep_assert_held(&ar->conf_mutex);
2295 2297
2296 if (ath10k_monitor_is_enabled(ar)) { 2298 if (ath10k_monitor_is_enabled(ar)) {
@@ -2313,6 +2315,17 @@ void ath10k_halt(struct ath10k *ar)
2313 ar->scan.in_progress = false; 2315 ar->scan.in_progress = false;
2314 ieee80211_scan_completed(ar->hw, true); 2316 ieee80211_scan_completed(ar->hw, true);
2315 } 2317 }
2318
2319 list_for_each_entry(arvif, &ar->arvifs, list) {
2320 if (!arvif->beacon)
2321 continue;
2322
2323 dma_unmap_single(arvif->ar->dev,
2324 ATH10K_SKB_CB(arvif->beacon)->paddr,
2325 arvif->beacon->len, DMA_TO_DEVICE);
2326 dev_kfree_skb_any(arvif->beacon);
2327 arvif->beacon = NULL;
2328 }
2316 spin_unlock_bh(&ar->data_lock); 2329 spin_unlock_bh(&ar->data_lock);
2317} 2330}
2318 2331
@@ -2771,6 +2784,9 @@ static void ath10k_remove_interface(struct ieee80211_hw *hw,
2771 2784
2772 spin_lock_bh(&ar->data_lock); 2785 spin_lock_bh(&ar->data_lock);
2773 if (arvif->beacon) { 2786 if (arvif->beacon) {
2787 dma_unmap_single(arvif->ar->dev,
2788 ATH10K_SKB_CB(arvif->beacon)->paddr,
2789 arvif->beacon->len, DMA_TO_DEVICE);
2774 dev_kfree_skb_any(arvif->beacon); 2790 dev_kfree_skb_any(arvif->beacon);
2775 arvif->beacon = NULL; 2791 arvif->beacon = NULL;
2776 } 2792 }
diff --git a/drivers/net/wireless/ath/ath10k/pci.c b/drivers/net/wireless/ath/ath10k/pci.c
index bf1083d52e61..66b1f3017f2b 100644
--- a/drivers/net/wireless/ath/ath10k/pci.c
+++ b/drivers/net/wireless/ath/ath10k/pci.c
@@ -2452,6 +2452,10 @@ static int ath10k_pci_wait_for_target_init(struct ath10k *ar)
2452 if (val == 0xffffffff) 2452 if (val == 0xffffffff)
2453 continue; 2453 continue;
2454 2454
2455 /* the device has crashed so don't bother trying anymore */
2456 if (val & FW_IND_EVENT_PENDING)
2457 break;
2458
2455 if (val & FW_IND_INITIALIZED) 2459 if (val & FW_IND_INITIALIZED)
2456 break; 2460 break;
2457 2461
@@ -2464,7 +2468,19 @@ static int ath10k_pci_wait_for_target_init(struct ath10k *ar)
2464 mdelay(10); 2468 mdelay(10);
2465 } while (time_before(jiffies, timeout)); 2469 } while (time_before(jiffies, timeout));
2466 2470
2467 if (val == 0xffffffff || !(val & FW_IND_INITIALIZED)) { 2471 if (val == 0xffffffff) {
2472 ath10k_err("failed to read device register, device is gone\n");
2473 ret = -EIO;
2474 goto out;
2475 }
2476
2477 if (val & FW_IND_EVENT_PENDING) {
2478 ath10k_warn("device has crashed during init\n");
2479 ret = -ECOMM;
2480 goto out;
2481 }
2482
2483 if (!(val & FW_IND_INITIALIZED)) {
2468 ath10k_err("failed to receive initialized event from target: %08x\n", 2484 ath10k_err("failed to receive initialized event from target: %08x\n",
2469 val); 2485 val);
2470 ret = -ETIMEDOUT; 2486 ret = -ETIMEDOUT;
diff --git a/drivers/net/wireless/ath/ath10k/wmi.c b/drivers/net/wireless/ath/ath10k/wmi.c
index fe4d5f1c672f..72cc4f20d102 100644
--- a/drivers/net/wireless/ath/ath10k/wmi.c
+++ b/drivers/net/wireless/ath/ath10k/wmi.c
@@ -1431,6 +1431,7 @@ static void ath10k_wmi_event_host_swba(struct ath10k *ar, struct sk_buff *skb)
1431 ATH10K_SKB_CB(arvif->beacon)->paddr, 1431 ATH10K_SKB_CB(arvif->beacon)->paddr,
1432 arvif->beacon->len, DMA_TO_DEVICE); 1432 arvif->beacon->len, DMA_TO_DEVICE);
1433 dev_kfree_skb_any(arvif->beacon); 1433 dev_kfree_skb_any(arvif->beacon);
1434 arvif->beacon = NULL;
1434 } 1435 }
1435 1436
1436 ATH10K_SKB_CB(bcn)->paddr = dma_map_single(arvif->ar->dev, 1437 ATH10K_SKB_CB(bcn)->paddr = dma_map_single(arvif->ar->dev,
@@ -1440,6 +1441,7 @@ static void ath10k_wmi_event_host_swba(struct ath10k *ar, struct sk_buff *skb)
1440 ATH10K_SKB_CB(bcn)->paddr); 1441 ATH10K_SKB_CB(bcn)->paddr);
1441 if (ret) { 1442 if (ret) {
1442 ath10k_warn("failed to map beacon: %d\n", ret); 1443 ath10k_warn("failed to map beacon: %d\n", ret);
1444 dev_kfree_skb_any(bcn);
1443 goto skip; 1445 goto skip;
1444 } 1446 }
1445 1447
diff --git a/drivers/net/wireless/ath/ath6kl/cfg80211.c b/drivers/net/wireless/ath/ath6kl/cfg80211.c
index 09285084bcd3..0e26f4a34fda 100644
--- a/drivers/net/wireless/ath/ath6kl/cfg80211.c
+++ b/drivers/net/wireless/ath/ath6kl/cfg80211.c
@@ -1759,7 +1759,7 @@ static bool is_rate_ht40(s32 rate, u8 *mcs, bool *sgi)
1759} 1759}
1760 1760
1761static int ath6kl_get_station(struct wiphy *wiphy, struct net_device *dev, 1761static int ath6kl_get_station(struct wiphy *wiphy, struct net_device *dev,
1762 u8 *mac, struct station_info *sinfo) 1762 const u8 *mac, struct station_info *sinfo)
1763{ 1763{
1764 struct ath6kl *ar = ath6kl_priv(dev); 1764 struct ath6kl *ar = ath6kl_priv(dev);
1765 struct ath6kl_vif *vif = netdev_priv(dev); 1765 struct ath6kl_vif *vif = netdev_priv(dev);
@@ -2974,7 +2974,7 @@ static int ath6kl_stop_ap(struct wiphy *wiphy, struct net_device *dev)
2974static const u8 bcast_addr[ETH_ALEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 2974static const u8 bcast_addr[ETH_ALEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
2975 2975
2976static int ath6kl_del_station(struct wiphy *wiphy, struct net_device *dev, 2976static int ath6kl_del_station(struct wiphy *wiphy, struct net_device *dev,
2977 u8 *mac) 2977 const u8 *mac)
2978{ 2978{
2979 struct ath6kl *ar = ath6kl_priv(dev); 2979 struct ath6kl *ar = ath6kl_priv(dev);
2980 struct ath6kl_vif *vif = netdev_priv(dev); 2980 struct ath6kl_vif *vif = netdev_priv(dev);
@@ -2985,7 +2985,8 @@ static int ath6kl_del_station(struct wiphy *wiphy, struct net_device *dev,
2985} 2985}
2986 2986
2987static int ath6kl_change_station(struct wiphy *wiphy, struct net_device *dev, 2987static int ath6kl_change_station(struct wiphy *wiphy, struct net_device *dev,
2988 u8 *mac, struct station_parameters *params) 2988 const u8 *mac,
2989 struct station_parameters *params)
2989{ 2990{
2990 struct ath6kl *ar = ath6kl_priv(dev); 2991 struct ath6kl *ar = ath6kl_priv(dev);
2991 struct ath6kl_vif *vif = netdev_priv(dev); 2992 struct ath6kl_vif *vif = netdev_priv(dev);
diff --git a/drivers/net/wireless/ath/ath6kl/wmi.c b/drivers/net/wireless/ath/ath6kl/wmi.c
index 0c0e1e36e40f..4d7f9e4712e9 100644
--- a/drivers/net/wireless/ath/ath6kl/wmi.c
+++ b/drivers/net/wireless/ath/ath6kl/wmi.c
@@ -2320,7 +2320,7 @@ int ath6kl_wmi_addkey_cmd(struct wmi *wmi, u8 if_idx, u8 key_index,
2320 return ret; 2320 return ret;
2321} 2321}
2322 2322
2323int ath6kl_wmi_add_krk_cmd(struct wmi *wmi, u8 if_idx, u8 *krk) 2323int ath6kl_wmi_add_krk_cmd(struct wmi *wmi, u8 if_idx, const u8 *krk)
2324{ 2324{
2325 struct sk_buff *skb; 2325 struct sk_buff *skb;
2326 struct wmi_add_krk_cmd *cmd; 2326 struct wmi_add_krk_cmd *cmd;
diff --git a/drivers/net/wireless/ath/ath6kl/wmi.h b/drivers/net/wireless/ath/ath6kl/wmi.h
index 1f05ecd97c91..7809afbb3e93 100644
--- a/drivers/net/wireless/ath/ath6kl/wmi.h
+++ b/drivers/net/wireless/ath/ath6kl/wmi.h
@@ -2616,7 +2616,7 @@ int ath6kl_wmi_addkey_cmd(struct wmi *wmi, u8 if_idx, u8 key_index,
2616 u8 *key_material, 2616 u8 *key_material,
2617 u8 key_op_ctrl, u8 *mac_addr, 2617 u8 key_op_ctrl, u8 *mac_addr,
2618 enum wmi_sync_flag sync_flag); 2618 enum wmi_sync_flag sync_flag);
2619int ath6kl_wmi_add_krk_cmd(struct wmi *wmi, u8 if_idx, u8 *krk); 2619int ath6kl_wmi_add_krk_cmd(struct wmi *wmi, u8 if_idx, const u8 *krk);
2620int ath6kl_wmi_deletekey_cmd(struct wmi *wmi, u8 if_idx, u8 key_index); 2620int ath6kl_wmi_deletekey_cmd(struct wmi *wmi, u8 if_idx, u8 key_index);
2621int ath6kl_wmi_setpmkid_cmd(struct wmi *wmi, u8 if_idx, const u8 *bssid, 2621int ath6kl_wmi_setpmkid_cmd(struct wmi *wmi, u8 if_idx, const u8 *bssid,
2622 const u8 *pmkid, bool set); 2622 const u8 *pmkid, bool set);
diff --git a/drivers/net/wireless/ath/ath9k/Makefile b/drivers/net/wireless/ath/ath9k/Makefile
index 8e1c7b0fe76c..8fcd586d1c39 100644
--- a/drivers/net/wireless/ath/ath9k/Makefile
+++ b/drivers/net/wireless/ath/ath9k/Makefile
@@ -53,7 +53,8 @@ obj-$(CONFIG_ATH9K_HW) += ath9k_hw.o
53obj-$(CONFIG_ATH9K_COMMON) += ath9k_common.o 53obj-$(CONFIG_ATH9K_COMMON) += ath9k_common.o
54ath9k_common-y:= common.o \ 54ath9k_common-y:= common.o \
55 common-init.o \ 55 common-init.o \
56 common-beacon.o 56 common-beacon.o \
57 common-debug.o
57 58
58ath9k_htc-y += htc_hst.o \ 59ath9k_htc-y += htc_hst.o \
59 hif_usb.o \ 60 hif_usb.o \
diff --git a/drivers/net/wireless/ath/ath9k/ath9k.h b/drivers/net/wireless/ath/ath9k/ath9k.h
index 33a2ae77b595..b20469425865 100644
--- a/drivers/net/wireless/ath/ath9k/ath9k.h
+++ b/drivers/net/wireless/ath/ath9k/ath9k.h
@@ -23,8 +23,8 @@
23#include <linux/leds.h> 23#include <linux/leds.h>
24#include <linux/completion.h> 24#include <linux/completion.h>
25 25
26#include "debug.h"
27#include "common.h" 26#include "common.h"
27#include "debug.h"
28#include "mci.h" 28#include "mci.h"
29#include "dfs.h" 29#include "dfs.h"
30#include "spectral.h" 30#include "spectral.h"
@@ -274,6 +274,7 @@ struct ath_node {
274#ifdef CONFIG_ATH9K_STATION_STATISTICS 274#ifdef CONFIG_ATH9K_STATION_STATISTICS
275 struct ath_rx_rate_stats rx_rate_stats; 275 struct ath_rx_rate_stats rx_rate_stats;
276#endif 276#endif
277 u8 key_idx[4];
277}; 278};
278 279
279struct ath_tx_control { 280struct ath_tx_control {
diff --git a/drivers/net/wireless/ath/ath9k/beacon.c b/drivers/net/wireless/ath/ath9k/beacon.c
index bd9e634879e6..e387f0b2954a 100644
--- a/drivers/net/wireless/ath/ath9k/beacon.c
+++ b/drivers/net/wireless/ath/ath9k/beacon.c
@@ -537,8 +537,6 @@ static void ath9k_cache_beacon_config(struct ath_softc *sc,
537 cur_conf->dtim_period = bss_conf->dtim_period; 537 cur_conf->dtim_period = bss_conf->dtim_period;
538 cur_conf->dtim_count = 1; 538 cur_conf->dtim_count = 1;
539 cur_conf->ibss_creator = bss_conf->ibss_creator; 539 cur_conf->ibss_creator = bss_conf->ibss_creator;
540 cur_conf->bmiss_timeout =
541 ATH_DEFAULT_BMISS_LIMIT * cur_conf->beacon_interval;
542 540
543 /* 541 /*
544 * It looks like mac80211 may end up using beacon interval of zero in 542 * It looks like mac80211 may end up using beacon interval of zero in
@@ -549,6 +547,9 @@ static void ath9k_cache_beacon_config(struct ath_softc *sc,
549 if (cur_conf->beacon_interval == 0) 547 if (cur_conf->beacon_interval == 0)
550 cur_conf->beacon_interval = 100; 548 cur_conf->beacon_interval = 100;
551 549
550 cur_conf->bmiss_timeout =
551 ATH_DEFAULT_BMISS_LIMIT * cur_conf->beacon_interval;
552
552 /* 553 /*
553 * We don't parse dtim period from mac80211 during the driver 554 * We don't parse dtim period from mac80211 during the driver
554 * initialization as it breaks association with hidden-ssid 555 * initialization as it breaks association with hidden-ssid
diff --git a/drivers/net/wireless/ath/ath9k/common-debug.c b/drivers/net/wireless/ath/ath9k/common-debug.c
new file mode 100644
index 000000000000..3b289f933405
--- /dev/null
+++ b/drivers/net/wireless/ath/ath9k/common-debug.c
@@ -0,0 +1,253 @@
1/*
2 * Copyright (c) 2008-2011 Atheros Communications Inc.
3 *
4 * Permission to use, copy, modify, and/or distribute this software for any
5 * purpose with or without fee is hereby granted, provided that the above
6 * copyright notice and this permission notice appear in all copies.
7 *
8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */
16
17#include "common.h"
18
19static ssize_t read_file_modal_eeprom(struct file *file, char __user *user_buf,
20 size_t count, loff_t *ppos)
21{
22 struct ath_hw *ah = file->private_data;
23 u32 len = 0, size = 6000;
24 char *buf;
25 size_t retval;
26
27 buf = kzalloc(size, GFP_KERNEL);
28 if (buf == NULL)
29 return -ENOMEM;
30
31 len = ah->eep_ops->dump_eeprom(ah, false, buf, len, size);
32
33 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
34 kfree(buf);
35
36 return retval;
37}
38
39static const struct file_operations fops_modal_eeprom = {
40 .read = read_file_modal_eeprom,
41 .open = simple_open,
42 .owner = THIS_MODULE,
43 .llseek = default_llseek,
44};
45
46
47void ath9k_cmn_debug_modal_eeprom(struct dentry *debugfs_phy,
48 struct ath_hw *ah)
49{
50 debugfs_create_file("modal_eeprom", S_IRUSR, debugfs_phy, ah,
51 &fops_modal_eeprom);
52}
53EXPORT_SYMBOL(ath9k_cmn_debug_modal_eeprom);
54
55static ssize_t read_file_base_eeprom(struct file *file, char __user *user_buf,
56 size_t count, loff_t *ppos)
57{
58 struct ath_hw *ah = file->private_data;
59 u32 len = 0, size = 1500;
60 ssize_t retval = 0;
61 char *buf;
62
63 buf = kzalloc(size, GFP_KERNEL);
64 if (!buf)
65 return -ENOMEM;
66
67 len = ah->eep_ops->dump_eeprom(ah, true, buf, len, size);
68
69 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
70 kfree(buf);
71
72 return retval;
73}
74
75static const struct file_operations fops_base_eeprom = {
76 .read = read_file_base_eeprom,
77 .open = simple_open,
78 .owner = THIS_MODULE,
79 .llseek = default_llseek,
80};
81
82void ath9k_cmn_debug_base_eeprom(struct dentry *debugfs_phy,
83 struct ath_hw *ah)
84{
85 debugfs_create_file("base_eeprom", S_IRUSR, debugfs_phy, ah,
86 &fops_base_eeprom);
87}
88EXPORT_SYMBOL(ath9k_cmn_debug_base_eeprom);
89
90void ath9k_cmn_debug_stat_rx(struct ath_rx_stats *rxstats,
91 struct ath_rx_status *rs)
92{
93#define RX_PHY_ERR_INC(c) rxstats->phy_err_stats[c]++
94#define RX_CMN_STAT_INC(c) (rxstats->c++)
95
96 RX_CMN_STAT_INC(rx_pkts_all);
97 rxstats->rx_bytes_all += rs->rs_datalen;
98
99 if (rs->rs_status & ATH9K_RXERR_CRC)
100 RX_CMN_STAT_INC(crc_err);
101 if (rs->rs_status & ATH9K_RXERR_DECRYPT)
102 RX_CMN_STAT_INC(decrypt_crc_err);
103 if (rs->rs_status & ATH9K_RXERR_MIC)
104 RX_CMN_STAT_INC(mic_err);
105 if (rs->rs_status & ATH9K_RX_DELIM_CRC_PRE)
106 RX_CMN_STAT_INC(pre_delim_crc_err);
107 if (rs->rs_status & ATH9K_RX_DELIM_CRC_POST)
108 RX_CMN_STAT_INC(post_delim_crc_err);
109 if (rs->rs_status & ATH9K_RX_DECRYPT_BUSY)
110 RX_CMN_STAT_INC(decrypt_busy_err);
111
112 if (rs->rs_status & ATH9K_RXERR_PHY) {
113 RX_CMN_STAT_INC(phy_err);
114 if (rs->rs_phyerr < ATH9K_PHYERR_MAX)
115 RX_PHY_ERR_INC(rs->rs_phyerr);
116 }
117
118#undef RX_CMN_STAT_INC
119#undef RX_PHY_ERR_INC
120}
121EXPORT_SYMBOL(ath9k_cmn_debug_stat_rx);
122
123static ssize_t read_file_recv(struct file *file, char __user *user_buf,
124 size_t count, loff_t *ppos)
125{
126#define RXS_ERR(s, e) \
127 do { \
128 len += scnprintf(buf + len, size - len, \
129 "%18s : %10u\n", s, \
130 rxstats->e); \
131 } while (0)
132
133 struct ath_rx_stats *rxstats = file->private_data;
134 char *buf;
135 unsigned int len = 0, size = 1600;
136 ssize_t retval = 0;
137
138 buf = kzalloc(size, GFP_KERNEL);
139 if (buf == NULL)
140 return -ENOMEM;
141
142 RXS_ERR("PKTS-ALL", rx_pkts_all);
143 RXS_ERR("BYTES-ALL", rx_bytes_all);
144 RXS_ERR("BEACONS", rx_beacons);
145 RXS_ERR("FRAGS", rx_frags);
146 RXS_ERR("SPECTRAL", rx_spectral);
147
148 RXS_ERR("CRC ERR", crc_err);
149 RXS_ERR("DECRYPT CRC ERR", decrypt_crc_err);
150 RXS_ERR("PHY ERR", phy_err);
151 RXS_ERR("MIC ERR", mic_err);
152 RXS_ERR("PRE-DELIM CRC ERR", pre_delim_crc_err);
153 RXS_ERR("POST-DELIM CRC ERR", post_delim_crc_err);
154 RXS_ERR("DECRYPT BUSY ERR", decrypt_busy_err);
155 RXS_ERR("LENGTH-ERR", rx_len_err);
156 RXS_ERR("OOM-ERR", rx_oom_err);
157 RXS_ERR("RATE-ERR", rx_rate_err);
158 RXS_ERR("TOO-MANY-FRAGS", rx_too_many_frags_err);
159
160 if (len > size)
161 len = size;
162
163 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
164 kfree(buf);
165
166 return retval;
167
168#undef RXS_ERR
169}
170
171static const struct file_operations fops_recv = {
172 .read = read_file_recv,
173 .open = simple_open,
174 .owner = THIS_MODULE,
175 .llseek = default_llseek,
176};
177
178void ath9k_cmn_debug_recv(struct dentry *debugfs_phy,
179 struct ath_rx_stats *rxstats)
180{
181 debugfs_create_file("recv", S_IRUSR, debugfs_phy, rxstats,
182 &fops_recv);
183}
184EXPORT_SYMBOL(ath9k_cmn_debug_recv);
185
186static ssize_t read_file_phy_err(struct file *file, char __user *user_buf,
187 size_t count, loff_t *ppos)
188{
189#define PHY_ERR(s, p) \
190 len += scnprintf(buf + len, size - len, "%22s : %10u\n", s, \
191 rxstats->phy_err_stats[p]);
192
193 struct ath_rx_stats *rxstats = file->private_data;
194 char *buf;
195 unsigned int len = 0, size = 1600;
196 ssize_t retval = 0;
197
198 buf = kzalloc(size, GFP_KERNEL);
199 if (buf == NULL)
200 return -ENOMEM;
201
202 PHY_ERR("UNDERRUN ERR", ATH9K_PHYERR_UNDERRUN);
203 PHY_ERR("TIMING ERR", ATH9K_PHYERR_TIMING);
204 PHY_ERR("PARITY ERR", ATH9K_PHYERR_PARITY);
205 PHY_ERR("RATE ERR", ATH9K_PHYERR_RATE);
206 PHY_ERR("LENGTH ERR", ATH9K_PHYERR_LENGTH);
207 PHY_ERR("RADAR ERR", ATH9K_PHYERR_RADAR);
208 PHY_ERR("SERVICE ERR", ATH9K_PHYERR_SERVICE);
209 PHY_ERR("TOR ERR", ATH9K_PHYERR_TOR);
210 PHY_ERR("OFDM-TIMING ERR", ATH9K_PHYERR_OFDM_TIMING);
211 PHY_ERR("OFDM-SIGNAL-PARITY ERR", ATH9K_PHYERR_OFDM_SIGNAL_PARITY);
212 PHY_ERR("OFDM-RATE ERR", ATH9K_PHYERR_OFDM_RATE_ILLEGAL);
213 PHY_ERR("OFDM-LENGTH ERR", ATH9K_PHYERR_OFDM_LENGTH_ILLEGAL);
214 PHY_ERR("OFDM-POWER-DROP ERR", ATH9K_PHYERR_OFDM_POWER_DROP);
215 PHY_ERR("OFDM-SERVICE ERR", ATH9K_PHYERR_OFDM_SERVICE);
216 PHY_ERR("OFDM-RESTART ERR", ATH9K_PHYERR_OFDM_RESTART);
217 PHY_ERR("FALSE-RADAR-EXT ERR", ATH9K_PHYERR_FALSE_RADAR_EXT);
218 PHY_ERR("CCK-TIMING ERR", ATH9K_PHYERR_CCK_TIMING);
219 PHY_ERR("CCK-HEADER-CRC ERR", ATH9K_PHYERR_CCK_HEADER_CRC);
220 PHY_ERR("CCK-RATE ERR", ATH9K_PHYERR_CCK_RATE_ILLEGAL);
221 PHY_ERR("CCK-SERVICE ERR", ATH9K_PHYERR_CCK_SERVICE);
222 PHY_ERR("CCK-RESTART ERR", ATH9K_PHYERR_CCK_RESTART);
223 PHY_ERR("CCK-LENGTH ERR", ATH9K_PHYERR_CCK_LENGTH_ILLEGAL);
224 PHY_ERR("CCK-POWER-DROP ERR", ATH9K_PHYERR_CCK_POWER_DROP);
225 PHY_ERR("HT-CRC ERR", ATH9K_PHYERR_HT_CRC_ERROR);
226 PHY_ERR("HT-LENGTH ERR", ATH9K_PHYERR_HT_LENGTH_ILLEGAL);
227 PHY_ERR("HT-RATE ERR", ATH9K_PHYERR_HT_RATE_ILLEGAL);
228
229 if (len > size)
230 len = size;
231
232 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
233 kfree(buf);
234
235 return retval;
236
237#undef PHY_ERR
238}
239
240static const struct file_operations fops_phy_err = {
241 .read = read_file_phy_err,
242 .open = simple_open,
243 .owner = THIS_MODULE,
244 .llseek = default_llseek,
245};
246
247void ath9k_cmn_debug_phy_err(struct dentry *debugfs_phy,
248 struct ath_rx_stats *rxstats)
249{
250 debugfs_create_file("phy_err", S_IRUSR, debugfs_phy, rxstats,
251 &fops_phy_err);
252}
253EXPORT_SYMBOL(ath9k_cmn_debug_phy_err);
diff --git a/drivers/net/wireless/ath/ath9k/common-debug.h b/drivers/net/wireless/ath/ath9k/common-debug.h
new file mode 100644
index 000000000000..7c9788490f7f
--- /dev/null
+++ b/drivers/net/wireless/ath/ath9k/common-debug.h
@@ -0,0 +1,72 @@
1/*
2 * Copyright (c) 2008-2011 Atheros Communications Inc.
3 *
4 * Permission to use, copy, modify, and/or distribute this software for any
5 * purpose with or without fee is hereby granted, provided that the above
6 * copyright notice and this permission notice appear in all copies.
7 *
8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */
16
17
18
19/**
20 * struct ath_rx_stats - RX Statistics
21 * @rx_pkts_all: No. of total frames received, including ones that
22 may have had errors.
23 * @rx_bytes_all: No. of total bytes received, including ones that
24 may have had errors.
25 * @crc_err: No. of frames with incorrect CRC value
26 * @decrypt_crc_err: No. of frames whose CRC check failed after
27 decryption process completed
28 * @phy_err: No. of frames whose reception failed because the PHY
29 encountered an error
30 * @mic_err: No. of frames with incorrect TKIP MIC verification failure
31 * @pre_delim_crc_err: Pre-Frame delimiter CRC error detections
32 * @post_delim_crc_err: Post-Frame delimiter CRC error detections
33 * @decrypt_busy_err: Decryption interruptions counter
34 * @phy_err_stats: Individual PHY error statistics
35 * @rx_len_err: No. of frames discarded due to bad length.
36 * @rx_oom_err: No. of frames dropped due to OOM issues.
37 * @rx_rate_err: No. of frames dropped due to rate errors.
38 * @rx_too_many_frags_err: Frames dropped due to too-many-frags received.
39 * @rx_beacons: No. of beacons received.
40 * @rx_frags: No. of rx-fragements received.
41 * @rx_spectral: No of spectral packets received.
42 */
43struct ath_rx_stats {
44 u32 rx_pkts_all;
45 u32 rx_bytes_all;
46 u32 crc_err;
47 u32 decrypt_crc_err;
48 u32 phy_err;
49 u32 mic_err;
50 u32 pre_delim_crc_err;
51 u32 post_delim_crc_err;
52 u32 decrypt_busy_err;
53 u32 phy_err_stats[ATH9K_PHYERR_MAX];
54 u32 rx_len_err;
55 u32 rx_oom_err;
56 u32 rx_rate_err;
57 u32 rx_too_many_frags_err;
58 u32 rx_beacons;
59 u32 rx_frags;
60 u32 rx_spectral;
61};
62
63void ath9k_cmn_debug_modal_eeprom(struct dentry *debugfs_phy,
64 struct ath_hw *ah);
65void ath9k_cmn_debug_base_eeprom(struct dentry *debugfs_phy,
66 struct ath_hw *ah);
67void ath9k_cmn_debug_stat_rx(struct ath_rx_stats *rxstats,
68 struct ath_rx_status *rs);
69void ath9k_cmn_debug_recv(struct dentry *debugfs_phy,
70 struct ath_rx_stats *rxstats);
71void ath9k_cmn_debug_phy_err(struct dentry *debugfs_phy,
72 struct ath_rx_stats *rxstats);
diff --git a/drivers/net/wireless/ath/ath9k/common.h b/drivers/net/wireless/ath/ath9k/common.h
index ca38116838f0..ffc454b18637 100644
--- a/drivers/net/wireless/ath/ath9k/common.h
+++ b/drivers/net/wireless/ath/ath9k/common.h
@@ -23,6 +23,7 @@
23 23
24#include "common-init.h" 24#include "common-init.h"
25#include "common-beacon.h" 25#include "common-beacon.h"
26#include "common-debug.h"
26 27
27/* Common header for Atheros 802.11n base driver cores */ 28/* Common header for Atheros 802.11n base driver cores */
28 29
diff --git a/drivers/net/wireless/ath/ath9k/debug.c b/drivers/net/wireless/ath/ath9k/debug.c
index 780ff1bee6f6..6cc42be48d4e 100644
--- a/drivers/net/wireless/ath/ath9k/debug.c
+++ b/drivers/net/wireless/ath/ath9k/debug.c
@@ -948,151 +948,11 @@ static const struct file_operations fops_reset = {
948 .llseek = default_llseek, 948 .llseek = default_llseek,
949}; 949};
950 950
951static ssize_t read_file_recv(struct file *file, char __user *user_buf,
952 size_t count, loff_t *ppos)
953{
954#define RXS_ERR(s, e) \
955 do { \
956 len += scnprintf(buf + len, size - len, \
957 "%18s : %10u\n", s, \
958 sc->debug.stats.rxstats.e);\
959 } while (0)
960
961 struct ath_softc *sc = file->private_data;
962 char *buf;
963 unsigned int len = 0, size = 1600;
964 ssize_t retval = 0;
965
966 buf = kzalloc(size, GFP_KERNEL);
967 if (buf == NULL)
968 return -ENOMEM;
969
970 RXS_ERR("PKTS-ALL", rx_pkts_all);
971 RXS_ERR("BYTES-ALL", rx_bytes_all);
972 RXS_ERR("BEACONS", rx_beacons);
973 RXS_ERR("FRAGS", rx_frags);
974 RXS_ERR("SPECTRAL", rx_spectral);
975
976 RXS_ERR("CRC ERR", crc_err);
977 RXS_ERR("DECRYPT CRC ERR", decrypt_crc_err);
978 RXS_ERR("PHY ERR", phy_err);
979 RXS_ERR("MIC ERR", mic_err);
980 RXS_ERR("PRE-DELIM CRC ERR", pre_delim_crc_err);
981 RXS_ERR("POST-DELIM CRC ERR", post_delim_crc_err);
982 RXS_ERR("DECRYPT BUSY ERR", decrypt_busy_err);
983 RXS_ERR("LENGTH-ERR", rx_len_err);
984 RXS_ERR("OOM-ERR", rx_oom_err);
985 RXS_ERR("RATE-ERR", rx_rate_err);
986 RXS_ERR("TOO-MANY-FRAGS", rx_too_many_frags_err);
987
988 if (len > size)
989 len = size;
990
991 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
992 kfree(buf);
993
994 return retval;
995
996#undef RXS_ERR
997}
998
999void ath_debug_stat_rx(struct ath_softc *sc, struct ath_rx_status *rs) 951void ath_debug_stat_rx(struct ath_softc *sc, struct ath_rx_status *rs)
1000{ 952{
1001#define RX_PHY_ERR_INC(c) sc->debug.stats.rxstats.phy_err_stats[c]++ 953 ath9k_cmn_debug_stat_rx(&sc->debug.stats.rxstats, rs);
1002
1003 RX_STAT_INC(rx_pkts_all);
1004 sc->debug.stats.rxstats.rx_bytes_all += rs->rs_datalen;
1005
1006 if (rs->rs_status & ATH9K_RXERR_CRC)
1007 RX_STAT_INC(crc_err);
1008 if (rs->rs_status & ATH9K_RXERR_DECRYPT)
1009 RX_STAT_INC(decrypt_crc_err);
1010 if (rs->rs_status & ATH9K_RXERR_MIC)
1011 RX_STAT_INC(mic_err);
1012 if (rs->rs_status & ATH9K_RX_DELIM_CRC_PRE)
1013 RX_STAT_INC(pre_delim_crc_err);
1014 if (rs->rs_status & ATH9K_RX_DELIM_CRC_POST)
1015 RX_STAT_INC(post_delim_crc_err);
1016 if (rs->rs_status & ATH9K_RX_DECRYPT_BUSY)
1017 RX_STAT_INC(decrypt_busy_err);
1018
1019 if (rs->rs_status & ATH9K_RXERR_PHY) {
1020 RX_STAT_INC(phy_err);
1021 if (rs->rs_phyerr < ATH9K_PHYERR_MAX)
1022 RX_PHY_ERR_INC(rs->rs_phyerr);
1023 }
1024
1025#undef RX_PHY_ERR_INC
1026} 954}
1027 955
1028static const struct file_operations fops_recv = {
1029 .read = read_file_recv,
1030 .open = simple_open,
1031 .owner = THIS_MODULE,
1032 .llseek = default_llseek,
1033};
1034
1035static ssize_t read_file_phy_err(struct file *file, char __user *user_buf,
1036 size_t count, loff_t *ppos)
1037{
1038#define PHY_ERR(s, p) \
1039 len += scnprintf(buf + len, size - len, "%22s : %10u\n", s, \
1040 sc->debug.stats.rxstats.phy_err_stats[p]);
1041
1042 struct ath_softc *sc = file->private_data;
1043 char *buf;
1044 unsigned int len = 0, size = 1600;
1045 ssize_t retval = 0;
1046
1047 buf = kzalloc(size, GFP_KERNEL);
1048 if (buf == NULL)
1049 return -ENOMEM;
1050
1051 PHY_ERR("UNDERRUN ERR", ATH9K_PHYERR_UNDERRUN);
1052 PHY_ERR("TIMING ERR", ATH9K_PHYERR_TIMING);
1053 PHY_ERR("PARITY ERR", ATH9K_PHYERR_PARITY);
1054 PHY_ERR("RATE ERR", ATH9K_PHYERR_RATE);
1055 PHY_ERR("LENGTH ERR", ATH9K_PHYERR_LENGTH);
1056 PHY_ERR("RADAR ERR", ATH9K_PHYERR_RADAR);
1057 PHY_ERR("SERVICE ERR", ATH9K_PHYERR_SERVICE);
1058 PHY_ERR("TOR ERR", ATH9K_PHYERR_TOR);
1059 PHY_ERR("OFDM-TIMING ERR", ATH9K_PHYERR_OFDM_TIMING);
1060 PHY_ERR("OFDM-SIGNAL-PARITY ERR", ATH9K_PHYERR_OFDM_SIGNAL_PARITY);
1061 PHY_ERR("OFDM-RATE ERR", ATH9K_PHYERR_OFDM_RATE_ILLEGAL);
1062 PHY_ERR("OFDM-LENGTH ERR", ATH9K_PHYERR_OFDM_LENGTH_ILLEGAL);
1063 PHY_ERR("OFDM-POWER-DROP ERR", ATH9K_PHYERR_OFDM_POWER_DROP);
1064 PHY_ERR("OFDM-SERVICE ERR", ATH9K_PHYERR_OFDM_SERVICE);
1065 PHY_ERR("OFDM-RESTART ERR", ATH9K_PHYERR_OFDM_RESTART);
1066 PHY_ERR("FALSE-RADAR-EXT ERR", ATH9K_PHYERR_FALSE_RADAR_EXT);
1067 PHY_ERR("CCK-TIMING ERR", ATH9K_PHYERR_CCK_TIMING);
1068 PHY_ERR("CCK-HEADER-CRC ERR", ATH9K_PHYERR_CCK_HEADER_CRC);
1069 PHY_ERR("CCK-RATE ERR", ATH9K_PHYERR_CCK_RATE_ILLEGAL);
1070 PHY_ERR("CCK-SERVICE ERR", ATH9K_PHYERR_CCK_SERVICE);
1071 PHY_ERR("CCK-RESTART ERR", ATH9K_PHYERR_CCK_RESTART);
1072 PHY_ERR("CCK-LENGTH ERR", ATH9K_PHYERR_CCK_LENGTH_ILLEGAL);
1073 PHY_ERR("CCK-POWER-DROP ERR", ATH9K_PHYERR_CCK_POWER_DROP);
1074 PHY_ERR("HT-CRC ERR", ATH9K_PHYERR_HT_CRC_ERROR);
1075 PHY_ERR("HT-LENGTH ERR", ATH9K_PHYERR_HT_LENGTH_ILLEGAL);
1076 PHY_ERR("HT-RATE ERR", ATH9K_PHYERR_HT_RATE_ILLEGAL);
1077
1078 if (len > size)
1079 len = size;
1080
1081 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
1082 kfree(buf);
1083
1084 return retval;
1085
1086#undef PHY_ERR
1087}
1088
1089static const struct file_operations fops_phy_err = {
1090 .read = read_file_phy_err,
1091 .open = simple_open,
1092 .owner = THIS_MODULE,
1093 .llseek = default_llseek,
1094};
1095
1096static ssize_t read_file_regidx(struct file *file, char __user *user_buf, 956static ssize_t read_file_regidx(struct file *file, char __user *user_buf,
1097 size_t count, loff_t *ppos) 957 size_t count, loff_t *ppos)
1098{ 958{
@@ -1268,62 +1128,6 @@ static const struct file_operations fops_dump_nfcal = {
1268 .llseek = default_llseek, 1128 .llseek = default_llseek,
1269}; 1129};
1270 1130
1271static ssize_t read_file_base_eeprom(struct file *file, char __user *user_buf,
1272 size_t count, loff_t *ppos)
1273{
1274 struct ath_softc *sc = file->private_data;
1275 struct ath_hw *ah = sc->sc_ah;
1276 u32 len = 0, size = 1500;
1277 ssize_t retval = 0;
1278 char *buf;
1279
1280 buf = kzalloc(size, GFP_KERNEL);
1281 if (!buf)
1282 return -ENOMEM;
1283
1284 len = ah->eep_ops->dump_eeprom(ah, true, buf, len, size);
1285
1286 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
1287 kfree(buf);
1288
1289 return retval;
1290}
1291
1292static const struct file_operations fops_base_eeprom = {
1293 .read = read_file_base_eeprom,
1294 .open = simple_open,
1295 .owner = THIS_MODULE,
1296 .llseek = default_llseek,
1297};
1298
1299static ssize_t read_file_modal_eeprom(struct file *file, char __user *user_buf,
1300 size_t count, loff_t *ppos)
1301{
1302 struct ath_softc *sc = file->private_data;
1303 struct ath_hw *ah = sc->sc_ah;
1304 u32 len = 0, size = 6000;
1305 char *buf;
1306 size_t retval;
1307
1308 buf = kzalloc(size, GFP_KERNEL);
1309 if (buf == NULL)
1310 return -ENOMEM;
1311
1312 len = ah->eep_ops->dump_eeprom(ah, false, buf, len, size);
1313
1314 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
1315 kfree(buf);
1316
1317 return retval;
1318}
1319
1320static const struct file_operations fops_modal_eeprom = {
1321 .read = read_file_modal_eeprom,
1322 .open = simple_open,
1323 .owner = THIS_MODULE,
1324 .llseek = default_llseek,
1325};
1326
1327#ifdef CONFIG_ATH9K_BTCOEX_SUPPORT 1131#ifdef CONFIG_ATH9K_BTCOEX_SUPPORT
1328static ssize_t read_file_btcoex(struct file *file, char __user *user_buf, 1132static ssize_t read_file_btcoex(struct file *file, char __user *user_buf,
1329 size_t count, loff_t *ppos) 1133 size_t count, loff_t *ppos)
@@ -1524,10 +1328,10 @@ int ath9k_init_debug(struct ath_hw *ah)
1524 &fops_misc); 1328 &fops_misc);
1525 debugfs_create_file("reset", S_IRUSR, sc->debug.debugfs_phy, sc, 1329 debugfs_create_file("reset", S_IRUSR, sc->debug.debugfs_phy, sc,
1526 &fops_reset); 1330 &fops_reset);
1527 debugfs_create_file("recv", S_IRUSR, sc->debug.debugfs_phy, sc, 1331
1528 &fops_recv); 1332 ath9k_cmn_debug_recv(sc->debug.debugfs_phy, &sc->debug.stats.rxstats);
1529 debugfs_create_file("phy_err", S_IRUSR, sc->debug.debugfs_phy, sc, 1333 ath9k_cmn_debug_phy_err(sc->debug.debugfs_phy, &sc->debug.stats.rxstats);
1530 &fops_phy_err); 1334
1531 debugfs_create_u8("rx_chainmask", S_IRUSR, sc->debug.debugfs_phy, 1335 debugfs_create_u8("rx_chainmask", S_IRUSR, sc->debug.debugfs_phy,
1532 &ah->rxchainmask); 1336 &ah->rxchainmask);
1533 debugfs_create_u8("tx_chainmask", S_IRUSR, sc->debug.debugfs_phy, 1337 debugfs_create_u8("tx_chainmask", S_IRUSR, sc->debug.debugfs_phy,
@@ -1547,10 +1351,10 @@ int ath9k_init_debug(struct ath_hw *ah)
1547 &fops_regdump); 1351 &fops_regdump);
1548 debugfs_create_file("dump_nfcal", S_IRUSR, sc->debug.debugfs_phy, sc, 1352 debugfs_create_file("dump_nfcal", S_IRUSR, sc->debug.debugfs_phy, sc,
1549 &fops_dump_nfcal); 1353 &fops_dump_nfcal);
1550 debugfs_create_file("base_eeprom", S_IRUSR, sc->debug.debugfs_phy, sc, 1354
1551 &fops_base_eeprom); 1355 ath9k_cmn_debug_base_eeprom(sc->debug.debugfs_phy, sc->sc_ah);
1552 debugfs_create_file("modal_eeprom", S_IRUSR, sc->debug.debugfs_phy, sc, 1356 ath9k_cmn_debug_modal_eeprom(sc->debug.debugfs_phy, sc->sc_ah);
1553 &fops_modal_eeprom); 1357
1554 debugfs_create_u32("gpio_mask", S_IRUSR | S_IWUSR, 1358 debugfs_create_u32("gpio_mask", S_IRUSR | S_IWUSR,
1555 sc->debug.debugfs_phy, &sc->sc_ah->gpio_mask); 1359 sc->debug.debugfs_phy, &sc->sc_ah->gpio_mask);
1556 debugfs_create_u32("gpio_val", S_IRUSR | S_IWUSR, 1360 debugfs_create_u32("gpio_val", S_IRUSR | S_IWUSR,
diff --git a/drivers/net/wireless/ath/ath9k/debug.h b/drivers/net/wireless/ath/ath9k/debug.h
index 559a68c2709c..53ae15bd0c9d 100644
--- a/drivers/net/wireless/ath/ath9k/debug.h
+++ b/drivers/net/wireless/ath/ath9k/debug.h
@@ -221,50 +221,6 @@ struct ath_rx_rate_stats {
221 } cck_stats[4]; 221 } cck_stats[4];
222}; 222};
223 223
224/**
225 * struct ath_rx_stats - RX Statistics
226 * @rx_pkts_all: No. of total frames received, including ones that
227 may have had errors.
228 * @rx_bytes_all: No. of total bytes received, including ones that
229 may have had errors.
230 * @crc_err: No. of frames with incorrect CRC value
231 * @decrypt_crc_err: No. of frames whose CRC check failed after
232 decryption process completed
233 * @phy_err: No. of frames whose reception failed because the PHY
234 encountered an error
235 * @mic_err: No. of frames with incorrect TKIP MIC verification failure
236 * @pre_delim_crc_err: Pre-Frame delimiter CRC error detections
237 * @post_delim_crc_err: Post-Frame delimiter CRC error detections
238 * @decrypt_busy_err: Decryption interruptions counter
239 * @phy_err_stats: Individual PHY error statistics
240 * @rx_len_err: No. of frames discarded due to bad length.
241 * @rx_oom_err: No. of frames dropped due to OOM issues.
242 * @rx_rate_err: No. of frames dropped due to rate errors.
243 * @rx_too_many_frags_err: Frames dropped due to too-many-frags received.
244 * @rx_beacons: No. of beacons received.
245 * @rx_frags: No. of rx-fragements received.
246 * @rx_spectral: No of spectral packets received.
247 */
248struct ath_rx_stats {
249 u32 rx_pkts_all;
250 u32 rx_bytes_all;
251 u32 crc_err;
252 u32 decrypt_crc_err;
253 u32 phy_err;
254 u32 mic_err;
255 u32 pre_delim_crc_err;
256 u32 post_delim_crc_err;
257 u32 decrypt_busy_err;
258 u32 phy_err_stats[ATH9K_PHYERR_MAX];
259 u32 rx_len_err;
260 u32 rx_oom_err;
261 u32 rx_rate_err;
262 u32 rx_too_many_frags_err;
263 u32 rx_beacons;
264 u32 rx_frags;
265 u32 rx_spectral;
266};
267
268#define ANT_MAIN 0 224#define ANT_MAIN 0
269#define ANT_ALT 1 225#define ANT_ALT 1
270 226
diff --git a/drivers/net/wireless/ath/ath9k/dfs.c b/drivers/net/wireless/ath/ath9k/dfs.c
index 857bb28b3894..e0c740dcfea8 100644
--- a/drivers/net/wireless/ath/ath9k/dfs.c
+++ b/drivers/net/wireless/ath/ath9k/dfs.c
@@ -178,12 +178,14 @@ void ath9k_dfs_process_phyerr(struct ath_softc *sc, void *data,
178 pe.ts = mactime; 178 pe.ts = mactime;
179 if (ath9k_postprocess_radar_event(sc, &ard, &pe)) { 179 if (ath9k_postprocess_radar_event(sc, &ard, &pe)) {
180 struct dfs_pattern_detector *pd = sc->dfs_detector; 180 struct dfs_pattern_detector *pd = sc->dfs_detector;
181 static u64 last_ts; 181#ifdef CONFIG_ATH9K_DEBUGFS
182 ath_dbg(common, DFS, 182 ath_dbg(common, DFS,
183 "ath9k_dfs_process_phyerr: channel=%d, ts=%llu, " 183 "ath9k_dfs_process_phyerr: channel=%d, ts=%llu, "
184 "width=%d, rssi=%d, delta_ts=%llu\n", 184 "width=%d, rssi=%d, delta_ts=%llu\n",
185 pe.freq, pe.ts, pe.width, pe.rssi, pe.ts-last_ts); 185 pe.freq, pe.ts, pe.width, pe.rssi,
186 last_ts = pe.ts; 186 pe.ts - sc->debug.stats.dfs_stats.last_ts);
187 sc->debug.stats.dfs_stats.last_ts = pe.ts;
188#endif
187 DFS_STAT_INC(sc, pulses_processed); 189 DFS_STAT_INC(sc, pulses_processed);
188 if (pd != NULL && pd->add_pulse(pd, &pe)) { 190 if (pd != NULL && pd->add_pulse(pd, &pe)) {
189 DFS_STAT_INC(sc, radar_detected); 191 DFS_STAT_INC(sc, radar_detected);
diff --git a/drivers/net/wireless/ath/ath9k/dfs_debug.h b/drivers/net/wireless/ath/ath9k/dfs_debug.h
index 7936c9126a20..d9486867a5e0 100644
--- a/drivers/net/wireless/ath/ath9k/dfs_debug.h
+++ b/drivers/net/wireless/ath/ath9k/dfs_debug.h
@@ -51,6 +51,7 @@ struct ath_dfs_stats {
51 /* pattern detection stats */ 51 /* pattern detection stats */
52 u32 pulses_processed; 52 u32 pulses_processed;
53 u32 radar_detected; 53 u32 radar_detected;
54 u64 last_ts;
54}; 55};
55 56
56#if defined(CONFIG_ATH9K_DFS_DEBUGFS) 57#if defined(CONFIG_ATH9K_DFS_DEBUGFS)
diff --git a/drivers/net/wireless/ath/ath9k/htc.h b/drivers/net/wireless/ath/ath9k/htc.h
index dab1f0cab993..09a5d72f3ff5 100644
--- a/drivers/net/wireless/ath/ath9k/htc.h
+++ b/drivers/net/wireless/ath/ath9k/htc.h
@@ -325,14 +325,14 @@ static inline struct ath9k_htc_tx_ctl *HTC_SKB_CB(struct sk_buff *skb)
325 325
326#define TX_STAT_INC(c) (hif_dev->htc_handle->drv_priv->debug.tx_stats.c++) 326#define TX_STAT_INC(c) (hif_dev->htc_handle->drv_priv->debug.tx_stats.c++)
327#define TX_STAT_ADD(c, a) (hif_dev->htc_handle->drv_priv->debug.tx_stats.c += a) 327#define TX_STAT_ADD(c, a) (hif_dev->htc_handle->drv_priv->debug.tx_stats.c += a)
328#define RX_STAT_INC(c) (hif_dev->htc_handle->drv_priv->debug.rx_stats.c++) 328#define RX_STAT_INC(c) (hif_dev->htc_handle->drv_priv->debug.skbrx_stats.c++)
329#define RX_STAT_ADD(c, a) (hif_dev->htc_handle->drv_priv->debug.rx_stats.c += a) 329#define RX_STAT_ADD(c, a) (hif_dev->htc_handle->drv_priv->debug.skbrx_stats.c += a)
330#define CAB_STAT_INC priv->debug.tx_stats.cab_queued++ 330#define CAB_STAT_INC priv->debug.tx_stats.cab_queued++
331 331
332#define TX_QSTAT_INC(q) (priv->debug.tx_stats.queue_stats[q]++) 332#define TX_QSTAT_INC(q) (priv->debug.tx_stats.queue_stats[q]++)
333 333
334void ath9k_htc_err_stat_rx(struct ath9k_htc_priv *priv, 334void ath9k_htc_err_stat_rx(struct ath9k_htc_priv *priv,
335 struct ath_htc_rx_status *rxs); 335 struct ath_rx_status *rs);
336 336
337struct ath_tx_stats { 337struct ath_tx_stats {
338 u32 buf_queued; 338 u32 buf_queued;
@@ -345,25 +345,18 @@ struct ath_tx_stats {
345 u32 queue_stats[IEEE80211_NUM_ACS]; 345 u32 queue_stats[IEEE80211_NUM_ACS];
346}; 346};
347 347
348struct ath_rx_stats { 348struct ath_skbrx_stats {
349 u32 skb_allocated; 349 u32 skb_allocated;
350 u32 skb_completed; 350 u32 skb_completed;
351 u32 skb_completed_bytes; 351 u32 skb_completed_bytes;
352 u32 skb_dropped; 352 u32 skb_dropped;
353 u32 err_crc;
354 u32 err_decrypt_crc;
355 u32 err_mic;
356 u32 err_pre_delim;
357 u32 err_post_delim;
358 u32 err_decrypt_busy;
359 u32 err_phy;
360 u32 err_phy_stats[ATH9K_PHYERR_MAX];
361}; 353};
362 354
363struct ath9k_debug { 355struct ath9k_debug {
364 struct dentry *debugfs_phy; 356 struct dentry *debugfs_phy;
365 struct ath_tx_stats tx_stats; 357 struct ath_tx_stats tx_stats;
366 struct ath_rx_stats rx_stats; 358 struct ath_rx_stats rx_stats;
359 struct ath_skbrx_stats skbrx_stats;
367}; 360};
368 361
369void ath9k_htc_get_et_strings(struct ieee80211_hw *hw, 362void ath9k_htc_get_et_strings(struct ieee80211_hw *hw,
@@ -385,7 +378,7 @@ void ath9k_htc_get_et_stats(struct ieee80211_hw *hw,
385#define TX_QSTAT_INC(c) do { } while (0) 378#define TX_QSTAT_INC(c) do { } while (0)
386 379
387static inline void ath9k_htc_err_stat_rx(struct ath9k_htc_priv *priv, 380static inline void ath9k_htc_err_stat_rx(struct ath9k_htc_priv *priv,
388 struct ath_htc_rx_status *rxs) 381 struct ath_rx_status *rs)
389{ 382{
390} 383}
391 384
diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_debug.c b/drivers/net/wireless/ath/ath9k/htc_drv_debug.c
index fb071ee4fcfb..8b529e4b8ac4 100644
--- a/drivers/net/wireless/ath/ath9k/htc_drv_debug.c
+++ b/drivers/net/wireless/ath/ath9k/htc_drv_debug.c
@@ -243,39 +243,14 @@ static const struct file_operations fops_xmit = {
243}; 243};
244 244
245void ath9k_htc_err_stat_rx(struct ath9k_htc_priv *priv, 245void ath9k_htc_err_stat_rx(struct ath9k_htc_priv *priv,
246 struct ath_htc_rx_status *rxs) 246 struct ath_rx_status *rs)
247{ 247{
248#define RX_PHY_ERR_INC(c) priv->debug.rx_stats.err_phy_stats[c]++ 248 ath9k_cmn_debug_stat_rx(&priv->debug.rx_stats, rs);
249
250 if (rxs->rs_status & ATH9K_RXERR_CRC)
251 priv->debug.rx_stats.err_crc++;
252 if (rxs->rs_status & ATH9K_RXERR_DECRYPT)
253 priv->debug.rx_stats.err_decrypt_crc++;
254 if (rxs->rs_status & ATH9K_RXERR_MIC)
255 priv->debug.rx_stats.err_mic++;
256 if (rxs->rs_status & ATH9K_RX_DELIM_CRC_PRE)
257 priv->debug.rx_stats.err_pre_delim++;
258 if (rxs->rs_status & ATH9K_RX_DELIM_CRC_POST)
259 priv->debug.rx_stats.err_post_delim++;
260 if (rxs->rs_status & ATH9K_RX_DECRYPT_BUSY)
261 priv->debug.rx_stats.err_decrypt_busy++;
262
263 if (rxs->rs_status & ATH9K_RXERR_PHY) {
264 priv->debug.rx_stats.err_phy++;
265 if (rxs->rs_phyerr < ATH9K_PHYERR_MAX)
266 RX_PHY_ERR_INC(rxs->rs_phyerr);
267 }
268
269#undef RX_PHY_ERR_INC
270} 249}
271 250
272static ssize_t read_file_recv(struct file *file, char __user *user_buf, 251static ssize_t read_file_skb_rx(struct file *file, char __user *user_buf,
273 size_t count, loff_t *ppos) 252 size_t count, loff_t *ppos)
274{ 253{
275#define PHY_ERR(s, p) \
276 len += scnprintf(buf + len, size - len, "%20s : %10u\n", s, \
277 priv->debug.rx_stats.err_phy_stats[p]);
278
279 struct ath9k_htc_priv *priv = file->private_data; 254 struct ath9k_htc_priv *priv = file->private_data;
280 char *buf; 255 char *buf;
281 unsigned int len = 0, size = 1500; 256 unsigned int len = 0, size = 1500;
@@ -287,63 +262,13 @@ static ssize_t read_file_recv(struct file *file, char __user *user_buf,
287 262
288 len += scnprintf(buf + len, size - len, 263 len += scnprintf(buf + len, size - len,
289 "%20s : %10u\n", "SKBs allocated", 264 "%20s : %10u\n", "SKBs allocated",
290 priv->debug.rx_stats.skb_allocated); 265 priv->debug.skbrx_stats.skb_allocated);
291 len += scnprintf(buf + len, size - len, 266 len += scnprintf(buf + len, size - len,
292 "%20s : %10u\n", "SKBs completed", 267 "%20s : %10u\n", "SKBs completed",
293 priv->debug.rx_stats.skb_completed); 268 priv->debug.skbrx_stats.skb_completed);
294 len += scnprintf(buf + len, size - len, 269 len += scnprintf(buf + len, size - len,
295 "%20s : %10u\n", "SKBs Dropped", 270 "%20s : %10u\n", "SKBs Dropped",
296 priv->debug.rx_stats.skb_dropped); 271 priv->debug.skbrx_stats.skb_dropped);
297
298 len += scnprintf(buf + len, size - len,
299 "%20s : %10u\n", "CRC ERR",
300 priv->debug.rx_stats.err_crc);
301 len += scnprintf(buf + len, size - len,
302 "%20s : %10u\n", "DECRYPT CRC ERR",
303 priv->debug.rx_stats.err_decrypt_crc);
304 len += scnprintf(buf + len, size - len,
305 "%20s : %10u\n", "MIC ERR",
306 priv->debug.rx_stats.err_mic);
307 len += scnprintf(buf + len, size - len,
308 "%20s : %10u\n", "PRE-DELIM CRC ERR",
309 priv->debug.rx_stats.err_pre_delim);
310 len += scnprintf(buf + len, size - len,
311 "%20s : %10u\n", "POST-DELIM CRC ERR",
312 priv->debug.rx_stats.err_post_delim);
313 len += scnprintf(buf + len, size - len,
314 "%20s : %10u\n", "DECRYPT BUSY ERR",
315 priv->debug.rx_stats.err_decrypt_busy);
316 len += scnprintf(buf + len, size - len,
317 "%20s : %10u\n", "TOTAL PHY ERR",
318 priv->debug.rx_stats.err_phy);
319
320
321 PHY_ERR("UNDERRUN", ATH9K_PHYERR_UNDERRUN);
322 PHY_ERR("TIMING", ATH9K_PHYERR_TIMING);
323 PHY_ERR("PARITY", ATH9K_PHYERR_PARITY);
324 PHY_ERR("RATE", ATH9K_PHYERR_RATE);
325 PHY_ERR("LENGTH", ATH9K_PHYERR_LENGTH);
326 PHY_ERR("RADAR", ATH9K_PHYERR_RADAR);
327 PHY_ERR("SERVICE", ATH9K_PHYERR_SERVICE);
328 PHY_ERR("TOR", ATH9K_PHYERR_TOR);
329 PHY_ERR("OFDM-TIMING", ATH9K_PHYERR_OFDM_TIMING);
330 PHY_ERR("OFDM-SIGNAL-PARITY", ATH9K_PHYERR_OFDM_SIGNAL_PARITY);
331 PHY_ERR("OFDM-RATE", ATH9K_PHYERR_OFDM_RATE_ILLEGAL);
332 PHY_ERR("OFDM-LENGTH", ATH9K_PHYERR_OFDM_LENGTH_ILLEGAL);
333 PHY_ERR("OFDM-POWER-DROP", ATH9K_PHYERR_OFDM_POWER_DROP);
334 PHY_ERR("OFDM-SERVICE", ATH9K_PHYERR_OFDM_SERVICE);
335 PHY_ERR("OFDM-RESTART", ATH9K_PHYERR_OFDM_RESTART);
336 PHY_ERR("FALSE-RADAR-EXT", ATH9K_PHYERR_FALSE_RADAR_EXT);
337 PHY_ERR("CCK-TIMING", ATH9K_PHYERR_CCK_TIMING);
338 PHY_ERR("CCK-HEADER-CRC", ATH9K_PHYERR_CCK_HEADER_CRC);
339 PHY_ERR("CCK-RATE", ATH9K_PHYERR_CCK_RATE_ILLEGAL);
340 PHY_ERR("CCK-SERVICE", ATH9K_PHYERR_CCK_SERVICE);
341 PHY_ERR("CCK-RESTART", ATH9K_PHYERR_CCK_RESTART);
342 PHY_ERR("CCK-LENGTH", ATH9K_PHYERR_CCK_LENGTH_ILLEGAL);
343 PHY_ERR("CCK-POWER-DROP", ATH9K_PHYERR_CCK_POWER_DROP);
344 PHY_ERR("HT-CRC", ATH9K_PHYERR_HT_CRC_ERROR);
345 PHY_ERR("HT-LENGTH", ATH9K_PHYERR_HT_LENGTH_ILLEGAL);
346 PHY_ERR("HT-RATE", ATH9K_PHYERR_HT_RATE_ILLEGAL);
347 272
348 if (len > size) 273 if (len > size)
349 len = size; 274 len = size;
@@ -352,12 +277,10 @@ static ssize_t read_file_recv(struct file *file, char __user *user_buf,
352 kfree(buf); 277 kfree(buf);
353 278
354 return retval; 279 return retval;
355
356#undef PHY_ERR
357} 280}
358 281
359static const struct file_operations fops_recv = { 282static const struct file_operations fops_skb_rx = {
360 .read = read_file_recv, 283 .read = read_file_skb_rx,
361 .open = simple_open, 284 .open = simple_open,
362 .owner = THIS_MODULE, 285 .owner = THIS_MODULE,
363 .llseek = default_llseek, 286 .llseek = default_llseek,
@@ -486,423 +409,6 @@ static const struct file_operations fops_debug = {
486 .llseek = default_llseek, 409 .llseek = default_llseek,
487}; 410};
488 411
489static ssize_t read_file_base_eeprom(struct file *file, char __user *user_buf,
490 size_t count, loff_t *ppos)
491{
492 struct ath9k_htc_priv *priv = file->private_data;
493 struct ath_common *common = ath9k_hw_common(priv->ah);
494 struct base_eep_header *pBase = NULL;
495 unsigned int len = 0, size = 1500;
496 ssize_t retval = 0;
497 char *buf;
498
499 pBase = ath9k_htc_get_eeprom_base(priv);
500
501 if (pBase == NULL) {
502 ath_err(common, "Unknown EEPROM type\n");
503 return 0;
504 }
505
506 buf = kzalloc(size, GFP_KERNEL);
507 if (buf == NULL)
508 return -ENOMEM;
509
510 len += scnprintf(buf + len, size - len,
511 "%20s : %10d\n", "Major Version",
512 pBase->version >> 12);
513 len += scnprintf(buf + len, size - len,
514 "%20s : %10d\n", "Minor Version",
515 pBase->version & 0xFFF);
516 len += scnprintf(buf + len, size - len,
517 "%20s : %10d\n", "Checksum",
518 pBase->checksum);
519 len += scnprintf(buf + len, size - len,
520 "%20s : %10d\n", "Length",
521 pBase->length);
522 len += scnprintf(buf + len, size - len,
523 "%20s : %10d\n", "RegDomain1",
524 pBase->regDmn[0]);
525 len += scnprintf(buf + len, size - len,
526 "%20s : %10d\n", "RegDomain2",
527 pBase->regDmn[1]);
528 len += scnprintf(buf + len, size - len,
529 "%20s : %10d\n",
530 "TX Mask", pBase->txMask);
531 len += scnprintf(buf + len, size - len,
532 "%20s : %10d\n",
533 "RX Mask", pBase->rxMask);
534 len += scnprintf(buf + len, size - len,
535 "%20s : %10d\n",
536 "Allow 5GHz",
537 !!(pBase->opCapFlags & AR5416_OPFLAGS_11A));
538 len += scnprintf(buf + len, size - len,
539 "%20s : %10d\n",
540 "Allow 2GHz",
541 !!(pBase->opCapFlags & AR5416_OPFLAGS_11G));
542 len += scnprintf(buf + len, size - len,
543 "%20s : %10d\n",
544 "Disable 2GHz HT20",
545 !!(pBase->opCapFlags & AR5416_OPFLAGS_N_2G_HT20));
546 len += scnprintf(buf + len, size - len,
547 "%20s : %10d\n",
548 "Disable 2GHz HT40",
549 !!(pBase->opCapFlags & AR5416_OPFLAGS_N_2G_HT40));
550 len += scnprintf(buf + len, size - len,
551 "%20s : %10d\n",
552 "Disable 5Ghz HT20",
553 !!(pBase->opCapFlags & AR5416_OPFLAGS_N_5G_HT20));
554 len += scnprintf(buf + len, size - len,
555 "%20s : %10d\n",
556 "Disable 5Ghz HT40",
557 !!(pBase->opCapFlags & AR5416_OPFLAGS_N_5G_HT40));
558 len += scnprintf(buf + len, size - len,
559 "%20s : %10d\n",
560 "Big Endian",
561 !!(pBase->eepMisc & 0x01));
562 len += scnprintf(buf + len, size - len,
563 "%20s : %10d\n",
564 "Cal Bin Major Ver",
565 (pBase->binBuildNumber >> 24) & 0xFF);
566 len += scnprintf(buf + len, size - len,
567 "%20s : %10d\n",
568 "Cal Bin Minor Ver",
569 (pBase->binBuildNumber >> 16) & 0xFF);
570 len += scnprintf(buf + len, size - len,
571 "%20s : %10d\n",
572 "Cal Bin Build",
573 (pBase->binBuildNumber >> 8) & 0xFF);
574
575 /*
576 * UB91 specific data.
577 */
578 if (AR_SREV_9271(priv->ah)) {
579 struct base_eep_header_4k *pBase4k =
580 &priv->ah->eeprom.map4k.baseEepHeader;
581
582 len += scnprintf(buf + len, size - len,
583 "%20s : %10d\n",
584 "TX Gain type",
585 pBase4k->txGainType);
586 }
587
588 /*
589 * UB95 specific data.
590 */
591 if (priv->ah->hw_version.usbdev == AR9287_USB) {
592 struct base_eep_ar9287_header *pBase9287 =
593 &priv->ah->eeprom.map9287.baseEepHeader;
594
595 len += scnprintf(buf + len, size - len,
596 "%20s : %10ddB\n",
597 "Power Table Offset",
598 pBase9287->pwrTableOffset);
599
600 len += scnprintf(buf + len, size - len,
601 "%20s : %10d\n",
602 "OpenLoop Power Ctrl",
603 pBase9287->openLoopPwrCntl);
604 }
605
606 len += scnprintf(buf + len, size - len, "%20s : %pM\n", "MacAddress",
607 pBase->macAddr);
608 if (len > size)
609 len = size;
610
611 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
612 kfree(buf);
613
614 return retval;
615}
616
617static const struct file_operations fops_base_eeprom = {
618 .read = read_file_base_eeprom,
619 .open = simple_open,
620 .owner = THIS_MODULE,
621 .llseek = default_llseek,
622};
623
624static ssize_t read_4k_modal_eeprom(struct file *file,
625 char __user *user_buf,
626 size_t count, loff_t *ppos)
627{
628#define PR_EEP(_s, _val) \
629 do { \
630 len += scnprintf(buf + len, size - len, "%20s : %10d\n",\
631 _s, (_val)); \
632 } while (0)
633
634 struct ath9k_htc_priv *priv = file->private_data;
635 struct modal_eep_4k_header *pModal = &priv->ah->eeprom.map4k.modalHeader;
636 unsigned int len = 0, size = 2048;
637 ssize_t retval = 0;
638 char *buf;
639
640 buf = kzalloc(size, GFP_KERNEL);
641 if (buf == NULL)
642 return -ENOMEM;
643
644 PR_EEP("Chain0 Ant. Control", pModal->antCtrlChain[0]);
645 PR_EEP("Ant. Common Control", pModal->antCtrlCommon);
646 PR_EEP("Chain0 Ant. Gain", pModal->antennaGainCh[0]);
647 PR_EEP("Switch Settle", pModal->switchSettling);
648 PR_EEP("Chain0 TxRxAtten", pModal->txRxAttenCh[0]);
649 PR_EEP("Chain0 RxTxMargin", pModal->rxTxMarginCh[0]);
650 PR_EEP("ADC Desired size", pModal->adcDesiredSize);
651 PR_EEP("PGA Desired size", pModal->pgaDesiredSize);
652 PR_EEP("Chain0 xlna Gain", pModal->xlnaGainCh[0]);
653 PR_EEP("txEndToXpaOff", pModal->txEndToXpaOff);
654 PR_EEP("txEndToRxOn", pModal->txEndToRxOn);
655 PR_EEP("txFrameToXpaOn", pModal->txFrameToXpaOn);
656 PR_EEP("CCA Threshold)", pModal->thresh62);
657 PR_EEP("Chain0 NF Threshold", pModal->noiseFloorThreshCh[0]);
658 PR_EEP("xpdGain", pModal->xpdGain);
659 PR_EEP("External PD", pModal->xpd);
660 PR_EEP("Chain0 I Coefficient", pModal->iqCalICh[0]);
661 PR_EEP("Chain0 Q Coefficient", pModal->iqCalQCh[0]);
662 PR_EEP("pdGainOverlap", pModal->pdGainOverlap);
663 PR_EEP("O/D Bias Version", pModal->version);
664 PR_EEP("CCK OutputBias", pModal->ob_0);
665 PR_EEP("BPSK OutputBias", pModal->ob_1);
666 PR_EEP("QPSK OutputBias", pModal->ob_2);
667 PR_EEP("16QAM OutputBias", pModal->ob_3);
668 PR_EEP("64QAM OutputBias", pModal->ob_4);
669 PR_EEP("CCK Driver1_Bias", pModal->db1_0);
670 PR_EEP("BPSK Driver1_Bias", pModal->db1_1);
671 PR_EEP("QPSK Driver1_Bias", pModal->db1_2);
672 PR_EEP("16QAM Driver1_Bias", pModal->db1_3);
673 PR_EEP("64QAM Driver1_Bias", pModal->db1_4);
674 PR_EEP("CCK Driver2_Bias", pModal->db2_0);
675 PR_EEP("BPSK Driver2_Bias", pModal->db2_1);
676 PR_EEP("QPSK Driver2_Bias", pModal->db2_2);
677 PR_EEP("16QAM Driver2_Bias", pModal->db2_3);
678 PR_EEP("64QAM Driver2_Bias", pModal->db2_4);
679 PR_EEP("xPA Bias Level", pModal->xpaBiasLvl);
680 PR_EEP("txFrameToDataStart", pModal->txFrameToDataStart);
681 PR_EEP("txFrameToPaOn", pModal->txFrameToPaOn);
682 PR_EEP("HT40 Power Inc.", pModal->ht40PowerIncForPdadc);
683 PR_EEP("Chain0 bswAtten", pModal->bswAtten[0]);
684 PR_EEP("Chain0 bswMargin", pModal->bswMargin[0]);
685 PR_EEP("HT40 Switch Settle", pModal->swSettleHt40);
686 PR_EEP("Chain0 xatten2Db", pModal->xatten2Db[0]);
687 PR_EEP("Chain0 xatten2Margin", pModal->xatten2Margin[0]);
688 PR_EEP("Ant. Diversity ctl1", pModal->antdiv_ctl1);
689 PR_EEP("Ant. Diversity ctl2", pModal->antdiv_ctl2);
690 PR_EEP("TX Diversity", pModal->tx_diversity);
691
692 if (len > size)
693 len = size;
694
695 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
696 kfree(buf);
697
698 return retval;
699
700#undef PR_EEP
701}
702
703static ssize_t read_def_modal_eeprom(struct file *file,
704 char __user *user_buf,
705 size_t count, loff_t *ppos)
706{
707#define PR_EEP(_s, _val) \
708 do { \
709 if (pBase->opCapFlags & AR5416_OPFLAGS_11G) { \
710 pModal = &priv->ah->eeprom.def.modalHeader[1]; \
711 len += scnprintf(buf + len, size - len, "%20s : %8d%7s", \
712 _s, (_val), "|"); \
713 } \
714 if (pBase->opCapFlags & AR5416_OPFLAGS_11A) { \
715 pModal = &priv->ah->eeprom.def.modalHeader[0]; \
716 len += scnprintf(buf + len, size - len, "%9d\n",\
717 (_val)); \
718 } \
719 } while (0)
720
721 struct ath9k_htc_priv *priv = file->private_data;
722 struct base_eep_header *pBase = &priv->ah->eeprom.def.baseEepHeader;
723 struct modal_eep_header *pModal = NULL;
724 unsigned int len = 0, size = 3500;
725 ssize_t retval = 0;
726 char *buf;
727
728 buf = kzalloc(size, GFP_KERNEL);
729 if (buf == NULL)
730 return -ENOMEM;
731
732 len += scnprintf(buf + len, size - len,
733 "%31s %15s\n", "2G", "5G");
734 len += scnprintf(buf + len, size - len,
735 "%32s %16s\n", "====", "====\n");
736
737 PR_EEP("Chain0 Ant. Control", pModal->antCtrlChain[0]);
738 PR_EEP("Chain1 Ant. Control", pModal->antCtrlChain[1]);
739 PR_EEP("Chain2 Ant. Control", pModal->antCtrlChain[2]);
740 PR_EEP("Ant. Common Control", pModal->antCtrlCommon);
741 PR_EEP("Chain0 Ant. Gain", pModal->antennaGainCh[0]);
742 PR_EEP("Chain1 Ant. Gain", pModal->antennaGainCh[1]);
743 PR_EEP("Chain2 Ant. Gain", pModal->antennaGainCh[2]);
744 PR_EEP("Switch Settle", pModal->switchSettling);
745 PR_EEP("Chain0 TxRxAtten", pModal->txRxAttenCh[0]);
746 PR_EEP("Chain1 TxRxAtten", pModal->txRxAttenCh[1]);
747 PR_EEP("Chain2 TxRxAtten", pModal->txRxAttenCh[2]);
748 PR_EEP("Chain0 RxTxMargin", pModal->rxTxMarginCh[0]);
749 PR_EEP("Chain1 RxTxMargin", pModal->rxTxMarginCh[1]);
750 PR_EEP("Chain2 RxTxMargin", pModal->rxTxMarginCh[2]);
751 PR_EEP("ADC Desired size", pModal->adcDesiredSize);
752 PR_EEP("PGA Desired size", pModal->pgaDesiredSize);
753 PR_EEP("Chain0 xlna Gain", pModal->xlnaGainCh[0]);
754 PR_EEP("Chain1 xlna Gain", pModal->xlnaGainCh[1]);
755 PR_EEP("Chain2 xlna Gain", pModal->xlnaGainCh[2]);
756 PR_EEP("txEndToXpaOff", pModal->txEndToXpaOff);
757 PR_EEP("txEndToRxOn", pModal->txEndToRxOn);
758 PR_EEP("txFrameToXpaOn", pModal->txFrameToXpaOn);
759 PR_EEP("CCA Threshold)", pModal->thresh62);
760 PR_EEP("Chain0 NF Threshold", pModal->noiseFloorThreshCh[0]);
761 PR_EEP("Chain1 NF Threshold", pModal->noiseFloorThreshCh[1]);
762 PR_EEP("Chain2 NF Threshold", pModal->noiseFloorThreshCh[2]);
763 PR_EEP("xpdGain", pModal->xpdGain);
764 PR_EEP("External PD", pModal->xpd);
765 PR_EEP("Chain0 I Coefficient", pModal->iqCalICh[0]);
766 PR_EEP("Chain1 I Coefficient", pModal->iqCalICh[1]);
767 PR_EEP("Chain2 I Coefficient", pModal->iqCalICh[2]);
768 PR_EEP("Chain0 Q Coefficient", pModal->iqCalQCh[0]);
769 PR_EEP("Chain1 Q Coefficient", pModal->iqCalQCh[1]);
770 PR_EEP("Chain2 Q Coefficient", pModal->iqCalQCh[2]);
771 PR_EEP("pdGainOverlap", pModal->pdGainOverlap);
772 PR_EEP("Chain0 OutputBias", pModal->ob);
773 PR_EEP("Chain0 DriverBias", pModal->db);
774 PR_EEP("xPA Bias Level", pModal->xpaBiasLvl);
775 PR_EEP("2chain pwr decrease", pModal->pwrDecreaseFor2Chain);
776 PR_EEP("3chain pwr decrease", pModal->pwrDecreaseFor3Chain);
777 PR_EEP("txFrameToDataStart", pModal->txFrameToDataStart);
778 PR_EEP("txFrameToPaOn", pModal->txFrameToPaOn);
779 PR_EEP("HT40 Power Inc.", pModal->ht40PowerIncForPdadc);
780 PR_EEP("Chain0 bswAtten", pModal->bswAtten[0]);
781 PR_EEP("Chain1 bswAtten", pModal->bswAtten[1]);
782 PR_EEP("Chain2 bswAtten", pModal->bswAtten[2]);
783 PR_EEP("Chain0 bswMargin", pModal->bswMargin[0]);
784 PR_EEP("Chain1 bswMargin", pModal->bswMargin[1]);
785 PR_EEP("Chain2 bswMargin", pModal->bswMargin[2]);
786 PR_EEP("HT40 Switch Settle", pModal->swSettleHt40);
787 PR_EEP("Chain0 xatten2Db", pModal->xatten2Db[0]);
788 PR_EEP("Chain1 xatten2Db", pModal->xatten2Db[1]);
789 PR_EEP("Chain2 xatten2Db", pModal->xatten2Db[2]);
790 PR_EEP("Chain0 xatten2Margin", pModal->xatten2Margin[0]);
791 PR_EEP("Chain1 xatten2Margin", pModal->xatten2Margin[1]);
792 PR_EEP("Chain2 xatten2Margin", pModal->xatten2Margin[2]);
793 PR_EEP("Chain1 OutputBias", pModal->ob_ch1);
794 PR_EEP("Chain1 DriverBias", pModal->db_ch1);
795 PR_EEP("LNA Control", pModal->lna_ctl);
796 PR_EEP("XPA Bias Freq0", pModal->xpaBiasLvlFreq[0]);
797 PR_EEP("XPA Bias Freq1", pModal->xpaBiasLvlFreq[1]);
798 PR_EEP("XPA Bias Freq2", pModal->xpaBiasLvlFreq[2]);
799
800 if (len > size)
801 len = size;
802
803 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
804 kfree(buf);
805
806 return retval;
807
808#undef PR_EEP
809}
810
811static ssize_t read_9287_modal_eeprom(struct file *file,
812 char __user *user_buf,
813 size_t count, loff_t *ppos)
814{
815#define PR_EEP(_s, _val) \
816 do { \
817 len += scnprintf(buf + len, size - len, "%20s : %10d\n",\
818 _s, (_val)); \
819 } while (0)
820
821 struct ath9k_htc_priv *priv = file->private_data;
822 struct modal_eep_ar9287_header *pModal = &priv->ah->eeprom.map9287.modalHeader;
823 unsigned int len = 0, size = 3000;
824 ssize_t retval = 0;
825 char *buf;
826
827 buf = kzalloc(size, GFP_KERNEL);
828 if (buf == NULL)
829 return -ENOMEM;
830
831 PR_EEP("Chain0 Ant. Control", pModal->antCtrlChain[0]);
832 PR_EEP("Chain1 Ant. Control", pModal->antCtrlChain[1]);
833 PR_EEP("Ant. Common Control", pModal->antCtrlCommon);
834 PR_EEP("Chain0 Ant. Gain", pModal->antennaGainCh[0]);
835 PR_EEP("Chain1 Ant. Gain", pModal->antennaGainCh[1]);
836 PR_EEP("Switch Settle", pModal->switchSettling);
837 PR_EEP("Chain0 TxRxAtten", pModal->txRxAttenCh[0]);
838 PR_EEP("Chain1 TxRxAtten", pModal->txRxAttenCh[1]);
839 PR_EEP("Chain0 RxTxMargin", pModal->rxTxMarginCh[0]);
840 PR_EEP("Chain1 RxTxMargin", pModal->rxTxMarginCh[1]);
841 PR_EEP("ADC Desired size", pModal->adcDesiredSize);
842 PR_EEP("txEndToXpaOff", pModal->txEndToXpaOff);
843 PR_EEP("txEndToRxOn", pModal->txEndToRxOn);
844 PR_EEP("txFrameToXpaOn", pModal->txFrameToXpaOn);
845 PR_EEP("CCA Threshold)", pModal->thresh62);
846 PR_EEP("Chain0 NF Threshold", pModal->noiseFloorThreshCh[0]);
847 PR_EEP("Chain1 NF Threshold", pModal->noiseFloorThreshCh[1]);
848 PR_EEP("xpdGain", pModal->xpdGain);
849 PR_EEP("External PD", pModal->xpd);
850 PR_EEP("Chain0 I Coefficient", pModal->iqCalICh[0]);
851 PR_EEP("Chain1 I Coefficient", pModal->iqCalICh[1]);
852 PR_EEP("Chain0 Q Coefficient", pModal->iqCalQCh[0]);
853 PR_EEP("Chain1 Q Coefficient", pModal->iqCalQCh[1]);
854 PR_EEP("pdGainOverlap", pModal->pdGainOverlap);
855 PR_EEP("xPA Bias Level", pModal->xpaBiasLvl);
856 PR_EEP("txFrameToDataStart", pModal->txFrameToDataStart);
857 PR_EEP("txFrameToPaOn", pModal->txFrameToPaOn);
858 PR_EEP("HT40 Power Inc.", pModal->ht40PowerIncForPdadc);
859 PR_EEP("Chain0 bswAtten", pModal->bswAtten[0]);
860 PR_EEP("Chain1 bswAtten", pModal->bswAtten[1]);
861 PR_EEP("Chain0 bswMargin", pModal->bswMargin[0]);
862 PR_EEP("Chain1 bswMargin", pModal->bswMargin[1]);
863 PR_EEP("HT40 Switch Settle", pModal->swSettleHt40);
864 PR_EEP("AR92x7 Version", pModal->version);
865 PR_EEP("DriverBias1", pModal->db1);
866 PR_EEP("DriverBias2", pModal->db1);
867 PR_EEP("CCK OutputBias", pModal->ob_cck);
868 PR_EEP("PSK OutputBias", pModal->ob_psk);
869 PR_EEP("QAM OutputBias", pModal->ob_qam);
870 PR_EEP("PAL_OFF OutputBias", pModal->ob_pal_off);
871
872 if (len > size)
873 len = size;
874
875 retval = simple_read_from_buffer(user_buf, count, ppos, buf, len);
876 kfree(buf);
877
878 return retval;
879
880#undef PR_EEP
881}
882
883static ssize_t read_file_modal_eeprom(struct file *file, char __user *user_buf,
884 size_t count, loff_t *ppos)
885{
886 struct ath9k_htc_priv *priv = file->private_data;
887
888 if (AR_SREV_9271(priv->ah))
889 return read_4k_modal_eeprom(file, user_buf, count, ppos);
890 else if (priv->ah->hw_version.usbdev == AR9280_USB)
891 return read_def_modal_eeprom(file, user_buf, count, ppos);
892 else if (priv->ah->hw_version.usbdev == AR9287_USB)
893 return read_9287_modal_eeprom(file, user_buf, count, ppos);
894
895 return 0;
896}
897
898static const struct file_operations fops_modal_eeprom = {
899 .read = read_file_modal_eeprom,
900 .open = simple_open,
901 .owner = THIS_MODULE,
902 .llseek = default_llseek,
903};
904
905
906/* Ethtool support for get-stats */ 412/* Ethtool support for get-stats */
907#define AMKSTR(nm) #nm "_BE", #nm "_BK", #nm "_VI", #nm "_VO" 413#define AMKSTR(nm) #nm "_BE", #nm "_BK", #nm "_VI", #nm "_VO"
908static const char ath9k_htc_gstrings_stats[][ETH_GSTRING_LEN] = { 414static const char ath9k_htc_gstrings_stats[][ETH_GSTRING_LEN] = {
@@ -947,6 +453,8 @@ int ath9k_htc_get_et_sset_count(struct ieee80211_hw *hw,
947 453
948#define STXBASE priv->debug.tx_stats 454#define STXBASE priv->debug.tx_stats
949#define SRXBASE priv->debug.rx_stats 455#define SRXBASE priv->debug.rx_stats
456#define SKBTXBASE priv->debug.tx_stats
457#define SKBRXBASE priv->debug.skbrx_stats
950#define ASTXQ(a) \ 458#define ASTXQ(a) \
951 data[i++] = STXBASE.a[IEEE80211_AC_BE]; \ 459 data[i++] = STXBASE.a[IEEE80211_AC_BE]; \
952 data[i++] = STXBASE.a[IEEE80211_AC_BK]; \ 460 data[i++] = STXBASE.a[IEEE80211_AC_BK]; \
@@ -960,24 +468,24 @@ void ath9k_htc_get_et_stats(struct ieee80211_hw *hw,
960 struct ath9k_htc_priv *priv = hw->priv; 468 struct ath9k_htc_priv *priv = hw->priv;
961 int i = 0; 469 int i = 0;
962 470
963 data[i++] = STXBASE.skb_success; 471 data[i++] = SKBTXBASE.skb_success;
964 data[i++] = STXBASE.skb_success_bytes; 472 data[i++] = SKBTXBASE.skb_success_bytes;
965 data[i++] = SRXBASE.skb_completed; 473 data[i++] = SKBRXBASE.skb_completed;
966 data[i++] = SRXBASE.skb_completed_bytes; 474 data[i++] = SKBRXBASE.skb_completed_bytes;
967 475
968 ASTXQ(queue_stats); 476 ASTXQ(queue_stats);
969 477
970 data[i++] = SRXBASE.err_crc; 478 data[i++] = SRXBASE.crc_err;
971 data[i++] = SRXBASE.err_decrypt_crc; 479 data[i++] = SRXBASE.decrypt_crc_err;
972 data[i++] = SRXBASE.err_phy; 480 data[i++] = SRXBASE.phy_err;
973 data[i++] = SRXBASE.err_mic; 481 data[i++] = SRXBASE.mic_err;
974 data[i++] = SRXBASE.err_pre_delim; 482 data[i++] = SRXBASE.pre_delim_crc_err;
975 data[i++] = SRXBASE.err_post_delim; 483 data[i++] = SRXBASE.post_delim_crc_err;
976 data[i++] = SRXBASE.err_decrypt_busy; 484 data[i++] = SRXBASE.decrypt_busy_err;
977 485
978 data[i++] = SRXBASE.err_phy_stats[ATH9K_PHYERR_RADAR]; 486 data[i++] = SRXBASE.phy_err_stats[ATH9K_PHYERR_RADAR];
979 data[i++] = SRXBASE.err_phy_stats[ATH9K_PHYERR_OFDM_TIMING]; 487 data[i++] = SRXBASE.phy_err_stats[ATH9K_PHYERR_OFDM_TIMING];
980 data[i++] = SRXBASE.err_phy_stats[ATH9K_PHYERR_CCK_TIMING]; 488 data[i++] = SRXBASE.phy_err_stats[ATH9K_PHYERR_CCK_TIMING];
981 489
982 WARN_ON(i != ATH9K_HTC_SSTATS_LEN); 490 WARN_ON(i != ATH9K_HTC_SSTATS_LEN);
983} 491}
@@ -1001,18 +509,21 @@ int ath9k_htc_init_debug(struct ath_hw *ah)
1001 priv, &fops_tgt_rx_stats); 509 priv, &fops_tgt_rx_stats);
1002 debugfs_create_file("xmit", S_IRUSR, priv->debug.debugfs_phy, 510 debugfs_create_file("xmit", S_IRUSR, priv->debug.debugfs_phy,
1003 priv, &fops_xmit); 511 priv, &fops_xmit);
1004 debugfs_create_file("recv", S_IRUSR, priv->debug.debugfs_phy, 512 debugfs_create_file("skb_rx", S_IRUSR, priv->debug.debugfs_phy,
1005 priv, &fops_recv); 513 priv, &fops_skb_rx);
514
515 ath9k_cmn_debug_recv(priv->debug.debugfs_phy, &priv->debug.rx_stats);
516 ath9k_cmn_debug_phy_err(priv->debug.debugfs_phy, &priv->debug.rx_stats);
517
1006 debugfs_create_file("slot", S_IRUSR, priv->debug.debugfs_phy, 518 debugfs_create_file("slot", S_IRUSR, priv->debug.debugfs_phy,
1007 priv, &fops_slot); 519 priv, &fops_slot);
1008 debugfs_create_file("queue", S_IRUSR, priv->debug.debugfs_phy, 520 debugfs_create_file("queue", S_IRUSR, priv->debug.debugfs_phy,
1009 priv, &fops_queue); 521 priv, &fops_queue);
1010 debugfs_create_file("debug", S_IRUSR | S_IWUSR, priv->debug.debugfs_phy, 522 debugfs_create_file("debug", S_IRUSR | S_IWUSR, priv->debug.debugfs_phy,
1011 priv, &fops_debug); 523 priv, &fops_debug);
1012 debugfs_create_file("base_eeprom", S_IRUSR, priv->debug.debugfs_phy, 524
1013 priv, &fops_base_eeprom); 525 ath9k_cmn_debug_base_eeprom(priv->debug.debugfs_phy, priv->ah);
1014 debugfs_create_file("modal_eeprom", S_IRUSR, priv->debug.debugfs_phy, 526 ath9k_cmn_debug_modal_eeprom(priv->debug.debugfs_phy, priv->ah);
1015 priv, &fops_modal_eeprom);
1016 527
1017 return 0; 528 return 0;
1018} 529}
diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_txrx.c b/drivers/net/wireless/ath/ath9k/htc_drv_txrx.c
index 289f3d8924b5..bb86eb2ffc95 100644
--- a/drivers/net/wireless/ath/ath9k/htc_drv_txrx.c
+++ b/drivers/net/wireless/ath/ath9k/htc_drv_txrx.c
@@ -996,8 +996,6 @@ static bool ath9k_rx_prepare(struct ath9k_htc_priv *priv,
996 goto rx_next; 996 goto rx_next;
997 } 997 }
998 998
999 ath9k_htc_err_stat_rx(priv, rxstatus);
1000
1001 /* Get the RX status information */ 999 /* Get the RX status information */
1002 1000
1003 memset(rx_status, 0, sizeof(struct ieee80211_rx_status)); 1001 memset(rx_status, 0, sizeof(struct ieee80211_rx_status));
@@ -1005,6 +1003,7 @@ static bool ath9k_rx_prepare(struct ath9k_htc_priv *priv,
1005 /* Copy everything from ath_htc_rx_status (HTC_RX_FRAME_HEADER). 1003 /* Copy everything from ath_htc_rx_status (HTC_RX_FRAME_HEADER).
1006 * After this, we can drop this part of skb. */ 1004 * After this, we can drop this part of skb. */
1007 rx_status_htc_to_ath(&rx_stats, rxstatus); 1005 rx_status_htc_to_ath(&rx_stats, rxstatus);
1006 ath9k_htc_err_stat_rx(priv, &rx_stats);
1008 rx_status->mactime = be64_to_cpu(rxstatus->rs_tstamp); 1007 rx_status->mactime = be64_to_cpu(rxstatus->rs_tstamp);
1009 skb_pull(skb, HTC_RX_FRAME_HEADER_SIZE); 1008 skb_pull(skb, HTC_RX_FRAME_HEADER_SIZE);
1010 1009
diff --git a/drivers/net/wireless/ath/ath9k/hw.c b/drivers/net/wireless/ath/ath9k/hw.c
index c8a9dfab1fee..2a8ed8375ec0 100644
--- a/drivers/net/wireless/ath/ath9k/hw.c
+++ b/drivers/net/wireless/ath/ath9k/hw.c
@@ -26,7 +26,6 @@
26#include "ar9003_mac.h" 26#include "ar9003_mac.h"
27#include "ar9003_mci.h" 27#include "ar9003_mci.h"
28#include "ar9003_phy.h" 28#include "ar9003_phy.h"
29#include "debug.h"
30#include "ath9k.h" 29#include "ath9k.h"
31 30
32static bool ath9k_hw_set_reset_reg(struct ath_hw *ah, u32 type); 31static bool ath9k_hw_set_reset_reg(struct ath_hw *ah, u32 type);
@@ -246,6 +245,8 @@ static void ath9k_hw_read_revisions(struct ath_hw *ah)
246 return; 245 return;
247 case AR9300_DEVID_AR953X: 246 case AR9300_DEVID_AR953X:
248 ah->hw_version.macVersion = AR_SREV_VERSION_9531; 247 ah->hw_version.macVersion = AR_SREV_VERSION_9531;
248 if (ah->get_mac_revision)
249 ah->hw_version.macRev = ah->get_mac_revision();
249 return; 250 return;
250 } 251 }
251 252
diff --git a/drivers/net/wireless/ath/ath9k/init.c b/drivers/net/wireless/ath/ath9k/init.c
index 4243509616bd..1af77081181e 100644
--- a/drivers/net/wireless/ath/ath9k/init.c
+++ b/drivers/net/wireless/ath/ath9k/init.c
@@ -508,7 +508,7 @@ static int ath9k_init_softc(u16 devid, struct ath_softc *sc,
508 sc->tx99_power = MAX_RATE_POWER + 1; 508 sc->tx99_power = MAX_RATE_POWER + 1;
509 init_waitqueue_head(&sc->tx_wait); 509 init_waitqueue_head(&sc->tx_wait);
510 510
511 if (!pdata) { 511 if (!pdata || pdata->use_eeprom) {
512 ah->ah_flags |= AH_USE_EEPROM; 512 ah->ah_flags |= AH_USE_EEPROM;
513 sc->sc_ah->led_pin = -1; 513 sc->sc_ah->led_pin = -1;
514 } else { 514 } else {
@@ -714,7 +714,8 @@ static void ath9k_set_hw_capab(struct ath_softc *sc, struct ieee80211_hw *hw)
714 if (AR_SREV_9160_10_OR_LATER(sc->sc_ah) || ath9k_modparam_nohwcrypt) 714 if (AR_SREV_9160_10_OR_LATER(sc->sc_ah) || ath9k_modparam_nohwcrypt)
715 hw->flags |= IEEE80211_HW_MFP_CAPABLE; 715 hw->flags |= IEEE80211_HW_MFP_CAPABLE;
716 716
717 hw->wiphy->features |= NL80211_FEATURE_ACTIVE_MONITOR; 717 hw->wiphy->features |= (NL80211_FEATURE_ACTIVE_MONITOR |
718 NL80211_FEATURE_AP_MODE_CHAN_WIDTH_CHANGE);
718 719
719 if (!config_enabled(CONFIG_ATH9K_TX99)) { 720 if (!config_enabled(CONFIG_ATH9K_TX99)) {
720 hw->wiphy->interface_modes = 721 hw->wiphy->interface_modes =
diff --git a/drivers/net/wireless/ath/ath9k/mac.c b/drivers/net/wireless/ath/ath9k/mac.c
index 51ce36f108f9..275205ab5f15 100644
--- a/drivers/net/wireless/ath/ath9k/mac.c
+++ b/drivers/net/wireless/ath/ath9k/mac.c
@@ -958,3 +958,25 @@ void ath9k_hw_set_interrupts(struct ath_hw *ah)
958 return; 958 return;
959} 959}
960EXPORT_SYMBOL(ath9k_hw_set_interrupts); 960EXPORT_SYMBOL(ath9k_hw_set_interrupts);
961
962#define ATH9K_HW_MAX_DCU 10
963#define ATH9K_HW_SLICE_PER_DCU 16
964#define ATH9K_HW_BIT_IN_SLICE 16
965void ath9k_hw_set_tx_filter(struct ath_hw *ah, u8 destidx, bool set)
966{
967 int dcu_idx;
968 u32 filter;
969
970 for (dcu_idx = 0; dcu_idx < 10; dcu_idx++) {
971 filter = SM(set, AR_D_TXBLK_WRITE_COMMAND);
972 filter |= SM(dcu_idx, AR_D_TXBLK_WRITE_DCU);
973 filter |= SM((destidx / ATH9K_HW_SLICE_PER_DCU),
974 AR_D_TXBLK_WRITE_SLICE);
975 filter |= BIT(destidx % ATH9K_HW_BIT_IN_SLICE);
976 ath_dbg(ath9k_hw_common(ah), PS,
977 "DCU%d staid %d set %d txfilter %08x\n",
978 dcu_idx, destidx, set, filter);
979 REG_WRITE(ah, AR_D_TXBLK_BASE, filter);
980 }
981}
982EXPORT_SYMBOL(ath9k_hw_set_tx_filter);
diff --git a/drivers/net/wireless/ath/ath9k/mac.h b/drivers/net/wireless/ath/ath9k/mac.h
index 89df634e81f9..da7686757535 100644
--- a/drivers/net/wireless/ath/ath9k/mac.h
+++ b/drivers/net/wireless/ath/ath9k/mac.h
@@ -729,6 +729,7 @@ void ath9k_hw_startpcureceive(struct ath_hw *ah, bool is_scanning);
729void ath9k_hw_abortpcurecv(struct ath_hw *ah); 729void ath9k_hw_abortpcurecv(struct ath_hw *ah);
730bool ath9k_hw_stopdmarecv(struct ath_hw *ah, bool *reset); 730bool ath9k_hw_stopdmarecv(struct ath_hw *ah, bool *reset);
731int ath9k_hw_beaconq_setup(struct ath_hw *ah); 731int ath9k_hw_beaconq_setup(struct ath_hw *ah);
732void ath9k_hw_set_tx_filter(struct ath_hw *ah, u8 destidx, bool set);
732 733
733/* Interrupt Handling */ 734/* Interrupt Handling */
734bool ath9k_hw_intrpend(struct ath_hw *ah); 735bool ath9k_hw_intrpend(struct ath_hw *ah);
diff --git a/drivers/net/wireless/ath/ath9k/main.c b/drivers/net/wireless/ath/ath9k/main.c
index 8d7b9b66fefa..6965ceac7bc6 100644
--- a/drivers/net/wireless/ath/ath9k/main.c
+++ b/drivers/net/wireless/ath/ath9k/main.c
@@ -421,6 +421,7 @@ static void ath_node_attach(struct ath_softc *sc, struct ieee80211_sta *sta,
421 an->sc = sc; 421 an->sc = sc;
422 an->sta = sta; 422 an->sta = sta;
423 an->vif = vif; 423 an->vif = vif;
424 memset(&an->key_idx, 0, sizeof(an->key_idx));
424 425
425 ath_tx_node_init(sc, an); 426 ath_tx_node_init(sc, an);
426} 427}
@@ -1461,8 +1462,10 @@ static int ath9k_sta_add(struct ieee80211_hw *hw,
1461 return 0; 1462 return 0;
1462 1463
1463 key = ath_key_config(common, vif, sta, &ps_key); 1464 key = ath_key_config(common, vif, sta, &ps_key);
1464 if (key > 0) 1465 if (key > 0) {
1465 an->ps_key = key; 1466 an->ps_key = key;
1467 an->key_idx[0] = key;
1468 }
1466 1469
1467 return 0; 1470 return 0;
1468} 1471}
@@ -1480,6 +1483,7 @@ static void ath9k_del_ps_key(struct ath_softc *sc,
1480 1483
1481 ath_key_delete(common, &ps_key); 1484 ath_key_delete(common, &ps_key);
1482 an->ps_key = 0; 1485 an->ps_key = 0;
1486 an->key_idx[0] = 0;
1483} 1487}
1484 1488
1485static int ath9k_sta_remove(struct ieee80211_hw *hw, 1489static int ath9k_sta_remove(struct ieee80211_hw *hw,
@@ -1494,6 +1498,19 @@ static int ath9k_sta_remove(struct ieee80211_hw *hw,
1494 return 0; 1498 return 0;
1495} 1499}
1496 1500
1501static void ath9k_sta_set_tx_filter(struct ath_hw *ah,
1502 struct ath_node *an,
1503 bool set)
1504{
1505 int i;
1506
1507 for (i = 0; i < ARRAY_SIZE(an->key_idx); i++) {
1508 if (!an->key_idx[i])
1509 continue;
1510 ath9k_hw_set_tx_filter(ah, an->key_idx[i], set);
1511 }
1512}
1513
1497static void ath9k_sta_notify(struct ieee80211_hw *hw, 1514static void ath9k_sta_notify(struct ieee80211_hw *hw,
1498 struct ieee80211_vif *vif, 1515 struct ieee80211_vif *vif,
1499 enum sta_notify_cmd cmd, 1516 enum sta_notify_cmd cmd,
@@ -1506,8 +1523,10 @@ static void ath9k_sta_notify(struct ieee80211_hw *hw,
1506 case STA_NOTIFY_SLEEP: 1523 case STA_NOTIFY_SLEEP:
1507 an->sleeping = true; 1524 an->sleeping = true;
1508 ath_tx_aggr_sleep(sta, sc, an); 1525 ath_tx_aggr_sleep(sta, sc, an);
1526 ath9k_sta_set_tx_filter(sc->sc_ah, an, true);
1509 break; 1527 break;
1510 case STA_NOTIFY_AWAKE: 1528 case STA_NOTIFY_AWAKE:
1529 ath9k_sta_set_tx_filter(sc->sc_ah, an, false);
1511 an->sleeping = false; 1530 an->sleeping = false;
1512 ath_tx_aggr_wakeup(sc, an); 1531 ath_tx_aggr_wakeup(sc, an);
1513 break; 1532 break;
@@ -1563,7 +1582,8 @@ static int ath9k_set_key(struct ieee80211_hw *hw,
1563{ 1582{
1564 struct ath_softc *sc = hw->priv; 1583 struct ath_softc *sc = hw->priv;
1565 struct ath_common *common = ath9k_hw_common(sc->sc_ah); 1584 struct ath_common *common = ath9k_hw_common(sc->sc_ah);
1566 int ret = 0; 1585 struct ath_node *an = NULL;
1586 int ret = 0, i;
1567 1587
1568 if (ath9k_modparam_nohwcrypt) 1588 if (ath9k_modparam_nohwcrypt)
1569 return -ENOSPC; 1589 return -ENOSPC;
@@ -1585,13 +1605,16 @@ static int ath9k_set_key(struct ieee80211_hw *hw,
1585 1605
1586 mutex_lock(&sc->mutex); 1606 mutex_lock(&sc->mutex);
1587 ath9k_ps_wakeup(sc); 1607 ath9k_ps_wakeup(sc);
1588 ath_dbg(common, CONFIG, "Set HW Key\n"); 1608 ath_dbg(common, CONFIG, "Set HW Key %d\n", cmd);
1609 if (sta)
1610 an = (struct ath_node *)sta->drv_priv;
1589 1611
1590 switch (cmd) { 1612 switch (cmd) {
1591 case SET_KEY: 1613 case SET_KEY:
1592 if (sta) 1614 if (sta)
1593 ath9k_del_ps_key(sc, vif, sta); 1615 ath9k_del_ps_key(sc, vif, sta);
1594 1616
1617 key->hw_key_idx = 0;
1595 ret = ath_key_config(common, vif, sta, key); 1618 ret = ath_key_config(common, vif, sta, key);
1596 if (ret >= 0) { 1619 if (ret >= 0) {
1597 key->hw_key_idx = ret; 1620 key->hw_key_idx = ret;
@@ -1604,9 +1627,27 @@ static int ath9k_set_key(struct ieee80211_hw *hw,
1604 key->flags |= IEEE80211_KEY_FLAG_SW_MGMT_TX; 1627 key->flags |= IEEE80211_KEY_FLAG_SW_MGMT_TX;
1605 ret = 0; 1628 ret = 0;
1606 } 1629 }
1630 if (an && key->hw_key_idx) {
1631 for (i = 0; i < ARRAY_SIZE(an->key_idx); i++) {
1632 if (an->key_idx[i])
1633 continue;
1634 an->key_idx[i] = key->hw_key_idx;
1635 break;
1636 }
1637 WARN_ON(i == ARRAY_SIZE(an->key_idx));
1638 }
1607 break; 1639 break;
1608 case DISABLE_KEY: 1640 case DISABLE_KEY:
1609 ath_key_delete(common, key); 1641 ath_key_delete(common, key);
1642 if (an) {
1643 for (i = 0; i < ARRAY_SIZE(an->key_idx); i++) {
1644 if (an->key_idx[i] != key->hw_key_idx)
1645 continue;
1646 an->key_idx[i] = 0;
1647 break;
1648 }
1649 }
1650 key->hw_key_idx = 0;
1610 break; 1651 break;
1611 default: 1652 default:
1612 ret = -EINVAL; 1653 ret = -EINVAL;
diff --git a/drivers/net/wireless/ath/ath9k/pci.c b/drivers/net/wireless/ath/ath9k/pci.c
index 914dbc6b1720..4dec09e565ed 100644
--- a/drivers/net/wireless/ath/ath9k/pci.c
+++ b/drivers/net/wireless/ath/ath9k/pci.c
@@ -686,7 +686,7 @@ static bool ath_pci_eeprom_read(struct ath_common *common, u32 off, u16 *data)
686 struct ath_softc *sc = (struct ath_softc *) common->priv; 686 struct ath_softc *sc = (struct ath_softc *) common->priv;
687 struct ath9k_platform_data *pdata = sc->dev->platform_data; 687 struct ath9k_platform_data *pdata = sc->dev->platform_data;
688 688
689 if (pdata) { 689 if (pdata && !pdata->use_eeprom) {
690 if (off >= (ARRAY_SIZE(pdata->eeprom_data))) { 690 if (off >= (ARRAY_SIZE(pdata->eeprom_data))) {
691 ath_err(common, 691 ath_err(common,
692 "%s: eeprom read failed, offset %08x is out of range\n", 692 "%s: eeprom read failed, offset %08x is out of range\n",
@@ -914,6 +914,7 @@ static int ath_pci_suspend(struct device *device)
914 */ 914 */
915 ath9k_stop_btcoex(sc); 915 ath9k_stop_btcoex(sc);
916 ath9k_hw_disable(sc->sc_ah); 916 ath9k_hw_disable(sc->sc_ah);
917 del_timer_sync(&sc->sleep_timer);
917 ath9k_hw_setpower(sc->sc_ah, ATH9K_PM_FULL_SLEEP); 918 ath9k_hw_setpower(sc->sc_ah, ATH9K_PM_FULL_SLEEP);
918 919
919 return 0; 920 return 0;
diff --git a/drivers/net/wireless/ath/ath9k/recv.c b/drivers/net/wireless/ath/ath9k/recv.c
index 441c71448e4c..43ae199601f7 100644
--- a/drivers/net/wireless/ath/ath9k/recv.c
+++ b/drivers/net/wireless/ath/ath9k/recv.c
@@ -538,8 +538,8 @@ static void ath_rx_ps_beacon(struct ath_softc *sc, struct sk_buff *skb)
538 sc->ps_flags &= ~PS_BEACON_SYNC; 538 sc->ps_flags &= ~PS_BEACON_SYNC;
539 ath_dbg(common, PS, 539 ath_dbg(common, PS,
540 "Reconfigure beacon timers based on synchronized timestamp\n"); 540 "Reconfigure beacon timers based on synchronized timestamp\n");
541 ath9k_set_beacon(sc); 541 if (!(WARN_ON_ONCE(sc->cur_beacon_conf.beacon_interval == 0)))
542 542 ath9k_set_beacon(sc);
543 if (sc->p2p_ps_vif) 543 if (sc->p2p_ps_vif)
544 ath9k_update_p2p_ps(sc, sc->p2p_ps_vif->vif); 544 ath9k_update_p2p_ps(sc, sc->p2p_ps_vif->vif);
545 } 545 }
diff --git a/drivers/net/wireless/ath/ath9k/reg.h b/drivers/net/wireless/ath/ath9k/reg.h
index b1fd3fa84983..f1bbce3f7774 100644
--- a/drivers/net/wireless/ath/ath9k/reg.h
+++ b/drivers/net/wireless/ath/ath9k/reg.h
@@ -505,9 +505,6 @@
505#define AR_D_QCUMASK 0x000003FF 505#define AR_D_QCUMASK 0x000003FF
506#define AR_D_QCUMASK_RESV0 0xFFFFFC00 506#define AR_D_QCUMASK_RESV0 0xFFFFFC00
507 507
508#define AR_D_TXBLK_CMD 0x1038
509#define AR_D_TXBLK_DATA(i) (AR_D_TXBLK_CMD+(i))
510
511#define AR_D0_LCL_IFS 0x1040 508#define AR_D0_LCL_IFS 0x1040
512#define AR_D1_LCL_IFS 0x1044 509#define AR_D1_LCL_IFS 0x1044
513#define AR_D2_LCL_IFS 0x1048 510#define AR_D2_LCL_IFS 0x1048
diff --git a/drivers/net/wireless/ath/carl9170/usb.c b/drivers/net/wireless/ath/carl9170/usb.c
index ca115f33746f..f35c7f30f9a6 100644
--- a/drivers/net/wireless/ath/carl9170/usb.c
+++ b/drivers/net/wireless/ath/carl9170/usb.c
@@ -1076,8 +1076,14 @@ static int carl9170_usb_probe(struct usb_interface *intf,
1076 1076
1077 carl9170_set_state(ar, CARL9170_STOPPED); 1077 carl9170_set_state(ar, CARL9170_STOPPED);
1078 1078
1079 return request_firmware_nowait(THIS_MODULE, 1, CARL9170FW_NAME, 1079 err = request_firmware_nowait(THIS_MODULE, 1, CARL9170FW_NAME,
1080 &ar->udev->dev, GFP_KERNEL, ar, carl9170_usb_firmware_step2); 1080 &ar->udev->dev, GFP_KERNEL, ar, carl9170_usb_firmware_step2);
1081 if (err) {
1082 usb_put_dev(udev);
1083 usb_put_dev(udev);
1084 carl9170_free(ar);
1085 }
1086 return err;
1081} 1087}
1082 1088
1083static void carl9170_usb_disconnect(struct usb_interface *intf) 1089static void carl9170_usb_disconnect(struct usb_interface *intf)
diff --git a/drivers/net/wireless/ath/dfs_pattern_detector.c b/drivers/net/wireless/ath/dfs_pattern_detector.c
index a1a69c5db409..650be79c7ac9 100644
--- a/drivers/net/wireless/ath/dfs_pattern_detector.c
+++ b/drivers/net/wireless/ath/dfs_pattern_detector.c
@@ -73,9 +73,52 @@ static const struct radar_types etsi_radar_types_v15 = {
73 .radar_types = etsi_radar_ref_types_v15, 73 .radar_types = etsi_radar_ref_types_v15,
74}; 74};
75 75
76/* for now, we support ETSI radar types, FCC and JP are TODO */ 76#define FCC_PATTERN(ID, WMIN, WMAX, PMIN, PMAX, PRF, PPB) \
77{ \
78 ID, WIDTH_LOWER(WMIN), WIDTH_UPPER(WMAX), \
79 PMIN - PRI_TOLERANCE, \
80 PMAX * PRF + PRI_TOLERANCE, PRF, PPB * PRF, \
81 PPB_THRESH(PPB), PRI_TOLERANCE, \
82}
83
84static const struct radar_detector_specs fcc_radar_ref_types[] = {
85 FCC_PATTERN(0, 0, 1, 1428, 1428, 1, 18),
86 FCC_PATTERN(1, 0, 5, 150, 230, 1, 23),
87 FCC_PATTERN(2, 6, 10, 200, 500, 1, 16),
88 FCC_PATTERN(3, 11, 20, 200, 500, 1, 12),
89 FCC_PATTERN(4, 50, 100, 1000, 2000, 20, 1),
90 FCC_PATTERN(5, 0, 1, 333, 333, 1, 9),
91};
92
93static const struct radar_types fcc_radar_types = {
94 .region = NL80211_DFS_FCC,
95 .num_radar_types = ARRAY_SIZE(fcc_radar_ref_types),
96 .radar_types = fcc_radar_ref_types,
97};
98
99#define JP_PATTERN FCC_PATTERN
100static const struct radar_detector_specs jp_radar_ref_types[] = {
101 JP_PATTERN(0, 0, 1, 1428, 1428, 1, 18),
102 JP_PATTERN(1, 2, 3, 3846, 3846, 1, 18),
103 JP_PATTERN(2, 0, 1, 1388, 1388, 1, 18),
104 JP_PATTERN(3, 1, 2, 4000, 4000, 1, 18),
105 JP_PATTERN(4, 0, 5, 150, 230, 1, 23),
106 JP_PATTERN(5, 6, 10, 200, 500, 1, 16),
107 JP_PATTERN(6, 11, 20, 200, 500, 1, 12),
108 JP_PATTERN(7, 50, 100, 1000, 2000, 20, 1),
109 JP_PATTERN(5, 0, 1, 333, 333, 1, 9),
110};
111
112static const struct radar_types jp_radar_types = {
113 .region = NL80211_DFS_JP,
114 .num_radar_types = ARRAY_SIZE(jp_radar_ref_types),
115 .radar_types = jp_radar_ref_types,
116};
117
77static const struct radar_types *dfs_domains[] = { 118static const struct radar_types *dfs_domains[] = {
78 &etsi_radar_types_v15, 119 &etsi_radar_types_v15,
120 &fcc_radar_types,
121 &jp_radar_types,
79}; 122};
80 123
81/** 124/**
diff --git a/drivers/net/wireless/ath/wil6210/cfg80211.c b/drivers/net/wireless/ath/wil6210/cfg80211.c
index 4806a49cb61b..6e699d050d1e 100644
--- a/drivers/net/wireless/ath/wil6210/cfg80211.c
+++ b/drivers/net/wireless/ath/wil6210/cfg80211.c
@@ -172,7 +172,7 @@ static int wil_cid_fill_sinfo(struct wil6210_priv *wil, int cid,
172 172
173static int wil_cfg80211_get_station(struct wiphy *wiphy, 173static int wil_cfg80211_get_station(struct wiphy *wiphy,
174 struct net_device *ndev, 174 struct net_device *ndev,
175 u8 *mac, struct station_info *sinfo) 175 const u8 *mac, struct station_info *sinfo)
176{ 176{
177 struct wil6210_priv *wil = wiphy_to_wil(wiphy); 177 struct wil6210_priv *wil = wiphy_to_wil(wiphy);
178 int rc; 178 int rc;
@@ -671,7 +671,7 @@ static int wil_cfg80211_stop_ap(struct wiphy *wiphy,
671} 671}
672 672
673static int wil_cfg80211_del_station(struct wiphy *wiphy, 673static int wil_cfg80211_del_station(struct wiphy *wiphy,
674 struct net_device *dev, u8 *mac) 674 struct net_device *dev, const u8 *mac)
675{ 675{
676 struct wil6210_priv *wil = wiphy_to_wil(wiphy); 676 struct wil6210_priv *wil = wiphy_to_wil(wiphy);
677 677
diff --git a/drivers/net/wireless/ath/wil6210/main.c b/drivers/net/wireless/ath/wil6210/main.c
index 1b265fd19de2..670cc6de3b4c 100644
--- a/drivers/net/wireless/ath/wil6210/main.c
+++ b/drivers/net/wireless/ath/wil6210/main.c
@@ -81,7 +81,7 @@ static void wil_disconnect_cid(struct wil6210_priv *wil, int cid)
81 memset(&sta->stats, 0, sizeof(sta->stats)); 81 memset(&sta->stats, 0, sizeof(sta->stats));
82} 82}
83 83
84static void _wil6210_disconnect(struct wil6210_priv *wil, void *bssid) 84static void _wil6210_disconnect(struct wil6210_priv *wil, const u8 *bssid)
85{ 85{
86 int cid = -ENOENT; 86 int cid = -ENOENT;
87 struct net_device *ndev = wil_to_ndev(wil); 87 struct net_device *ndev = wil_to_ndev(wil);
@@ -252,7 +252,7 @@ int wil_priv_init(struct wil6210_priv *wil)
252 return 0; 252 return 0;
253} 253}
254 254
255void wil6210_disconnect(struct wil6210_priv *wil, void *bssid) 255void wil6210_disconnect(struct wil6210_priv *wil, const u8 *bssid)
256{ 256{
257 del_timer_sync(&wil->connect_timer); 257 del_timer_sync(&wil->connect_timer);
258 _wil6210_disconnect(wil, bssid); 258 _wil6210_disconnect(wil, bssid);
diff --git a/drivers/net/wireless/ath/wil6210/wil6210.h b/drivers/net/wireless/ath/wil6210/wil6210.h
index d3b8659ca32e..3427ac4a4fa1 100644
--- a/drivers/net/wireless/ath/wil6210/wil6210.h
+++ b/drivers/net/wireless/ath/wil6210/wil6210.h
@@ -508,7 +508,7 @@ void wil_wdev_free(struct wil6210_priv *wil);
508int wmi_set_mac_address(struct wil6210_priv *wil, void *addr); 508int wmi_set_mac_address(struct wil6210_priv *wil, void *addr);
509int wmi_pcp_start(struct wil6210_priv *wil, int bi, u8 wmi_nettype, u8 chan); 509int wmi_pcp_start(struct wil6210_priv *wil, int bi, u8 wmi_nettype, u8 chan);
510int wmi_pcp_stop(struct wil6210_priv *wil); 510int wmi_pcp_stop(struct wil6210_priv *wil);
511void wil6210_disconnect(struct wil6210_priv *wil, void *bssid); 511void wil6210_disconnect(struct wil6210_priv *wil, const u8 *bssid);
512 512
513int wil_rx_init(struct wil6210_priv *wil); 513int wil_rx_init(struct wil6210_priv *wil);
514void wil_rx_fini(struct wil6210_priv *wil); 514void wil_rx_fini(struct wil6210_priv *wil);
diff --git a/drivers/net/wireless/b43/Kconfig b/drivers/net/wireless/b43/Kconfig
index 088d544ec63f..e3f67b8d3f80 100644
--- a/drivers/net/wireless/b43/Kconfig
+++ b/drivers/net/wireless/b43/Kconfig
@@ -1,7 +1,8 @@
1config B43 1config B43
2 tristate "Broadcom 43xx wireless support (mac80211 stack)" 2 tristate "Broadcom 43xx wireless support (mac80211 stack)"
3 depends on SSB_POSSIBLE && MAC80211 && HAS_DMA 3 depends on (BCMA_POSSIBLE || SSB_POSSIBLE) && MAC80211 && HAS_DMA
4 select SSB 4 select BCMA if B43_BCMA
5 select SSB if B43_SSB
5 select FW_LOADER 6 select FW_LOADER
6 ---help--- 7 ---help---
7 b43 is a driver for the Broadcom 43xx series wireless devices. 8 b43 is a driver for the Broadcom 43xx series wireless devices.
@@ -27,14 +28,33 @@ config B43
27 If unsure, say M. 28 If unsure, say M.
28 29
29config B43_BCMA 30config B43_BCMA
30 bool "Support for BCMA bus" 31 bool
31 depends on B43 && (BCMA = y || BCMA = B43)
32 default y
33 32
34config B43_SSB 33config B43_SSB
35 bool 34 bool
36 depends on B43 && (SSB = y || SSB = B43) 35
37 default y 36choice
37 prompt "Supported bus types"
38 depends on B43
39 default B43_BCMA_AND_SSB
40
41config B43_BUSES_BCMA_AND_SSB
42 bool "BCMA and SSB"
43 depends on BCMA_POSSIBLE && SSB_POSSIBLE
44 select B43_BCMA
45 select B43_SSB
46
47config B43_BUSES_BCMA
48 bool "BCMA only"
49 depends on BCMA_POSSIBLE
50 select B43_BCMA
51
52config B43_BUSES_SSB
53 bool "SSB only"
54 depends on SSB_POSSIBLE
55 select B43_SSB
56
57endchoice
38 58
39# Auto-select SSB PCI-HOST support, if possible 59# Auto-select SSB PCI-HOST support, if possible
40config B43_PCI_AUTOSELECT 60config B43_PCI_AUTOSELECT
@@ -53,7 +73,7 @@ config B43_PCICORE_AUTOSELECT
53 73
54config B43_PCMCIA 74config B43_PCMCIA
55 bool "Broadcom 43xx PCMCIA device support" 75 bool "Broadcom 43xx PCMCIA device support"
56 depends on B43 && SSB_PCMCIAHOST_POSSIBLE 76 depends on B43 && B43_SSB && SSB_PCMCIAHOST_POSSIBLE
57 select SSB_PCMCIAHOST 77 select SSB_PCMCIAHOST
58 ---help--- 78 ---help---
59 Broadcom 43xx PCMCIA device support. 79 Broadcom 43xx PCMCIA device support.
@@ -73,7 +93,7 @@ config B43_PCMCIA
73 93
74config B43_SDIO 94config B43_SDIO
75 bool "Broadcom 43xx SDIO device support" 95 bool "Broadcom 43xx SDIO device support"
76 depends on B43 && SSB_SDIOHOST_POSSIBLE 96 depends on B43 && B43_SSB && SSB_SDIOHOST_POSSIBLE
77 select SSB_SDIOHOST 97 select SSB_SDIOHOST
78 ---help--- 98 ---help---
79 Broadcom 43xx device support for Soft-MAC SDIO devices. 99 Broadcom 43xx device support for Soft-MAC SDIO devices.
@@ -98,7 +118,7 @@ config B43_BCMA_PIO
98 118
99config B43_PIO 119config B43_PIO
100 bool 120 bool
101 depends on B43 121 depends on B43 && B43_SSB
102 select SSB_BLOCKIO 122 select SSB_BLOCKIO
103 default y 123 default y
104 124
@@ -116,7 +136,7 @@ config B43_PHY_N
116 136
117config B43_PHY_LP 137config B43_PHY_LP
118 bool "Support for low-power (LP-PHY) devices" 138 bool "Support for low-power (LP-PHY) devices"
119 depends on B43 139 depends on B43 && B43_SSB
120 default y 140 default y
121 ---help--- 141 ---help---
122 Support for the LP-PHY. 142 Support for the LP-PHY.
diff --git a/drivers/net/wireless/b43/bus.h b/drivers/net/wireless/b43/bus.h
index 184c95659279..f3205c6988bc 100644
--- a/drivers/net/wireless/b43/bus.h
+++ b/drivers/net/wireless/b43/bus.h
@@ -5,7 +5,9 @@ enum b43_bus_type {
5#ifdef CONFIG_B43_BCMA 5#ifdef CONFIG_B43_BCMA
6 B43_BUS_BCMA, 6 B43_BUS_BCMA,
7#endif 7#endif
8#ifdef CONFIG_B43_SSB
8 B43_BUS_SSB, 9 B43_BUS_SSB,
10#endif
9}; 11};
10 12
11struct b43_bus_dev { 13struct b43_bus_dev {
@@ -52,13 +54,21 @@ struct b43_bus_dev {
52 54
53static inline bool b43_bus_host_is_pcmcia(struct b43_bus_dev *dev) 55static inline bool b43_bus_host_is_pcmcia(struct b43_bus_dev *dev)
54{ 56{
57#ifdef CONFIG_B43_SSB
55 return (dev->bus_type == B43_BUS_SSB && 58 return (dev->bus_type == B43_BUS_SSB &&
56 dev->sdev->bus->bustype == SSB_BUSTYPE_PCMCIA); 59 dev->sdev->bus->bustype == SSB_BUSTYPE_PCMCIA);
60#else
61 return false;
62#endif
57} 63}
58static inline bool b43_bus_host_is_sdio(struct b43_bus_dev *dev) 64static inline bool b43_bus_host_is_sdio(struct b43_bus_dev *dev)
59{ 65{
66#ifdef CONFIG_B43_SSB
60 return (dev->bus_type == B43_BUS_SSB && 67 return (dev->bus_type == B43_BUS_SSB &&
61 dev->sdev->bus->bustype == SSB_BUSTYPE_SDIO); 68 dev->sdev->bus->bustype == SSB_BUSTYPE_SDIO);
69#else
70 return false;
71#endif
62} 72}
63 73
64struct b43_bus_dev *b43_bus_dev_bcma_init(struct bcma_device *core); 74struct b43_bus_dev *b43_bus_dev_bcma_init(struct bcma_device *core);
diff --git a/drivers/net/wireless/b43/main.c b/drivers/net/wireless/b43/main.c
index 32e08d35c06e..3d67e6b08e1c 100644
--- a/drivers/net/wireless/b43/main.c
+++ b/drivers/net/wireless/b43/main.c
@@ -182,7 +182,7 @@ static struct ieee80211_rate __b43_ratetable[] = {
182#define b43_g_ratetable (__b43_ratetable + 0) 182#define b43_g_ratetable (__b43_ratetable + 0)
183#define b43_g_ratetable_size 12 183#define b43_g_ratetable_size 12
184 184
185#define CHAN4G(_channel, _freq, _flags) { \ 185#define CHAN2G(_channel, _freq, _flags) { \
186 .band = IEEE80211_BAND_2GHZ, \ 186 .band = IEEE80211_BAND_2GHZ, \
187 .center_freq = (_freq), \ 187 .center_freq = (_freq), \
188 .hw_value = (_channel), \ 188 .hw_value = (_channel), \
@@ -191,23 +191,31 @@ static struct ieee80211_rate __b43_ratetable[] = {
191 .max_power = 30, \ 191 .max_power = 30, \
192} 192}
193static struct ieee80211_channel b43_2ghz_chantable[] = { 193static struct ieee80211_channel b43_2ghz_chantable[] = {
194 CHAN4G(1, 2412, 0), 194 CHAN2G(1, 2412, 0),
195 CHAN4G(2, 2417, 0), 195 CHAN2G(2, 2417, 0),
196 CHAN4G(3, 2422, 0), 196 CHAN2G(3, 2422, 0),
197 CHAN4G(4, 2427, 0), 197 CHAN2G(4, 2427, 0),
198 CHAN4G(5, 2432, 0), 198 CHAN2G(5, 2432, 0),
199 CHAN4G(6, 2437, 0), 199 CHAN2G(6, 2437, 0),
200 CHAN4G(7, 2442, 0), 200 CHAN2G(7, 2442, 0),
201 CHAN4G(8, 2447, 0), 201 CHAN2G(8, 2447, 0),
202 CHAN4G(9, 2452, 0), 202 CHAN2G(9, 2452, 0),
203 CHAN4G(10, 2457, 0), 203 CHAN2G(10, 2457, 0),
204 CHAN4G(11, 2462, 0), 204 CHAN2G(11, 2462, 0),
205 CHAN4G(12, 2467, 0), 205 CHAN2G(12, 2467, 0),
206 CHAN4G(13, 2472, 0), 206 CHAN2G(13, 2472, 0),
207 CHAN4G(14, 2484, 0), 207 CHAN2G(14, 2484, 0),
208}; 208};
209#undef CHAN4G 209#undef CHAN2G
210 210
211#define CHAN4G(_channel, _flags) { \
212 .band = IEEE80211_BAND_5GHZ, \
213 .center_freq = 4000 + (5 * (_channel)), \
214 .hw_value = (_channel), \
215 .flags = (_flags), \
216 .max_antenna_gain = 0, \
217 .max_power = 30, \
218}
211#define CHAN5G(_channel, _flags) { \ 219#define CHAN5G(_channel, _flags) { \
212 .band = IEEE80211_BAND_5GHZ, \ 220 .band = IEEE80211_BAND_5GHZ, \
213 .center_freq = 5000 + (5 * (_channel)), \ 221 .center_freq = 5000 + (5 * (_channel)), \
@@ -217,6 +225,18 @@ static struct ieee80211_channel b43_2ghz_chantable[] = {
217 .max_power = 30, \ 225 .max_power = 30, \
218} 226}
219static struct ieee80211_channel b43_5ghz_nphy_chantable[] = { 227static struct ieee80211_channel b43_5ghz_nphy_chantable[] = {
228 CHAN4G(184, 0), CHAN4G(186, 0),
229 CHAN4G(188, 0), CHAN4G(190, 0),
230 CHAN4G(192, 0), CHAN4G(194, 0),
231 CHAN4G(196, 0), CHAN4G(198, 0),
232 CHAN4G(200, 0), CHAN4G(202, 0),
233 CHAN4G(204, 0), CHAN4G(206, 0),
234 CHAN4G(208, 0), CHAN4G(210, 0),
235 CHAN4G(212, 0), CHAN4G(214, 0),
236 CHAN4G(216, 0), CHAN4G(218, 0),
237 CHAN4G(220, 0), CHAN4G(222, 0),
238 CHAN4G(224, 0), CHAN4G(226, 0),
239 CHAN4G(228, 0),
220 CHAN5G(32, 0), CHAN5G(34, 0), 240 CHAN5G(32, 0), CHAN5G(34, 0),
221 CHAN5G(36, 0), CHAN5G(38, 0), 241 CHAN5G(36, 0), CHAN5G(38, 0),
222 CHAN5G(40, 0), CHAN5G(42, 0), 242 CHAN5G(40, 0), CHAN5G(42, 0),
@@ -260,18 +280,7 @@ static struct ieee80211_channel b43_5ghz_nphy_chantable[] = {
260 CHAN5G(170, 0), CHAN5G(172, 0), 280 CHAN5G(170, 0), CHAN5G(172, 0),
261 CHAN5G(174, 0), CHAN5G(176, 0), 281 CHAN5G(174, 0), CHAN5G(176, 0),
262 CHAN5G(178, 0), CHAN5G(180, 0), 282 CHAN5G(178, 0), CHAN5G(180, 0),
263 CHAN5G(182, 0), CHAN5G(184, 0), 283 CHAN5G(182, 0),
264 CHAN5G(186, 0), CHAN5G(188, 0),
265 CHAN5G(190, 0), CHAN5G(192, 0),
266 CHAN5G(194, 0), CHAN5G(196, 0),
267 CHAN5G(198, 0), CHAN5G(200, 0),
268 CHAN5G(202, 0), CHAN5G(204, 0),
269 CHAN5G(206, 0), CHAN5G(208, 0),
270 CHAN5G(210, 0), CHAN5G(212, 0),
271 CHAN5G(214, 0), CHAN5G(216, 0),
272 CHAN5G(218, 0), CHAN5G(220, 0),
273 CHAN5G(222, 0), CHAN5G(224, 0),
274 CHAN5G(226, 0), CHAN5G(228, 0),
275}; 284};
276 285
277static struct ieee80211_channel b43_5ghz_aphy_chantable[] = { 286static struct ieee80211_channel b43_5ghz_aphy_chantable[] = {
@@ -295,6 +304,7 @@ static struct ieee80211_channel b43_5ghz_aphy_chantable[] = {
295 CHAN5G(208, 0), CHAN5G(212, 0), 304 CHAN5G(208, 0), CHAN5G(212, 0),
296 CHAN5G(216, 0), 305 CHAN5G(216, 0),
297}; 306};
307#undef CHAN4G
298#undef CHAN5G 308#undef CHAN5G
299 309
300static struct ieee80211_supported_band b43_band_5GHz_nphy = { 310static struct ieee80211_supported_band b43_band_5GHz_nphy = {
@@ -1175,18 +1185,7 @@ static void b43_bcma_phy_reset(struct b43_wldev *dev)
1175 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, flags); 1185 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, flags);
1176 udelay(2); 1186 udelay(2);
1177 1187
1178 /* Take PHY out of reset */ 1188 b43_phy_take_out_of_reset(dev);
1179 flags = bcma_aread32(dev->dev->bdev, BCMA_IOCTL);
1180 flags &= ~B43_BCMA_IOCTL_PHY_RESET;
1181 flags |= BCMA_IOCTL_FGC;
1182 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, flags);
1183 udelay(1);
1184
1185 /* Do not force clock anymore */
1186 flags = bcma_aread32(dev->dev->bdev, BCMA_IOCTL);
1187 flags &= ~BCMA_IOCTL_FGC;
1188 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, flags);
1189 udelay(1);
1190} 1189}
1191 1190
1192static void b43_bcma_wireless_core_reset(struct b43_wldev *dev, bool gmode) 1191static void b43_bcma_wireless_core_reset(struct b43_wldev *dev, bool gmode)
@@ -1208,10 +1207,9 @@ static void b43_bcma_wireless_core_reset(struct b43_wldev *dev, bool gmode)
1208} 1207}
1209#endif 1208#endif
1210 1209
1210#ifdef CONFIG_B43_SSB
1211static void b43_ssb_wireless_core_reset(struct b43_wldev *dev, bool gmode) 1211static void b43_ssb_wireless_core_reset(struct b43_wldev *dev, bool gmode)
1212{ 1212{
1213 struct ssb_device *sdev = dev->dev->sdev;
1214 u32 tmslow;
1215 u32 flags = 0; 1213 u32 flags = 0;
1216 1214
1217 if (gmode) 1215 if (gmode)
@@ -1223,18 +1221,9 @@ static void b43_ssb_wireless_core_reset(struct b43_wldev *dev, bool gmode)
1223 b43_device_enable(dev, flags); 1221 b43_device_enable(dev, flags);
1224 msleep(2); /* Wait for the PLL to turn on. */ 1222 msleep(2); /* Wait for the PLL to turn on. */
1225 1223
1226 /* Now take the PHY out of Reset again */ 1224 b43_phy_take_out_of_reset(dev);
1227 tmslow = ssb_read32(sdev, SSB_TMSLOW);
1228 tmslow |= SSB_TMSLOW_FGC;
1229 tmslow &= ~B43_TMSLOW_PHYRESET;
1230 ssb_write32(sdev, SSB_TMSLOW, tmslow);
1231 ssb_read32(sdev, SSB_TMSLOW); /* flush */
1232 msleep(1);
1233 tmslow &= ~SSB_TMSLOW_FGC;
1234 ssb_write32(sdev, SSB_TMSLOW, tmslow);
1235 ssb_read32(sdev, SSB_TMSLOW); /* flush */
1236 msleep(1);
1237} 1225}
1226#endif
1238 1227
1239void b43_wireless_core_reset(struct b43_wldev *dev, bool gmode) 1228void b43_wireless_core_reset(struct b43_wldev *dev, bool gmode)
1240{ 1229{
@@ -2709,32 +2698,37 @@ static int b43_upload_initvals(struct b43_wldev *dev)
2709 struct b43_firmware *fw = &dev->fw; 2698 struct b43_firmware *fw = &dev->fw;
2710 const struct b43_iv *ivals; 2699 const struct b43_iv *ivals;
2711 size_t count; 2700 size_t count;
2712 int err;
2713 2701
2714 hdr = (const struct b43_fw_header *)(fw->initvals.data->data); 2702 hdr = (const struct b43_fw_header *)(fw->initvals.data->data);
2715 ivals = (const struct b43_iv *)(fw->initvals.data->data + hdr_len); 2703 ivals = (const struct b43_iv *)(fw->initvals.data->data + hdr_len);
2716 count = be32_to_cpu(hdr->size); 2704 count = be32_to_cpu(hdr->size);
2717 err = b43_write_initvals(dev, ivals, count, 2705 return b43_write_initvals(dev, ivals, count,
2718 fw->initvals.data->size - hdr_len); 2706 fw->initvals.data->size - hdr_len);
2719 if (err) 2707}
2720 goto out;
2721 if (fw->initvals_band.data) {
2722 hdr = (const struct b43_fw_header *)(fw->initvals_band.data->data);
2723 ivals = (const struct b43_iv *)(fw->initvals_band.data->data + hdr_len);
2724 count = be32_to_cpu(hdr->size);
2725 err = b43_write_initvals(dev, ivals, count,
2726 fw->initvals_band.data->size - hdr_len);
2727 if (err)
2728 goto out;
2729 }
2730out:
2731 2708
2732 return err; 2709static int b43_upload_initvals_band(struct b43_wldev *dev)
2710{
2711 const size_t hdr_len = sizeof(struct b43_fw_header);
2712 const struct b43_fw_header *hdr;
2713 struct b43_firmware *fw = &dev->fw;
2714 const struct b43_iv *ivals;
2715 size_t count;
2716
2717 if (!fw->initvals_band.data)
2718 return 0;
2719
2720 hdr = (const struct b43_fw_header *)(fw->initvals_band.data->data);
2721 ivals = (const struct b43_iv *)(fw->initvals_band.data->data + hdr_len);
2722 count = be32_to_cpu(hdr->size);
2723 return b43_write_initvals(dev, ivals, count,
2724 fw->initvals_band.data->size - hdr_len);
2733} 2725}
2734 2726
2735/* Initialize the GPIOs 2727/* Initialize the GPIOs
2736 * http://bcm-specs.sipsolutions.net/GPIO 2728 * http://bcm-specs.sipsolutions.net/GPIO
2737 */ 2729 */
2730
2731#ifdef CONFIG_B43_SSB
2738static struct ssb_device *b43_ssb_gpio_dev(struct b43_wldev *dev) 2732static struct ssb_device *b43_ssb_gpio_dev(struct b43_wldev *dev)
2739{ 2733{
2740 struct ssb_bus *bus = dev->dev->sdev->bus; 2734 struct ssb_bus *bus = dev->dev->sdev->bus;
@@ -2745,10 +2739,13 @@ static struct ssb_device *b43_ssb_gpio_dev(struct b43_wldev *dev)
2745 return bus->chipco.dev; 2739 return bus->chipco.dev;
2746#endif 2740#endif
2747} 2741}
2742#endif
2748 2743
2749static int b43_gpio_init(struct b43_wldev *dev) 2744static int b43_gpio_init(struct b43_wldev *dev)
2750{ 2745{
2746#ifdef CONFIG_B43_SSB
2751 struct ssb_device *gpiodev; 2747 struct ssb_device *gpiodev;
2748#endif
2752 u32 mask, set; 2749 u32 mask, set;
2753 2750
2754 b43_maskset32(dev, B43_MMIO_MACCTL, ~B43_MACCTL_GPOUTSMSK, 0); 2751 b43_maskset32(dev, B43_MMIO_MACCTL, ~B43_MACCTL_GPOUTSMSK, 0);
@@ -2807,7 +2804,9 @@ static int b43_gpio_init(struct b43_wldev *dev)
2807/* Turn off all GPIO stuff. Call this on module unload, for example. */ 2804/* Turn off all GPIO stuff. Call this on module unload, for example. */
2808static void b43_gpio_cleanup(struct b43_wldev *dev) 2805static void b43_gpio_cleanup(struct b43_wldev *dev)
2809{ 2806{
2807#ifdef CONFIG_B43_SSB
2810 struct ssb_device *gpiodev; 2808 struct ssb_device *gpiodev;
2809#endif
2811 2810
2812 switch (dev->dev->bus_type) { 2811 switch (dev->dev->bus_type) {
2813#ifdef CONFIG_B43_BCMA 2812#ifdef CONFIG_B43_BCMA
@@ -3091,6 +3090,10 @@ static int b43_chip_init(struct b43_wldev *dev)
3091 if (err) 3090 if (err)
3092 goto err_gpio_clean; 3091 goto err_gpio_clean;
3093 3092
3093 err = b43_upload_initvals_band(dev);
3094 if (err)
3095 goto err_gpio_clean;
3096
3094 /* Turn the Analog on and initialize the PHY. */ 3097 /* Turn the Analog on and initialize the PHY. */
3095 phy->ops->switch_analog(dev, 1); 3098 phy->ops->switch_analog(dev, 1);
3096 err = b43_phy_init(dev); 3099 err = b43_phy_init(dev);
@@ -3690,37 +3693,6 @@ static void b43_op_set_tsf(struct ieee80211_hw *hw,
3690 mutex_unlock(&wl->mutex); 3693 mutex_unlock(&wl->mutex);
3691} 3694}
3692 3695
3693static void b43_put_phy_into_reset(struct b43_wldev *dev)
3694{
3695 u32 tmp;
3696
3697 switch (dev->dev->bus_type) {
3698#ifdef CONFIG_B43_BCMA
3699 case B43_BUS_BCMA:
3700 b43err(dev->wl,
3701 "Putting PHY into reset not supported on BCMA\n");
3702 break;
3703#endif
3704#ifdef CONFIG_B43_SSB
3705 case B43_BUS_SSB:
3706 tmp = ssb_read32(dev->dev->sdev, SSB_TMSLOW);
3707 tmp &= ~B43_TMSLOW_GMODE;
3708 tmp |= B43_TMSLOW_PHYRESET;
3709 tmp |= SSB_TMSLOW_FGC;
3710 ssb_write32(dev->dev->sdev, SSB_TMSLOW, tmp);
3711 msleep(1);
3712
3713 tmp = ssb_read32(dev->dev->sdev, SSB_TMSLOW);
3714 tmp &= ~SSB_TMSLOW_FGC;
3715 tmp |= B43_TMSLOW_PHYRESET;
3716 ssb_write32(dev->dev->sdev, SSB_TMSLOW, tmp);
3717 msleep(1);
3718
3719 break;
3720#endif
3721 }
3722}
3723
3724static const char *band_to_string(enum ieee80211_band band) 3696static const char *band_to_string(enum ieee80211_band band)
3725{ 3697{
3726 switch (band) { 3698 switch (band) {
@@ -3736,89 +3708,73 @@ static const char *band_to_string(enum ieee80211_band band)
3736} 3708}
3737 3709
3738/* Expects wl->mutex locked */ 3710/* Expects wl->mutex locked */
3739static int b43_switch_band(struct b43_wl *wl, struct ieee80211_channel *chan) 3711static int b43_switch_band(struct b43_wldev *dev,
3712 struct ieee80211_channel *chan)
3740{ 3713{
3741 struct b43_wldev *up_dev = NULL; 3714 struct b43_phy *phy = &dev->phy;
3742 struct b43_wldev *down_dev; 3715 bool gmode;
3743 int err; 3716 u32 tmp;
3744 bool uninitialized_var(gmode);
3745 int prev_status;
3746 3717
3747 /* Find a device and PHY which supports the band. */
3748 switch (chan->band) { 3718 switch (chan->band) {
3749 case IEEE80211_BAND_5GHZ: 3719 case IEEE80211_BAND_5GHZ:
3750 if (wl->current_dev->phy.supports_5ghz) { 3720 gmode = false;
3751 up_dev = wl->current_dev;
3752 gmode = false;
3753 }
3754 break; 3721 break;
3755 case IEEE80211_BAND_2GHZ: 3722 case IEEE80211_BAND_2GHZ:
3756 if (wl->current_dev->phy.supports_2ghz) { 3723 gmode = true;
3757 up_dev = wl->current_dev;
3758 gmode = true;
3759 }
3760 break; 3724 break;
3761 default: 3725 default:
3762 B43_WARN_ON(1); 3726 B43_WARN_ON(1);
3763 return -EINVAL; 3727 return -EINVAL;
3764 } 3728 }
3765 3729
3766 if (!up_dev) { 3730 if (!((gmode && phy->supports_2ghz) ||
3767 b43err(wl, "Could not find a device for %s-GHz band operation\n", 3731 (!gmode && phy->supports_5ghz))) {
3732 b43err(dev->wl, "This device doesn't support %s-GHz band\n",
3768 band_to_string(chan->band)); 3733 band_to_string(chan->band));
3769 return -ENODEV; 3734 return -ENODEV;
3770 } 3735 }
3771 if (!!wl->current_dev->phy.gmode == !!gmode) { 3736
3737 if (!!phy->gmode == !!gmode) {
3772 /* This device is already running. */ 3738 /* This device is already running. */
3773 return 0; 3739 return 0;
3774 } 3740 }
3775 b43dbg(wl, "Switching to %s-GHz band\n", 3741
3742 b43dbg(dev->wl, "Switching to %s GHz band\n",
3776 band_to_string(chan->band)); 3743 band_to_string(chan->band));
3777 down_dev = wl->current_dev;
3778 3744
3779 prev_status = b43_status(down_dev); 3745 b43_software_rfkill(dev, true);
3780 /* Shutdown the currently running core. */
3781 if (prev_status >= B43_STAT_STARTED)
3782 down_dev = b43_wireless_core_stop(down_dev);
3783 if (prev_status >= B43_STAT_INITIALIZED)
3784 b43_wireless_core_exit(down_dev);
3785 3746
3786 if (down_dev != up_dev) { 3747 phy->gmode = gmode;
3787 /* We switch to a different core, so we put PHY into 3748 b43_phy_put_into_reset(dev);
3788 * RESET on the old core. */ 3749 switch (dev->dev->bus_type) {
3789 b43_put_phy_into_reset(down_dev); 3750#ifdef CONFIG_B43_BCMA
3751 case B43_BUS_BCMA:
3752 tmp = bcma_aread32(dev->dev->bdev, BCMA_IOCTL);
3753 if (gmode)
3754 tmp |= B43_BCMA_IOCTL_GMODE;
3755 else
3756 tmp &= ~B43_BCMA_IOCTL_GMODE;
3757 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, tmp);
3758 break;
3759#endif
3760#ifdef CONFIG_B43_SSB
3761 case B43_BUS_SSB:
3762 tmp = ssb_read32(dev->dev->sdev, SSB_TMSLOW);
3763 if (gmode)
3764 tmp |= B43_TMSLOW_GMODE;
3765 else
3766 tmp &= ~B43_TMSLOW_GMODE;
3767 ssb_write32(dev->dev->sdev, SSB_TMSLOW, tmp);
3768 break;
3769#endif
3790 } 3770 }
3771 b43_phy_take_out_of_reset(dev);
3791 3772
3792 /* Now start the new core. */ 3773 b43_upload_initvals_band(dev);
3793 up_dev->phy.gmode = gmode;
3794 if (prev_status >= B43_STAT_INITIALIZED) {
3795 err = b43_wireless_core_init(up_dev);
3796 if (err) {
3797 b43err(wl, "Fatal: Could not initialize device for "
3798 "selected %s-GHz band\n",
3799 band_to_string(chan->band));
3800 goto init_failure;
3801 }
3802 }
3803 if (prev_status >= B43_STAT_STARTED) {
3804 err = b43_wireless_core_start(up_dev);
3805 if (err) {
3806 b43err(wl, "Fatal: Could not start device for "
3807 "selected %s-GHz band\n",
3808 band_to_string(chan->band));
3809 b43_wireless_core_exit(up_dev);
3810 goto init_failure;
3811 }
3812 }
3813 B43_WARN_ON(b43_status(up_dev) != prev_status);
3814 3774
3815 wl->current_dev = up_dev; 3775 b43_phy_init(dev);
3816 3776
3817 return 0; 3777 return 0;
3818init_failure:
3819 /* Whoops, failed to init the new core. No core is operating now. */
3820 wl->current_dev = NULL;
3821 return err;
3822} 3778}
3823 3779
3824/* Write the short and long frame retry limit values. */ 3780/* Write the short and long frame retry limit values. */
@@ -3851,8 +3807,10 @@ static int b43_op_config(struct ieee80211_hw *hw, u32 changed)
3851 3807
3852 dev = wl->current_dev; 3808 dev = wl->current_dev;
3853 3809
3810 b43_mac_suspend(dev);
3811
3854 /* Switch the band (if necessary). This might change the active core. */ 3812 /* Switch the band (if necessary). This might change the active core. */
3855 err = b43_switch_band(wl, conf->chandef.chan); 3813 err = b43_switch_band(dev, conf->chandef.chan);
3856 if (err) 3814 if (err)
3857 goto out_unlock_mutex; 3815 goto out_unlock_mutex;
3858 3816
@@ -3871,8 +3829,6 @@ static int b43_op_config(struct ieee80211_hw *hw, u32 changed)
3871 else 3829 else
3872 phy->is_40mhz = false; 3830 phy->is_40mhz = false;
3873 3831
3874 b43_mac_suspend(dev);
3875
3876 if (changed & IEEE80211_CONF_CHANGE_RETRY_LIMITS) 3832 if (changed & IEEE80211_CONF_CHANGE_RETRY_LIMITS)
3877 b43_set_retry_limits(dev, conf->short_frame_max_tx_count, 3833 b43_set_retry_limits(dev, conf->short_frame_max_tx_count,
3878 conf->long_frame_max_tx_count); 3834 conf->long_frame_max_tx_count);
@@ -4582,8 +4538,12 @@ static void b43_imcfglo_timeouts_workaround(struct b43_wldev *dev)
4582 struct ssb_bus *bus; 4538 struct ssb_bus *bus;
4583 u32 tmp; 4539 u32 tmp;
4584 4540
4541#ifdef CONFIG_B43_SSB
4585 if (dev->dev->bus_type != B43_BUS_SSB) 4542 if (dev->dev->bus_type != B43_BUS_SSB)
4586 return; 4543 return;
4544#else
4545 return;
4546#endif
4587 4547
4588 bus = dev->dev->sdev->bus; 4548 bus = dev->dev->sdev->bus;
4589 4549
@@ -4738,7 +4698,7 @@ static int b43_wireless_core_init(struct b43_wldev *dev)
4738 } 4698 }
4739 if (sprom->boardflags_lo & B43_BFL_XTAL_NOSLOW) 4699 if (sprom->boardflags_lo & B43_BFL_XTAL_NOSLOW)
4740 hf |= B43_HF_DSCRQ; /* Disable slowclock requests from ucode. */ 4700 hf |= B43_HF_DSCRQ; /* Disable slowclock requests from ucode. */
4741#ifdef CONFIG_SSB_DRIVER_PCICORE 4701#if defined(CONFIG_B43_SSB) && defined(CONFIG_SSB_DRIVER_PCICORE)
4742 if (dev->dev->bus_type == B43_BUS_SSB && 4702 if (dev->dev->bus_type == B43_BUS_SSB &&
4743 dev->dev->sdev->bus->bustype == SSB_BUSTYPE_PCI && 4703 dev->dev->sdev->bus->bustype == SSB_BUSTYPE_PCI &&
4744 dev->dev->sdev->bus->pcicore.dev->id.revision <= 10) 4704 dev->dev->sdev->bus->pcicore.dev->id.revision <= 10)
@@ -5129,10 +5089,81 @@ static void b43_wireless_core_detach(struct b43_wldev *dev)
5129 b43_phy_free(dev); 5089 b43_phy_free(dev);
5130} 5090}
5131 5091
5092static void b43_supported_bands(struct b43_wldev *dev, bool *have_2ghz_phy,
5093 bool *have_5ghz_phy)
5094{
5095 u16 dev_id = 0;
5096
5097#ifdef CONFIG_B43_BCMA
5098 if (dev->dev->bus_type == B43_BUS_BCMA &&
5099 dev->dev->bdev->bus->hosttype == BCMA_HOSTTYPE_PCI)
5100 dev_id = dev->dev->bdev->bus->host_pci->device;
5101#endif
5102#ifdef CONFIG_B43_SSB
5103 if (dev->dev->bus_type == B43_BUS_SSB &&
5104 dev->dev->sdev->bus->bustype == SSB_BUSTYPE_PCI)
5105 dev_id = dev->dev->sdev->bus->host_pci->device;
5106#endif
5107 /* Override with SPROM value if available */
5108 if (dev->dev->bus_sprom->dev_id)
5109 dev_id = dev->dev->bus_sprom->dev_id;
5110
5111 /* Note: below IDs can be "virtual" (not maching e.g. real PCI ID) */
5112 switch (dev_id) {
5113 case 0x4324: /* BCM4306 */
5114 case 0x4312: /* BCM4311 */
5115 case 0x4319: /* BCM4318 */
5116 case 0x4328: /* BCM4321 */
5117 case 0x432b: /* BCM4322 */
5118 case 0x4350: /* BCM43222 */
5119 case 0x4353: /* BCM43224 */
5120 case 0x0576: /* BCM43224 */
5121 case 0x435f: /* BCM6362 */
5122 case 0x4331: /* BCM4331 */
5123 case 0x4359: /* BCM43228 */
5124 case 0x43a0: /* BCM4360 */
5125 case 0x43b1: /* BCM4352 */
5126 /* Dual band devices */
5127 *have_2ghz_phy = true;
5128 *have_5ghz_phy = true;
5129 return;
5130 case 0x4321: /* BCM4306 */
5131 case 0x4313: /* BCM4311 */
5132 case 0x431a: /* BCM4318 */
5133 case 0x432a: /* BCM4321 */
5134 case 0x432d: /* BCM4322 */
5135 case 0x4352: /* BCM43222 */
5136 case 0x4333: /* BCM4331 */
5137 case 0x43a2: /* BCM4360 */
5138 case 0x43b3: /* BCM4352 */
5139 /* 5 GHz only devices */
5140 *have_2ghz_phy = false;
5141 *have_5ghz_phy = true;
5142 return;
5143 }
5144
5145 /* As a fallback, try to guess using PHY type */
5146 switch (dev->phy.type) {
5147 case B43_PHYTYPE_A:
5148 *have_2ghz_phy = false;
5149 *have_5ghz_phy = true;
5150 return;
5151 case B43_PHYTYPE_G:
5152 case B43_PHYTYPE_N:
5153 case B43_PHYTYPE_LP:
5154 case B43_PHYTYPE_HT:
5155 case B43_PHYTYPE_LCN:
5156 *have_2ghz_phy = true;
5157 *have_5ghz_phy = false;
5158 return;
5159 }
5160
5161 B43_WARN_ON(1);
5162}
5163
5132static int b43_wireless_core_attach(struct b43_wldev *dev) 5164static int b43_wireless_core_attach(struct b43_wldev *dev)
5133{ 5165{
5134 struct b43_wl *wl = dev->wl; 5166 struct b43_wl *wl = dev->wl;
5135 struct pci_dev *pdev = NULL;
5136 int err; 5167 int err;
5137 u32 tmp; 5168 u32 tmp;
5138 bool have_2ghz_phy = false, have_5ghz_phy = false; 5169 bool have_2ghz_phy = false, have_5ghz_phy = false;
@@ -5144,19 +5175,13 @@ static int b43_wireless_core_attach(struct b43_wldev *dev)
5144 * that in core_init(), too. 5175 * that in core_init(), too.
5145 */ 5176 */
5146 5177
5147#ifdef CONFIG_B43_SSB
5148 if (dev->dev->bus_type == B43_BUS_SSB &&
5149 dev->dev->sdev->bus->bustype == SSB_BUSTYPE_PCI)
5150 pdev = dev->dev->sdev->bus->host_pci;
5151#endif
5152
5153 err = b43_bus_powerup(dev, 0); 5178 err = b43_bus_powerup(dev, 0);
5154 if (err) { 5179 if (err) {
5155 b43err(wl, "Bus powerup failed\n"); 5180 b43err(wl, "Bus powerup failed\n");
5156 goto out; 5181 goto out;
5157 } 5182 }
5158 5183
5159 /* Get the PHY type. */ 5184 /* Try to guess supported bands for the first init needs */
5160 switch (dev->dev->bus_type) { 5185 switch (dev->dev->bus_type) {
5161#ifdef CONFIG_B43_BCMA 5186#ifdef CONFIG_B43_BCMA
5162 case B43_BUS_BCMA: 5187 case B43_BUS_BCMA:
@@ -5180,48 +5205,29 @@ static int b43_wireless_core_attach(struct b43_wldev *dev)
5180 dev->phy.gmode = have_2ghz_phy; 5205 dev->phy.gmode = have_2ghz_phy;
5181 b43_wireless_core_reset(dev, dev->phy.gmode); 5206 b43_wireless_core_reset(dev, dev->phy.gmode);
5182 5207
5208 /* Get the PHY type. */
5183 err = b43_phy_versioning(dev); 5209 err = b43_phy_versioning(dev);
5184 if (err) 5210 if (err)
5185 goto err_powerdown; 5211 goto err_powerdown;
5186 /* Check if this device supports multiband. */ 5212
5187 if (!pdev || 5213 /* Get real info about supported bands */
5188 (pdev->device != 0x4312 && 5214 b43_supported_bands(dev, &have_2ghz_phy, &have_5ghz_phy);
5189 pdev->device != 0x4319 && pdev->device != 0x4324)) { 5215
5190 /* No multiband support. */ 5216 /* We don't support 5 GHz on some PHYs yet */
5191 have_2ghz_phy = false; 5217 switch (dev->phy.type) {
5218 case B43_PHYTYPE_A:
5219 case B43_PHYTYPE_N:
5220 case B43_PHYTYPE_LP:
5221 case B43_PHYTYPE_HT:
5222 b43warn(wl, "5 GHz band is unsupported on this PHY\n");
5192 have_5ghz_phy = false; 5223 have_5ghz_phy = false;
5193 switch (dev->phy.type) {
5194 case B43_PHYTYPE_A:
5195 have_5ghz_phy = true;
5196 break;
5197 case B43_PHYTYPE_LP: //FIXME not always!
5198#if 0 //FIXME enabling 5GHz causes a NULL pointer dereference
5199 have_5ghz_phy = 1;
5200#endif
5201 case B43_PHYTYPE_G:
5202 case B43_PHYTYPE_N:
5203 case B43_PHYTYPE_HT:
5204 case B43_PHYTYPE_LCN:
5205 have_2ghz_phy = true;
5206 break;
5207 default:
5208 B43_WARN_ON(1);
5209 }
5210 } 5224 }
5211 if (dev->phy.type == B43_PHYTYPE_A) { 5225
5212 /* FIXME */ 5226 if (!have_2ghz_phy && !have_5ghz_phy) {
5213 b43err(wl, "IEEE 802.11a devices are unsupported\n"); 5227 b43err(wl, "b43 can't support any band on this device\n");
5214 err = -EOPNOTSUPP; 5228 err = -EOPNOTSUPP;
5215 goto err_powerdown; 5229 goto err_powerdown;
5216 } 5230 }
5217 if (1 /* disable A-PHY */) {
5218 /* FIXME: For now we disable the A-PHY on multi-PHY devices. */
5219 if (dev->phy.type != B43_PHYTYPE_N &&
5220 dev->phy.type != B43_PHYTYPE_LP) {
5221 have_2ghz_phy = true;
5222 have_5ghz_phy = false;
5223 }
5224 }
5225 5231
5226 err = b43_phy_allocate(dev); 5232 err = b43_phy_allocate(dev);
5227 if (err) 5233 if (err)
@@ -5310,6 +5316,7 @@ static int b43_one_core_attach(struct b43_bus_dev *dev, struct b43_wl *wl)
5310 (pdev->subsystem_vendor == PCI_VENDOR_ID_##_subvendor) && \ 5316 (pdev->subsystem_vendor == PCI_VENDOR_ID_##_subvendor) && \
5311 (pdev->subsystem_device == _subdevice) ) 5317 (pdev->subsystem_device == _subdevice) )
5312 5318
5319#ifdef CONFIG_B43_SSB
5313static void b43_sprom_fixup(struct ssb_bus *bus) 5320static void b43_sprom_fixup(struct ssb_bus *bus)
5314{ 5321{
5315 struct pci_dev *pdev; 5322 struct pci_dev *pdev;
@@ -5341,6 +5348,7 @@ static void b43_wireless_exit(struct b43_bus_dev *dev, struct b43_wl *wl)
5341 ssb_set_devtypedata(dev->sdev, NULL); 5348 ssb_set_devtypedata(dev->sdev, NULL);
5342 ieee80211_free_hw(hw); 5349 ieee80211_free_hw(hw);
5343} 5350}
5351#endif
5344 5352
5345static struct b43_wl *b43_wireless_init(struct b43_bus_dev *dev) 5353static struct b43_wl *b43_wireless_init(struct b43_bus_dev *dev)
5346{ 5354{
diff --git a/drivers/net/wireless/b43/phy_common.c b/drivers/net/wireless/b43/phy_common.c
index 3e45989f418d..fb0ddddde16b 100644
--- a/drivers/net/wireless/b43/phy_common.c
+++ b/drivers/net/wireless/b43/phy_common.c
@@ -96,6 +96,7 @@ int b43_phy_init(struct b43_wldev *dev)
96 96
97 phy->channel = ops->get_default_chan(dev); 97 phy->channel = ops->get_default_chan(dev);
98 98
99 phy->ops->switch_analog(dev, true);
99 b43_software_rfkill(dev, false); 100 b43_software_rfkill(dev, false);
100 err = ops->init(dev); 101 err = ops->init(dev);
101 if (err) { 102 if (err) {
@@ -312,6 +313,90 @@ void b43_phy_maskset(struct b43_wldev *dev, u16 offset, u16 mask, u16 set)
312 } 313 }
313} 314}
314 315
316void b43_phy_put_into_reset(struct b43_wldev *dev)
317{
318 u32 tmp;
319
320 switch (dev->dev->bus_type) {
321#ifdef CONFIG_B43_BCMA
322 case B43_BUS_BCMA:
323 tmp = bcma_aread32(dev->dev->bdev, BCMA_IOCTL);
324 tmp &= ~B43_BCMA_IOCTL_GMODE;
325 tmp |= B43_BCMA_IOCTL_PHY_RESET;
326 tmp |= BCMA_IOCTL_FGC;
327 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, tmp);
328 udelay(1);
329
330 tmp = bcma_aread32(dev->dev->bdev, BCMA_IOCTL);
331 tmp &= ~BCMA_IOCTL_FGC;
332 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, tmp);
333 udelay(1);
334 break;
335#endif
336#ifdef CONFIG_B43_SSB
337 case B43_BUS_SSB:
338 tmp = ssb_read32(dev->dev->sdev, SSB_TMSLOW);
339 tmp &= ~B43_TMSLOW_GMODE;
340 tmp |= B43_TMSLOW_PHYRESET;
341 tmp |= SSB_TMSLOW_FGC;
342 ssb_write32(dev->dev->sdev, SSB_TMSLOW, tmp);
343 usleep_range(1000, 2000);
344
345 tmp = ssb_read32(dev->dev->sdev, SSB_TMSLOW);
346 tmp &= ~SSB_TMSLOW_FGC;
347 ssb_write32(dev->dev->sdev, SSB_TMSLOW, tmp);
348 usleep_range(1000, 2000);
349
350 break;
351#endif
352 }
353}
354
355void b43_phy_take_out_of_reset(struct b43_wldev *dev)
356{
357 u32 tmp;
358
359 switch (dev->dev->bus_type) {
360#ifdef CONFIG_B43_BCMA
361 case B43_BUS_BCMA:
362 /* Unset reset bit (with forcing clock) */
363 tmp = bcma_aread32(dev->dev->bdev, BCMA_IOCTL);
364 tmp &= ~B43_BCMA_IOCTL_PHY_RESET;
365 tmp &= ~B43_BCMA_IOCTL_PHY_CLKEN;
366 tmp |= BCMA_IOCTL_FGC;
367 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, tmp);
368 udelay(1);
369
370 /* Do not force clock anymore */
371 tmp = bcma_aread32(dev->dev->bdev, BCMA_IOCTL);
372 tmp &= ~BCMA_IOCTL_FGC;
373 tmp |= B43_BCMA_IOCTL_PHY_CLKEN;
374 bcma_awrite32(dev->dev->bdev, BCMA_IOCTL, tmp);
375 udelay(1);
376 break;
377#endif
378#ifdef CONFIG_B43_SSB
379 case B43_BUS_SSB:
380 /* Unset reset bit (with forcing clock) */
381 tmp = ssb_read32(dev->dev->sdev, SSB_TMSLOW);
382 tmp &= ~B43_TMSLOW_PHYRESET;
383 tmp &= ~B43_TMSLOW_PHYCLKEN;
384 tmp |= SSB_TMSLOW_FGC;
385 ssb_write32(dev->dev->sdev, SSB_TMSLOW, tmp);
386 ssb_read32(dev->dev->sdev, SSB_TMSLOW); /* flush */
387 usleep_range(1000, 2000);
388
389 tmp = ssb_read32(dev->dev->sdev, SSB_TMSLOW);
390 tmp &= ~SSB_TMSLOW_FGC;
391 tmp |= B43_TMSLOW_PHYCLKEN;
392 ssb_write32(dev->dev->sdev, SSB_TMSLOW, tmp);
393 ssb_read32(dev->dev->sdev, SSB_TMSLOW); /* flush */
394 usleep_range(1000, 2000);
395 break;
396#endif
397 }
398}
399
315int b43_switch_channel(struct b43_wldev *dev, unsigned int new_channel) 400int b43_switch_channel(struct b43_wldev *dev, unsigned int new_channel)
316{ 401{
317 struct b43_phy *phy = &(dev->phy); 402 struct b43_phy *phy = &(dev->phy);
diff --git a/drivers/net/wireless/b43/phy_common.h b/drivers/net/wireless/b43/phy_common.h
index f1b999349876..47b55855c37d 100644
--- a/drivers/net/wireless/b43/phy_common.h
+++ b/drivers/net/wireless/b43/phy_common.h
@@ -231,7 +231,7 @@ struct b43_phy {
231 /* HT info */ 231 /* HT info */
232 bool is_40mhz; 232 bool is_40mhz;
233 233
234 /* GMODE bit enabled? */ 234 /* Is GMODE (2 GHz mode) bit enabled? */
235 bool gmode; 235 bool gmode;
236 236
237 /* Analog Type */ 237 /* Analog Type */
@@ -390,6 +390,9 @@ void b43_phy_lock(struct b43_wldev *dev);
390 */ 390 */
391void b43_phy_unlock(struct b43_wldev *dev); 391void b43_phy_unlock(struct b43_wldev *dev);
392 392
393void b43_phy_put_into_reset(struct b43_wldev *dev);
394void b43_phy_take_out_of_reset(struct b43_wldev *dev);
395
393/** 396/**
394 * b43_switch_channel - Switch to another channel 397 * b43_switch_channel - Switch to another channel
395 */ 398 */
diff --git a/drivers/net/wireless/b43/radio_2056.c b/drivers/net/wireless/b43/radio_2056.c
index a07e4cacab77..2ce25607c60d 100644
--- a/drivers/net/wireless/b43/radio_2056.c
+++ b/drivers/net/wireless/b43/radio_2056.c
@@ -9058,6 +9058,231 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9058 9058
9059static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev11[] = { 9059static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev11[] = {
9060 { 9060 {
9061 .freq = 4920,
9062 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xec, 0x05, 0x05, 0x02,
9063 0x0c, 0x01, 0x00, 0x00, 0x00, 0x8f, 0x0f, 0x00,
9064 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9065 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9066 0x00, 0x0f, 0x00, 0x6f, 0x00),
9067 PHYREGS(0x07b4, 0x07b0, 0x07ac, 0x0214, 0x0215, 0x0216),
9068 },
9069 {
9070 .freq = 4930,
9071 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xed, 0x05, 0x05, 0x02,
9072 0x0c, 0x01, 0x00, 0x00, 0x00, 0x8f, 0x0f, 0x00,
9073 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9074 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9075 0x00, 0x0f, 0x00, 0x6f, 0x00),
9076 PHYREGS(0x07b8, 0x07b4, 0x07b0, 0x0213, 0x0214, 0x0215),
9077 },
9078 {
9079 .freq = 4940,
9080 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xee, 0x05, 0x05, 0x02,
9081 0x0c, 0x01, 0x00, 0x00, 0x00, 0x8f, 0x0f, 0x00,
9082 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9083 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9084 0x00, 0x0f, 0x00, 0x6f, 0x00),
9085 PHYREGS(0x07bc, 0x07b8, 0x07b4, 0x0212, 0x0213, 0x0214),
9086 },
9087 {
9088 .freq = 4950,
9089 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xef, 0x05, 0x05, 0x02,
9090 0x0c, 0x01, 0x00, 0x00, 0x00, 0x8f, 0x0f, 0x00,
9091 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9092 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9093 0x00, 0x0f, 0x00, 0x6f, 0x00),
9094 PHYREGS(0x07c0, 0x07bc, 0x07b8, 0x0211, 0x0212, 0x0213),
9095 },
9096 {
9097 .freq = 4960,
9098 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xf0, 0x05, 0x05, 0x02,
9099 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9100 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9101 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9102 0x00, 0x0f, 0x00, 0x6f, 0x00),
9103 PHYREGS(0x07c4, 0x07c0, 0x07bc, 0x020f, 0x0211, 0x0212),
9104 },
9105 {
9106 .freq = 4970,
9107 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xf1, 0x05, 0x05, 0x02,
9108 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9109 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9110 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9111 0x00, 0x0f, 0x00, 0x6f, 0x00),
9112 PHYREGS(0x07c8, 0x07c4, 0x07c0, 0x020e, 0x020f, 0x0211),
9113 },
9114 {
9115 .freq = 4980,
9116 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xf2, 0x05, 0x05, 0x02,
9117 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9118 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9119 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9120 0x00, 0x0f, 0x00, 0x6f, 0x00),
9121 PHYREGS(0x07cc, 0x07c8, 0x07c4, 0x020d, 0x020e, 0x020f),
9122 },
9123 {
9124 .freq = 4990,
9125 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xf3, 0x05, 0x05, 0x02,
9126 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9127 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9128 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9129 0x00, 0x0f, 0x00, 0x6f, 0x00),
9130 PHYREGS(0x07d0, 0x07cc, 0x07c8, 0x020c, 0x020d, 0x020e),
9131 },
9132 {
9133 .freq = 5000,
9134 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xf4, 0x05, 0x05, 0x02,
9135 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9136 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9137 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9138 0x00, 0x0f, 0x00, 0x6f, 0x00),
9139 PHYREGS(0x07d4, 0x07d0, 0x07cc, 0x020b, 0x020c, 0x020d),
9140 },
9141 {
9142 .freq = 5010,
9143 RADIOREGS3(0xff, 0x01, 0x01, 0x01, 0xf5, 0x05, 0x05, 0x02,
9144 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9145 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9146 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9147 0x00, 0x0f, 0x00, 0x6f, 0x00),
9148 PHYREGS(0x07d8, 0x07d4, 0x07d0, 0x020a, 0x020b, 0x020c),
9149 },
9150 {
9151 .freq = 5020,
9152 RADIOREGS3(0xf7, 0x01, 0x01, 0x01, 0xf6, 0x05, 0x05, 0x02,
9153 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9154 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9155 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9156 0x00, 0x0f, 0x00, 0x6f, 0x00),
9157 PHYREGS(0x07dc, 0x07d8, 0x07d4, 0x0209, 0x020a, 0x020b),
9158 },
9159 {
9160 .freq = 5030,
9161 RADIOREGS3(0xf7, 0x01, 0x01, 0x01, 0xf7, 0x05, 0x05, 0x02,
9162 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9163 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9164 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9165 0x00, 0x0f, 0x00, 0x6f, 0x00),
9166 PHYREGS(0x07e0, 0x07dc, 0x07d8, 0x0208, 0x0209, 0x020a),
9167 },
9168 {
9169 .freq = 5040,
9170 RADIOREGS3(0xef, 0x01, 0x01, 0x01, 0xf8, 0x05, 0x05, 0x02,
9171 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9172 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9173 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9174 0x00, 0x0f, 0x00, 0x6f, 0x00),
9175 PHYREGS(0x07e4, 0x07e0, 0x07dc, 0x0207, 0x0208, 0x0209),
9176 },
9177 {
9178 .freq = 5050,
9179 RADIOREGS3(0xef, 0x01, 0x01, 0x01, 0xf9, 0x05, 0x05, 0x02,
9180 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9181 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9182 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9183 0x00, 0x0f, 0x00, 0x6f, 0x00),
9184 PHYREGS(0x07e8, 0x07e4, 0x07e0, 0x0206, 0x0207, 0x0208),
9185 },
9186 {
9187 .freq = 5060,
9188 RADIOREGS3(0xe6, 0x01, 0x01, 0x01, 0xfa, 0x05, 0x05, 0x02,
9189 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9190 0xff, 0xfe, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9191 0x00, 0x6f, 0x00, 0xfe, 0x00, 0x09, 0x00, 0x77,
9192 0x00, 0x0f, 0x00, 0x6f, 0x00),
9193 PHYREGS(0x07ec, 0x07e8, 0x07e4, 0x0205, 0x0206, 0x0207),
9194 },
9195 {
9196 .freq = 5070,
9197 RADIOREGS3(0xe6, 0x01, 0x01, 0x01, 0xfb, 0x05, 0x05, 0x02,
9198 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9199 0xff, 0xfd, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9200 0x00, 0x6f, 0x00, 0xfd, 0x00, 0x09, 0x00, 0x77,
9201 0x00, 0x0f, 0x00, 0x6f, 0x00),
9202 PHYREGS(0x07f0, 0x07ec, 0x07e8, 0x0204, 0x0205, 0x0206),
9203 },
9204 {
9205 .freq = 5080,
9206 RADIOREGS3(0xde, 0x01, 0x01, 0x01, 0xfc, 0x05, 0x05, 0x02,
9207 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9208 0xff, 0xfd, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9209 0x00, 0x6f, 0x00, 0xfd, 0x00, 0x09, 0x00, 0x77,
9210 0x00, 0x0f, 0x00, 0x6f, 0x00),
9211 PHYREGS(0x07f4, 0x07f0, 0x07ec, 0x0203, 0x0204, 0x0205),
9212 },
9213 {
9214 .freq = 5090,
9215 RADIOREGS3(0xde, 0x01, 0x01, 0x01, 0xfd, 0x05, 0x05, 0x02,
9216 0x0c, 0x01, 0x01, 0x01, 0x01, 0x8f, 0x0f, 0x00,
9217 0xff, 0xfd, 0x00, 0x09, 0x00, 0x77, 0x00, 0x0f,
9218 0x00, 0x6f, 0x00, 0xfd, 0x00, 0x09, 0x00, 0x77,
9219 0x00, 0x0f, 0x00, 0x6f, 0x00),
9220 PHYREGS(0x07f8, 0x07f4, 0x07f0, 0x0202, 0x0203, 0x0204),
9221 },
9222 {
9223 .freq = 5100,
9224 RADIOREGS3(0xd6, 0x01, 0x01, 0x01, 0xfe, 0x05, 0x05, 0x02,
9225 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9226 0xff, 0xfd, 0x00, 0x08, 0x00, 0x77, 0x00, 0x0f,
9227 0x00, 0x6f, 0x00, 0xfd, 0x00, 0x08, 0x00, 0x77,
9228 0x00, 0x0f, 0x00, 0x6f, 0x00),
9229 PHYREGS(0x07fc, 0x07f8, 0x07f4, 0x0201, 0x0202, 0x0203),
9230 },
9231 {
9232 .freq = 5110,
9233 RADIOREGS3(0xd6, 0x01, 0x01, 0x01, 0xff, 0x05, 0x05, 0x02,
9234 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9235 0xff, 0xfc, 0x00, 0x08, 0x00, 0x77, 0x00, 0x0f,
9236 0x00, 0x6f, 0x00, 0xfc, 0x00, 0x08, 0x00, 0x77,
9237 0x00, 0x0f, 0x00, 0x6f, 0x00),
9238 PHYREGS(0x0800, 0x07fc, 0x07f8, 0x0200, 0x0201, 0x0202),
9239 },
9240 {
9241 .freq = 5120,
9242 RADIOREGS3(0xce, 0x01, 0x01, 0x02, 0x00, 0x05, 0x05, 0x02,
9243 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9244 0xff, 0xfc, 0x00, 0x08, 0x00, 0x77, 0x00, 0x0f,
9245 0x00, 0x6f, 0x00, 0xfc, 0x00, 0x08, 0x00, 0x77,
9246 0x00, 0x0f, 0x00, 0x6f, 0x00),
9247 PHYREGS(0x0804, 0x0800, 0x07fc, 0x01ff, 0x0200, 0x0201),
9248 },
9249 {
9250 .freq = 5130,
9251 RADIOREGS3(0xce, 0x01, 0x01, 0x02, 0x01, 0x05, 0x05, 0x02,
9252 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9253 0xff, 0xfc, 0x00, 0x08, 0x00, 0x77, 0x00, 0x0f,
9254 0x00, 0x6f, 0x00, 0xfc, 0x00, 0x08, 0x00, 0x77,
9255 0x00, 0x0f, 0x00, 0x6f, 0x00),
9256 PHYREGS(0x0808, 0x0804, 0x0800, 0x01fe, 0x01ff, 0x0200),
9257 },
9258 {
9259 .freq = 5140,
9260 RADIOREGS3(0xc6, 0x01, 0x01, 0x02, 0x02, 0x05, 0x05, 0x02,
9261 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9262 0xff, 0xfb, 0x00, 0x08, 0x00, 0x77, 0x00, 0x0f,
9263 0x00, 0x6f, 0x00, 0xfb, 0x00, 0x08, 0x00, 0x77,
9264 0x00, 0x0f, 0x00, 0x6f, 0x00),
9265 PHYREGS(0x080c, 0x0808, 0x0804, 0x01fd, 0x01fe, 0x01ff),
9266 },
9267 {
9268 .freq = 5160,
9269 RADIOREGS3(0xbe, 0x01, 0x01, 0x02, 0x04, 0x05, 0x05, 0x02,
9270 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9271 0xff, 0xfa, 0x00, 0x07, 0x00, 0x77, 0x00, 0x0e,
9272 0x00, 0x6f, 0x00, 0xfa, 0x00, 0x07, 0x00, 0x77,
9273 0x00, 0x0e, 0x00, 0x6f, 0x00),
9274 PHYREGS(0x0814, 0x0810, 0x080c, 0x01fb, 0x01fc, 0x01fd),
9275 },
9276 {
9277 .freq = 5170,
9278 RADIOREGS3(0xbe, 0x01, 0x01, 0x02, 0x05, 0x05, 0x05, 0x02,
9279 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9280 0xff, 0xfa, 0x00, 0x07, 0x00, 0x77, 0x00, 0x0e,
9281 0x00, 0x6f, 0x00, 0xfa, 0x00, 0x07, 0x00, 0x77,
9282 0x00, 0x0e, 0x00, 0x6f, 0x00),
9283 PHYREGS(0x0818, 0x0814, 0x0810, 0x01fa, 0x01fb, 0x01fc),
9284 },
9285 {
9061 .freq = 5180, 9286 .freq = 5180,
9062 RADIOREGS3(0xb6, 0x01, 0x01, 0x02, 0x06, 0x05, 0x05, 0x02, 9287 RADIOREGS3(0xb6, 0x01, 0x01, 0x02, 0x06, 0x05, 0x05, 0x02,
9063 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00, 9288 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
@@ -9067,6 +9292,15 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9067 PHYREGS(0x081c, 0x0818, 0x0814, 0x01f9, 0x01fa, 0x01fb), 9292 PHYREGS(0x081c, 0x0818, 0x0814, 0x01f9, 0x01fa, 0x01fb),
9068 }, 9293 },
9069 { 9294 {
9295 .freq = 5190,
9296 RADIOREGS3(0xb6, 0x01, 0x01, 0x02, 0x07, 0x05, 0x05, 0x02,
9297 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9298 0xff, 0xf9, 0x00, 0x06, 0x00, 0x77, 0x00, 0x0d,
9299 0x00, 0x6f, 0x00, 0xf9, 0x00, 0x06, 0x00, 0x77,
9300 0x00, 0x0d, 0x00, 0x6f, 0x00),
9301 PHYREGS(0x0820, 0x081c, 0x0818, 0x01f8, 0x01f9, 0x01fa),
9302 },
9303 {
9070 .freq = 5200, 9304 .freq = 5200,
9071 RADIOREGS3(0xaf, 0x01, 0x01, 0x02, 0x08, 0x05, 0x05, 0x02, 9305 RADIOREGS3(0xaf, 0x01, 0x01, 0x02, 0x08, 0x05, 0x05, 0x02,
9072 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00, 9306 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
@@ -9076,6 +9310,15 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9076 PHYREGS(0x0824, 0x0820, 0x081c, 0x01f7, 0x01f8, 0x01f9), 9310 PHYREGS(0x0824, 0x0820, 0x081c, 0x01f7, 0x01f8, 0x01f9),
9077 }, 9311 },
9078 { 9312 {
9313 .freq = 5210,
9314 RADIOREGS3(0xaf, 0x01, 0x01, 0x02, 0x09, 0x05, 0x05, 0x02,
9315 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8f, 0x0f, 0x00,
9316 0xff, 0xf9, 0x00, 0x05, 0x00, 0x77, 0x00, 0x0d,
9317 0x00, 0x6f, 0x00, 0xf9, 0x00, 0x05, 0x00, 0x77,
9318 0x00, 0x0d, 0x00, 0x6f, 0x00),
9319 PHYREGS(0x0828, 0x0824, 0x0820, 0x01f6, 0x01f7, 0x01f8),
9320 },
9321 {
9079 .freq = 5220, 9322 .freq = 5220,
9080 RADIOREGS3(0xa7, 0x01, 0x01, 0x02, 0x0a, 0x05, 0x05, 0x02, 9323 RADIOREGS3(0xa7, 0x01, 0x01, 0x02, 0x0a, 0x05, 0x05, 0x02,
9081 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8e, 0x0f, 0x00, 9324 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8e, 0x0f, 0x00,
@@ -9085,6 +9328,492 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9085 PHYREGS(0x082c, 0x0828, 0x0824, 0x01f5, 0x01f6, 0x01f7), 9328 PHYREGS(0x082c, 0x0828, 0x0824, 0x01f5, 0x01f6, 0x01f7),
9086 }, 9329 },
9087 { 9330 {
9331 .freq = 5230,
9332 RADIOREGS3(0xa7, 0x01, 0x01, 0x02, 0x0b, 0x05, 0x05, 0x02,
9333 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8e, 0x0f, 0x00,
9334 0xee, 0xd8, 0x00, 0x05, 0x00, 0x77, 0x00, 0x0d,
9335 0x00, 0x6f, 0x00, 0xd8, 0x00, 0x05, 0x00, 0x77,
9336 0x00, 0x0d, 0x00, 0x6f, 0x00),
9337 PHYREGS(0x0830, 0x082c, 0x0828, 0x01f4, 0x01f5, 0x01f6),
9338 },
9339 {
9340 .freq = 5240,
9341 RADIOREGS3(0xa0, 0x01, 0x01, 0x02, 0x0c, 0x05, 0x05, 0x02,
9342 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8e, 0x0f, 0x00,
9343 0xee, 0xc8, 0x00, 0x05, 0x00, 0x77, 0x00, 0x0d,
9344 0x00, 0x6f, 0x00, 0xc8, 0x00, 0x05, 0x00, 0x77,
9345 0x00, 0x0d, 0x00, 0x6f, 0x00),
9346 PHYREGS(0x0834, 0x0830, 0x082c, 0x01f3, 0x01f4, 0x01f5),
9347 },
9348 {
9349 .freq = 5250,
9350 RADIOREGS3(0xa0, 0x01, 0x01, 0x02, 0x0d, 0x05, 0x05, 0x02,
9351 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8e, 0x0f, 0x00,
9352 0xed, 0xc7, 0x00, 0x05, 0x00, 0x77, 0x00, 0x0d,
9353 0x00, 0x6f, 0x00, 0xc7, 0x00, 0x05, 0x00, 0x77,
9354 0x00, 0x0d, 0x00, 0x6f, 0x00),
9355 PHYREGS(0x0838, 0x0834, 0x0830, 0x01f2, 0x01f3, 0x01f4),
9356 },
9357 {
9358 .freq = 5260,
9359 RADIOREGS3(0x98, 0x01, 0x01, 0x02, 0x0e, 0x05, 0x05, 0x02,
9360 0x0c, 0x01, 0x02, 0x02, 0x02, 0x8e, 0x0e, 0x00,
9361 0xed, 0xc7, 0x00, 0x04, 0x00, 0x77, 0x00, 0x0d,
9362 0x00, 0x6f, 0x00, 0xc7, 0x00, 0x04, 0x00, 0x77,
9363 0x00, 0x0d, 0x00, 0x6f, 0x00),
9364 PHYREGS(0x083c, 0x0838, 0x0834, 0x01f1, 0x01f2, 0x01f3),
9365 },
9366 {
9367 .freq = 5270,
9368 RADIOREGS3(0x98, 0x01, 0x01, 0x02, 0x0f, 0x05, 0x05, 0x02,
9369 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8e, 0x0e, 0x00,
9370 0xed, 0xc7, 0x00, 0x04, 0x00, 0x77, 0x00, 0x0c,
9371 0x00, 0x6f, 0x00, 0xc7, 0x00, 0x04, 0x00, 0x77,
9372 0x00, 0x0c, 0x00, 0x6f, 0x00),
9373 PHYREGS(0x0840, 0x083c, 0x0838, 0x01f0, 0x01f1, 0x01f2),
9374 },
9375 {
9376 .freq = 5280,
9377 RADIOREGS3(0x91, 0x01, 0x01, 0x02, 0x10, 0x05, 0x05, 0x02,
9378 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8d, 0x0e, 0x00,
9379 0xdc, 0xb7, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0c,
9380 0x00, 0x6f, 0x00, 0xb7, 0x00, 0x03, 0x00, 0x77,
9381 0x00, 0x0c, 0x00, 0x6f, 0x00),
9382 PHYREGS(0x0844, 0x0840, 0x083c, 0x01f0, 0x01f0, 0x01f1),
9383 },
9384 {
9385 .freq = 5290,
9386 RADIOREGS3(0x91, 0x01, 0x01, 0x02, 0x11, 0x05, 0x05, 0x02,
9387 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8d, 0x0e, 0x00,
9388 0xdc, 0xb7, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0c,
9389 0x00, 0x6f, 0x00, 0xb7, 0x00, 0x03, 0x00, 0x77,
9390 0x00, 0x0c, 0x00, 0x6f, 0x00),
9391 PHYREGS(0x0848, 0x0844, 0x0840, 0x01ef, 0x01f0, 0x01f0),
9392 },
9393 {
9394 .freq = 5300,
9395 RADIOREGS3(0x8a, 0x01, 0x01, 0x02, 0x12, 0x05, 0x05, 0x02,
9396 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8d, 0x0e, 0x00,
9397 0xdc, 0xb7, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0c,
9398 0x00, 0x6f, 0x00, 0xb7, 0x00, 0x03, 0x00, 0x77,
9399 0x00, 0x0c, 0x00, 0x6f, 0x00),
9400 PHYREGS(0x084c, 0x0848, 0x0844, 0x01ee, 0x01ef, 0x01f0),
9401 },
9402 {
9403 .freq = 5310,
9404 RADIOREGS3(0x8a, 0x01, 0x01, 0x02, 0x13, 0x05, 0x05, 0x02,
9405 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8d, 0x0e, 0x00,
9406 0xdc, 0xb7, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0c,
9407 0x00, 0x6f, 0x00, 0xb7, 0x00, 0x03, 0x00, 0x77,
9408 0x00, 0x0c, 0x00, 0x6f, 0x00),
9409 PHYREGS(0x0850, 0x084c, 0x0848, 0x01ed, 0x01ee, 0x01ef),
9410 },
9411 {
9412 .freq = 5320,
9413 RADIOREGS3(0x83, 0x01, 0x01, 0x02, 0x14, 0x05, 0x05, 0x02,
9414 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8d, 0x0e, 0x00,
9415 0xdb, 0xb7, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0c,
9416 0x00, 0x6f, 0x00, 0xb7, 0x00, 0x03, 0x00, 0x77,
9417 0x00, 0x0c, 0x00, 0x6f, 0x00),
9418 PHYREGS(0x0854, 0x0850, 0x084c, 0x01ec, 0x01ed, 0x01ee),
9419 },
9420 {
9421 .freq = 5330,
9422 RADIOREGS3(0x83, 0x01, 0x01, 0x02, 0x15, 0x05, 0x05, 0x02,
9423 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8d, 0x0d, 0x00,
9424 0xcb, 0xa6, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0b,
9425 0x00, 0x6f, 0x00, 0xa6, 0x00, 0x03, 0x00, 0x77,
9426 0x00, 0x0b, 0x00, 0x6f, 0x00),
9427 PHYREGS(0x0858, 0x0854, 0x0850, 0x01eb, 0x01ec, 0x01ed),
9428 },
9429 {
9430 .freq = 5340,
9431 RADIOREGS3(0x7c, 0x01, 0x01, 0x02, 0x16, 0x05, 0x05, 0x02,
9432 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8d, 0x0d, 0x00,
9433 0xca, 0xa6, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0b,
9434 0x00, 0x6f, 0x00, 0xa6, 0x00, 0x03, 0x00, 0x77,
9435 0x00, 0x0b, 0x00, 0x6f, 0x00),
9436 PHYREGS(0x085c, 0x0858, 0x0854, 0x01ea, 0x01eb, 0x01ec),
9437 },
9438 {
9439 .freq = 5350,
9440 RADIOREGS3(0x7c, 0x01, 0x01, 0x02, 0x17, 0x05, 0x05, 0x02,
9441 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0d, 0x00,
9442 0xca, 0xa6, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0b,
9443 0x00, 0x6f, 0x00, 0xa6, 0x00, 0x03, 0x00, 0x77,
9444 0x00, 0x0b, 0x00, 0x6f, 0x00),
9445 PHYREGS(0x0860, 0x085c, 0x0858, 0x01e9, 0x01ea, 0x01eb),
9446 },
9447 {
9448 .freq = 5360,
9449 RADIOREGS3(0x75, 0x01, 0x01, 0x02, 0x18, 0x05, 0x05, 0x02,
9450 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0d, 0x00,
9451 0xc9, 0x95, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0a,
9452 0x00, 0x6f, 0x00, 0x95, 0x00, 0x03, 0x00, 0x77,
9453 0x00, 0x0a, 0x00, 0x6f, 0x00),
9454 PHYREGS(0x0864, 0x0860, 0x085c, 0x01e8, 0x01e9, 0x01ea),
9455 },
9456 {
9457 .freq = 5370,
9458 RADIOREGS3(0x75, 0x01, 0x01, 0x02, 0x19, 0x05, 0x05, 0x02,
9459 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0d, 0x00,
9460 0xc9, 0x95, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0a,
9461 0x00, 0x6f, 0x00, 0x95, 0x00, 0x03, 0x00, 0x77,
9462 0x00, 0x0a, 0x00, 0x6f, 0x00),
9463 PHYREGS(0x0868, 0x0864, 0x0860, 0x01e7, 0x01e8, 0x01e9),
9464 },
9465 {
9466 .freq = 5380,
9467 RADIOREGS3(0x6e, 0x01, 0x01, 0x02, 0x1a, 0x05, 0x05, 0x02,
9468 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0c, 0x00,
9469 0xb8, 0x95, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0a,
9470 0x00, 0x6f, 0x00, 0x95, 0x00, 0x03, 0x00, 0x77,
9471 0x00, 0x0a, 0x00, 0x6f, 0x00),
9472 PHYREGS(0x086c, 0x0868, 0x0864, 0x01e6, 0x01e7, 0x01e8),
9473 },
9474 {
9475 .freq = 5390,
9476 RADIOREGS3(0x6e, 0x01, 0x01, 0x02, 0x1b, 0x05, 0x05, 0x02,
9477 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0c, 0x00,
9478 0xb8, 0x84, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0a,
9479 0x00, 0x6f, 0x00, 0x84, 0x00, 0x03, 0x00, 0x77,
9480 0x00, 0x0a, 0x00, 0x6f, 0x00),
9481 PHYREGS(0x0870, 0x086c, 0x0868, 0x01e5, 0x01e6, 0x01e7),
9482 },
9483 {
9484 .freq = 5400,
9485 RADIOREGS3(0x67, 0x01, 0x01, 0x02, 0x1c, 0x05, 0x05, 0x02,
9486 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0c, 0x00,
9487 0xb8, 0x84, 0x00, 0x03, 0x00, 0x77, 0x00, 0x0a,
9488 0x00, 0x6f, 0x00, 0x84, 0x00, 0x03, 0x00, 0x77,
9489 0x00, 0x0a, 0x00, 0x6f, 0x00),
9490 PHYREGS(0x0874, 0x0870, 0x086c, 0x01e5, 0x01e5, 0x01e6),
9491 },
9492 {
9493 .freq = 5410,
9494 RADIOREGS3(0x67, 0x01, 0x01, 0x02, 0x1d, 0x05, 0x05, 0x02,
9495 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0c, 0x00,
9496 0xb7, 0x84, 0x00, 0x02, 0x00, 0x77, 0x00, 0x0a,
9497 0x00, 0x6f, 0x00, 0x84, 0x00, 0x02, 0x00, 0x77,
9498 0x00, 0x0a, 0x00, 0x6f, 0x00),
9499 PHYREGS(0x0878, 0x0874, 0x0870, 0x01e4, 0x01e5, 0x01e5),
9500 },
9501 {
9502 .freq = 5420,
9503 RADIOREGS3(0x61, 0x01, 0x01, 0x02, 0x1e, 0x05, 0x05, 0x02,
9504 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0c, 0x00,
9505 0xa7, 0x84, 0x00, 0x02, 0x00, 0x77, 0x00, 0x0a,
9506 0x00, 0x6f, 0x00, 0x84, 0x00, 0x02, 0x00, 0x77,
9507 0x00, 0x0a, 0x00, 0x6f, 0x00),
9508 PHYREGS(0x087c, 0x0878, 0x0874, 0x01e3, 0x01e4, 0x01e5),
9509 },
9510 {
9511 .freq = 5430,
9512 RADIOREGS3(0x61, 0x01, 0x01, 0x02, 0x1f, 0x05, 0x05, 0x02,
9513 0x0c, 0x01, 0x03, 0x03, 0x03, 0x8c, 0x0b, 0x00,
9514 0xa6, 0x84, 0x00, 0x02, 0x00, 0x77, 0x00, 0x0a,
9515 0x00, 0x6f, 0x00, 0x84, 0x00, 0x02, 0x00, 0x77,
9516 0x00, 0x0a, 0x00, 0x6f, 0x00),
9517 PHYREGS(0x0880, 0x087c, 0x0878, 0x01e2, 0x01e3, 0x01e4),
9518 },
9519 {
9520 .freq = 5440,
9521 RADIOREGS3(0x5a, 0x01, 0x01, 0x02, 0x20, 0x05, 0x05, 0x02,
9522 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8b, 0x0b, 0x00,
9523 0xa6, 0x84, 0x00, 0x02, 0x00, 0x77, 0x00, 0x09,
9524 0x00, 0x6f, 0x00, 0x84, 0x00, 0x02, 0x00, 0x77,
9525 0x00, 0x09, 0x00, 0x6f, 0x00),
9526 PHYREGS(0x0884, 0x0880, 0x087c, 0x01e1, 0x01e2, 0x01e3),
9527 },
9528 {
9529 .freq = 5450,
9530 RADIOREGS3(0x5a, 0x01, 0x01, 0x02, 0x21, 0x05, 0x05, 0x02,
9531 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8b, 0x0b, 0x00,
9532 0x95, 0x84, 0x00, 0x01, 0x00, 0x77, 0x00, 0x09,
9533 0x00, 0x6f, 0x00, 0x84, 0x00, 0x01, 0x00, 0x77,
9534 0x00, 0x09, 0x00, 0x6f, 0x00),
9535 PHYREGS(0x0888, 0x0884, 0x0880, 0x01e0, 0x01e1, 0x01e2),
9536 },
9537 {
9538 .freq = 5460,
9539 RADIOREGS3(0x53, 0x01, 0x01, 0x02, 0x22, 0x05, 0x05, 0x02,
9540 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8b, 0x0b, 0x00,
9541 0x95, 0x84, 0x00, 0x01, 0x00, 0x77, 0x00, 0x09,
9542 0x00, 0x6f, 0x00, 0x84, 0x00, 0x01, 0x00, 0x77,
9543 0x00, 0x09, 0x00, 0x6f, 0x00),
9544 PHYREGS(0x088c, 0x0888, 0x0884, 0x01df, 0x01e0, 0x01e1),
9545 },
9546 {
9547 .freq = 5470,
9548 RADIOREGS3(0x53, 0x01, 0x01, 0x02, 0x23, 0x05, 0x05, 0x02,
9549 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8b, 0x0b, 0x00,
9550 0x94, 0x73, 0x00, 0x01, 0x00, 0x77, 0x00, 0x09,
9551 0x00, 0x6f, 0x00, 0x73, 0x00, 0x01, 0x00, 0x77,
9552 0x00, 0x09, 0x00, 0x6f, 0x00),
9553 PHYREGS(0x0890, 0x088c, 0x0888, 0x01de, 0x01df, 0x01e0),
9554 },
9555 {
9556 .freq = 5480,
9557 RADIOREGS3(0x4d, 0x01, 0x01, 0x02, 0x24, 0x05, 0x05, 0x02,
9558 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8a, 0x0a, 0x00,
9559 0x84, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9560 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9561 0x00, 0x09, 0x00, 0x6f, 0x00),
9562 PHYREGS(0x0894, 0x0890, 0x088c, 0x01dd, 0x01de, 0x01df),
9563 },
9564 {
9565 .freq = 5490,
9566 RADIOREGS3(0x4d, 0x01, 0x01, 0x02, 0x25, 0x05, 0x05, 0x02,
9567 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8a, 0x0a, 0x00,
9568 0x83, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9569 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9570 0x00, 0x09, 0x00, 0x6f, 0x00),
9571 PHYREGS(0x0898, 0x0894, 0x0890, 0x01dd, 0x01dd, 0x01de),
9572 },
9573 {
9574 .freq = 5500,
9575 RADIOREGS3(0x47, 0x01, 0x01, 0x02, 0x26, 0x05, 0x05, 0x02,
9576 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8a, 0x0a, 0x00,
9577 0x82, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9578 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9579 0x00, 0x09, 0x00, 0x6f, 0x00),
9580 PHYREGS(0x089c, 0x0898, 0x0894, 0x01dc, 0x01dd, 0x01dd),
9581 },
9582 {
9583 .freq = 5510,
9584 RADIOREGS3(0x47, 0x01, 0x01, 0x02, 0x27, 0x05, 0x05, 0x02,
9585 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8a, 0x0a, 0x00,
9586 0x82, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9587 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9588 0x00, 0x09, 0x00, 0x6f, 0x00),
9589 PHYREGS(0x08a0, 0x089c, 0x0898, 0x01db, 0x01dc, 0x01dd),
9590 },
9591 {
9592 .freq = 5520,
9593 RADIOREGS3(0x40, 0x01, 0x01, 0x02, 0x28, 0x05, 0x05, 0x02,
9594 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8a, 0x0a, 0x00,
9595 0x72, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9596 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9597 0x00, 0x09, 0x00, 0x6f, 0x00),
9598 PHYREGS(0x08a4, 0x08a0, 0x089c, 0x01da, 0x01db, 0x01dc),
9599 },
9600 {
9601 .freq = 5530,
9602 RADIOREGS3(0x40, 0x01, 0x01, 0x02, 0x29, 0x05, 0x05, 0x02,
9603 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8a, 0x09, 0x00,
9604 0x72, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9605 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9606 0x00, 0x09, 0x00, 0x6f, 0x00),
9607 PHYREGS(0x08a8, 0x08a4, 0x08a0, 0x01d9, 0x01da, 0x01db),
9608 },
9609 {
9610 .freq = 5540,
9611 RADIOREGS3(0x3a, 0x01, 0x01, 0x02, 0x2a, 0x05, 0x05, 0x02,
9612 0x0c, 0x01, 0x04, 0x04, 0x04, 0x8a, 0x09, 0x00,
9613 0x71, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9614 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9615 0x00, 0x09, 0x00, 0x6f, 0x00),
9616 PHYREGS(0x08ac, 0x08a8, 0x08a4, 0x01d8, 0x01d9, 0x01da),
9617 },
9618 {
9619 .freq = 5550,
9620 RADIOREGS3(0x3a, 0x01, 0x01, 0x02, 0x2b, 0x05, 0x05, 0x02,
9621 0x0c, 0x01, 0x04, 0x04, 0x04, 0x89, 0x09, 0x00,
9622 0x61, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9623 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9624 0x00, 0x09, 0x00, 0x6f, 0x00),
9625 PHYREGS(0x08b0, 0x08ac, 0x08a8, 0x01d7, 0x01d8, 0x01d9),
9626 },
9627 {
9628 .freq = 5560,
9629 RADIOREGS3(0x34, 0x01, 0x01, 0x02, 0x2c, 0x05, 0x05, 0x02,
9630 0x0c, 0x01, 0x04, 0x04, 0x04, 0x89, 0x09, 0x00,
9631 0x61, 0x73, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9632 0x00, 0x6f, 0x00, 0x73, 0x00, 0x00, 0x00, 0x77,
9633 0x00, 0x09, 0x00, 0x6f, 0x00),
9634 PHYREGS(0x08b4, 0x08b0, 0x08ac, 0x01d7, 0x01d7, 0x01d8),
9635 },
9636 {
9637 .freq = 5570,
9638 RADIOREGS3(0x34, 0x01, 0x01, 0x02, 0x2d, 0x05, 0x05, 0x02,
9639 0x0c, 0x01, 0x04, 0x04, 0x04, 0x89, 0x09, 0x00,
9640 0x61, 0x62, 0x00, 0x00, 0x00, 0x77, 0x00, 0x09,
9641 0x00, 0x6f, 0x00, 0x62, 0x00, 0x00, 0x00, 0x77,
9642 0x00, 0x09, 0x00, 0x6f, 0x00),
9643 PHYREGS(0x08b8, 0x08b4, 0x08b0, 0x01d6, 0x01d7, 0x01d7),
9644 },
9645 {
9646 .freq = 5580,
9647 RADIOREGS3(0x2e, 0x01, 0x01, 0x02, 0x2e, 0x05, 0x05, 0x02,
9648 0x0c, 0x01, 0x04, 0x04, 0x04, 0x89, 0x08, 0x00,
9649 0x60, 0x62, 0x00, 0x00, 0x00, 0x77, 0x00, 0x08,
9650 0x00, 0x6f, 0x00, 0x62, 0x00, 0x00, 0x00, 0x77,
9651 0x00, 0x08, 0x00, 0x6f, 0x00),
9652 PHYREGS(0x08bc, 0x08b8, 0x08b4, 0x01d5, 0x01d6, 0x01d7),
9653 },
9654 {
9655 .freq = 5590,
9656 RADIOREGS3(0x2e, 0x01, 0x01, 0x02, 0x2f, 0x05, 0x05, 0x02,
9657 0x0c, 0x01, 0x04, 0x04, 0x04, 0x89, 0x08, 0x00,
9658 0x50, 0x61, 0x00, 0x00, 0x00, 0x77, 0x00, 0x08,
9659 0x00, 0x6f, 0x00, 0x61, 0x00, 0x00, 0x00, 0x77,
9660 0x00, 0x08, 0x00, 0x6f, 0x00),
9661 PHYREGS(0x08c0, 0x08bc, 0x08b8, 0x01d4, 0x01d5, 0x01d6),
9662 },
9663 {
9664 .freq = 5600,
9665 RADIOREGS3(0x28, 0x01, 0x01, 0x02, 0x30, 0x05, 0x05, 0x02,
9666 0x0c, 0x01, 0x05, 0x05, 0x05, 0x89, 0x08, 0x00,
9667 0x50, 0x51, 0x00, 0x00, 0x00, 0x77, 0x00, 0x08,
9668 0x00, 0x6f, 0x00, 0x51, 0x00, 0x00, 0x00, 0x77,
9669 0x00, 0x08, 0x00, 0x6f, 0x00),
9670 PHYREGS(0x08c4, 0x08c0, 0x08bc, 0x01d3, 0x01d4, 0x01d5),
9671 },
9672 {
9673 .freq = 5610,
9674 RADIOREGS3(0x28, 0x01, 0x01, 0x02, 0x31, 0x05, 0x05, 0x02,
9675 0x0c, 0x01, 0x05, 0x05, 0x05, 0x89, 0x08, 0x00,
9676 0x50, 0x51, 0x00, 0x00, 0x00, 0x77, 0x00, 0x08,
9677 0x00, 0x6f, 0x00, 0x51, 0x00, 0x00, 0x00, 0x77,
9678 0x00, 0x08, 0x00, 0x6f, 0x00),
9679 PHYREGS(0x08c8, 0x08c4, 0x08c0, 0x01d2, 0x01d3, 0x01d4),
9680 },
9681 {
9682 .freq = 5620,
9683 RADIOREGS3(0x21, 0x01, 0x01, 0x02, 0x32, 0x05, 0x05, 0x02,
9684 0x0c, 0x01, 0x05, 0x05, 0x05, 0x89, 0x08, 0x00,
9685 0x50, 0x50, 0x00, 0x00, 0x00, 0x77, 0x00, 0x07,
9686 0x00, 0x6f, 0x00, 0x50, 0x00, 0x00, 0x00, 0x77,
9687 0x00, 0x07, 0x00, 0x6f, 0x00),
9688 PHYREGS(0x08cc, 0x08c8, 0x08c4, 0x01d2, 0x01d2, 0x01d3),
9689 },
9690 {
9691 .freq = 5630,
9692 RADIOREGS3(0x21, 0x01, 0x01, 0x02, 0x33, 0x05, 0x05, 0x02,
9693 0x0c, 0x01, 0x05, 0x05, 0x05, 0x88, 0x07, 0x00,
9694 0x50, 0x50, 0x00, 0x00, 0x00, 0x77, 0x00, 0x07,
9695 0x00, 0x6f, 0x00, 0x50, 0x00, 0x00, 0x00, 0x77,
9696 0x00, 0x07, 0x00, 0x6f, 0x00),
9697 PHYREGS(0x08d0, 0x08cc, 0x08c8, 0x01d1, 0x01d2, 0x01d2),
9698 },
9699 {
9700 .freq = 5640,
9701 RADIOREGS3(0x1c, 0x01, 0x01, 0x02, 0x34, 0x05, 0x05, 0x02,
9702 0x0c, 0x01, 0x05, 0x05, 0x05, 0x88, 0x07, 0x00,
9703 0x40, 0x50, 0x00, 0x00, 0x00, 0x77, 0x00, 0x07,
9704 0x00, 0x6f, 0x00, 0x50, 0x00, 0x00, 0x00, 0x77,
9705 0x00, 0x07, 0x00, 0x6f, 0x00),
9706 PHYREGS(0x08d4, 0x08d0, 0x08cc, 0x01d0, 0x01d1, 0x01d2),
9707 },
9708 {
9709 .freq = 5650,
9710 RADIOREGS3(0x1c, 0x01, 0x01, 0x02, 0x35, 0x05, 0x05, 0x02,
9711 0x0c, 0x01, 0x05, 0x05, 0x05, 0x88, 0x07, 0x00,
9712 0x40, 0x40, 0x00, 0x00, 0x00, 0x77, 0x00, 0x07,
9713 0x00, 0x6f, 0x00, 0x40, 0x00, 0x00, 0x00, 0x77,
9714 0x00, 0x07, 0x00, 0x6f, 0x00),
9715 PHYREGS(0x08d8, 0x08d4, 0x08d0, 0x01cf, 0x01d0, 0x01d1),
9716 },
9717 {
9718 .freq = 5660,
9719 RADIOREGS3(0x16, 0x01, 0x01, 0x02, 0x36, 0x05, 0x05, 0x02,
9720 0x0c, 0x01, 0x05, 0x05, 0x05, 0x88, 0x07, 0x00,
9721 0x40, 0x40, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9722 0x00, 0x6f, 0x00, 0x40, 0x00, 0x00, 0x00, 0x77,
9723 0x00, 0x06, 0x00, 0x6f, 0x00),
9724 PHYREGS(0x08dc, 0x08d8, 0x08d4, 0x01ce, 0x01cf, 0x01d0),
9725 },
9726 {
9727 .freq = 5670,
9728 RADIOREGS3(0x16, 0x01, 0x01, 0x02, 0x37, 0x05, 0x05, 0x02,
9729 0x0c, 0x01, 0x05, 0x05, 0x05, 0x88, 0x07, 0x00,
9730 0x40, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9731 0x00, 0x6f, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9732 0x00, 0x06, 0x00, 0x6f, 0x00),
9733 PHYREGS(0x08e0, 0x08dc, 0x08d8, 0x01ce, 0x01ce, 0x01cf),
9734 },
9735 {
9736 .freq = 5680,
9737 RADIOREGS3(0x10, 0x01, 0x01, 0x02, 0x38, 0x05, 0x05, 0x02,
9738 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x06, 0x00,
9739 0x30, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9740 0x00, 0x6f, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9741 0x00, 0x06, 0x00, 0x6f, 0x00),
9742 PHYREGS(0x08e4, 0x08e0, 0x08dc, 0x01cd, 0x01ce, 0x01ce),
9743 },
9744 {
9745 .freq = 5690,
9746 RADIOREGS3(0x10, 0x01, 0x01, 0x02, 0x39, 0x05, 0x05, 0x02,
9747 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x06, 0x00,
9748 0x30, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9749 0x00, 0x6f, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9750 0x00, 0x06, 0x00, 0x6f, 0x00),
9751 PHYREGS(0x08e8, 0x08e4, 0x08e0, 0x01cc, 0x01cd, 0x01ce),
9752 },
9753 {
9754 .freq = 5700,
9755 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x3a, 0x05, 0x05, 0x02,
9756 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x06, 0x00,
9757 0x30, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9758 0x00, 0x6e, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9759 0x00, 0x06, 0x00, 0x6e, 0x00),
9760 PHYREGS(0x08ec, 0x08e8, 0x08e4, 0x01cb, 0x01cc, 0x01cd),
9761 },
9762 {
9763 .freq = 5710,
9764 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x3b, 0x05, 0x05, 0x02,
9765 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x06, 0x00,
9766 0x30, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9767 0x00, 0x6e, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9768 0x00, 0x06, 0x00, 0x6e, 0x00),
9769 PHYREGS(0x08f0, 0x08ec, 0x08e8, 0x01ca, 0x01cb, 0x01cc),
9770 },
9771 {
9772 .freq = 5720,
9773 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x3c, 0x05, 0x05, 0x02,
9774 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x06, 0x00,
9775 0x30, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9776 0x00, 0x6e, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9777 0x00, 0x06, 0x00, 0x6e, 0x00),
9778 PHYREGS(0x08f4, 0x08f0, 0x08ec, 0x01c9, 0x01ca, 0x01cb),
9779 },
9780 {
9781 .freq = 5725,
9782 RADIOREGS3(0x03, 0x01, 0x02, 0x04, 0x79, 0x05, 0x05, 0x02,
9783 0x15, 0x01, 0x05, 0x05, 0x05, 0x87, 0x06, 0x00,
9784 0x30, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9785 0x00, 0x6e, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9786 0x00, 0x06, 0x00, 0x6e, 0x00),
9787 PHYREGS(0x08f6, 0x08f2, 0x08ee, 0x01c9, 0x01ca, 0x01cb),
9788 },
9789 {
9790 .freq = 5730,
9791 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x3d, 0x05, 0x05, 0x02,
9792 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x05, 0x00,
9793 0x20, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9794 0x00, 0x6e, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9795 0x00, 0x06, 0x00, 0x6e, 0x00),
9796 PHYREGS(0x08f8, 0x08f4, 0x08f0, 0x01c9, 0x01c9, 0x01ca),
9797 },
9798 {
9799 .freq = 5735,
9800 RADIOREGS3(0x03, 0x01, 0x02, 0x04, 0x7b, 0x05, 0x05, 0x02,
9801 0x15, 0x01, 0x05, 0x05, 0x05, 0x87, 0x05, 0x00,
9802 0x20, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9803 0x00, 0x6d, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9804 0x00, 0x06, 0x00, 0x6d, 0x00),
9805 PHYREGS(0x08fa, 0x08f6, 0x08f2, 0x01c8, 0x01c9, 0x01ca),
9806 },
9807 {
9808 .freq = 5740,
9809 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x3e, 0x05, 0x05, 0x02,
9810 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x05, 0x00,
9811 0x20, 0x30, 0x00, 0x00, 0x00, 0x77, 0x00, 0x06,
9812 0x00, 0x6d, 0x00, 0x30, 0x00, 0x00, 0x00, 0x77,
9813 0x00, 0x06, 0x00, 0x6d, 0x00),
9814 PHYREGS(0x08fc, 0x08f8, 0x08f4, 0x01c8, 0x01c9, 0x01c9),
9815 },
9816 {
9088 .freq = 5745, 9817 .freq = 5745,
9089 RADIOREGS3(0xfe, 0x00, 0x02, 0x04, 0x7d, 0x05, 0x05, 0x02, 9818 RADIOREGS3(0xfe, 0x00, 0x02, 0x04, 0x7d, 0x05, 0x05, 0x02,
9090 0x15, 0x01, 0x05, 0x05, 0x05, 0x87, 0x05, 0x00, 9819 0x15, 0x01, 0x05, 0x05, 0x05, 0x87, 0x05, 0x00,
@@ -9094,6 +9823,33 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9094 PHYREGS(0x08fe, 0x08fa, 0x08f6, 0x01c8, 0x01c8, 0x01c9), 9823 PHYREGS(0x08fe, 0x08fa, 0x08f6, 0x01c8, 0x01c8, 0x01c9),
9095 }, 9824 },
9096 { 9825 {
9826 .freq = 5750,
9827 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x3f, 0x05, 0x05, 0x02,
9828 0x0c, 0x01, 0x05, 0x05, 0x05, 0x87, 0x05, 0x00,
9829 0x20, 0x20, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9830 0x00, 0x6d, 0x00, 0x20, 0x00, 0x00, 0x00, 0x77,
9831 0x00, 0x05, 0x00, 0x6d, 0x00),
9832 PHYREGS(0x0900, 0x08fc, 0x08f8, 0x01c7, 0x01c8, 0x01c9),
9833 },
9834 {
9835 .freq = 5755,
9836 RADIOREGS3(0xfe, 0x00, 0x02, 0x04, 0x7f, 0x05, 0x05, 0x02,
9837 0x15, 0x01, 0x05, 0x05, 0x05, 0x87, 0x05, 0x00,
9838 0x10, 0x20, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9839 0x00, 0x6c, 0x00, 0x20, 0x00, 0x00, 0x00, 0x77,
9840 0x00, 0x05, 0x00, 0x6c, 0x00),
9841 PHYREGS(0x0902, 0x08fe, 0x08fa, 0x01c7, 0x01c8, 0x01c8),
9842 },
9843 {
9844 .freq = 5760,
9845 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x40, 0x05, 0x05, 0x02,
9846 0x0c, 0x01, 0x05, 0x05, 0x05, 0x86, 0x05, 0x00,
9847 0x10, 0x20, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9848 0x00, 0x6c, 0x00, 0x20, 0x00, 0x00, 0x00, 0x77,
9849 0x00, 0x05, 0x00, 0x6c, 0x00),
9850 PHYREGS(0x0904, 0x0900, 0x08fc, 0x01c6, 0x01c7, 0x01c8),
9851 },
9852 {
9097 .freq = 5765, 9853 .freq = 5765,
9098 RADIOREGS3(0xf8, 0x00, 0x02, 0x04, 0x81, 0x05, 0x05, 0x02, 9854 RADIOREGS3(0xf8, 0x00, 0x02, 0x04, 0x81, 0x05, 0x05, 0x02,
9099 0x15, 0x01, 0x05, 0x05, 0x05, 0x86, 0x05, 0x00, 9855 0x15, 0x01, 0x05, 0x05, 0x05, 0x86, 0x05, 0x00,
@@ -9103,6 +9859,33 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9103 PHYREGS(0x0906, 0x0902, 0x08fe, 0x01c6, 0x01c7, 0x01c8), 9859 PHYREGS(0x0906, 0x0902, 0x08fe, 0x01c6, 0x01c7, 0x01c8),
9104 }, 9860 },
9105 { 9861 {
9862 .freq = 5770,
9863 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x41, 0x05, 0x05, 0x02,
9864 0x0c, 0x01, 0x05, 0x05, 0x05, 0x86, 0x04, 0x00,
9865 0x10, 0x10, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9866 0x00, 0x6b, 0x00, 0x10, 0x00, 0x00, 0x00, 0x77,
9867 0x00, 0x05, 0x00, 0x6b, 0x00),
9868 PHYREGS(0x0908, 0x0904, 0x0900, 0x01c6, 0x01c6, 0x01c7),
9869 },
9870 {
9871 .freq = 5775,
9872 RADIOREGS3(0xf8, 0x00, 0x02, 0x04, 0x83, 0x05, 0x05, 0x02,
9873 0x15, 0x01, 0x05, 0x05, 0x05, 0x86, 0x04, 0x00,
9874 0x10, 0x10, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9875 0x00, 0x6b, 0x00, 0x10, 0x00, 0x00, 0x00, 0x77,
9876 0x00, 0x05, 0x00, 0x6b, 0x00),
9877 PHYREGS(0x090a, 0x0906, 0x0902, 0x01c5, 0x01c6, 0x01c7),
9878 },
9879 {
9880 .freq = 5780,
9881 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x42, 0x05, 0x05, 0x02,
9882 0x0c, 0x01, 0x05, 0x05, 0x05, 0x86, 0x04, 0x00,
9883 0x10, 0x10, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9884 0x00, 0x6b, 0x00, 0x10, 0x00, 0x00, 0x00, 0x77,
9885 0x00, 0x05, 0x00, 0x6b, 0x00),
9886 PHYREGS(0x090c, 0x0908, 0x0904, 0x01c5, 0x01c6, 0x01c6),
9887 },
9888 {
9106 .freq = 5785, 9889 .freq = 5785,
9107 RADIOREGS3(0xf2, 0x00, 0x02, 0x04, 0x85, 0x05, 0x05, 0x02, 9890 RADIOREGS3(0xf2, 0x00, 0x02, 0x04, 0x85, 0x05, 0x05, 0x02,
9108 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00, 9891 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
@@ -9112,6 +9895,33 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9112 PHYREGS(0x090e, 0x090a, 0x0906, 0x01c4, 0x01c5, 0x01c6), 9895 PHYREGS(0x090e, 0x090a, 0x0906, 0x01c4, 0x01c5, 0x01c6),
9113 }, 9896 },
9114 { 9897 {
9898 .freq = 5790,
9899 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x43, 0x05, 0x05, 0x02,
9900 0x0c, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9901 0x00, 0x10, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9902 0x00, 0x6b, 0x00, 0x10, 0x00, 0x00, 0x00, 0x77,
9903 0x00, 0x05, 0x00, 0x6b, 0x00),
9904 PHYREGS(0x0910, 0x090c, 0x0908, 0x01c4, 0x01c5, 0x01c6),
9905 },
9906 {
9907 .freq = 5795,
9908 RADIOREGS3(0xf2, 0x00, 0x02, 0x04, 0x87, 0x05, 0x05, 0x02,
9909 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9910 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9911 0x00, 0x6b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9912 0x00, 0x05, 0x00, 0x6b, 0x00),
9913 PHYREGS(0x0912, 0x090e, 0x090a, 0x01c4, 0x01c4, 0x01c5),
9914 },
9915 {
9916 .freq = 5800,
9917 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x44, 0x05, 0x05, 0x02,
9918 0x0c, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9919 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9920 0x00, 0x6b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9921 0x00, 0x05, 0x00, 0x6b, 0x00),
9922 PHYREGS(0x0914, 0x0910, 0x090c, 0x01c3, 0x01c4, 0x01c5),
9923 },
9924 {
9115 .freq = 5805, 9925 .freq = 5805,
9116 RADIOREGS3(0xed, 0x00, 0x02, 0x04, 0x89, 0x05, 0x05, 0x02, 9926 RADIOREGS3(0xed, 0x00, 0x02, 0x04, 0x89, 0x05, 0x05, 0x02,
9117 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00, 9927 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
@@ -9121,6 +9931,33 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9121 PHYREGS(0x0916, 0x0912, 0x090e, 0x01c3, 0x01c4, 0x01c4), 9931 PHYREGS(0x0916, 0x0912, 0x090e, 0x01c3, 0x01c4, 0x01c4),
9122 }, 9932 },
9123 { 9933 {
9934 .freq = 5810,
9935 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x45, 0x05, 0x05, 0x02,
9936 0x0c, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9937 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9938 0x00, 0x6a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9939 0x00, 0x05, 0x00, 0x6a, 0x00),
9940 PHYREGS(0x0918, 0x0914, 0x0910, 0x01c2, 0x01c3, 0x01c4),
9941 },
9942 {
9943 .freq = 5815,
9944 RADIOREGS3(0xed, 0x00, 0x02, 0x04, 0x8b, 0x05, 0x05, 0x02,
9945 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9946 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9947 0x00, 0x6a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9948 0x00, 0x05, 0x00, 0x6a, 0x00),
9949 PHYREGS(0x091a, 0x0916, 0x0912, 0x01c2, 0x01c3, 0x01c4),
9950 },
9951 {
9952 .freq = 5820,
9953 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x46, 0x05, 0x05, 0x02,
9954 0x0c, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9955 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9956 0x00, 0x6a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9957 0x00, 0x05, 0x00, 0x6a, 0x00),
9958 PHYREGS(0x091c, 0x0918, 0x0914, 0x01c2, 0x01c2, 0x01c3),
9959 },
9960 {
9124 .freq = 5825, 9961 .freq = 5825,
9125 RADIOREGS3(0xed, 0x00, 0x02, 0x04, 0x8d, 0x05, 0x05, 0x02, 9962 RADIOREGS3(0xed, 0x00, 0x02, 0x04, 0x8d, 0x05, 0x05, 0x02,
9126 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00, 9963 0x15, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
@@ -9130,6 +9967,87 @@ static const struct b43_nphy_channeltab_entry_rev3 b43_nphy_channeltab_radio_rev
9130 PHYREGS(0x091e, 0x091a, 0x0916, 0x01c1, 0x01c2, 0x01c3), 9967 PHYREGS(0x091e, 0x091a, 0x0916, 0x01c1, 0x01c2, 0x01c3),
9131 }, 9968 },
9132 { 9969 {
9970 .freq = 5830,
9971 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x47, 0x05, 0x05, 0x02,
9972 0x0c, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9973 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x05,
9974 0x00, 0x69, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9975 0x00, 0x05, 0x00, 0x69, 0x00),
9976 PHYREGS(0x0920, 0x091c, 0x0918, 0x01c1, 0x01c2, 0x01c2),
9977 },
9978 {
9979 .freq = 5840,
9980 RADIOREGS3(0x0a, 0x01, 0x01, 0x02, 0x48, 0x05, 0x05, 0x02,
9981 0x0c, 0x01, 0x06, 0x06, 0x06, 0x86, 0x04, 0x00,
9982 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
9983 0x00, 0x69, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9984 0x00, 0x04, 0x00, 0x69, 0x00),
9985 PHYREGS(0x0924, 0x0920, 0x091c, 0x01c0, 0x01c1, 0x01c2),
9986 },
9987 {
9988 .freq = 5850,
9989 RADIOREGS3(0xe0, 0x00, 0x01, 0x02, 0x49, 0x05, 0x05, 0x02,
9990 0x0c, 0x01, 0x06, 0x06, 0x06, 0x85, 0x03, 0x00,
9991 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
9992 0x00, 0x69, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
9993 0x00, 0x04, 0x00, 0x69, 0x00),
9994 PHYREGS(0x0928, 0x0924, 0x0920, 0x01bf, 0x01c0, 0x01c1),
9995 },
9996 {
9997 .freq = 5860,
9998 RADIOREGS3(0xde, 0x00, 0x01, 0x02, 0x4a, 0x05, 0x05, 0x02,
9999 0x0c, 0x01, 0x06, 0x06, 0x06, 0x85, 0x03, 0x00,
10000 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
10001 0x00, 0x69, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
10002 0x00, 0x04, 0x00, 0x69, 0x00),
10003 PHYREGS(0x092c, 0x0928, 0x0924, 0x01bf, 0x01bf, 0x01c0),
10004 },
10005 {
10006 .freq = 5870,
10007 RADIOREGS3(0xdb, 0x00, 0x01, 0x02, 0x4b, 0x05, 0x05, 0x02,
10008 0x0c, 0x01, 0x06, 0x06, 0x06, 0x85, 0x03, 0x00,
10009 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
10010 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
10011 0x00, 0x04, 0x00, 0x68, 0x00),
10012 PHYREGS(0x0930, 0x092c, 0x0928, 0x01be, 0x01bf, 0x01bf),
10013 },
10014 {
10015 .freq = 5880,
10016 RADIOREGS3(0xd8, 0x00, 0x01, 0x02, 0x4c, 0x05, 0x05, 0x02,
10017 0x0c, 0x01, 0x06, 0x06, 0x06, 0x85, 0x03, 0x00,
10018 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
10019 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
10020 0x00, 0x04, 0x00, 0x68, 0x00),
10021 PHYREGS(0x0934, 0x0930, 0x092c, 0x01bd, 0x01be, 0x01bf),
10022 },
10023 {
10024 .freq = 5890,
10025 RADIOREGS3(0xd6, 0x00, 0x01, 0x02, 0x4d, 0x05, 0x05, 0x02,
10026 0x0c, 0x01, 0x06, 0x06, 0x06, 0x85, 0x03, 0x00,
10027 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
10028 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
10029 0x00, 0x04, 0x00, 0x68, 0x00),
10030 PHYREGS(0x0938, 0x0934, 0x0930, 0x01bc, 0x01bd, 0x01be),
10031 },
10032 {
10033 .freq = 5900,
10034 RADIOREGS3(0xd3, 0x00, 0x01, 0x02, 0x4e, 0x05, 0x05, 0x02,
10035 0x0c, 0x01, 0x06, 0x06, 0x06, 0x85, 0x03, 0x00,
10036 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
10037 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
10038 0x00, 0x04, 0x00, 0x68, 0x00),
10039 PHYREGS(0x093c, 0x0938, 0x0934, 0x01bc, 0x01bc, 0x01bd),
10040 },
10041 {
10042 .freq = 5910,
10043 RADIOREGS3(0xd6, 0x00, 0x01, 0x02, 0x4f, 0x05, 0x05, 0x02,
10044 0x0c, 0x01, 0x06, 0x06, 0x06, 0x85, 0x03, 0x00,
10045 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x00, 0x04,
10046 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77,
10047 0x00, 0x04, 0x00, 0x68, 0x00),
10048 PHYREGS(0x0940, 0x093c, 0x0938, 0x01bb, 0x01bc, 0x01bc),
10049 },
10050 {
9133 .freq = 2412, 10051 .freq = 2412,
9134 RADIOREGS3(0x00, 0x01, 0x03, 0x09, 0x6c, 0x06, 0x06, 0x04, 10052 RADIOREGS3(0x00, 0x01, 0x03, 0x09, 0x6c, 0x06, 0x06, 0x04,
9135 0x2b, 0x01, 0x04, 0x04, 0x04, 0x8f, 0x30, 0x00, 10053 0x2b, 0x01, 0x04, 0x04, 0x04, 0x8f, 0x30, 0x00,
diff --git a/drivers/net/wireless/b43/xmit.c b/drivers/net/wireless/b43/xmit.c
index 31adb8cf0291..4f38f19b8e3d 100644
--- a/drivers/net/wireless/b43/xmit.c
+++ b/drivers/net/wireless/b43/xmit.c
@@ -408,7 +408,7 @@ int b43_generate_txhdr(struct b43_wldev *dev,
408 mac_ctl |= B43_TXH_MAC_HWSEQ; 408 mac_ctl |= B43_TXH_MAC_HWSEQ;
409 if (info->flags & IEEE80211_TX_CTL_FIRST_FRAGMENT) 409 if (info->flags & IEEE80211_TX_CTL_FIRST_FRAGMENT)
410 mac_ctl |= B43_TXH_MAC_STMSDU; 410 mac_ctl |= B43_TXH_MAC_STMSDU;
411 if (phy->type == B43_PHYTYPE_A) 411 if (!phy->gmode)
412 mac_ctl |= B43_TXH_MAC_5GHZ; 412 mac_ctl |= B43_TXH_MAC_5GHZ;
413 413
414 /* Overwrite rates[0].count to make the retry calculation 414 /* Overwrite rates[0].count to make the retry calculation
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd.h b/drivers/net/wireless/brcm80211/brcmfmac/dhd.h
index 939d6b132922..16f9ab2568a8 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd.h
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd.h
@@ -186,7 +186,7 @@ void brcmf_del_if(struct brcmf_pub *drvr, s32 bssidx);
186void brcmf_txflowblock_if(struct brcmf_if *ifp, 186void brcmf_txflowblock_if(struct brcmf_if *ifp,
187 enum brcmf_netif_stop_reason reason, bool state); 187 enum brcmf_netif_stop_reason reason, bool state);
188u32 brcmf_get_chip_info(struct brcmf_if *ifp); 188u32 brcmf_get_chip_info(struct brcmf_if *ifp);
189void brcmf_txfinalize(struct brcmf_pub *drvr, struct sk_buff *txp, 189void brcmf_txfinalize(struct brcmf_pub *drvr, struct sk_buff *txp, u8 ifidx,
190 bool success); 190 bool success);
191 191
192/* Sets dongle media info (drv_version, mac address). */ 192/* Sets dongle media info (drv_version, mac address). */
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd_bus.h b/drivers/net/wireless/brcm80211/brcmfmac/dhd_bus.h
index c4535616064e..c5dcd82e884b 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd_bus.h
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd_bus.h
@@ -99,6 +99,7 @@ struct brcmf_bus {
99 unsigned long tx_realloc; 99 unsigned long tx_realloc;
100 u32 chip; 100 u32 chip;
101 u32 chiprev; 101 u32 chiprev;
102 bool always_use_fws_queue;
102 103
103 struct brcmf_bus_ops *ops; 104 struct brcmf_bus_ops *ops;
104}; 105};
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c b/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c
index 6a8983a1fb9c..ed3e32ce8c23 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c
@@ -32,6 +32,9 @@
32#define BRCMF_DEFAULT_SCAN_UNASSOC_TIME 40 32#define BRCMF_DEFAULT_SCAN_UNASSOC_TIME 40
33#define BRCMF_DEFAULT_PACKET_FILTER "100 0 0 0 0x01 0x00" 33#define BRCMF_DEFAULT_PACKET_FILTER "100 0 0 0 0x01 0x00"
34 34
35/* boost value for RSSI_DELTA in preferred join selection */
36#define BRCMF_JOIN_PREF_RSSI_BOOST 8
37
35 38
36bool brcmf_c_prec_enq(struct device *dev, struct pktq *q, 39bool brcmf_c_prec_enq(struct device *dev, struct pktq *q,
37 struct sk_buff *pkt, int prec) 40 struct sk_buff *pkt, int prec)
@@ -246,6 +249,7 @@ int brcmf_c_preinit_dcmds(struct brcmf_if *ifp)
246{ 249{
247 s8 eventmask[BRCMF_EVENTING_MASK_LEN]; 250 s8 eventmask[BRCMF_EVENTING_MASK_LEN];
248 u8 buf[BRCMF_DCMD_SMLEN]; 251 u8 buf[BRCMF_DCMD_SMLEN];
252 struct brcmf_join_pref_params join_pref_params[2];
249 char *ptr; 253 char *ptr;
250 s32 err; 254 s32 err;
251 255
@@ -298,6 +302,20 @@ int brcmf_c_preinit_dcmds(struct brcmf_if *ifp)
298 goto done; 302 goto done;
299 } 303 }
300 304
305 /* Setup join_pref to select target by RSSI(with boost on 5GHz) */
306 join_pref_params[0].type = BRCMF_JOIN_PREF_RSSI_DELTA;
307 join_pref_params[0].len = 2;
308 join_pref_params[0].rssi_gain = BRCMF_JOIN_PREF_RSSI_BOOST;
309 join_pref_params[0].band = WLC_BAND_5G;
310 join_pref_params[1].type = BRCMF_JOIN_PREF_RSSI;
311 join_pref_params[1].len = 2;
312 join_pref_params[1].rssi_gain = 0;
313 join_pref_params[1].band = 0;
314 err = brcmf_fil_iovar_data_set(ifp, "join_pref", join_pref_params,
315 sizeof(join_pref_params));
316 if (err)
317 brcmf_err("Set join_pref error (%d)\n", err);
318
301 /* Setup event_msgs, enable E_IF */ 319 /* Setup event_msgs, enable E_IF */
302 err = brcmf_fil_iovar_data_get(ifp, "event_msgs", eventmask, 320 err = brcmf_fil_iovar_data_get(ifp, "event_msgs", eventmask,
303 BRCMF_EVENTING_MASK_LEN); 321 BRCMF_EVENTING_MASK_LEN);
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c b/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c
index 7d28cd385092..4cacc3d85212 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c
@@ -190,7 +190,7 @@ static netdev_tx_t brcmf_netdev_start_xmit(struct sk_buff *skb,
190 int ret; 190 int ret;
191 struct brcmf_if *ifp = netdev_priv(ndev); 191 struct brcmf_if *ifp = netdev_priv(ndev);
192 struct brcmf_pub *drvr = ifp->drvr; 192 struct brcmf_pub *drvr = ifp->drvr;
193 struct ethhdr *eh; 193 struct ethhdr *eh = (struct ethhdr *)(skb->data);
194 194
195 brcmf_dbg(DATA, "Enter, idx=%d\n", ifp->bssidx); 195 brcmf_dbg(DATA, "Enter, idx=%d\n", ifp->bssidx);
196 196
@@ -236,6 +236,9 @@ static netdev_tx_t brcmf_netdev_start_xmit(struct sk_buff *skb,
236 goto done; 236 goto done;
237 } 237 }
238 238
239 if (eh->h_proto == htons(ETH_P_PAE))
240 atomic_inc(&ifp->pend_8021x_cnt);
241
239 ret = brcmf_fws_process_skb(ifp, skb); 242 ret = brcmf_fws_process_skb(ifp, skb);
240 243
241done: 244done:
@@ -538,31 +541,26 @@ void brcmf_rx_frame(struct device *dev, struct sk_buff *skb)
538 brcmf_netif_rx(ifp, skb); 541 brcmf_netif_rx(ifp, skb);
539} 542}
540 543
541void brcmf_txfinalize(struct brcmf_pub *drvr, struct sk_buff *txp, 544void brcmf_txfinalize(struct brcmf_pub *drvr, struct sk_buff *txp, u8 ifidx,
542 bool success) 545 bool success)
543{ 546{
544 struct brcmf_if *ifp; 547 struct brcmf_if *ifp;
545 struct ethhdr *eh; 548 struct ethhdr *eh;
546 u8 ifidx;
547 u16 type; 549 u16 type;
548 int res;
549
550 res = brcmf_proto_hdrpull(drvr, false, &ifidx, txp);
551 550
552 ifp = drvr->iflist[ifidx]; 551 ifp = drvr->iflist[ifidx];
553 if (!ifp) 552 if (!ifp)
554 goto done; 553 goto done;
555 554
556 if (res == 0) { 555 eh = (struct ethhdr *)(txp->data);
557 eh = (struct ethhdr *)(txp->data); 556 type = ntohs(eh->h_proto);
558 type = ntohs(eh->h_proto);
559 557
560 if (type == ETH_P_PAE) { 558 if (type == ETH_P_PAE) {
561 atomic_dec(&ifp->pend_8021x_cnt); 559 atomic_dec(&ifp->pend_8021x_cnt);
562 if (waitqueue_active(&ifp->pend_8021x_wait)) 560 if (waitqueue_active(&ifp->pend_8021x_wait))
563 wake_up(&ifp->pend_8021x_wait); 561 wake_up(&ifp->pend_8021x_wait);
564 }
565 } 562 }
563
566 if (!success) 564 if (!success)
567 ifp->stats.tx_errors++; 565 ifp->stats.tx_errors++;
568done: 566done:
@@ -573,13 +571,17 @@ void brcmf_txcomplete(struct device *dev, struct sk_buff *txp, bool success)
573{ 571{
574 struct brcmf_bus *bus_if = dev_get_drvdata(dev); 572 struct brcmf_bus *bus_if = dev_get_drvdata(dev);
575 struct brcmf_pub *drvr = bus_if->drvr; 573 struct brcmf_pub *drvr = bus_if->drvr;
574 u8 ifidx;
576 575
577 /* await txstatus signal for firmware if active */ 576 /* await txstatus signal for firmware if active */
578 if (brcmf_fws_fc_active(drvr->fws)) { 577 if (brcmf_fws_fc_active(drvr->fws)) {
579 if (!success) 578 if (!success)
580 brcmf_fws_bustxfail(drvr->fws, txp); 579 brcmf_fws_bustxfail(drvr->fws, txp);
581 } else { 580 } else {
582 brcmf_txfinalize(drvr, txp, success); 581 if (brcmf_proto_hdrpull(drvr, false, &ifidx, txp))
582 brcmu_pkt_buf_free_skb(txp);
583 else
584 brcmf_txfinalize(drvr, txp, ifidx, success);
583 } 585 }
584} 586}
585 587
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/fwil_types.h b/drivers/net/wireless/brcm80211/brcmfmac/fwil_types.h
index 614e4888504f..2bc68a2137fc 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/fwil_types.h
+++ b/drivers/net/wireless/brcm80211/brcmfmac/fwil_types.h
@@ -53,6 +53,14 @@
53#define BRCMF_OBSS_COEX_OFF 0 53#define BRCMF_OBSS_COEX_OFF 0
54#define BRCMF_OBSS_COEX_ON 1 54#define BRCMF_OBSS_COEX_ON 1
55 55
56/* join preference types for join_pref iovar */
57enum brcmf_join_pref_types {
58 BRCMF_JOIN_PREF_RSSI = 1,
59 BRCMF_JOIN_PREF_WPA,
60 BRCMF_JOIN_PREF_BAND,
61 BRCMF_JOIN_PREF_RSSI_DELTA,
62};
63
56enum brcmf_fil_p2p_if_types { 64enum brcmf_fil_p2p_if_types {
57 BRCMF_FIL_P2P_IF_CLIENT, 65 BRCMF_FIL_P2P_IF_CLIENT,
58 BRCMF_FIL_P2P_IF_GO, 66 BRCMF_FIL_P2P_IF_GO,
@@ -282,6 +290,22 @@ struct brcmf_assoc_params_le {
282 __le16 chanspec_list[1]; 290 __le16 chanspec_list[1];
283}; 291};
284 292
293/**
294 * struct join_pref params - parameters for preferred join selection.
295 *
296 * @type: preference type (see enum brcmf_join_pref_types).
297 * @len: length of bytes following (currently always 2).
298 * @rssi_gain: signal gain for selection (only when @type is RSSI_DELTA).
299 * @band: band to which selection preference applies.
300 * This is used if @type is BAND or RSSI_DELTA.
301 */
302struct brcmf_join_pref_params {
303 u8 type;
304 u8 len;
305 u8 rssi_gain;
306 u8 band;
307};
308
285/* used for join with or without a specific bssid and channel list */ 309/* used for join with or without a specific bssid and channel list */
286struct brcmf_join_params { 310struct brcmf_join_params {
287 struct brcmf_ssid_le ssid_le; 311 struct brcmf_ssid_le ssid_le;
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/fwsignal.c b/drivers/net/wireless/brcm80211/brcmfmac/fwsignal.c
index c3e7d76dbf35..699908de314a 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/fwsignal.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/fwsignal.c
@@ -476,6 +476,7 @@ struct brcmf_fws_info {
476 bool bus_flow_blocked; 476 bool bus_flow_blocked;
477 bool creditmap_received; 477 bool creditmap_received;
478 u8 mode; 478 u8 mode;
479 bool avoid_queueing;
479}; 480};
480 481
481/* 482/*
@@ -1369,13 +1370,12 @@ done:
1369} 1370}
1370 1371
1371static int brcmf_fws_txstatus_suppressed(struct brcmf_fws_info *fws, int fifo, 1372static int brcmf_fws_txstatus_suppressed(struct brcmf_fws_info *fws, int fifo,
1372 struct sk_buff *skb, u32 genbit, 1373 struct sk_buff *skb, u8 ifidx,
1373 u16 seq) 1374 u32 genbit, u16 seq)
1374{ 1375{
1375 struct brcmf_fws_mac_descriptor *entry = brcmf_skbcb(skb)->mac; 1376 struct brcmf_fws_mac_descriptor *entry = brcmf_skbcb(skb)->mac;
1376 u32 hslot; 1377 u32 hslot;
1377 int ret; 1378 int ret;
1378 u8 ifidx;
1379 1379
1380 hslot = brcmf_skb_htod_tag_get_field(skb, HSLOT); 1380 hslot = brcmf_skb_htod_tag_get_field(skb, HSLOT);
1381 1381
@@ -1389,29 +1389,21 @@ static int brcmf_fws_txstatus_suppressed(struct brcmf_fws_info *fws, int fifo,
1389 1389
1390 entry->generation = genbit; 1390 entry->generation = genbit;
1391 1391
1392 ret = brcmf_proto_hdrpull(fws->drvr, false, &ifidx, skb); 1392 brcmf_skb_htod_tag_set_field(skb, GENERATION, genbit);
1393 if (ret == 0) { 1393 brcmf_skbcb(skb)->htod_seq = seq;
1394 brcmf_skb_htod_tag_set_field(skb, GENERATION, genbit); 1394 if (brcmf_skb_htod_seq_get_field(skb, FROMFW)) {
1395 brcmf_skbcb(skb)->htod_seq = seq; 1395 brcmf_skb_htod_seq_set_field(skb, FROMDRV, 1);
1396 if (brcmf_skb_htod_seq_get_field(skb, FROMFW)) { 1396 brcmf_skb_htod_seq_set_field(skb, FROMFW, 0);
1397 brcmf_skb_htod_seq_set_field(skb, FROMDRV, 1); 1397 } else {
1398 brcmf_skb_htod_seq_set_field(skb, FROMFW, 0); 1398 brcmf_skb_htod_seq_set_field(skb, FROMDRV, 0);
1399 } else {
1400 brcmf_skb_htod_seq_set_field(skb, FROMDRV, 0);
1401 }
1402 ret = brcmf_fws_enq(fws, BRCMF_FWS_SKBSTATE_SUPPRESSED, fifo,
1403 skb);
1404 } 1399 }
1400 ret = brcmf_fws_enq(fws, BRCMF_FWS_SKBSTATE_SUPPRESSED, fifo, skb);
1405 1401
1406 if (ret != 0) { 1402 if (ret != 0) {
1407 /* suppress q is full or hdrpull failed, drop this packet */ 1403 /* suppress q is full drop this packet */
1408 brcmf_fws_hanger_poppkt(&fws->hanger, hslot, &skb, 1404 brcmf_fws_hanger_poppkt(&fws->hanger, hslot, &skb, true);
1409 true);
1410 } else { 1405 } else {
1411 /* 1406 /* Mark suppressed to avoid a double free during wlfc cleanup */
1412 * Mark suppressed to avoid a double free during
1413 * wlfc cleanup
1414 */
1415 brcmf_fws_hanger_mark_suppressed(&fws->hanger, hslot); 1407 brcmf_fws_hanger_mark_suppressed(&fws->hanger, hslot);
1416 } 1408 }
1417 1409
@@ -1428,6 +1420,7 @@ brcmf_fws_txs_process(struct brcmf_fws_info *fws, u8 flags, u32 hslot,
1428 struct sk_buff *skb; 1420 struct sk_buff *skb;
1429 struct brcmf_skbuff_cb *skcb; 1421 struct brcmf_skbuff_cb *skcb;
1430 struct brcmf_fws_mac_descriptor *entry = NULL; 1422 struct brcmf_fws_mac_descriptor *entry = NULL;
1423 u8 ifidx;
1431 1424
1432 brcmf_dbg(DATA, "flags %d\n", flags); 1425 brcmf_dbg(DATA, "flags %d\n", flags);
1433 1426
@@ -1476,12 +1469,15 @@ brcmf_fws_txs_process(struct brcmf_fws_info *fws, u8 flags, u32 hslot,
1476 } 1469 }
1477 brcmf_fws_macdesc_return_req_credit(skb); 1470 brcmf_fws_macdesc_return_req_credit(skb);
1478 1471
1472 if (brcmf_proto_hdrpull(fws->drvr, false, &ifidx, skb)) {
1473 brcmu_pkt_buf_free_skb(skb);
1474 return -EINVAL;
1475 }
1479 if (!remove_from_hanger) 1476 if (!remove_from_hanger)
1480 ret = brcmf_fws_txstatus_suppressed(fws, fifo, skb, genbit, 1477 ret = brcmf_fws_txstatus_suppressed(fws, fifo, skb, ifidx,
1481 seq); 1478 genbit, seq);
1482
1483 if (remove_from_hanger || ret) 1479 if (remove_from_hanger || ret)
1484 brcmf_txfinalize(fws->drvr, skb, true); 1480 brcmf_txfinalize(fws->drvr, skb, ifidx, true);
1485 1481
1486 return 0; 1482 return 0;
1487} 1483}
@@ -1868,7 +1864,7 @@ int brcmf_fws_process_skb(struct brcmf_if *ifp, struct sk_buff *skb)
1868 struct ethhdr *eh = (struct ethhdr *)(skb->data); 1864 struct ethhdr *eh = (struct ethhdr *)(skb->data);
1869 int fifo = BRCMF_FWS_FIFO_BCMC; 1865 int fifo = BRCMF_FWS_FIFO_BCMC;
1870 bool multicast = is_multicast_ether_addr(eh->h_dest); 1866 bool multicast = is_multicast_ether_addr(eh->h_dest);
1871 bool pae = eh->h_proto == htons(ETH_P_PAE); 1867 int rc = 0;
1872 1868
1873 brcmf_dbg(DATA, "tx proto=0x%X\n", ntohs(eh->h_proto)); 1869 brcmf_dbg(DATA, "tx proto=0x%X\n", ntohs(eh->h_proto));
1874 /* determine the priority */ 1870 /* determine the priority */
@@ -1876,8 +1872,13 @@ int brcmf_fws_process_skb(struct brcmf_if *ifp, struct sk_buff *skb)
1876 skb->priority = cfg80211_classify8021d(skb, NULL); 1872 skb->priority = cfg80211_classify8021d(skb, NULL);
1877 1873
1878 drvr->tx_multicast += !!multicast; 1874 drvr->tx_multicast += !!multicast;
1879 if (pae) 1875
1880 atomic_inc(&ifp->pend_8021x_cnt); 1876 if (fws->avoid_queueing) {
1877 rc = brcmf_proto_txdata(drvr, ifp->ifidx, 0, skb);
1878 if (rc < 0)
1879 brcmf_txfinalize(drvr, skb, ifp->ifidx, false);
1880 return rc;
1881 }
1881 1882
1882 /* set control buffer information */ 1883 /* set control buffer information */
1883 skcb->if_flags = 0; 1884 skcb->if_flags = 0;
@@ -1899,15 +1900,12 @@ int brcmf_fws_process_skb(struct brcmf_if *ifp, struct sk_buff *skb)
1899 brcmf_fws_schedule_deq(fws); 1900 brcmf_fws_schedule_deq(fws);
1900 } else { 1901 } else {
1901 brcmf_err("drop skb: no hanger slot\n"); 1902 brcmf_err("drop skb: no hanger slot\n");
1902 if (pae) { 1903 brcmf_txfinalize(drvr, skb, ifp->ifidx, false);
1903 atomic_dec(&ifp->pend_8021x_cnt); 1904 rc = -ENOMEM;
1904 if (waitqueue_active(&ifp->pend_8021x_wait))
1905 wake_up(&ifp->pend_8021x_wait);
1906 }
1907 brcmu_pkt_buf_free_skb(skb);
1908 } 1905 }
1909 brcmf_fws_unlock(fws); 1906 brcmf_fws_unlock(fws);
1910 return 0; 1907
1908 return rc;
1911} 1909}
1912 1910
1913void brcmf_fws_reset_interface(struct brcmf_if *ifp) 1911void brcmf_fws_reset_interface(struct brcmf_if *ifp)
@@ -1982,7 +1980,8 @@ static void brcmf_fws_dequeue_worker(struct work_struct *worker)
1982 ret = brcmf_proto_txdata(drvr, ifidx, 0, skb); 1980 ret = brcmf_proto_txdata(drvr, ifidx, 0, skb);
1983 brcmf_fws_lock(fws); 1981 brcmf_fws_lock(fws);
1984 if (ret < 0) 1982 if (ret < 0)
1985 brcmf_txfinalize(drvr, skb, false); 1983 brcmf_txfinalize(drvr, skb, ifidx,
1984 false);
1986 if (fws->bus_flow_blocked) 1985 if (fws->bus_flow_blocked)
1987 break; 1986 break;
1988 } 1987 }
@@ -2039,6 +2038,13 @@ int brcmf_fws_init(struct brcmf_pub *drvr)
2039 fws->drvr = drvr; 2038 fws->drvr = drvr;
2040 fws->fcmode = fcmode; 2039 fws->fcmode = fcmode;
2041 2040
2041 if ((drvr->bus_if->always_use_fws_queue == false) &&
2042 (fcmode == BRCMF_FWS_FCMODE_NONE)) {
2043 fws->avoid_queueing = true;
2044 brcmf_dbg(INFO, "FWS queueing will be avoided\n");
2045 return 0;
2046 }
2047
2042 fws->fws_wq = create_singlethread_workqueue("brcmf_fws_wq"); 2048 fws->fws_wq = create_singlethread_workqueue("brcmf_fws_wq");
2043 if (fws->fws_wq == NULL) { 2049 if (fws->fws_wq == NULL) {
2044 brcmf_err("workqueue creation failed\n"); 2050 brcmf_err("workqueue creation failed\n");
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/nvram.c b/drivers/net/wireless/brcm80211/brcmfmac/nvram.c
index d5ef86db631b..5c450d11dbc9 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/nvram.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/nvram.c
@@ -18,72 +18,205 @@
18#include <linux/slab.h> 18#include <linux/slab.h>
19#include <linux/firmware.h> 19#include <linux/firmware.h>
20 20
21#include "dhd_dbg.h"
21#include "nvram.h" 22#include "nvram.h"
22 23
23/* brcmf_nvram_strip :Takes a buffer of "<var>=<value>\n" lines read from a file 24enum nvram_parser_state {
25 IDLE,
26 KEY,
27 VALUE,
28 COMMENT,
29 END
30};
31
32/**
33 * struct nvram_parser - internal info for parser.
34 *
35 * @state: current parser state.
36 * @fwnv: input buffer being parsed.
37 * @nvram: output buffer with parse result.
38 * @nvram_len: lenght of parse result.
39 * @line: current line.
40 * @column: current column in line.
41 * @pos: byte offset in input buffer.
42 * @entry: start position of key,value entry.
43 */
44struct nvram_parser {
45 enum nvram_parser_state state;
46 const struct firmware *fwnv;
47 u8 *nvram;
48 u32 nvram_len;
49 u32 line;
50 u32 column;
51 u32 pos;
52 u32 entry;
53};
54
55static bool is_nvram_char(char c)
56{
57 /* comment marker excluded */
58 if (c == '#')
59 return false;
60
61 /* key and value may have any other readable character */
62 return (c > 0x20 && c < 0x7f);
63}
64
65static bool is_whitespace(char c)
66{
67 return (c == ' ' || c == '\r' || c == '\n' || c == '\t');
68}
69
70static enum nvram_parser_state brcmf_nvram_handle_idle(struct nvram_parser *nvp)
71{
72 char c;
73
74 c = nvp->fwnv->data[nvp->pos];
75 if (c == '\n')
76 return COMMENT;
77 if (is_whitespace(c))
78 goto proceed;
79 if (c == '#')
80 return COMMENT;
81 if (is_nvram_char(c)) {
82 nvp->entry = nvp->pos;
83 return KEY;
84 }
85 brcmf_dbg(INFO, "warning: ln=%d:col=%d: ignoring invalid character\n",
86 nvp->line, nvp->column);
87proceed:
88 nvp->column++;
89 nvp->pos++;
90 return IDLE;
91}
92
93static enum nvram_parser_state brcmf_nvram_handle_key(struct nvram_parser *nvp)
94{
95 enum nvram_parser_state st = nvp->state;
96 char c;
97
98 c = nvp->fwnv->data[nvp->pos];
99 if (c == '=') {
100 st = VALUE;
101 } else if (!is_nvram_char(c)) {
102 brcmf_dbg(INFO, "warning: ln=%d:col=%d: '=' expected, skip invalid key entry\n",
103 nvp->line, nvp->column);
104 return COMMENT;
105 }
106
107 nvp->column++;
108 nvp->pos++;
109 return st;
110}
111
112static enum nvram_parser_state
113brcmf_nvram_handle_value(struct nvram_parser *nvp)
114{
115 char c;
116 char *skv;
117 char *ekv;
118 u32 cplen;
119
120 c = nvp->fwnv->data[nvp->pos];
121 if (!is_nvram_char(c)) {
122 /* key,value pair complete */
123 ekv = (u8 *)&nvp->fwnv->data[nvp->pos];
124 skv = (u8 *)&nvp->fwnv->data[nvp->entry];
125 cplen = ekv - skv;
126 /* copy to output buffer */
127 memcpy(&nvp->nvram[nvp->nvram_len], skv, cplen);
128 nvp->nvram_len += cplen;
129 nvp->nvram[nvp->nvram_len] = '\0';
130 nvp->nvram_len++;
131 return IDLE;
132 }
133 nvp->pos++;
134 nvp->column++;
135 return VALUE;
136}
137
138static enum nvram_parser_state
139brcmf_nvram_handle_comment(struct nvram_parser *nvp)
140{
141 char *eol, *sol;
142
143 sol = (char *)&nvp->fwnv->data[nvp->pos];
144 eol = strchr(sol, '\n');
145 if (eol == NULL)
146 return END;
147
148 /* eat all moving to next line */
149 nvp->line++;
150 nvp->column = 1;
151 nvp->pos += (eol - sol) + 1;
152 return IDLE;
153}
154
155static enum nvram_parser_state brcmf_nvram_handle_end(struct nvram_parser *nvp)
156{
157 /* final state */
158 return END;
159}
160
161static enum nvram_parser_state
162(*nv_parser_states[])(struct nvram_parser *nvp) = {
163 brcmf_nvram_handle_idle,
164 brcmf_nvram_handle_key,
165 brcmf_nvram_handle_value,
166 brcmf_nvram_handle_comment,
167 brcmf_nvram_handle_end
168};
169
170static int brcmf_init_nvram_parser(struct nvram_parser *nvp,
171 const struct firmware *nv)
172{
173 memset(nvp, 0, sizeof(*nvp));
174 nvp->fwnv = nv;
175 /* Alloc for extra 0 byte + roundup by 4 + length field */
176 nvp->nvram = kzalloc(nv->size + 1 + 3 + sizeof(u32), GFP_KERNEL);
177 if (!nvp->nvram)
178 return -ENOMEM;
179
180 nvp->line = 1;
181 nvp->column = 1;
182 return 0;
183}
184
185/* brcmf_nvram_strip :Takes a buffer of "<var>=<value>\n" lines read from a fil
24 * and ending in a NUL. Removes carriage returns, empty lines, comment lines, 186 * and ending in a NUL. Removes carriage returns, empty lines, comment lines,
25 * and converts newlines to NULs. Shortens buffer as needed and pads with NULs. 187 * and converts newlines to NULs. Shortens buffer as needed and pads with NULs.
26 * End of buffer is completed with token identifying length of buffer. 188 * End of buffer is completed with token identifying length of buffer.
27 */ 189 */
28void *brcmf_nvram_strip(const struct firmware *nv, u32 *new_length) 190void *brcmf_nvram_strip(const struct firmware *nv, u32 *new_length)
29{ 191{
30 u8 *nvram; 192 struct nvram_parser nvp;
31 u32 i; 193 u32 pad;
32 u32 len;
33 u32 column;
34 u8 val;
35 bool comment;
36 u32 token; 194 u32 token;
37 __le32 token_le; 195 __le32 token_le;
38 196
39 /* Alloc for extra 0 byte + roundup by 4 + length field */ 197 if (brcmf_init_nvram_parser(&nvp, nv) < 0)
40 nvram = kmalloc(nv->size + 1 + 3 + sizeof(token_le), GFP_KERNEL);
41 if (!nvram)
42 return NULL; 198 return NULL;
43 199
44 len = 0; 200 while (nvp.pos < nv->size) {
45 column = 0; 201 nvp.state = nv_parser_states[nvp.state](&nvp);
46 comment = false; 202 if (nvp.state == END)
47 for (i = 0; i < nv->size; i++) {
48 val = nv->data[i];
49 if (val == 0)
50 break; 203 break;
51 if (val == '\r')
52 continue;
53 if (comment && (val != '\n'))
54 continue;
55 comment = false;
56 if (val == '#') {
57 comment = true;
58 continue;
59 }
60 if (val == '\n') {
61 if (column == 0)
62 continue;
63 nvram[len] = 0;
64 len++;
65 column = 0;
66 continue;
67 }
68 nvram[len] = val;
69 len++;
70 column++;
71 } 204 }
72 column = len; 205 pad = nvp.nvram_len;
73 *new_length = roundup(len + 1, 4); 206 *new_length = roundup(nvp.nvram_len + 1, 4);
74 while (column != *new_length) { 207 while (pad != *new_length) {
75 nvram[column] = 0; 208 nvp.nvram[pad] = 0;
76 column++; 209 pad++;
77 } 210 }
78 211
79 token = *new_length / 4; 212 token = *new_length / 4;
80 token = (~token << 16) | (token & 0x0000FFFF); 213 token = (~token << 16) | (token & 0x0000FFFF);
81 token_le = cpu_to_le32(token); 214 token_le = cpu_to_le32(token);
82 215
83 memcpy(&nvram[*new_length], &token_le, sizeof(token_le)); 216 memcpy(&nvp.nvram[*new_length], &token_le, sizeof(token_le));
84 *new_length += sizeof(token_le); 217 *new_length += sizeof(token_le);
85 218
86 return nvram; 219 return nvp.nvram;
87} 220}
88 221
89void brcmf_nvram_free(void *nvram) 222void brcmf_nvram_free(void *nvram)
@@ -91,4 +224,3 @@ void brcmf_nvram_free(void *nvram)
91 kfree(nvram); 224 kfree(nvram);
92} 225}
93 226
94
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/usb.c b/drivers/net/wireless/brcm80211/brcmfmac/usb.c
index 24f65cd53859..3ce0e7cfd027 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/usb.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/usb.c
@@ -1254,6 +1254,7 @@ static int brcmf_usb_probe_cb(struct brcmf_usbdev_info *devinfo)
1254 bus->chip = bus_pub->devid; 1254 bus->chip = bus_pub->devid;
1255 bus->chiprev = bus_pub->chiprev; 1255 bus->chiprev = bus_pub->chiprev;
1256 bus->proto_type = BRCMF_PROTO_BCDC; 1256 bus->proto_type = BRCMF_PROTO_BCDC;
1257 bus->always_use_fws_queue = true;
1257 1258
1258 /* Attach to the common driver interface */ 1259 /* Attach to the common driver interface */
1259 ret = brcmf_attach(dev); 1260 ret = brcmf_attach(dev);
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c b/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c
index be1985296bdc..92cb29a2003f 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c
@@ -221,9 +221,9 @@ static const struct ieee80211_regdomain brcmf_regdom = {
221 */ 221 */
222 REG_RULE(2484-10, 2484+10, 20, 6, 20, 0), 222 REG_RULE(2484-10, 2484+10, 20, 6, 20, 0),
223 /* IEEE 802.11a, channel 36..64 */ 223 /* IEEE 802.11a, channel 36..64 */
224 REG_RULE(5150-10, 5350+10, 40, 6, 20, 0), 224 REG_RULE(5150-10, 5350+10, 80, 6, 20, 0),
225 /* IEEE 802.11a, channel 100..165 */ 225 /* IEEE 802.11a, channel 100..165 */
226 REG_RULE(5470-10, 5850+10, 40, 6, 20, 0), } 226 REG_RULE(5470-10, 5850+10, 80, 6, 20, 0), }
227}; 227};
228 228
229static const u32 __wl_cipher_suites[] = { 229static const u32 __wl_cipher_suites[] = {
@@ -341,6 +341,60 @@ static u8 brcmf_mw_to_qdbm(u16 mw)
341 return qdbm; 341 return qdbm;
342} 342}
343 343
344u16 chandef_to_chanspec(struct brcmu_d11inf *d11inf,
345 struct cfg80211_chan_def *ch)
346{
347 struct brcmu_chan ch_inf;
348 s32 primary_offset;
349
350 brcmf_dbg(TRACE, "chandef: control %d center %d width %d\n",
351 ch->chan->center_freq, ch->center_freq1, ch->width);
352 ch_inf.chnum = ieee80211_frequency_to_channel(ch->center_freq1);
353 primary_offset = ch->center_freq1 - ch->chan->center_freq;
354 switch (ch->width) {
355 case NL80211_CHAN_WIDTH_20:
356 ch_inf.bw = BRCMU_CHAN_BW_20;
357 WARN_ON(primary_offset != 0);
358 break;
359 case NL80211_CHAN_WIDTH_40:
360 ch_inf.bw = BRCMU_CHAN_BW_40;
361 if (primary_offset < 0)
362 ch_inf.sb = BRCMU_CHAN_SB_U;
363 else
364 ch_inf.sb = BRCMU_CHAN_SB_L;
365 break;
366 case NL80211_CHAN_WIDTH_80:
367 ch_inf.bw = BRCMU_CHAN_BW_80;
368 if (primary_offset < 0) {
369 if (primary_offset < -CH_10MHZ_APART)
370 ch_inf.sb = BRCMU_CHAN_SB_UU;
371 else
372 ch_inf.sb = BRCMU_CHAN_SB_UL;
373 } else {
374 if (primary_offset > CH_10MHZ_APART)
375 ch_inf.sb = BRCMU_CHAN_SB_LL;
376 else
377 ch_inf.sb = BRCMU_CHAN_SB_LU;
378 }
379 break;
380 default:
381 WARN_ON_ONCE(1);
382 }
383 switch (ch->chan->band) {
384 case IEEE80211_BAND_2GHZ:
385 ch_inf.band = BRCMU_CHAN_BAND_2G;
386 break;
387 case IEEE80211_BAND_5GHZ:
388 ch_inf.band = BRCMU_CHAN_BAND_5G;
389 break;
390 default:
391 WARN_ON_ONCE(1);
392 }
393 d11inf->encchspec(&ch_inf);
394
395 return ch_inf.chspec;
396}
397
344u16 channel_to_chanspec(struct brcmu_d11inf *d11inf, 398u16 channel_to_chanspec(struct brcmu_d11inf *d11inf,
345 struct ieee80211_channel *ch) 399 struct ieee80211_channel *ch)
346{ 400{
@@ -1236,8 +1290,8 @@ brcmf_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *ndev,
1236 params->chandef.chan->center_freq); 1290 params->chandef.chan->center_freq);
1237 if (params->channel_fixed) { 1291 if (params->channel_fixed) {
1238 /* adding chanspec */ 1292 /* adding chanspec */
1239 chanspec = channel_to_chanspec(&cfg->d11inf, 1293 chanspec = chandef_to_chanspec(&cfg->d11inf,
1240 params->chandef.chan); 1294 &params->chandef);
1241 join_params.params_le.chanspec_list[0] = 1295 join_params.params_le.chanspec_list[0] =
1242 cpu_to_le16(chanspec); 1296 cpu_to_le16(chanspec);
1243 join_params.params_le.chanspec_num = cpu_to_le32(1); 1297 join_params.params_le.chanspec_num = cpu_to_le32(1);
@@ -2182,7 +2236,7 @@ brcmf_cfg80211_config_default_mgmt_key(struct wiphy *wiphy,
2182 2236
2183static s32 2237static s32
2184brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev, 2238brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev,
2185 u8 *mac, struct station_info *sinfo) 2239 const u8 *mac, struct station_info *sinfo)
2186{ 2240{
2187 struct brcmf_if *ifp = netdev_priv(ndev); 2241 struct brcmf_if *ifp = netdev_priv(ndev);
2188 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile; 2242 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
@@ -3734,23 +3788,6 @@ brcmf_config_ap_mgmt_ie(struct brcmf_cfg80211_vif *vif,
3734} 3788}
3735 3789
3736static s32 3790static s32
3737brcmf_cfg80211_set_channel(struct brcmf_cfg80211_info *cfg,
3738 struct brcmf_if *ifp,
3739 struct ieee80211_channel *channel)
3740{
3741 u16 chanspec;
3742 s32 err;
3743
3744 brcmf_dbg(TRACE, "band=%d, center_freq=%d\n", channel->band,
3745 channel->center_freq);
3746
3747 chanspec = channel_to_chanspec(&cfg->d11inf, channel);
3748 err = brcmf_fil_iovar_int_set(ifp, "chanspec", chanspec);
3749
3750 return err;
3751}
3752
3753static s32
3754brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev, 3791brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
3755 struct cfg80211_ap_settings *settings) 3792 struct cfg80211_ap_settings *settings)
3756{ 3793{
@@ -3765,11 +3802,12 @@ brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
3765 struct brcmf_join_params join_params; 3802 struct brcmf_join_params join_params;
3766 enum nl80211_iftype dev_role; 3803 enum nl80211_iftype dev_role;
3767 struct brcmf_fil_bss_enable_le bss_enable; 3804 struct brcmf_fil_bss_enable_le bss_enable;
3805 u16 chanspec;
3768 3806
3769 brcmf_dbg(TRACE, "channel_type=%d, beacon_interval=%d, dtim_period=%d,\n", 3807 brcmf_dbg(TRACE, "ctrlchn=%d, center=%d, bw=%d, beacon_interval=%d, dtim_period=%d,\n",
3770 cfg80211_get_chandef_type(&settings->chandef), 3808 settings->chandef.chan->hw_value,
3771 settings->beacon_interval, 3809 settings->chandef.center_freq1, settings->chandef.width,
3772 settings->dtim_period); 3810 settings->beacon_interval, settings->dtim_period);
3773 brcmf_dbg(TRACE, "ssid=%s(%zu), auth_type=%d, inactivity_timeout=%d\n", 3811 brcmf_dbg(TRACE, "ssid=%s(%zu), auth_type=%d, inactivity_timeout=%d\n",
3774 settings->ssid, settings->ssid_len, settings->auth_type, 3812 settings->ssid, settings->ssid_len, settings->auth_type,
3775 settings->inactivity_timeout); 3813 settings->inactivity_timeout);
@@ -3826,9 +3864,10 @@ brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
3826 3864
3827 brcmf_config_ap_mgmt_ie(ifp->vif, &settings->beacon); 3865 brcmf_config_ap_mgmt_ie(ifp->vif, &settings->beacon);
3828 3866
3829 err = brcmf_cfg80211_set_channel(cfg, ifp, settings->chandef.chan); 3867 chanspec = chandef_to_chanspec(&cfg->d11inf, &settings->chandef);
3868 err = brcmf_fil_iovar_int_set(ifp, "chanspec", chanspec);
3830 if (err < 0) { 3869 if (err < 0) {
3831 brcmf_err("Set Channel failed, %d\n", err); 3870 brcmf_err("Set Channel failed: chspec=%d, %d\n", chanspec, err);
3832 goto exit; 3871 goto exit;
3833 } 3872 }
3834 3873
@@ -3975,7 +4014,7 @@ brcmf_cfg80211_change_beacon(struct wiphy *wiphy, struct net_device *ndev,
3975 4014
3976static int 4015static int
3977brcmf_cfg80211_del_station(struct wiphy *wiphy, struct net_device *ndev, 4016brcmf_cfg80211_del_station(struct wiphy *wiphy, struct net_device *ndev,
3978 u8 *mac) 4017 const u8 *mac)
3979{ 4018{
3980 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy); 4019 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3981 struct brcmf_scb_val_le scbval; 4020 struct brcmf_scb_val_le scbval;
@@ -4203,7 +4242,7 @@ static int brcmf_convert_nl80211_tdls_oper(enum nl80211_tdls_operation oper)
4203} 4242}
4204 4243
4205static int brcmf_cfg80211_tdls_oper(struct wiphy *wiphy, 4244static int brcmf_cfg80211_tdls_oper(struct wiphy *wiphy,
4206 struct net_device *ndev, u8 *peer, 4245 struct net_device *ndev, const u8 *peer,
4207 enum nl80211_tdls_operation oper) 4246 enum nl80211_tdls_operation oper)
4208{ 4247{
4209 struct brcmf_if *ifp; 4248 struct brcmf_if *ifp;
@@ -4364,6 +4403,8 @@ static struct wiphy *brcmf_setup_wiphy(struct device *phydev)
4364 WIPHY_FLAG_OFFCHAN_TX | 4403 WIPHY_FLAG_OFFCHAN_TX |
4365 WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL | 4404 WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL |
4366 WIPHY_FLAG_SUPPORTS_TDLS; 4405 WIPHY_FLAG_SUPPORTS_TDLS;
4406 if (!brcmf_roamoff)
4407 wiphy->flags |= WIPHY_FLAG_SUPPORTS_FW_ROAM;
4367 wiphy->mgmt_stypes = brcmf_txrx_stypes; 4408 wiphy->mgmt_stypes = brcmf_txrx_stypes;
4368 wiphy->max_remain_on_channel_duration = 5000; 4409 wiphy->max_remain_on_channel_duration = 5000;
4369 brcmf_wiphy_pno_params(wiphy); 4410 brcmf_wiphy_pno_params(wiphy);
@@ -4685,7 +4726,6 @@ brcmf_notify_connect_status(struct brcmf_if *ifp,
4685 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile; 4726 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
4686 struct ieee80211_channel *chan; 4727 struct ieee80211_channel *chan;
4687 s32 err = 0; 4728 s32 err = 0;
4688 u16 reason;
4689 4729
4690 if (brcmf_is_apmode(ifp->vif)) { 4730 if (brcmf_is_apmode(ifp->vif)) {
4691 err = brcmf_notify_connect_status_ap(cfg, ndev, e, data); 4731 err = brcmf_notify_connect_status_ap(cfg, ndev, e, data);
@@ -4706,16 +4746,6 @@ brcmf_notify_connect_status(struct brcmf_if *ifp,
4706 brcmf_dbg(CONN, "Linkdown\n"); 4746 brcmf_dbg(CONN, "Linkdown\n");
4707 if (!brcmf_is_ibssmode(ifp->vif)) { 4747 if (!brcmf_is_ibssmode(ifp->vif)) {
4708 brcmf_bss_connect_done(cfg, ndev, e, false); 4748 brcmf_bss_connect_done(cfg, ndev, e, false);
4709 if (test_and_clear_bit(BRCMF_VIF_STATUS_CONNECTED,
4710 &ifp->vif->sme_state)) {
4711 reason = 0;
4712 if (((e->event_code == BRCMF_E_DEAUTH_IND) ||
4713 (e->event_code == BRCMF_E_DISASSOC_IND)) &&
4714 (e->reason != WLAN_REASON_UNSPECIFIED))
4715 reason = e->reason;
4716 cfg80211_disconnected(ndev, reason, NULL, 0,
4717 GFP_KERNEL);
4718 }
4719 } 4749 }
4720 brcmf_link_down(ifp->vif); 4750 brcmf_link_down(ifp->vif);
4721 brcmf_init_prof(ndev_to_prof(ndev)); 4751 brcmf_init_prof(ndev_to_prof(ndev));
@@ -5215,6 +5245,9 @@ static s32 brcmf_construct_reginfo(struct brcmf_cfg80211_info *cfg,
5215 if (!(bw_cap[band] & WLC_BW_40MHZ_BIT) && 5245 if (!(bw_cap[band] & WLC_BW_40MHZ_BIT) &&
5216 ch.bw == BRCMU_CHAN_BW_40) 5246 ch.bw == BRCMU_CHAN_BW_40)
5217 continue; 5247 continue;
5248 if (!(bw_cap[band] & WLC_BW_80MHZ_BIT) &&
5249 ch.bw == BRCMU_CHAN_BW_80)
5250 continue;
5218 update = false; 5251 update = false;
5219 for (j = 0; (j < *n_cnt && (*n_cnt < array_size)); j++) { 5252 for (j = 0; (j < *n_cnt && (*n_cnt < array_size)); j++) {
5220 if (band_chan_arr[j].hw_value == ch.chnum) { 5253 if (band_chan_arr[j].hw_value == ch.chnum) {
@@ -5231,10 +5264,13 @@ static s32 brcmf_construct_reginfo(struct brcmf_cfg80211_info *cfg,
5231 ieee80211_channel_to_frequency(ch.chnum, band); 5264 ieee80211_channel_to_frequency(ch.chnum, band);
5232 band_chan_arr[index].hw_value = ch.chnum; 5265 band_chan_arr[index].hw_value = ch.chnum;
5233 5266
5234 if (ch.bw == BRCMU_CHAN_BW_40) { 5267 /* assuming the chanspecs order is HT20,
5235 /* assuming the order is HT20, HT40 Upper, 5268 * HT40 upper, HT40 lower, and VHT80.
5236 * HT40 lower from chanspecs 5269 */
5237 */ 5270 if (ch.bw == BRCMU_CHAN_BW_80) {
5271 band_chan_arr[index].flags &=
5272 ~IEEE80211_CHAN_NO_80MHZ;
5273 } else if (ch.bw == BRCMU_CHAN_BW_40) {
5238 ht40_flag = band_chan_arr[index].flags & 5274 ht40_flag = band_chan_arr[index].flags &
5239 IEEE80211_CHAN_NO_HT40; 5275 IEEE80211_CHAN_NO_HT40;
5240 if (ch.sb == BRCMU_CHAN_SB_U) { 5276 if (ch.sb == BRCMU_CHAN_SB_U) {
@@ -5255,8 +5291,13 @@ static s32 brcmf_construct_reginfo(struct brcmf_cfg80211_info *cfg,
5255 IEEE80211_CHAN_NO_HT40MINUS; 5291 IEEE80211_CHAN_NO_HT40MINUS;
5256 } 5292 }
5257 } else { 5293 } else {
5294 /* disable other bandwidths for now as mentioned
5295 * order assure they are enabled for subsequent
5296 * chanspecs.
5297 */
5258 band_chan_arr[index].flags = 5298 band_chan_arr[index].flags =
5259 IEEE80211_CHAN_NO_HT40; 5299 IEEE80211_CHAN_NO_HT40 |
5300 IEEE80211_CHAN_NO_80MHZ;
5260 ch.bw = BRCMU_CHAN_BW_20; 5301 ch.bw = BRCMU_CHAN_BW_20;
5261 cfg->d11inf.encchspec(&ch); 5302 cfg->d11inf.encchspec(&ch);
5262 channel = ch.chspec; 5303 channel = ch.chspec;
@@ -5323,13 +5364,63 @@ static void brcmf_get_bwcap(struct brcmf_if *ifp, u32 bw_cap[])
5323 } 5364 }
5324} 5365}
5325 5366
5367static void brcmf_update_ht_cap(struct ieee80211_supported_band *band,
5368 u32 bw_cap[2], u32 nchain)
5369{
5370 band->ht_cap.ht_supported = true;
5371 if (bw_cap[band->band] & WLC_BW_40MHZ_BIT) {
5372 band->ht_cap.cap |= IEEE80211_HT_CAP_SGI_40;
5373 band->ht_cap.cap |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
5374 }
5375 band->ht_cap.cap |= IEEE80211_HT_CAP_SGI_20;
5376 band->ht_cap.cap |= IEEE80211_HT_CAP_DSSSCCK40;
5377 band->ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
5378 band->ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_16;
5379 memset(band->ht_cap.mcs.rx_mask, 0xff, nchain);
5380 band->ht_cap.mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
5381}
5382
5383static __le16 brcmf_get_mcs_map(u32 nchain, enum ieee80211_vht_mcs_support supp)
5384{
5385 u16 mcs_map;
5386 int i;
5387
5388 for (i = 0, mcs_map = 0xFFFF; i < nchain; i++)
5389 mcs_map = (mcs_map << 2) | supp;
5390
5391 return cpu_to_le16(mcs_map);
5392}
5393
5394static void brcmf_update_vht_cap(struct ieee80211_supported_band *band,
5395 u32 bw_cap[2], u32 nchain)
5396{
5397 __le16 mcs_map;
5398
5399 /* not allowed in 2.4G band */
5400 if (band->band == IEEE80211_BAND_2GHZ)
5401 return;
5402
5403 band->vht_cap.vht_supported = true;
5404 /* 80MHz is mandatory */
5405 band->vht_cap.cap |= IEEE80211_VHT_CAP_SHORT_GI_80;
5406 if (bw_cap[band->band] & WLC_BW_160MHZ_BIT) {
5407 band->vht_cap.cap |= IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
5408 band->vht_cap.cap |= IEEE80211_VHT_CAP_SHORT_GI_160;
5409 }
5410 /* all support 256-QAM */
5411 mcs_map = brcmf_get_mcs_map(nchain, IEEE80211_VHT_MCS_SUPPORT_0_9);
5412 band->vht_cap.vht_mcs.rx_mcs_map = mcs_map;
5413 band->vht_cap.vht_mcs.tx_mcs_map = mcs_map;
5414}
5415
5326static s32 brcmf_update_wiphybands(struct brcmf_cfg80211_info *cfg) 5416static s32 brcmf_update_wiphybands(struct brcmf_cfg80211_info *cfg)
5327{ 5417{
5328 struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg)); 5418 struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg));
5329 struct wiphy *wiphy; 5419 struct wiphy *wiphy;
5330 s32 phy_list; 5420 s32 phy_list;
5331 u32 band_list[3]; 5421 u32 band_list[3];
5332 u32 nmode; 5422 u32 nmode = 0;
5423 u32 vhtmode = 0;
5333 u32 bw_cap[2] = { 0, 0 }; 5424 u32 bw_cap[2] = { 0, 0 };
5334 u32 rxchain; 5425 u32 rxchain;
5335 u32 nchain; 5426 u32 nchain;
@@ -5360,14 +5451,16 @@ static s32 brcmf_update_wiphybands(struct brcmf_cfg80211_info *cfg)
5360 brcmf_dbg(INFO, "BRCMF_C_GET_BANDLIST reported: 0x%08x 0x%08x 0x%08x phy\n", 5451 brcmf_dbg(INFO, "BRCMF_C_GET_BANDLIST reported: 0x%08x 0x%08x 0x%08x phy\n",
5361 band_list[0], band_list[1], band_list[2]); 5452 band_list[0], band_list[1], band_list[2]);
5362 5453
5454 (void)brcmf_fil_iovar_int_get(ifp, "vhtmode", &vhtmode);
5363 err = brcmf_fil_iovar_int_get(ifp, "nmode", &nmode); 5455 err = brcmf_fil_iovar_int_get(ifp, "nmode", &nmode);
5364 if (err) { 5456 if (err) {
5365 brcmf_err("nmode error (%d)\n", err); 5457 brcmf_err("nmode error (%d)\n", err);
5366 } else { 5458 } else {
5367 brcmf_get_bwcap(ifp, bw_cap); 5459 brcmf_get_bwcap(ifp, bw_cap);
5368 } 5460 }
5369 brcmf_dbg(INFO, "nmode=%d, bw_cap=(%d, %d)\n", nmode, 5461 brcmf_dbg(INFO, "nmode=%d, vhtmode=%d, bw_cap=(%d, %d)\n",
5370 bw_cap[IEEE80211_BAND_2GHZ], bw_cap[IEEE80211_BAND_5GHZ]); 5462 nmode, vhtmode, bw_cap[IEEE80211_BAND_2GHZ],
5463 bw_cap[IEEE80211_BAND_5GHZ]);
5371 5464
5372 err = brcmf_fil_iovar_int_get(ifp, "rxchain", &rxchain); 5465 err = brcmf_fil_iovar_int_get(ifp, "rxchain", &rxchain);
5373 if (err) { 5466 if (err) {
@@ -5398,17 +5491,10 @@ static s32 brcmf_update_wiphybands(struct brcmf_cfg80211_info *cfg)
5398 else 5491 else
5399 continue; 5492 continue;
5400 5493
5401 if (bw_cap[band->band] & WLC_BW_40MHZ_BIT) { 5494 if (nmode)
5402 band->ht_cap.cap |= IEEE80211_HT_CAP_SGI_40; 5495 brcmf_update_ht_cap(band, bw_cap, nchain);
5403 band->ht_cap.cap |= IEEE80211_HT_CAP_SUP_WIDTH_20_40; 5496 if (vhtmode)
5404 } 5497 brcmf_update_vht_cap(band, bw_cap, nchain);
5405 band->ht_cap.cap |= IEEE80211_HT_CAP_SGI_20;
5406 band->ht_cap.cap |= IEEE80211_HT_CAP_DSSSCCK40;
5407 band->ht_cap.ht_supported = true;
5408 band->ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
5409 band->ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_16;
5410 memset(band->ht_cap.mcs.rx_mask, 0xff, nchain);
5411 band->ht_cap.mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
5412 bands[band->band] = band; 5498 bands[band->band] = band;
5413 } 5499 }
5414 5500
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/main.c b/drivers/net/wireless/brcm80211/brcmsmac/main.c
index 9417cb5a2553..af8ba64ace39 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/main.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/main.c
@@ -4870,14 +4870,11 @@ static void brcms_c_detach_module(struct brcms_c_info *wlc)
4870/* 4870/*
4871 * low level detach 4871 * low level detach
4872 */ 4872 */
4873static int brcms_b_detach(struct brcms_c_info *wlc) 4873static void brcms_b_detach(struct brcms_c_info *wlc)
4874{ 4874{
4875 uint i; 4875 uint i;
4876 struct brcms_hw_band *band; 4876 struct brcms_hw_band *band;
4877 struct brcms_hardware *wlc_hw = wlc->hw; 4877 struct brcms_hardware *wlc_hw = wlc->hw;
4878 int callbacks;
4879
4880 callbacks = 0;
4881 4878
4882 brcms_b_detach_dmapio(wlc_hw); 4879 brcms_b_detach_dmapio(wlc_hw);
4883 4880
@@ -4900,9 +4897,6 @@ static int brcms_b_detach(struct brcms_c_info *wlc)
4900 ai_detach(wlc_hw->sih); 4897 ai_detach(wlc_hw->sih);
4901 wlc_hw->sih = NULL; 4898 wlc_hw->sih = NULL;
4902 } 4899 }
4903
4904 return callbacks;
4905
4906} 4900}
4907 4901
4908/* 4902/*
@@ -4917,14 +4911,15 @@ static int brcms_b_detach(struct brcms_c_info *wlc)
4917 */ 4911 */
4918uint brcms_c_detach(struct brcms_c_info *wlc) 4912uint brcms_c_detach(struct brcms_c_info *wlc)
4919{ 4913{
4920 uint callbacks = 0; 4914 uint callbacks;
4921 4915
4922 if (wlc == NULL) 4916 if (wlc == NULL)
4923 return 0; 4917 return 0;
4924 4918
4925 callbacks += brcms_b_detach(wlc); 4919 brcms_b_detach(wlc);
4926 4920
4927 /* delete software timers */ 4921 /* delete software timers */
4922 callbacks = 0;
4928 if (!brcms_c_radio_monitor_stop(wlc)) 4923 if (!brcms_c_radio_monitor_stop(wlc))
4929 callbacks++; 4924 callbacks++;
4930 4925
diff --git a/drivers/net/wireless/brcm80211/brcmutil/d11.c b/drivers/net/wireless/brcm80211/brcmutil/d11.c
index 30e54e2c6c9b..6cbc33d0fc19 100644
--- a/drivers/net/wireless/brcm80211/brcmutil/d11.c
+++ b/drivers/net/wireless/brcm80211/brcmutil/d11.c
@@ -21,43 +21,81 @@
21#include <brcmu_wifi.h> 21#include <brcmu_wifi.h>
22#include <brcmu_d11.h> 22#include <brcmu_d11.h>
23 23
24static void brcmu_d11n_encchspec(struct brcmu_chan *ch) 24static u16 d11n_sb(enum brcmu_chan_sb sb)
25{ 25{
26 ch->chspec = ch->chnum & BRCMU_CHSPEC_CH_MASK; 26 switch (sb) {
27 case BRCMU_CHAN_SB_NONE:
28 return BRCMU_CHSPEC_D11N_SB_N;
29 case BRCMU_CHAN_SB_L:
30 return BRCMU_CHSPEC_D11N_SB_L;
31 case BRCMU_CHAN_SB_U:
32 return BRCMU_CHSPEC_D11N_SB_U;
33 default:
34 WARN_ON(1);
35 }
36 return 0;
37}
27 38
28 switch (ch->bw) { 39static u16 d11n_bw(enum brcmu_chan_bw bw)
40{
41 switch (bw) {
29 case BRCMU_CHAN_BW_20: 42 case BRCMU_CHAN_BW_20:
30 ch->chspec |= BRCMU_CHSPEC_D11N_BW_20 | BRCMU_CHSPEC_D11N_SB_N; 43 return BRCMU_CHSPEC_D11N_BW_20;
31 break;
32 case BRCMU_CHAN_BW_40: 44 case BRCMU_CHAN_BW_40:
45 return BRCMU_CHSPEC_D11N_BW_40;
33 default: 46 default:
34 WARN_ON_ONCE(1); 47 WARN_ON(1);
35 break;
36 } 48 }
49 return 0;
50}
37 51
52static void brcmu_d11n_encchspec(struct brcmu_chan *ch)
53{
54 if (ch->bw == BRCMU_CHAN_BW_20)
55 ch->sb = BRCMU_CHAN_SB_NONE;
56
57 brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_CH_MASK,
58 BRCMU_CHSPEC_CH_SHIFT, ch->chnum);
59 brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11N_SB_MASK,
60 0, d11n_sb(ch->sb));
61 brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11N_BW_MASK,
62 0, d11n_bw(ch->bw));
63
64 ch->chspec &= ~BRCMU_CHSPEC_D11N_BND_MASK;
38 if (ch->chnum <= CH_MAX_2G_CHANNEL) 65 if (ch->chnum <= CH_MAX_2G_CHANNEL)
39 ch->chspec |= BRCMU_CHSPEC_D11N_BND_2G; 66 ch->chspec |= BRCMU_CHSPEC_D11N_BND_2G;
40 else 67 else
41 ch->chspec |= BRCMU_CHSPEC_D11N_BND_5G; 68 ch->chspec |= BRCMU_CHSPEC_D11N_BND_5G;
42} 69}
43 70
44static void brcmu_d11ac_encchspec(struct brcmu_chan *ch) 71static u16 d11ac_bw(enum brcmu_chan_bw bw)
45{ 72{
46 ch->chspec = ch->chnum & BRCMU_CHSPEC_CH_MASK; 73 switch (bw) {
47
48 switch (ch->bw) {
49 case BRCMU_CHAN_BW_20: 74 case BRCMU_CHAN_BW_20:
50 ch->chspec |= BRCMU_CHSPEC_D11AC_BW_20; 75 return BRCMU_CHSPEC_D11AC_BW_20;
51 break;
52 case BRCMU_CHAN_BW_40: 76 case BRCMU_CHAN_BW_40:
77 return BRCMU_CHSPEC_D11AC_BW_40;
53 case BRCMU_CHAN_BW_80: 78 case BRCMU_CHAN_BW_80:
54 case BRCMU_CHAN_BW_80P80: 79 return BRCMU_CHSPEC_D11AC_BW_80;
55 case BRCMU_CHAN_BW_160:
56 default: 80 default:
57 WARN_ON_ONCE(1); 81 WARN_ON(1);
58 break;
59 } 82 }
83 return 0;
84}
60 85
86static void brcmu_d11ac_encchspec(struct brcmu_chan *ch)
87{
88 if (ch->bw == BRCMU_CHAN_BW_20 || ch->sb == BRCMU_CHAN_SB_NONE)
89 ch->sb = BRCMU_CHAN_SB_L;
90
91 brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_CH_MASK,
92 BRCMU_CHSPEC_CH_SHIFT, ch->chnum);
93 brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11AC_SB_MASK,
94 BRCMU_CHSPEC_D11AC_SB_SHIFT, ch->sb);
95 brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11AC_BW_MASK,
96 0, d11ac_bw(ch->bw));
97
98 ch->chspec &= ~BRCMU_CHSPEC_D11AC_BND_MASK;
61 if (ch->chnum <= CH_MAX_2G_CHANNEL) 99 if (ch->chnum <= CH_MAX_2G_CHANNEL)
62 ch->chspec |= BRCMU_CHSPEC_D11AC_BND_2G; 100 ch->chspec |= BRCMU_CHSPEC_D11AC_BND_2G;
63 else 101 else
@@ -73,6 +111,7 @@ static void brcmu_d11n_decchspec(struct brcmu_chan *ch)
73 switch (ch->chspec & BRCMU_CHSPEC_D11N_BW_MASK) { 111 switch (ch->chspec & BRCMU_CHSPEC_D11N_BW_MASK) {
74 case BRCMU_CHSPEC_D11N_BW_20: 112 case BRCMU_CHSPEC_D11N_BW_20:
75 ch->bw = BRCMU_CHAN_BW_20; 113 ch->bw = BRCMU_CHAN_BW_20;
114 ch->sb = BRCMU_CHAN_SB_NONE;
76 break; 115 break;
77 case BRCMU_CHSPEC_D11N_BW_40: 116 case BRCMU_CHSPEC_D11N_BW_40:
78 ch->bw = BRCMU_CHAN_BW_40; 117 ch->bw = BRCMU_CHAN_BW_40;
@@ -112,6 +151,7 @@ static void brcmu_d11ac_decchspec(struct brcmu_chan *ch)
112 switch (ch->chspec & BRCMU_CHSPEC_D11AC_BW_MASK) { 151 switch (ch->chspec & BRCMU_CHSPEC_D11AC_BW_MASK) {
113 case BRCMU_CHSPEC_D11AC_BW_20: 152 case BRCMU_CHSPEC_D11AC_BW_20:
114 ch->bw = BRCMU_CHAN_BW_20; 153 ch->bw = BRCMU_CHAN_BW_20;
154 ch->sb = BRCMU_CHAN_SB_NONE;
115 break; 155 break;
116 case BRCMU_CHSPEC_D11AC_BW_40: 156 case BRCMU_CHSPEC_D11AC_BW_40:
117 ch->bw = BRCMU_CHAN_BW_40; 157 ch->bw = BRCMU_CHAN_BW_40;
@@ -128,6 +168,25 @@ static void brcmu_d11ac_decchspec(struct brcmu_chan *ch)
128 break; 168 break;
129 case BRCMU_CHSPEC_D11AC_BW_80: 169 case BRCMU_CHSPEC_D11AC_BW_80:
130 ch->bw = BRCMU_CHAN_BW_80; 170 ch->bw = BRCMU_CHAN_BW_80;
171 ch->sb = brcmu_maskget16(ch->chspec, BRCMU_CHSPEC_D11AC_SB_MASK,
172 BRCMU_CHSPEC_D11AC_SB_SHIFT);
173 switch (ch->sb) {
174 case BRCMU_CHAN_SB_LL:
175 ch->chnum -= CH_30MHZ_APART;
176 break;
177 case BRCMU_CHAN_SB_LU:
178 ch->chnum -= CH_10MHZ_APART;
179 break;
180 case BRCMU_CHAN_SB_UL:
181 ch->chnum += CH_10MHZ_APART;
182 break;
183 case BRCMU_CHAN_SB_UU:
184 ch->chnum += CH_30MHZ_APART;
185 break;
186 default:
187 WARN_ON_ONCE(1);
188 break;
189 }
131 break; 190 break;
132 case BRCMU_CHSPEC_D11AC_BW_8080: 191 case BRCMU_CHSPEC_D11AC_BW_8080:
133 case BRCMU_CHSPEC_D11AC_BW_160: 192 case BRCMU_CHSPEC_D11AC_BW_160:
diff --git a/drivers/net/wireless/brcm80211/include/brcmu_d11.h b/drivers/net/wireless/brcm80211/include/brcmu_d11.h
index 8660a2cba098..f9745ea8b3e0 100644
--- a/drivers/net/wireless/brcm80211/include/brcmu_d11.h
+++ b/drivers/net/wireless/brcm80211/include/brcmu_d11.h
@@ -108,13 +108,7 @@ enum brcmu_chan_bw {
108}; 108};
109 109
110enum brcmu_chan_sb { 110enum brcmu_chan_sb {
111 BRCMU_CHAN_SB_NONE = 0, 111 BRCMU_CHAN_SB_NONE = -1,
112 BRCMU_CHAN_SB_L,
113 BRCMU_CHAN_SB_U,
114 BRCMU_CHAN_SB_LL,
115 BRCMU_CHAN_SB_LU,
116 BRCMU_CHAN_SB_UL,
117 BRCMU_CHAN_SB_UU,
118 BRCMU_CHAN_SB_LLL, 112 BRCMU_CHAN_SB_LLL,
119 BRCMU_CHAN_SB_LLU, 113 BRCMU_CHAN_SB_LLU,
120 BRCMU_CHAN_SB_LUL, 114 BRCMU_CHAN_SB_LUL,
@@ -123,6 +117,12 @@ enum brcmu_chan_sb {
123 BRCMU_CHAN_SB_ULU, 117 BRCMU_CHAN_SB_ULU,
124 BRCMU_CHAN_SB_UUL, 118 BRCMU_CHAN_SB_UUL,
125 BRCMU_CHAN_SB_UUU, 119 BRCMU_CHAN_SB_UUU,
120 BRCMU_CHAN_SB_L = BRCMU_CHAN_SB_LLL,
121 BRCMU_CHAN_SB_U = BRCMU_CHAN_SB_LLU,
122 BRCMU_CHAN_SB_LL = BRCMU_CHAN_SB_LLL,
123 BRCMU_CHAN_SB_LU = BRCMU_CHAN_SB_LLU,
124 BRCMU_CHAN_SB_UL = BRCMU_CHAN_SB_LUL,
125 BRCMU_CHAN_SB_UU = BRCMU_CHAN_SB_LUU,
126}; 126};
127 127
128struct brcmu_chan { 128struct brcmu_chan {
diff --git a/drivers/net/wireless/brcm80211/include/brcmu_wifi.h b/drivers/net/wireless/brcm80211/include/brcmu_wifi.h
index 74419d4bd123..76b5d3a86294 100644
--- a/drivers/net/wireless/brcm80211/include/brcmu_wifi.h
+++ b/drivers/net/wireless/brcm80211/include/brcmu_wifi.h
@@ -29,6 +29,7 @@
29#define CH_UPPER_SB 0x01 29#define CH_UPPER_SB 0x01
30#define CH_LOWER_SB 0x02 30#define CH_LOWER_SB 0x02
31#define CH_EWA_VALID 0x04 31#define CH_EWA_VALID 0x04
32#define CH_30MHZ_APART 6
32#define CH_20MHZ_APART 4 33#define CH_20MHZ_APART 4
33#define CH_10MHZ_APART 2 34#define CH_10MHZ_APART 2
34#define CH_5MHZ_APART 1 /* 2G band channels are 5 Mhz apart */ 35#define CH_5MHZ_APART 1 /* 2G band channels are 5 Mhz apart */
diff --git a/drivers/net/wireless/iwlwifi/Kconfig b/drivers/net/wireless/iwlwifi/Kconfig
index 74b3b4de7bb7..7fd50428b934 100644
--- a/drivers/net/wireless/iwlwifi/Kconfig
+++ b/drivers/net/wireless/iwlwifi/Kconfig
@@ -2,10 +2,6 @@ config IWLWIFI
2 tristate "Intel Wireless WiFi Next Gen AGN - Wireless-N/Advanced-N/Ultimate-N (iwlwifi) " 2 tristate "Intel Wireless WiFi Next Gen AGN - Wireless-N/Advanced-N/Ultimate-N (iwlwifi) "
3 depends on PCI && MAC80211 && HAS_IOMEM 3 depends on PCI && MAC80211 && HAS_IOMEM
4 select FW_LOADER 4 select FW_LOADER
5 select NEW_LEDS
6 select LEDS_CLASS
7 select LEDS_TRIGGERS
8 select MAC80211_LEDS
9 ---help--- 5 ---help---
10 Select to build the driver supporting the: 6 Select to build the driver supporting the:
11 7
@@ -43,6 +39,14 @@ config IWLWIFI
43 say M here and read <file:Documentation/kbuild/modules.txt>. The 39 say M here and read <file:Documentation/kbuild/modules.txt>. The
44 module will be called iwlwifi. 40 module will be called iwlwifi.
45 41
42config IWLWIFI_LEDS
43 bool
44 depends on IWLWIFI
45 depends on LEDS_CLASS=y || LEDS_CLASS=IWLWIFI
46 select LEDS_TRIGGERS
47 select MAC80211_LEDS
48 default y
49
46config IWLDVM 50config IWLDVM
47 tristate "Intel Wireless WiFi DVM Firmware support" 51 tristate "Intel Wireless WiFi DVM Firmware support"
48 depends on IWLWIFI 52 depends on IWLWIFI
@@ -124,7 +128,6 @@ config IWLWIFI_DEBUG_EXPERIMENTAL_UCODE
124 Enable use of experimental ucode for testing and debugging. 128 Enable use of experimental ucode for testing and debugging.
125 129
126config IWLWIFI_DEVICE_TRACING 130config IWLWIFI_DEVICE_TRACING
127
128 bool "iwlwifi device access tracing" 131 bool "iwlwifi device access tracing"
129 depends on IWLWIFI 132 depends on IWLWIFI
130 depends on EVENT_TRACING 133 depends on EVENT_TRACING
diff --git a/drivers/net/wireless/iwlwifi/dvm/Makefile b/drivers/net/wireless/iwlwifi/dvm/Makefile
index dce7ab2e0c4b..4d19685f31c3 100644
--- a/drivers/net/wireless/iwlwifi/dvm/Makefile
+++ b/drivers/net/wireless/iwlwifi/dvm/Makefile
@@ -4,9 +4,10 @@ iwldvm-objs += main.o rs.o mac80211.o ucode.o tx.o
4iwldvm-objs += lib.o calib.o tt.o sta.o rx.o 4iwldvm-objs += lib.o calib.o tt.o sta.o rx.o
5 5
6iwldvm-objs += power.o 6iwldvm-objs += power.o
7iwldvm-objs += scan.o led.o 7iwldvm-objs += scan.o
8iwldvm-objs += rxon.o devices.o 8iwldvm-objs += rxon.o devices.o
9 9
10iwldvm-$(CONFIG_IWLWIFI_LEDS) += led.o
10iwldvm-$(CONFIG_IWLWIFI_DEBUGFS) += debugfs.o 11iwldvm-$(CONFIG_IWLWIFI_DEBUGFS) += debugfs.o
11 12
12ccflags-y += -D__CHECK_ENDIAN__ -I$(src)/../ 13ccflags-y += -D__CHECK_ENDIAN__ -I$(src)/../
diff --git a/drivers/net/wireless/iwlwifi/dvm/calib.c b/drivers/net/wireless/iwlwifi/dvm/calib.c
index be1086c87157..20e6aa910700 100644
--- a/drivers/net/wireless/iwlwifi/dvm/calib.c
+++ b/drivers/net/wireless/iwlwifi/dvm/calib.c
@@ -94,7 +94,6 @@ int iwl_send_calib_results(struct iwl_priv *priv)
94{ 94{
95 struct iwl_host_cmd hcmd = { 95 struct iwl_host_cmd hcmd = {
96 .id = REPLY_PHY_CALIBRATION_CMD, 96 .id = REPLY_PHY_CALIBRATION_CMD,
97 .flags = CMD_SYNC,
98 }; 97 };
99 struct iwl_calib_result *res; 98 struct iwl_calib_result *res;
100 99
diff --git a/drivers/net/wireless/iwlwifi/dvm/debugfs.c b/drivers/net/wireless/iwlwifi/dvm/debugfs.c
index d2fe2596d54e..0ffb6ff1a255 100644
--- a/drivers/net/wireless/iwlwifi/dvm/debugfs.c
+++ b/drivers/net/wireless/iwlwifi/dvm/debugfs.c
@@ -1481,7 +1481,7 @@ static ssize_t iwl_dbgfs_ucode_bt_stats_read(struct file *file,
1481 1481
1482 /* make request to uCode to retrieve statistics information */ 1482 /* make request to uCode to retrieve statistics information */
1483 mutex_lock(&priv->mutex); 1483 mutex_lock(&priv->mutex);
1484 ret = iwl_send_statistics_request(priv, CMD_SYNC, false); 1484 ret = iwl_send_statistics_request(priv, 0, false);
1485 mutex_unlock(&priv->mutex); 1485 mutex_unlock(&priv->mutex);
1486 1486
1487 if (ret) 1487 if (ret)
@@ -1868,7 +1868,7 @@ static ssize_t iwl_dbgfs_clear_ucode_statistics_write(struct file *file,
1868 1868
1869 /* make request to uCode to retrieve statistics information */ 1869 /* make request to uCode to retrieve statistics information */
1870 mutex_lock(&priv->mutex); 1870 mutex_lock(&priv->mutex);
1871 iwl_send_statistics_request(priv, CMD_SYNC, true); 1871 iwl_send_statistics_request(priv, 0, true);
1872 mutex_unlock(&priv->mutex); 1872 mutex_unlock(&priv->mutex);
1873 1873
1874 return count; 1874 return count;
@@ -2188,7 +2188,6 @@ static int iwl_cmd_echo_test(struct iwl_priv *priv)
2188 struct iwl_host_cmd cmd = { 2188 struct iwl_host_cmd cmd = {
2189 .id = REPLY_ECHO, 2189 .id = REPLY_ECHO,
2190 .len = { 0 }, 2190 .len = { 0 },
2191 .flags = CMD_SYNC,
2192 }; 2191 };
2193 2192
2194 ret = iwl_dvm_send_cmd(priv, &cmd); 2193 ret = iwl_dvm_send_cmd(priv, &cmd);
@@ -2320,7 +2319,7 @@ static ssize_t iwl_dbgfs_fw_restart_write(struct file *file,
2320 mutex_lock(&priv->mutex); 2319 mutex_lock(&priv->mutex);
2321 2320
2322 /* take the return value to make compiler happy - it will fail anyway */ 2321 /* take the return value to make compiler happy - it will fail anyway */
2323 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_ERROR, CMD_SYNC, 0, NULL); 2322 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_ERROR, 0, 0, NULL);
2324 2323
2325 mutex_unlock(&priv->mutex); 2324 mutex_unlock(&priv->mutex);
2326 2325
diff --git a/drivers/net/wireless/iwlwifi/dvm/dev.h b/drivers/net/wireless/iwlwifi/dvm/dev.h
index 3441f70d0ff9..a6f22c32a279 100644
--- a/drivers/net/wireless/iwlwifi/dvm/dev.h
+++ b/drivers/net/wireless/iwlwifi/dvm/dev.h
@@ -888,9 +888,11 @@ struct iwl_priv {
888 888
889 struct iwl_event_log event_log; 889 struct iwl_event_log event_log;
890 890
891#ifdef CONFIG_IWLWIFI_LEDS
891 struct led_classdev led; 892 struct led_classdev led;
892 unsigned long blink_on, blink_off; 893 unsigned long blink_on, blink_off;
893 bool led_registered; 894 bool led_registered;
895#endif
894 896
895 /* WoWLAN GTK rekey data */ 897 /* WoWLAN GTK rekey data */
896 u8 kck[NL80211_KCK_LEN], kek[NL80211_KEK_LEN]; 898 u8 kck[NL80211_KCK_LEN], kek[NL80211_KEK_LEN];
diff --git a/drivers/net/wireless/iwlwifi/dvm/devices.c b/drivers/net/wireless/iwlwifi/dvm/devices.c
index 758c54eeb206..34b41e5f7cfc 100644
--- a/drivers/net/wireless/iwlwifi/dvm/devices.c
+++ b/drivers/net/wireless/iwlwifi/dvm/devices.c
@@ -417,7 +417,6 @@ static int iwl5000_hw_channel_switch(struct iwl_priv *priv,
417 struct iwl_host_cmd hcmd = { 417 struct iwl_host_cmd hcmd = {
418 .id = REPLY_CHANNEL_SWITCH, 418 .id = REPLY_CHANNEL_SWITCH,
419 .len = { sizeof(cmd), }, 419 .len = { sizeof(cmd), },
420 .flags = CMD_SYNC,
421 .data = { &cmd, }, 420 .data = { &cmd, },
422 }; 421 };
423 422
@@ -579,7 +578,6 @@ static int iwl6000_hw_channel_switch(struct iwl_priv *priv,
579 struct iwl_host_cmd hcmd = { 578 struct iwl_host_cmd hcmd = {
580 .id = REPLY_CHANNEL_SWITCH, 579 .id = REPLY_CHANNEL_SWITCH,
581 .len = { sizeof(*cmd), }, 580 .len = { sizeof(*cmd), },
582 .flags = CMD_SYNC,
583 .dataflags[0] = IWL_HCMD_DFL_NOCOPY, 581 .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
584 }; 582 };
585 int err; 583 int err;
diff --git a/drivers/net/wireless/iwlwifi/dvm/led.h b/drivers/net/wireless/iwlwifi/dvm/led.h
index 6a0817d9c4fa..1c6b2252d0f2 100644
--- a/drivers/net/wireless/iwlwifi/dvm/led.h
+++ b/drivers/net/wireless/iwlwifi/dvm/led.h
@@ -36,8 +36,20 @@ struct iwl_priv;
36#define IWL_LED_ACTIVITY (0<<1) 36#define IWL_LED_ACTIVITY (0<<1)
37#define IWL_LED_LINK (1<<1) 37#define IWL_LED_LINK (1<<1)
38 38
39#ifdef CONFIG_IWLWIFI_LEDS
39void iwlagn_led_enable(struct iwl_priv *priv); 40void iwlagn_led_enable(struct iwl_priv *priv);
40void iwl_leds_init(struct iwl_priv *priv); 41void iwl_leds_init(struct iwl_priv *priv);
41void iwl_leds_exit(struct iwl_priv *priv); 42void iwl_leds_exit(struct iwl_priv *priv);
43#else
44static inline void iwlagn_led_enable(struct iwl_priv *priv)
45{
46}
47static inline void iwl_leds_init(struct iwl_priv *priv)
48{
49}
50static inline void iwl_leds_exit(struct iwl_priv *priv)
51{
52}
53#endif
42 54
43#endif /* __iwl_leds_h__ */ 55#endif /* __iwl_leds_h__ */
diff --git a/drivers/net/wireless/iwlwifi/dvm/lib.c b/drivers/net/wireless/iwlwifi/dvm/lib.c
index d169228f59e7..2191621d69c1 100644
--- a/drivers/net/wireless/iwlwifi/dvm/lib.c
+++ b/drivers/net/wireless/iwlwifi/dvm/lib.c
@@ -81,7 +81,7 @@ int iwlagn_send_tx_power(struct iwl_priv *priv)
81 else 81 else
82 tx_ant_cfg_cmd = REPLY_TX_POWER_DBM_CMD; 82 tx_ant_cfg_cmd = REPLY_TX_POWER_DBM_CMD;
83 83
84 return iwl_dvm_send_cmd_pdu(priv, tx_ant_cfg_cmd, CMD_SYNC, 84 return iwl_dvm_send_cmd_pdu(priv, tx_ant_cfg_cmd, 0,
85 sizeof(tx_power_cmd), &tx_power_cmd); 85 sizeof(tx_power_cmd), &tx_power_cmd);
86} 86}
87 87
@@ -141,7 +141,6 @@ int iwlagn_txfifo_flush(struct iwl_priv *priv, u32 scd_q_msk)
141 struct iwl_host_cmd cmd = { 141 struct iwl_host_cmd cmd = {
142 .id = REPLY_TXFIFO_FLUSH, 142 .id = REPLY_TXFIFO_FLUSH,
143 .len = { sizeof(struct iwl_txfifo_flush_cmd), }, 143 .len = { sizeof(struct iwl_txfifo_flush_cmd), },
144 .flags = CMD_SYNC,
145 .data = { &flush_cmd, }, 144 .data = { &flush_cmd, },
146 }; 145 };
147 146
@@ -333,12 +332,12 @@ void iwlagn_send_advance_bt_config(struct iwl_priv *priv)
333 memcpy(&bt_cmd_v2.basic, &basic, 332 memcpy(&bt_cmd_v2.basic, &basic,
334 sizeof(basic)); 333 sizeof(basic));
335 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_BT_CONFIG, 334 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_BT_CONFIG,
336 CMD_SYNC, sizeof(bt_cmd_v2), &bt_cmd_v2); 335 0, sizeof(bt_cmd_v2), &bt_cmd_v2);
337 } else { 336 } else {
338 memcpy(&bt_cmd_v1.basic, &basic, 337 memcpy(&bt_cmd_v1.basic, &basic,
339 sizeof(basic)); 338 sizeof(basic));
340 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_BT_CONFIG, 339 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_BT_CONFIG,
341 CMD_SYNC, sizeof(bt_cmd_v1), &bt_cmd_v1); 340 0, sizeof(bt_cmd_v1), &bt_cmd_v1);
342 } 341 }
343 if (ret) 342 if (ret)
344 IWL_ERR(priv, "failed to send BT Coex Config\n"); 343 IWL_ERR(priv, "failed to send BT Coex Config\n");
@@ -1044,7 +1043,6 @@ int iwlagn_send_patterns(struct iwl_priv *priv,
1044 struct iwl_host_cmd cmd = { 1043 struct iwl_host_cmd cmd = {
1045 .id = REPLY_WOWLAN_PATTERNS, 1044 .id = REPLY_WOWLAN_PATTERNS,
1046 .dataflags[0] = IWL_HCMD_DFL_NOCOPY, 1045 .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
1047 .flags = CMD_SYNC,
1048 }; 1046 };
1049 int i, err; 1047 int i, err;
1050 1048
@@ -1201,7 +1199,6 @@ int iwlagn_suspend(struct iwl_priv *priv, struct cfg80211_wowlan *wowlan)
1201 if (key_data.use_rsc_tsc) { 1199 if (key_data.use_rsc_tsc) {
1202 struct iwl_host_cmd rsc_tsc_cmd = { 1200 struct iwl_host_cmd rsc_tsc_cmd = {
1203 .id = REPLY_WOWLAN_TSC_RSC_PARAMS, 1201 .id = REPLY_WOWLAN_TSC_RSC_PARAMS,
1204 .flags = CMD_SYNC,
1205 .data[0] = key_data.rsc_tsc, 1202 .data[0] = key_data.rsc_tsc,
1206 .dataflags[0] = IWL_HCMD_DFL_NOCOPY, 1203 .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
1207 .len[0] = sizeof(*key_data.rsc_tsc), 1204 .len[0] = sizeof(*key_data.rsc_tsc),
@@ -1215,7 +1212,7 @@ int iwlagn_suspend(struct iwl_priv *priv, struct cfg80211_wowlan *wowlan)
1215 if (key_data.use_tkip) { 1212 if (key_data.use_tkip) {
1216 ret = iwl_dvm_send_cmd_pdu(priv, 1213 ret = iwl_dvm_send_cmd_pdu(priv,
1217 REPLY_WOWLAN_TKIP_PARAMS, 1214 REPLY_WOWLAN_TKIP_PARAMS,
1218 CMD_SYNC, sizeof(tkip_cmd), 1215 0, sizeof(tkip_cmd),
1219 &tkip_cmd); 1216 &tkip_cmd);
1220 if (ret) 1217 if (ret)
1221 goto out; 1218 goto out;
@@ -1231,20 +1228,20 @@ int iwlagn_suspend(struct iwl_priv *priv, struct cfg80211_wowlan *wowlan)
1231 1228
1232 ret = iwl_dvm_send_cmd_pdu(priv, 1229 ret = iwl_dvm_send_cmd_pdu(priv,
1233 REPLY_WOWLAN_KEK_KCK_MATERIAL, 1230 REPLY_WOWLAN_KEK_KCK_MATERIAL,
1234 CMD_SYNC, sizeof(kek_kck_cmd), 1231 0, sizeof(kek_kck_cmd),
1235 &kek_kck_cmd); 1232 &kek_kck_cmd);
1236 if (ret) 1233 if (ret)
1237 goto out; 1234 goto out;
1238 } 1235 }
1239 } 1236 }
1240 1237
1241 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_D3_CONFIG, CMD_SYNC, 1238 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_D3_CONFIG, 0,
1242 sizeof(d3_cfg_cmd), &d3_cfg_cmd); 1239 sizeof(d3_cfg_cmd), &d3_cfg_cmd);
1243 if (ret) 1240 if (ret)
1244 goto out; 1241 goto out;
1245 1242
1246 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_WOWLAN_WAKEUP_FILTER, 1243 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_WOWLAN_WAKEUP_FILTER,
1247 CMD_SYNC, sizeof(wakeup_filter_cmd), 1244 0, sizeof(wakeup_filter_cmd),
1248 &wakeup_filter_cmd); 1245 &wakeup_filter_cmd);
1249 if (ret) 1246 if (ret)
1250 goto out; 1247 goto out;
diff --git a/drivers/net/wireless/iwlwifi/dvm/main.c b/drivers/net/wireless/iwlwifi/dvm/main.c
index 6a00353768f3..0b7f46f0b079 100644
--- a/drivers/net/wireless/iwlwifi/dvm/main.c
+++ b/drivers/net/wireless/iwlwifi/dvm/main.c
@@ -128,7 +128,6 @@ int iwlagn_send_beacon_cmd(struct iwl_priv *priv)
128 struct iwl_tx_beacon_cmd *tx_beacon_cmd; 128 struct iwl_tx_beacon_cmd *tx_beacon_cmd;
129 struct iwl_host_cmd cmd = { 129 struct iwl_host_cmd cmd = {
130 .id = REPLY_TX_BEACON, 130 .id = REPLY_TX_BEACON,
131 .flags = CMD_SYNC,
132 }; 131 };
133 struct ieee80211_tx_info *info; 132 struct ieee80211_tx_info *info;
134 u32 frame_size; 133 u32 frame_size;
@@ -311,8 +310,7 @@ int iwl_send_statistics_request(struct iwl_priv *priv, u8 flags, bool clear)
311 sizeof(struct iwl_statistics_cmd), 310 sizeof(struct iwl_statistics_cmd),
312 &statistics_cmd); 311 &statistics_cmd);
313 else 312 else
314 return iwl_dvm_send_cmd_pdu(priv, REPLY_STATISTICS_CMD, 313 return iwl_dvm_send_cmd_pdu(priv, REPLY_STATISTICS_CMD, 0,
315 CMD_SYNC,
316 sizeof(struct iwl_statistics_cmd), 314 sizeof(struct iwl_statistics_cmd),
317 &statistics_cmd); 315 &statistics_cmd);
318} 316}
@@ -622,7 +620,7 @@ static void iwl_rf_kill_ct_config(struct iwl_priv *priv)
622 620
623 ret = iwl_dvm_send_cmd_pdu(priv, 621 ret = iwl_dvm_send_cmd_pdu(priv,
624 REPLY_CT_KILL_CONFIG_CMD, 622 REPLY_CT_KILL_CONFIG_CMD,
625 CMD_SYNC, sizeof(adv_cmd), &adv_cmd); 623 0, sizeof(adv_cmd), &adv_cmd);
626 if (ret) 624 if (ret)
627 IWL_ERR(priv, "REPLY_CT_KILL_CONFIG_CMD failed\n"); 625 IWL_ERR(priv, "REPLY_CT_KILL_CONFIG_CMD failed\n");
628 else 626 else
@@ -637,7 +635,7 @@ static void iwl_rf_kill_ct_config(struct iwl_priv *priv)
637 635
638 ret = iwl_dvm_send_cmd_pdu(priv, 636 ret = iwl_dvm_send_cmd_pdu(priv,
639 REPLY_CT_KILL_CONFIG_CMD, 637 REPLY_CT_KILL_CONFIG_CMD,
640 CMD_SYNC, sizeof(cmd), &cmd); 638 0, sizeof(cmd), &cmd);
641 if (ret) 639 if (ret)
642 IWL_ERR(priv, "REPLY_CT_KILL_CONFIG_CMD failed\n"); 640 IWL_ERR(priv, "REPLY_CT_KILL_CONFIG_CMD failed\n");
643 else 641 else
@@ -673,9 +671,7 @@ static int iwlagn_send_tx_ant_config(struct iwl_priv *priv, u8 valid_tx_ant)
673 671
674 if (IWL_UCODE_API(priv->fw->ucode_ver) > 1) { 672 if (IWL_UCODE_API(priv->fw->ucode_ver) > 1) {
675 IWL_DEBUG_HC(priv, "select valid tx ant: %u\n", valid_tx_ant); 673 IWL_DEBUG_HC(priv, "select valid tx ant: %u\n", valid_tx_ant);
676 return iwl_dvm_send_cmd_pdu(priv, 674 return iwl_dvm_send_cmd_pdu(priv, TX_ANT_CONFIGURATION_CMD, 0,
677 TX_ANT_CONFIGURATION_CMD,
678 CMD_SYNC,
679 sizeof(struct iwl_tx_ant_config_cmd), 675 sizeof(struct iwl_tx_ant_config_cmd),
680 &tx_ant_cmd); 676 &tx_ant_cmd);
681 } else { 677 } else {
@@ -703,7 +699,7 @@ static void iwl_send_bt_config(struct iwl_priv *priv)
703 (bt_cmd.flags == BT_COEX_DISABLE) ? "disable" : "active"); 699 (bt_cmd.flags == BT_COEX_DISABLE) ? "disable" : "active");
704 700
705 if (iwl_dvm_send_cmd_pdu(priv, REPLY_BT_CONFIG, 701 if (iwl_dvm_send_cmd_pdu(priv, REPLY_BT_CONFIG,
706 CMD_SYNC, sizeof(struct iwl_bt_cmd), &bt_cmd)) 702 0, sizeof(struct iwl_bt_cmd), &bt_cmd))
707 IWL_ERR(priv, "failed to send BT Coex Config\n"); 703 IWL_ERR(priv, "failed to send BT Coex Config\n");
708} 704}
709 705
@@ -987,7 +983,7 @@ static void iwl_bg_restart(struct work_struct *data)
987 ieee80211_restart_hw(priv->hw); 983 ieee80211_restart_hw(priv->hw);
988 else 984 else
989 IWL_ERR(priv, 985 IWL_ERR(priv,
990 "Cannot request restart before registrating with mac80211"); 986 "Cannot request restart before registrating with mac80211\n");
991 } else { 987 } else {
992 WARN_ON(1); 988 WARN_ON(1);
993 } 989 }
@@ -1127,7 +1123,6 @@ static void iwl_option_config(struct iwl_priv *priv)
1127static int iwl_eeprom_init_hw_params(struct iwl_priv *priv) 1123static int iwl_eeprom_init_hw_params(struct iwl_priv *priv)
1128{ 1124{
1129 struct iwl_nvm_data *data = priv->nvm_data; 1125 struct iwl_nvm_data *data = priv->nvm_data;
1130 char *debug_msg;
1131 1126
1132 if (data->sku_cap_11n_enable && 1127 if (data->sku_cap_11n_enable &&
1133 !priv->cfg->ht_params) { 1128 !priv->cfg->ht_params) {
@@ -1141,8 +1136,8 @@ static int iwl_eeprom_init_hw_params(struct iwl_priv *priv)
1141 return -EINVAL; 1136 return -EINVAL;
1142 } 1137 }
1143 1138
1144 debug_msg = "Device SKU: 24GHz %s %s, 52GHz %s %s, 11.n %s %s\n"; 1139 IWL_DEBUG_INFO(priv,
1145 IWL_DEBUG_INFO(priv, debug_msg, 1140 "Device SKU: 24GHz %s %s, 52GHz %s %s, 11.n %s %s\n",
1146 data->sku_cap_band_24GHz_enable ? "" : "NOT", "enabled", 1141 data->sku_cap_band_24GHz_enable ? "" : "NOT", "enabled",
1147 data->sku_cap_band_52GHz_enable ? "" : "NOT", "enabled", 1142 data->sku_cap_band_52GHz_enable ? "" : "NOT", "enabled",
1148 data->sku_cap_11n_enable ? "" : "NOT", "enabled"); 1143 data->sku_cap_11n_enable ? "" : "NOT", "enabled");
@@ -1350,7 +1345,7 @@ static struct iwl_op_mode *iwl_op_mode_dvm_start(struct iwl_trans *trans,
1350 iwl_set_hw_params(priv); 1345 iwl_set_hw_params(priv);
1351 1346
1352 if (!(priv->nvm_data->sku_cap_ipan_enable)) { 1347 if (!(priv->nvm_data->sku_cap_ipan_enable)) {
1353 IWL_DEBUG_INFO(priv, "Your EEPROM disabled PAN"); 1348 IWL_DEBUG_INFO(priv, "Your EEPROM disabled PAN\n");
1354 ucode_flags &= ~IWL_UCODE_TLV_FLAGS_PAN; 1349 ucode_flags &= ~IWL_UCODE_TLV_FLAGS_PAN;
1355 /* 1350 /*
1356 * if not PAN, then don't support P2P -- might be a uCode 1351 * if not PAN, then don't support P2P -- might be a uCode
@@ -2019,10 +2014,10 @@ void iwlagn_lift_passive_no_rx(struct iwl_priv *priv)
2019 2014
2020 for (mq = 0; mq < IWLAGN_FIRST_AMPDU_QUEUE; mq++) { 2015 for (mq = 0; mq < IWLAGN_FIRST_AMPDU_QUEUE; mq++) {
2021 if (!test_bit(mq, &priv->transport_queue_stop)) { 2016 if (!test_bit(mq, &priv->transport_queue_stop)) {
2022 IWL_DEBUG_TX_QUEUES(priv, "Wake queue %d", mq); 2017 IWL_DEBUG_TX_QUEUES(priv, "Wake queue %d\n", mq);
2023 ieee80211_wake_queue(priv->hw, mq); 2018 ieee80211_wake_queue(priv->hw, mq);
2024 } else { 2019 } else {
2025 IWL_DEBUG_TX_QUEUES(priv, "Don't wake queue %d", mq); 2020 IWL_DEBUG_TX_QUEUES(priv, "Don't wake queue %d\n", mq);
2026 } 2021 }
2027 } 2022 }
2028 2023
diff --git a/drivers/net/wireless/iwlwifi/dvm/power.c b/drivers/net/wireless/iwlwifi/dvm/power.c
index b4e61417013a..f2c1439566b5 100644
--- a/drivers/net/wireless/iwlwifi/dvm/power.c
+++ b/drivers/net/wireless/iwlwifi/dvm/power.c
@@ -278,7 +278,7 @@ static int iwl_set_power(struct iwl_priv *priv, struct iwl_powertable_cmd *cmd)
278 le32_to_cpu(cmd->sleep_interval[3]), 278 le32_to_cpu(cmd->sleep_interval[3]),
279 le32_to_cpu(cmd->sleep_interval[4])); 279 le32_to_cpu(cmd->sleep_interval[4]));
280 280
281 return iwl_dvm_send_cmd_pdu(priv, POWER_TABLE_CMD, CMD_SYNC, 281 return iwl_dvm_send_cmd_pdu(priv, POWER_TABLE_CMD, 0,
282 sizeof(struct iwl_powertable_cmd), cmd); 282 sizeof(struct iwl_powertable_cmd), cmd);
283} 283}
284 284
@@ -361,7 +361,7 @@ int iwl_power_set_mode(struct iwl_priv *priv, struct iwl_powertable_cmd *cmd,
361 361
362 memcpy(&priv->power_data.sleep_cmd, cmd, sizeof(*cmd)); 362 memcpy(&priv->power_data.sleep_cmd, cmd, sizeof(*cmd));
363 } else 363 } else
364 IWL_ERR(priv, "set power fail, ret = %d", ret); 364 IWL_ERR(priv, "set power fail, ret = %d\n", ret);
365 365
366 return ret; 366 return ret;
367} 367}
diff --git a/drivers/net/wireless/iwlwifi/dvm/rs.c b/drivers/net/wireless/iwlwifi/dvm/rs.c
index aa773a2da4ab..32b78a66536d 100644
--- a/drivers/net/wireless/iwlwifi/dvm/rs.c
+++ b/drivers/net/wireless/iwlwifi/dvm/rs.c
@@ -1453,7 +1453,7 @@ static int rs_move_legacy_other(struct iwl_priv *priv,
1453 tbl->action = IWL_LEGACY_SWITCH_SISO; 1453 tbl->action = IWL_LEGACY_SWITCH_SISO;
1454 break; 1454 break;
1455 default: 1455 default:
1456 IWL_ERR(priv, "Invalid BT load %d", priv->bt_traffic_load); 1456 IWL_ERR(priv, "Invalid BT load %d\n", priv->bt_traffic_load);
1457 break; 1457 break;
1458 } 1458 }
1459 1459
@@ -1628,7 +1628,7 @@ static int rs_move_siso_to_other(struct iwl_priv *priv,
1628 tbl->action = IWL_SISO_SWITCH_ANTENNA1; 1628 tbl->action = IWL_SISO_SWITCH_ANTENNA1;
1629 break; 1629 break;
1630 default: 1630 default:
1631 IWL_ERR(priv, "Invalid BT load %d", priv->bt_traffic_load); 1631 IWL_ERR(priv, "Invalid BT load %d\n", priv->bt_traffic_load);
1632 break; 1632 break;
1633 } 1633 }
1634 1634
@@ -1799,7 +1799,7 @@ static int rs_move_mimo2_to_other(struct iwl_priv *priv,
1799 tbl->action = IWL_MIMO2_SWITCH_SISO_A; 1799 tbl->action = IWL_MIMO2_SWITCH_SISO_A;
1800 break; 1800 break;
1801 default: 1801 default:
1802 IWL_ERR(priv, "Invalid BT load %d", priv->bt_traffic_load); 1802 IWL_ERR(priv, "Invalid BT load %d\n", priv->bt_traffic_load);
1803 break; 1803 break;
1804 } 1804 }
1805 1805
@@ -1969,7 +1969,7 @@ static int rs_move_mimo3_to_other(struct iwl_priv *priv,
1969 tbl->action = IWL_MIMO3_SWITCH_SISO_A; 1969 tbl->action = IWL_MIMO3_SWITCH_SISO_A;
1970 break; 1970 break;
1971 default: 1971 default:
1972 IWL_ERR(priv, "Invalid BT load %d", priv->bt_traffic_load); 1972 IWL_ERR(priv, "Invalid BT load %d\n", priv->bt_traffic_load);
1973 break; 1973 break;
1974 } 1974 }
1975 1975
@@ -2709,7 +2709,7 @@ static void rs_initialize_lq(struct iwl_priv *priv,
2709 rs_set_expected_tpt_table(lq_sta, tbl); 2709 rs_set_expected_tpt_table(lq_sta, tbl);
2710 rs_fill_link_cmd(NULL, lq_sta, rate); 2710 rs_fill_link_cmd(NULL, lq_sta, rate);
2711 priv->stations[lq_sta->lq.sta_id].lq = &lq_sta->lq; 2711 priv->stations[lq_sta->lq.sta_id].lq = &lq_sta->lq;
2712 iwl_send_lq_cmd(priv, ctx, &lq_sta->lq, CMD_SYNC, true); 2712 iwl_send_lq_cmd(priv, ctx, &lq_sta->lq, 0, true);
2713} 2713}
2714 2714
2715static void rs_get_rate(void *priv_r, struct ieee80211_sta *sta, void *priv_sta, 2715static void rs_get_rate(void *priv_r, struct ieee80211_sta *sta, void *priv_sta,
diff --git a/drivers/net/wireless/iwlwifi/dvm/rx.c b/drivers/net/wireless/iwlwifi/dvm/rx.c
index cd8377346aff..debec963c610 100644
--- a/drivers/net/wireless/iwlwifi/dvm/rx.c
+++ b/drivers/net/wireless/iwlwifi/dvm/rx.c
@@ -786,7 +786,7 @@ static void iwlagn_pass_packet_to_mac80211(struct iwl_priv *priv,
786 786
787 memcpy(IEEE80211_SKB_RXCB(skb), stats, sizeof(*stats)); 787 memcpy(IEEE80211_SKB_RXCB(skb), stats, sizeof(*stats));
788 788
789 ieee80211_rx_ni(priv->hw, skb); 789 ieee80211_rx(priv->hw, skb);
790} 790}
791 791
792static u32 iwlagn_translate_rx_status(struct iwl_priv *priv, u32 decrypt_in) 792static u32 iwlagn_translate_rx_status(struct iwl_priv *priv, u32 decrypt_in)
diff --git a/drivers/net/wireless/iwlwifi/dvm/rxon.c b/drivers/net/wireless/iwlwifi/dvm/rxon.c
index 503a81e58185..ed50de6362ed 100644
--- a/drivers/net/wireless/iwlwifi/dvm/rxon.c
+++ b/drivers/net/wireless/iwlwifi/dvm/rxon.c
@@ -104,7 +104,7 @@ static int iwlagn_disable_bss(struct iwl_priv *priv,
104 104
105 send->filter_flags &= ~RXON_FILTER_ASSOC_MSK; 105 send->filter_flags &= ~RXON_FILTER_ASSOC_MSK;
106 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd, 106 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd,
107 CMD_SYNC, sizeof(*send), send); 107 0, sizeof(*send), send);
108 108
109 send->filter_flags = old_filter; 109 send->filter_flags = old_filter;
110 110
@@ -134,7 +134,7 @@ static int iwlagn_disable_pan(struct iwl_priv *priv,
134 send->filter_flags &= ~RXON_FILTER_ASSOC_MSK; 134 send->filter_flags &= ~RXON_FILTER_ASSOC_MSK;
135 send->dev_type = RXON_DEV_TYPE_P2P; 135 send->dev_type = RXON_DEV_TYPE_P2P;
136 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd, 136 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd,
137 CMD_SYNC, sizeof(*send), send); 137 0, sizeof(*send), send);
138 138
139 send->filter_flags = old_filter; 139 send->filter_flags = old_filter;
140 send->dev_type = old_dev_type; 140 send->dev_type = old_dev_type;
@@ -160,7 +160,7 @@ static int iwlagn_disconn_pan(struct iwl_priv *priv,
160 int ret; 160 int ret;
161 161
162 send->filter_flags &= ~RXON_FILTER_ASSOC_MSK; 162 send->filter_flags &= ~RXON_FILTER_ASSOC_MSK;
163 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd, CMD_SYNC, 163 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd, 0,
164 sizeof(*send), send); 164 sizeof(*send), send);
165 165
166 send->filter_flags = old_filter; 166 send->filter_flags = old_filter;
@@ -189,7 +189,7 @@ static void iwlagn_update_qos(struct iwl_priv *priv,
189 ctx->qos_data.qos_active, 189 ctx->qos_data.qos_active,
190 ctx->qos_data.def_qos_parm.qos_flags); 190 ctx->qos_data.def_qos_parm.qos_flags);
191 191
192 ret = iwl_dvm_send_cmd_pdu(priv, ctx->qos_cmd, CMD_SYNC, 192 ret = iwl_dvm_send_cmd_pdu(priv, ctx->qos_cmd, 0,
193 sizeof(struct iwl_qosparam_cmd), 193 sizeof(struct iwl_qosparam_cmd),
194 &ctx->qos_data.def_qos_parm); 194 &ctx->qos_data.def_qos_parm);
195 if (ret) 195 if (ret)
@@ -353,7 +353,7 @@ static int iwl_send_rxon_timing(struct iwl_priv *priv,
353 le16_to_cpu(ctx->timing.atim_window)); 353 le16_to_cpu(ctx->timing.atim_window));
354 354
355 return iwl_dvm_send_cmd_pdu(priv, ctx->rxon_timing_cmd, 355 return iwl_dvm_send_cmd_pdu(priv, ctx->rxon_timing_cmd,
356 CMD_SYNC, sizeof(ctx->timing), &ctx->timing); 356 0, sizeof(ctx->timing), &ctx->timing);
357} 357}
358 358
359static int iwlagn_rxon_disconn(struct iwl_priv *priv, 359static int iwlagn_rxon_disconn(struct iwl_priv *priv,
@@ -495,7 +495,7 @@ static int iwlagn_rxon_connect(struct iwl_priv *priv,
495 * Associated RXON doesn't clear the station table in uCode, 495 * Associated RXON doesn't clear the station table in uCode,
496 * so we don't need to restore stations etc. after this. 496 * so we don't need to restore stations etc. after this.
497 */ 497 */
498 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd, CMD_SYNC, 498 ret = iwl_dvm_send_cmd_pdu(priv, ctx->rxon_cmd, 0,
499 sizeof(struct iwl_rxon_cmd), &ctx->staging); 499 sizeof(struct iwl_rxon_cmd), &ctx->staging);
500 if (ret) { 500 if (ret) {
501 IWL_ERR(priv, "Error setting new RXON (%d)\n", ret); 501 IWL_ERR(priv, "Error setting new RXON (%d)\n", ret);
@@ -610,7 +610,7 @@ int iwlagn_set_pan_params(struct iwl_priv *priv)
610 cmd.slots[0].width = cpu_to_le16(slot0); 610 cmd.slots[0].width = cpu_to_le16(slot0);
611 cmd.slots[1].width = cpu_to_le16(slot1); 611 cmd.slots[1].width = cpu_to_le16(slot1);
612 612
613 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_WIPAN_PARAMS, CMD_SYNC, 613 ret = iwl_dvm_send_cmd_pdu(priv, REPLY_WIPAN_PARAMS, 0,
614 sizeof(cmd), &cmd); 614 sizeof(cmd), &cmd);
615 if (ret) 615 if (ret)
616 IWL_ERR(priv, "Error setting PAN parameters (%d)\n", ret); 616 IWL_ERR(priv, "Error setting PAN parameters (%d)\n", ret);
@@ -823,7 +823,7 @@ static int iwl_check_rxon_cmd(struct iwl_priv *priv,
823 823
824 if ((rxon->flags & (RXON_FLG_CCK_MSK | RXON_FLG_AUTO_DETECT_MSK)) 824 if ((rxon->flags & (RXON_FLG_CCK_MSK | RXON_FLG_AUTO_DETECT_MSK))
825 == (RXON_FLG_CCK_MSK | RXON_FLG_AUTO_DETECT_MSK)) { 825 == (RXON_FLG_CCK_MSK | RXON_FLG_AUTO_DETECT_MSK)) {
826 IWL_WARN(priv, "CCK and auto detect"); 826 IWL_WARN(priv, "CCK and auto detect\n");
827 errors |= BIT(8); 827 errors |= BIT(8);
828 } 828 }
829 829
@@ -1395,7 +1395,7 @@ static void iwlagn_chain_noise_reset(struct iwl_priv *priv)
1395 priv->phy_calib_chain_noise_reset_cmd); 1395 priv->phy_calib_chain_noise_reset_cmd);
1396 ret = iwl_dvm_send_cmd_pdu(priv, 1396 ret = iwl_dvm_send_cmd_pdu(priv,
1397 REPLY_PHY_CALIBRATION_CMD, 1397 REPLY_PHY_CALIBRATION_CMD,
1398 CMD_SYNC, sizeof(cmd), &cmd); 1398 0, sizeof(cmd), &cmd);
1399 if (ret) 1399 if (ret)
1400 IWL_ERR(priv, 1400 IWL_ERR(priv,
1401 "Could not send REPLY_PHY_CALIBRATION_CMD\n"); 1401 "Could not send REPLY_PHY_CALIBRATION_CMD\n");
diff --git a/drivers/net/wireless/iwlwifi/dvm/scan.c b/drivers/net/wireless/iwlwifi/dvm/scan.c
index be98b913ed58..43bef901e8f9 100644
--- a/drivers/net/wireless/iwlwifi/dvm/scan.c
+++ b/drivers/net/wireless/iwlwifi/dvm/scan.c
@@ -59,7 +59,7 @@ static int iwl_send_scan_abort(struct iwl_priv *priv)
59 int ret; 59 int ret;
60 struct iwl_host_cmd cmd = { 60 struct iwl_host_cmd cmd = {
61 .id = REPLY_SCAN_ABORT_CMD, 61 .id = REPLY_SCAN_ABORT_CMD,
62 .flags = CMD_SYNC | CMD_WANT_SKB, 62 .flags = CMD_WANT_SKB,
63 }; 63 };
64 __le32 *status; 64 __le32 *status;
65 65
@@ -639,7 +639,6 @@ static int iwlagn_request_scan(struct iwl_priv *priv, struct ieee80211_vif *vif)
639 struct iwl_host_cmd cmd = { 639 struct iwl_host_cmd cmd = {
640 .id = REPLY_SCAN_CMD, 640 .id = REPLY_SCAN_CMD,
641 .len = { sizeof(struct iwl_scan_cmd), }, 641 .len = { sizeof(struct iwl_scan_cmd), },
642 .flags = CMD_SYNC,
643 }; 642 };
644 struct iwl_scan_cmd *scan; 643 struct iwl_scan_cmd *scan;
645 struct iwl_rxon_context *ctx = &priv->contexts[IWL_RXON_CTX_BSS]; 644 struct iwl_rxon_context *ctx = &priv->contexts[IWL_RXON_CTX_BSS];
diff --git a/drivers/net/wireless/iwlwifi/dvm/sta.c b/drivers/net/wireless/iwlwifi/dvm/sta.c
index 9cdd91cdf661..6ec86adbe4a1 100644
--- a/drivers/net/wireless/iwlwifi/dvm/sta.c
+++ b/drivers/net/wireless/iwlwifi/dvm/sta.c
@@ -39,7 +39,7 @@ static int iwl_sta_ucode_activate(struct iwl_priv *priv, u8 sta_id)
39 lockdep_assert_held(&priv->sta_lock); 39 lockdep_assert_held(&priv->sta_lock);
40 40
41 if (sta_id >= IWLAGN_STATION_COUNT) { 41 if (sta_id >= IWLAGN_STATION_COUNT) {
42 IWL_ERR(priv, "invalid sta_id %u", sta_id); 42 IWL_ERR(priv, "invalid sta_id %u\n", sta_id);
43 return -EINVAL; 43 return -EINVAL;
44 } 44 }
45 if (!(priv->stations[sta_id].used & IWL_STA_DRIVER_ACTIVE)) 45 if (!(priv->stations[sta_id].used & IWL_STA_DRIVER_ACTIVE))
@@ -165,7 +165,7 @@ int iwl_send_add_sta(struct iwl_priv *priv,
165 iwl_free_resp(&cmd); 165 iwl_free_resp(&cmd);
166 166
167 if (cmd.handler_status) 167 if (cmd.handler_status)
168 IWL_ERR(priv, "%s - error in the CMD response %d", __func__, 168 IWL_ERR(priv, "%s - error in the CMD response %d\n", __func__,
169 cmd.handler_status); 169 cmd.handler_status);
170 170
171 return cmd.handler_status; 171 return cmd.handler_status;
@@ -261,7 +261,7 @@ int iwl_sta_update_ht(struct iwl_priv *priv, struct iwl_rxon_context *ctx,
261 cmd.station_flags = flags; 261 cmd.station_flags = flags;
262 cmd.sta.sta_id = sta_id; 262 cmd.sta.sta_id = sta_id;
263 263
264 return iwl_send_add_sta(priv, &cmd, CMD_SYNC); 264 return iwl_send_add_sta(priv, &cmd, 0);
265} 265}
266 266
267static void iwl_set_ht_add_station(struct iwl_priv *priv, u8 index, 267static void iwl_set_ht_add_station(struct iwl_priv *priv, u8 index,
@@ -413,7 +413,7 @@ int iwl_add_station_common(struct iwl_priv *priv, struct iwl_rxon_context *ctx,
413 spin_unlock_bh(&priv->sta_lock); 413 spin_unlock_bh(&priv->sta_lock);
414 414
415 /* Add station to device's station table */ 415 /* Add station to device's station table */
416 ret = iwl_send_add_sta(priv, &sta_cmd, CMD_SYNC); 416 ret = iwl_send_add_sta(priv, &sta_cmd, 0);
417 if (ret) { 417 if (ret) {
418 spin_lock_bh(&priv->sta_lock); 418 spin_lock_bh(&priv->sta_lock);
419 IWL_ERR(priv, "Adding station %pM failed.\n", 419 IWL_ERR(priv, "Adding station %pM failed.\n",
@@ -456,7 +456,6 @@ static int iwl_send_remove_station(struct iwl_priv *priv,
456 struct iwl_host_cmd cmd = { 456 struct iwl_host_cmd cmd = {
457 .id = REPLY_REMOVE_STA, 457 .id = REPLY_REMOVE_STA,
458 .len = { sizeof(struct iwl_rem_sta_cmd), }, 458 .len = { sizeof(struct iwl_rem_sta_cmd), },
459 .flags = CMD_SYNC,
460 .data = { &rm_sta_cmd, }, 459 .data = { &rm_sta_cmd, },
461 }; 460 };
462 461
@@ -740,7 +739,7 @@ void iwl_restore_stations(struct iwl_priv *priv, struct iwl_rxon_context *ctx)
740 send_lq = true; 739 send_lq = true;
741 } 740 }
742 spin_unlock_bh(&priv->sta_lock); 741 spin_unlock_bh(&priv->sta_lock);
743 ret = iwl_send_add_sta(priv, &sta_cmd, CMD_SYNC); 742 ret = iwl_send_add_sta(priv, &sta_cmd, 0);
744 if (ret) { 743 if (ret) {
745 spin_lock_bh(&priv->sta_lock); 744 spin_lock_bh(&priv->sta_lock);
746 IWL_ERR(priv, "Adding station %pM failed.\n", 745 IWL_ERR(priv, "Adding station %pM failed.\n",
@@ -756,8 +755,7 @@ void iwl_restore_stations(struct iwl_priv *priv, struct iwl_rxon_context *ctx)
756 * current LQ command 755 * current LQ command
757 */ 756 */
758 if (send_lq) 757 if (send_lq)
759 iwl_send_lq_cmd(priv, ctx, &lq, 758 iwl_send_lq_cmd(priv, ctx, &lq, 0, true);
760 CMD_SYNC, true);
761 spin_lock_bh(&priv->sta_lock); 759 spin_lock_bh(&priv->sta_lock);
762 priv->stations[i].used &= ~IWL_STA_UCODE_INPROGRESS; 760 priv->stations[i].used &= ~IWL_STA_UCODE_INPROGRESS;
763 } 761 }
@@ -968,7 +966,7 @@ int iwlagn_add_bssid_station(struct iwl_priv *priv,
968 return -ENOMEM; 966 return -ENOMEM;
969 } 967 }
970 968
971 ret = iwl_send_lq_cmd(priv, ctx, link_cmd, CMD_SYNC, true); 969 ret = iwl_send_lq_cmd(priv, ctx, link_cmd, 0, true);
972 if (ret) 970 if (ret)
973 IWL_ERR(priv, "Link quality command failed (%d)\n", ret); 971 IWL_ERR(priv, "Link quality command failed (%d)\n", ret);
974 972
@@ -999,7 +997,6 @@ static int iwl_send_static_wepkey_cmd(struct iwl_priv *priv,
999 struct iwl_host_cmd cmd = { 997 struct iwl_host_cmd cmd = {
1000 .id = ctx->wep_key_cmd, 998 .id = ctx->wep_key_cmd,
1001 .data = { wep_cmd, }, 999 .data = { wep_cmd, },
1002 .flags = CMD_SYNC,
1003 }; 1000 };
1004 1001
1005 might_sleep(); 1002 might_sleep();
@@ -1248,7 +1245,7 @@ int iwl_remove_dynamic_key(struct iwl_priv *priv,
1248 sta_cmd.sta.modify_mask = STA_MODIFY_KEY_MASK; 1245 sta_cmd.sta.modify_mask = STA_MODIFY_KEY_MASK;
1249 sta_cmd.mode = STA_CONTROL_MODIFY_MSK; 1246 sta_cmd.mode = STA_CONTROL_MODIFY_MSK;
1250 1247
1251 return iwl_send_add_sta(priv, &sta_cmd, CMD_SYNC); 1248 return iwl_send_add_sta(priv, &sta_cmd, 0);
1252} 1249}
1253 1250
1254int iwl_set_dynamic_key(struct iwl_priv *priv, 1251int iwl_set_dynamic_key(struct iwl_priv *priv,
@@ -1284,13 +1281,13 @@ int iwl_set_dynamic_key(struct iwl_priv *priv,
1284 ieee80211_get_key_rx_seq(keyconf, 0, &seq); 1281 ieee80211_get_key_rx_seq(keyconf, 0, &seq);
1285 ieee80211_get_tkip_rx_p1k(keyconf, addr, seq.tkip.iv32, p1k); 1282 ieee80211_get_tkip_rx_p1k(keyconf, addr, seq.tkip.iv32, p1k);
1286 ret = iwlagn_send_sta_key(priv, keyconf, sta_id, 1283 ret = iwlagn_send_sta_key(priv, keyconf, sta_id,
1287 seq.tkip.iv32, p1k, CMD_SYNC); 1284 seq.tkip.iv32, p1k, 0);
1288 break; 1285 break;
1289 case WLAN_CIPHER_SUITE_CCMP: 1286 case WLAN_CIPHER_SUITE_CCMP:
1290 case WLAN_CIPHER_SUITE_WEP40: 1287 case WLAN_CIPHER_SUITE_WEP40:
1291 case WLAN_CIPHER_SUITE_WEP104: 1288 case WLAN_CIPHER_SUITE_WEP104:
1292 ret = iwlagn_send_sta_key(priv, keyconf, sta_id, 1289 ret = iwlagn_send_sta_key(priv, keyconf, sta_id,
1293 0, NULL, CMD_SYNC); 1290 0, NULL, 0);
1294 break; 1291 break;
1295 default: 1292 default:
1296 IWL_ERR(priv, "Unknown cipher %x\n", keyconf->cipher); 1293 IWL_ERR(priv, "Unknown cipher %x\n", keyconf->cipher);
@@ -1409,7 +1406,7 @@ int iwl_sta_tx_modify_enable_tid(struct iwl_priv *priv, int sta_id, int tid)
1409 memcpy(&sta_cmd, &priv->stations[sta_id].sta, sizeof(struct iwl_addsta_cmd)); 1406 memcpy(&sta_cmd, &priv->stations[sta_id].sta, sizeof(struct iwl_addsta_cmd));
1410 spin_unlock_bh(&priv->sta_lock); 1407 spin_unlock_bh(&priv->sta_lock);
1411 1408
1412 return iwl_send_add_sta(priv, &sta_cmd, CMD_SYNC); 1409 return iwl_send_add_sta(priv, &sta_cmd, 0);
1413} 1410}
1414 1411
1415int iwl_sta_rx_agg_start(struct iwl_priv *priv, struct ieee80211_sta *sta, 1412int iwl_sta_rx_agg_start(struct iwl_priv *priv, struct ieee80211_sta *sta,
@@ -1433,7 +1430,7 @@ int iwl_sta_rx_agg_start(struct iwl_priv *priv, struct ieee80211_sta *sta,
1433 memcpy(&sta_cmd, &priv->stations[sta_id].sta, sizeof(struct iwl_addsta_cmd)); 1430 memcpy(&sta_cmd, &priv->stations[sta_id].sta, sizeof(struct iwl_addsta_cmd));
1434 spin_unlock_bh(&priv->sta_lock); 1431 spin_unlock_bh(&priv->sta_lock);
1435 1432
1436 return iwl_send_add_sta(priv, &sta_cmd, CMD_SYNC); 1433 return iwl_send_add_sta(priv, &sta_cmd, 0);
1437} 1434}
1438 1435
1439int iwl_sta_rx_agg_stop(struct iwl_priv *priv, struct ieee80211_sta *sta, 1436int iwl_sta_rx_agg_stop(struct iwl_priv *priv, struct ieee80211_sta *sta,
@@ -1458,7 +1455,7 @@ int iwl_sta_rx_agg_stop(struct iwl_priv *priv, struct ieee80211_sta *sta,
1458 memcpy(&sta_cmd, &priv->stations[sta_id].sta, sizeof(struct iwl_addsta_cmd)); 1455 memcpy(&sta_cmd, &priv->stations[sta_id].sta, sizeof(struct iwl_addsta_cmd));
1459 spin_unlock_bh(&priv->sta_lock); 1456 spin_unlock_bh(&priv->sta_lock);
1460 1457
1461 return iwl_send_add_sta(priv, &sta_cmd, CMD_SYNC); 1458 return iwl_send_add_sta(priv, &sta_cmd, 0);
1462} 1459}
1463 1460
1464 1461
diff --git a/drivers/net/wireless/iwlwifi/dvm/tt.c b/drivers/net/wireless/iwlwifi/dvm/tt.c
index 058c5892c427..acb981a0a0aa 100644
--- a/drivers/net/wireless/iwlwifi/dvm/tt.c
+++ b/drivers/net/wireless/iwlwifi/dvm/tt.c
@@ -236,7 +236,7 @@ static void iwl_prepare_ct_kill_task(struct iwl_priv *priv)
236{ 236{
237 IWL_DEBUG_TEMP(priv, "Prepare to enter IWL_TI_CT_KILL\n"); 237 IWL_DEBUG_TEMP(priv, "Prepare to enter IWL_TI_CT_KILL\n");
238 /* make request to retrieve statistics information */ 238 /* make request to retrieve statistics information */
239 iwl_send_statistics_request(priv, CMD_SYNC, false); 239 iwl_send_statistics_request(priv, 0, false);
240 /* Reschedule the ct_kill wait timer */ 240 /* Reschedule the ct_kill wait timer */
241 mod_timer(&priv->thermal_throttle.ct_kill_waiting_tm, 241 mod_timer(&priv->thermal_throttle.ct_kill_waiting_tm,
242 jiffies + msecs_to_jiffies(CT_KILL_WAITING_DURATION)); 242 jiffies + msecs_to_jiffies(CT_KILL_WAITING_DURATION));
diff --git a/drivers/net/wireless/iwlwifi/dvm/tx.c b/drivers/net/wireless/iwlwifi/dvm/tx.c
index 398dd096674c..3255a1723d17 100644
--- a/drivers/net/wireless/iwlwifi/dvm/tx.c
+++ b/drivers/net/wireless/iwlwifi/dvm/tx.c
@@ -402,10 +402,10 @@ int iwlagn_tx_skb(struct iwl_priv *priv,
402 /* aggregation is on for this <sta,tid> */ 402 /* aggregation is on for this <sta,tid> */
403 if (info->flags & IEEE80211_TX_CTL_AMPDU && 403 if (info->flags & IEEE80211_TX_CTL_AMPDU &&
404 tid_data->agg.state != IWL_AGG_ON) { 404 tid_data->agg.state != IWL_AGG_ON) {
405 IWL_ERR(priv, "TX_CTL_AMPDU while not in AGG:" 405 IWL_ERR(priv,
406 " Tx flags = 0x%08x, agg.state = %d", 406 "TX_CTL_AMPDU while not in AGG: Tx flags = 0x%08x, agg.state = %d\n",
407 info->flags, tid_data->agg.state); 407 info->flags, tid_data->agg.state);
408 IWL_ERR(priv, "sta_id = %d, tid = %d seq_num = %d", 408 IWL_ERR(priv, "sta_id = %d, tid = %d seq_num = %d\n",
409 sta_id, tid, 409 sta_id, tid,
410 IEEE80211_SEQ_TO_SN(tid_data->seq_number)); 410 IEEE80211_SEQ_TO_SN(tid_data->seq_number));
411 goto drop_unlock_sta; 411 goto drop_unlock_sta;
@@ -416,7 +416,7 @@ int iwlagn_tx_skb(struct iwl_priv *priv,
416 */ 416 */
417 if (WARN_ONCE(tid_data->agg.state != IWL_AGG_ON && 417 if (WARN_ONCE(tid_data->agg.state != IWL_AGG_ON &&
418 tid_data->agg.state != IWL_AGG_OFF, 418 tid_data->agg.state != IWL_AGG_OFF,
419 "Tx while agg.state = %d", tid_data->agg.state)) 419 "Tx while agg.state = %d\n", tid_data->agg.state))
420 goto drop_unlock_sta; 420 goto drop_unlock_sta;
421 421
422 seq_number = tid_data->seq_number; 422 seq_number = tid_data->seq_number;
@@ -778,8 +778,8 @@ static void iwlagn_check_ratid_empty(struct iwl_priv *priv, int sta_id, u8 tid)
778 /* There are no packets for this RA / TID in the HW any more */ 778 /* There are no packets for this RA / TID in the HW any more */
779 if (tid_data->agg.ssn == tid_data->next_reclaimed) { 779 if (tid_data->agg.ssn == tid_data->next_reclaimed) {
780 IWL_DEBUG_TX_QUEUES(priv, 780 IWL_DEBUG_TX_QUEUES(priv,
781 "Can continue DELBA flow ssn = next_recl =" 781 "Can continue DELBA flow ssn = next_recl = %d\n",
782 " %d", tid_data->next_reclaimed); 782 tid_data->next_reclaimed);
783 iwl_trans_txq_disable(priv->trans, 783 iwl_trans_txq_disable(priv->trans,
784 tid_data->agg.txq_id); 784 tid_data->agg.txq_id);
785 iwlagn_dealloc_agg_txq(priv, tid_data->agg.txq_id); 785 iwlagn_dealloc_agg_txq(priv, tid_data->agg.txq_id);
@@ -791,8 +791,8 @@ static void iwlagn_check_ratid_empty(struct iwl_priv *priv, int sta_id, u8 tid)
791 /* There are no packets for this RA / TID in the HW any more */ 791 /* There are no packets for this RA / TID in the HW any more */
792 if (tid_data->agg.ssn == tid_data->next_reclaimed) { 792 if (tid_data->agg.ssn == tid_data->next_reclaimed) {
793 IWL_DEBUG_TX_QUEUES(priv, 793 IWL_DEBUG_TX_QUEUES(priv,
794 "Can continue ADDBA flow ssn = next_recl =" 794 "Can continue ADDBA flow ssn = next_recl = %d\n",
795 " %d", tid_data->next_reclaimed); 795 tid_data->next_reclaimed);
796 tid_data->agg.state = IWL_AGG_STARTING; 796 tid_data->agg.state = IWL_AGG_STARTING;
797 ieee80211_start_tx_ba_cb_irqsafe(vif, addr, tid); 797 ieee80211_start_tx_ba_cb_irqsafe(vif, addr, tid);
798 } 798 }
@@ -1216,8 +1216,8 @@ int iwlagn_rx_reply_tx(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb,
1216 ctx->vif->type == NL80211_IFTYPE_STATION) { 1216 ctx->vif->type == NL80211_IFTYPE_STATION) {
1217 /* block and stop all queues */ 1217 /* block and stop all queues */
1218 priv->passive_no_rx = true; 1218 priv->passive_no_rx = true;
1219 IWL_DEBUG_TX_QUEUES(priv, "stop all queues: " 1219 IWL_DEBUG_TX_QUEUES(priv,
1220 "passive channel"); 1220 "stop all queues: passive channel\n");
1221 ieee80211_stop_queues(priv->hw); 1221 ieee80211_stop_queues(priv->hw);
1222 1222
1223 IWL_DEBUG_TX_REPLY(priv, 1223 IWL_DEBUG_TX_REPLY(priv,
@@ -1271,7 +1271,7 @@ int iwlagn_rx_reply_tx(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb,
1271 1271
1272 while (!skb_queue_empty(&skbs)) { 1272 while (!skb_queue_empty(&skbs)) {
1273 skb = __skb_dequeue(&skbs); 1273 skb = __skb_dequeue(&skbs);
1274 ieee80211_tx_status_ni(priv->hw, skb); 1274 ieee80211_tx_status(priv->hw, skb);
1275 } 1275 }
1276 1276
1277 return 0; 1277 return 0;
@@ -1411,7 +1411,7 @@ int iwlagn_rx_reply_compressed_ba(struct iwl_priv *priv,
1411 1411
1412 while (!skb_queue_empty(&reclaimed_skbs)) { 1412 while (!skb_queue_empty(&reclaimed_skbs)) {
1413 skb = __skb_dequeue(&reclaimed_skbs); 1413 skb = __skb_dequeue(&reclaimed_skbs);
1414 ieee80211_tx_status_ni(priv->hw, skb); 1414 ieee80211_tx_status(priv->hw, skb);
1415 } 1415 }
1416 1416
1417 return 0; 1417 return 0;
diff --git a/drivers/net/wireless/iwlwifi/dvm/ucode.c b/drivers/net/wireless/iwlwifi/dvm/ucode.c
index cf03ef5619d9..d5cee1530597 100644
--- a/drivers/net/wireless/iwlwifi/dvm/ucode.c
+++ b/drivers/net/wireless/iwlwifi/dvm/ucode.c
@@ -172,7 +172,7 @@ static int iwl_send_wimax_coex(struct iwl_priv *priv)
172 memset(&coex_cmd, 0, sizeof(coex_cmd)); 172 memset(&coex_cmd, 0, sizeof(coex_cmd));
173 173
174 return iwl_dvm_send_cmd_pdu(priv, 174 return iwl_dvm_send_cmd_pdu(priv,
175 COEX_PRIORITY_TABLE_CMD, CMD_SYNC, 175 COEX_PRIORITY_TABLE_CMD, 0,
176 sizeof(coex_cmd), &coex_cmd); 176 sizeof(coex_cmd), &coex_cmd);
177} 177}
178 178
@@ -205,7 +205,7 @@ void iwl_send_prio_tbl(struct iwl_priv *priv)
205 memcpy(prio_tbl_cmd.prio_tbl, iwl_bt_prio_tbl, 205 memcpy(prio_tbl_cmd.prio_tbl, iwl_bt_prio_tbl,
206 sizeof(iwl_bt_prio_tbl)); 206 sizeof(iwl_bt_prio_tbl));
207 if (iwl_dvm_send_cmd_pdu(priv, 207 if (iwl_dvm_send_cmd_pdu(priv,
208 REPLY_BT_COEX_PRIO_TABLE, CMD_SYNC, 208 REPLY_BT_COEX_PRIO_TABLE, 0,
209 sizeof(prio_tbl_cmd), &prio_tbl_cmd)) 209 sizeof(prio_tbl_cmd), &prio_tbl_cmd))
210 IWL_ERR(priv, "failed to send BT prio tbl command\n"); 210 IWL_ERR(priv, "failed to send BT prio tbl command\n");
211} 211}
@@ -218,7 +218,7 @@ int iwl_send_bt_env(struct iwl_priv *priv, u8 action, u8 type)
218 env_cmd.action = action; 218 env_cmd.action = action;
219 env_cmd.type = type; 219 env_cmd.type = type;
220 ret = iwl_dvm_send_cmd_pdu(priv, 220 ret = iwl_dvm_send_cmd_pdu(priv,
221 REPLY_BT_COEX_PROT_ENV, CMD_SYNC, 221 REPLY_BT_COEX_PROT_ENV, 0,
222 sizeof(env_cmd), &env_cmd); 222 sizeof(env_cmd), &env_cmd);
223 if (ret) 223 if (ret)
224 IWL_ERR(priv, "failed to send BT env command\n"); 224 IWL_ERR(priv, "failed to send BT env command\n");
diff --git a/drivers/net/wireless/iwlwifi/iwl-7000.c b/drivers/net/wireless/iwlwifi/iwl-7000.c
index f73de239cdc1..48730064da73 100644
--- a/drivers/net/wireless/iwlwifi/iwl-7000.c
+++ b/drivers/net/wireless/iwlwifi/iwl-7000.c
@@ -98,7 +98,7 @@
98#define NVM_HW_SECTION_NUM_FAMILY_7000 0 98#define NVM_HW_SECTION_NUM_FAMILY_7000 0
99 99
100static const struct iwl_base_params iwl7000_base_params = { 100static const struct iwl_base_params iwl7000_base_params = {
101 .eeprom_size = OTP_LOW_IMAGE_SIZE, 101 .eeprom_size = OTP_LOW_IMAGE_SIZE_FAMILY_7000,
102 .num_of_queues = IWLAGN_NUM_QUEUES, 102 .num_of_queues = IWLAGN_NUM_QUEUES,
103 .pll_cfg_val = 0, 103 .pll_cfg_val = 0,
104 .shadow_ram_support = true, 104 .shadow_ram_support = true,
diff --git a/drivers/net/wireless/iwlwifi/iwl-8000.c b/drivers/net/wireless/iwlwifi/iwl-8000.c
index f5bd82b88592..51c41531d81d 100644
--- a/drivers/net/wireless/iwlwifi/iwl-8000.c
+++ b/drivers/net/wireless/iwlwifi/iwl-8000.c
@@ -83,9 +83,10 @@
83#define IWL8000_MODULE_FIRMWARE(api) IWL8000_FW_PRE __stringify(api) ".ucode" 83#define IWL8000_MODULE_FIRMWARE(api) IWL8000_FW_PRE __stringify(api) ".ucode"
84 84
85#define NVM_HW_SECTION_NUM_FAMILY_8000 10 85#define NVM_HW_SECTION_NUM_FAMILY_8000 10
86#define DEFAULT_NVM_FILE_FAMILY_8000 "iwl_nvm_8000.bin"
86 87
87static const struct iwl_base_params iwl8000_base_params = { 88static const struct iwl_base_params iwl8000_base_params = {
88 .eeprom_size = OTP_LOW_IMAGE_SIZE, 89 .eeprom_size = OTP_LOW_IMAGE_SIZE_FAMILY_8000,
89 .num_of_queues = IWLAGN_NUM_QUEUES, 90 .num_of_queues = IWLAGN_NUM_QUEUES,
90 .pll_cfg_val = 0, 91 .pll_cfg_val = 0,
91 .shadow_ram_support = true, 92 .shadow_ram_support = true,
@@ -118,6 +119,7 @@ const struct iwl_cfg iwl8260_2ac_cfg = {
118 .ht_params = &iwl8000_ht_params, 119 .ht_params = &iwl8000_ht_params,
119 .nvm_ver = IWL8000_NVM_VERSION, 120 .nvm_ver = IWL8000_NVM_VERSION,
120 .nvm_calib_ver = IWL8000_TX_POWER_VERSION, 121 .nvm_calib_ver = IWL8000_TX_POWER_VERSION,
122 .default_nvm_file = DEFAULT_NVM_FILE_FAMILY_8000,
121}; 123};
122 124
123const struct iwl_cfg iwl8260_n_cfg = { 125const struct iwl_cfg iwl8260_n_cfg = {
@@ -127,6 +129,7 @@ const struct iwl_cfg iwl8260_n_cfg = {
127 .ht_params = &iwl8000_ht_params, 129 .ht_params = &iwl8000_ht_params,
128 .nvm_ver = IWL8000_NVM_VERSION, 130 .nvm_ver = IWL8000_NVM_VERSION,
129 .nvm_calib_ver = IWL8000_TX_POWER_VERSION, 131 .nvm_calib_ver = IWL8000_TX_POWER_VERSION,
132 .default_nvm_file = DEFAULT_NVM_FILE_FAMILY_8000,
130}; 133};
131 134
132MODULE_FIRMWARE(IWL8000_MODULE_FIRMWARE(IWL8000_UCODE_API_OK)); 135MODULE_FIRMWARE(IWL8000_MODULE_FIRMWARE(IWL8000_UCODE_API_OK));
diff --git a/drivers/net/wireless/iwlwifi/iwl-agn-hw.h b/drivers/net/wireless/iwlwifi/iwl-agn-hw.h
index 7f37fb86837b..04a483d38659 100644
--- a/drivers/net/wireless/iwlwifi/iwl-agn-hw.h
+++ b/drivers/net/wireless/iwlwifi/iwl-agn-hw.h
@@ -102,9 +102,7 @@
102 102
103/* EEPROM */ 103/* EEPROM */
104#define IWLAGN_EEPROM_IMG_SIZE 2048 104#define IWLAGN_EEPROM_IMG_SIZE 2048
105/* OTP */ 105
106/* lower blocks contain EEPROM image and calibration data */
107#define OTP_LOW_IMAGE_SIZE (2 * 512 * sizeof(u16)) /* 2 KB */
108/* high blocks contain PAPD data */ 106/* high blocks contain PAPD data */
109#define OTP_HIGH_IMAGE_SIZE_6x00 (6 * 512 * sizeof(u16)) /* 6 KB */ 107#define OTP_HIGH_IMAGE_SIZE_6x00 (6 * 512 * sizeof(u16)) /* 6 KB */
110#define OTP_HIGH_IMAGE_SIZE_1000 (0x200 * sizeof(u16)) /* 1024 bytes */ 108#define OTP_HIGH_IMAGE_SIZE_1000 (0x200 * sizeof(u16)) /* 1024 bytes */
diff --git a/drivers/net/wireless/iwlwifi/iwl-config.h b/drivers/net/wireless/iwlwifi/iwl-config.h
index 7ce82d9c7222..b7047905f41a 100644
--- a/drivers/net/wireless/iwlwifi/iwl-config.h
+++ b/drivers/net/wireless/iwlwifi/iwl-config.h
@@ -193,6 +193,11 @@ struct iwl_ht_params {
193#define EEPROM_6000_REG_BAND_24_HT40_CHANNELS 0x80 193#define EEPROM_6000_REG_BAND_24_HT40_CHANNELS 0x80
194#define EEPROM_REGULATORY_BAND_NO_HT40 0 194#define EEPROM_REGULATORY_BAND_NO_HT40 0
195 195
196/* lower blocks contain EEPROM image and calibration data */
197#define OTP_LOW_IMAGE_SIZE (2 * 512 * sizeof(u16)) /* 2 KB */
198#define OTP_LOW_IMAGE_SIZE_FAMILY_7000 (16 * 512 * sizeof(u16)) /* 16 KB */
199#define OTP_LOW_IMAGE_SIZE_FAMILY_8000 (32 * 512 * sizeof(u16)) /* 32 KB */
200
196struct iwl_eeprom_params { 201struct iwl_eeprom_params {
197 const u8 regulatory_bands[7]; 202 const u8 regulatory_bands[7];
198 bool enhanced_txpower; 203 bool enhanced_txpower;
@@ -269,6 +274,8 @@ struct iwl_cfg {
269 u8 nvm_hw_section_num; 274 u8 nvm_hw_section_num;
270 bool lp_xtal_workaround; 275 bool lp_xtal_workaround;
271 const struct iwl_pwr_tx_backoff *pwr_tx_backoffs; 276 const struct iwl_pwr_tx_backoff *pwr_tx_backoffs;
277 bool no_power_up_nic_in_init;
278 const char *default_nvm_file;
272}; 279};
273 280
274/* 281/*
diff --git a/drivers/net/wireless/iwlwifi/iwl-debug.c b/drivers/net/wireless/iwlwifi/iwl-debug.c
index 8a44f594528d..09feff4fa226 100644
--- a/drivers/net/wireless/iwlwifi/iwl-debug.c
+++ b/drivers/net/wireless/iwlwifi/iwl-debug.c
@@ -61,8 +61,6 @@
61 * 61 *
62 *****************************************************************************/ 62 *****************************************************************************/
63 63
64#define DEBUG
65
66#include <linux/device.h> 64#include <linux/device.h>
67#include <linux/interrupt.h> 65#include <linux/interrupt.h>
68#include <linux/export.h> 66#include <linux/export.h>
@@ -128,8 +126,8 @@ void __iwl_dbg(struct device *dev,
128#ifdef CONFIG_IWLWIFI_DEBUG 126#ifdef CONFIG_IWLWIFI_DEBUG
129 if (iwl_have_debug_level(level) && 127 if (iwl_have_debug_level(level) &&
130 (!limit || net_ratelimit())) 128 (!limit || net_ratelimit()))
131 dev_dbg(dev, "%c %s %pV", in_interrupt() ? 'I' : 'U', 129 dev_printk(KERN_DEBUG, dev, "%c %s %pV",
132 function, &vaf); 130 in_interrupt() ? 'I' : 'U', function, &vaf);
133#endif 131#endif
134 trace_iwlwifi_dbg(level, in_interrupt(), function, &vaf); 132 trace_iwlwifi_dbg(level, in_interrupt(), function, &vaf);
135 va_end(args); 133 va_end(args);
diff --git a/drivers/net/wireless/iwlwifi/iwl-debug.h b/drivers/net/wireless/iwlwifi/iwl-debug.h
index c8cbdbe15924..295083510e72 100644
--- a/drivers/net/wireless/iwlwifi/iwl-debug.h
+++ b/drivers/net/wireless/iwlwifi/iwl-debug.h
@@ -47,12 +47,32 @@ void __iwl_warn(struct device *dev, const char *fmt, ...) __printf(2, 3);
47void __iwl_info(struct device *dev, const char *fmt, ...) __printf(2, 3); 47void __iwl_info(struct device *dev, const char *fmt, ...) __printf(2, 3);
48void __iwl_crit(struct device *dev, const char *fmt, ...) __printf(2, 3); 48void __iwl_crit(struct device *dev, const char *fmt, ...) __printf(2, 3);
49 49
50/* not all compilers can evaluate strlen() at compile time, so use sizeof() */
51#define CHECK_FOR_NEWLINE(f) BUILD_BUG_ON(f[sizeof(f) - 2] != '\n')
52
50/* No matter what is m (priv, bus, trans), this will work */ 53/* No matter what is m (priv, bus, trans), this will work */
51#define IWL_ERR(m, f, a...) __iwl_err((m)->dev, false, false, f, ## a) 54#define IWL_ERR_DEV(d, f, a...) \
52#define IWL_ERR_DEV(d, f, a...) __iwl_err((d), false, false, f, ## a) 55 do { \
53#define IWL_WARN(m, f, a...) __iwl_warn((m)->dev, f, ## a) 56 CHECK_FOR_NEWLINE(f); \
54#define IWL_INFO(m, f, a...) __iwl_info((m)->dev, f, ## a) 57 __iwl_err((d), false, false, f, ## a); \
55#define IWL_CRIT(m, f, a...) __iwl_crit((m)->dev, f, ## a) 58 } while (0)
59#define IWL_ERR(m, f, a...) \
60 IWL_ERR_DEV((m)->dev, f, ## a)
61#define IWL_WARN(m, f, a...) \
62 do { \
63 CHECK_FOR_NEWLINE(f); \
64 __iwl_warn((m)->dev, f, ## a); \
65 } while (0)
66#define IWL_INFO(m, f, a...) \
67 do { \
68 CHECK_FOR_NEWLINE(f); \
69 __iwl_info((m)->dev, f, ## a); \
70 } while (0)
71#define IWL_CRIT(m, f, a...) \
72 do { \
73 CHECK_FOR_NEWLINE(f); \
74 __iwl_crit((m)->dev, f, ## a); \
75 } while (0)
56 76
57#if defined(CONFIG_IWLWIFI_DEBUG) || defined(CONFIG_IWLWIFI_DEVICE_TRACING) 77#if defined(CONFIG_IWLWIFI_DEBUG) || defined(CONFIG_IWLWIFI_DEVICE_TRACING)
58void __iwl_dbg(struct device *dev, 78void __iwl_dbg(struct device *dev,
@@ -72,12 +92,17 @@ do { \
72 DUMP_PREFIX_OFFSET, 16, 1, p, len, 1); \ 92 DUMP_PREFIX_OFFSET, 16, 1, p, len, 1); \
73} while (0) 93} while (0)
74 94
95#define __IWL_DEBUG_DEV(dev, level, limit, fmt, args...) \
96 do { \
97 CHECK_FOR_NEWLINE(fmt); \
98 __iwl_dbg(dev, level, limit, __func__, fmt, ##args); \
99 } while (0)
75#define IWL_DEBUG(m, level, fmt, args...) \ 100#define IWL_DEBUG(m, level, fmt, args...) \
76 __iwl_dbg((m)->dev, level, false, __func__, fmt, ##args) 101 __IWL_DEBUG_DEV((m)->dev, level, false, fmt, ##args)
77#define IWL_DEBUG_DEV(dev, level, fmt, args...) \ 102#define IWL_DEBUG_DEV(dev, level, fmt, args...) \
78 __iwl_dbg((dev), level, false, __func__, fmt, ##args) 103 __IWL_DEBUG_DEV(dev, level, false, fmt, ##args)
79#define IWL_DEBUG_LIMIT(m, level, fmt, args...) \ 104#define IWL_DEBUG_LIMIT(m, level, fmt, args...) \
80 __iwl_dbg((m)->dev, level, true, __func__, fmt, ##args) 105 __IWL_DEBUG_DEV((m)->dev, level, true, fmt, ##args)
81 106
82#ifdef CONFIG_IWLWIFI_DEBUG 107#ifdef CONFIG_IWLWIFI_DEBUG
83#define iwl_print_hex_dump(m, level, p, len) \ 108#define iwl_print_hex_dump(m, level, p, len) \
diff --git a/drivers/net/wireless/iwlwifi/iwl-drv.c b/drivers/net/wireless/iwlwifi/iwl-drv.c
index 0a3e841b44a9..f2a5c12269a3 100644
--- a/drivers/net/wireless/iwlwifi/iwl-drv.c
+++ b/drivers/net/wireless/iwlwifi/iwl-drv.c
@@ -1243,6 +1243,7 @@ struct iwl_mod_params iwlwifi_mod_params = {
1243 .bt_coex_active = true, 1243 .bt_coex_active = true,
1244 .power_level = IWL_POWER_INDEX_1, 1244 .power_level = IWL_POWER_INDEX_1,
1245 .wd_disable = true, 1245 .wd_disable = true,
1246 .uapsd_disable = false,
1246 /* the rest are 0 by default */ 1247 /* the rest are 0 by default */
1247}; 1248};
1248IWL_EXPORT_SYMBOL(iwlwifi_mod_params); 1249IWL_EXPORT_SYMBOL(iwlwifi_mod_params);
@@ -1356,6 +1357,10 @@ MODULE_PARM_DESC(wd_disable,
1356module_param_named(nvm_file, iwlwifi_mod_params.nvm_file, charp, S_IRUGO); 1357module_param_named(nvm_file, iwlwifi_mod_params.nvm_file, charp, S_IRUGO);
1357MODULE_PARM_DESC(nvm_file, "NVM file name"); 1358MODULE_PARM_DESC(nvm_file, "NVM file name");
1358 1359
1360module_param_named(uapsd_disable, iwlwifi_mod_params.uapsd_disable,
1361 bool, S_IRUGO);
1362MODULE_PARM_DESC(uapsd_disable, "disable U-APSD functionality (default: N)");
1363
1359/* 1364/*
1360 * set bt_coex_active to true, uCode will do kill/defer 1365 * set bt_coex_active to true, uCode will do kill/defer
1361 * every time the priority line is asserted (BT is sending signals on the 1366 * every time the priority line is asserted (BT is sending signals on the
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-error-dump.h b/drivers/net/wireless/iwlwifi/iwl-fw-error-dump.h
index f381908be7e5..2953ffceda38 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw-error-dump.h
+++ b/drivers/net/wireless/iwlwifi/iwl-fw-error-dump.h
@@ -72,11 +72,14 @@
72 * @IWL_FW_ERROR_DUMP_SRAM: 72 * @IWL_FW_ERROR_DUMP_SRAM:
73 * @IWL_FW_ERROR_DUMP_REG: 73 * @IWL_FW_ERROR_DUMP_REG:
74 * @IWL_FW_ERROR_DUMP_RXF: 74 * @IWL_FW_ERROR_DUMP_RXF:
75 * @IWL_FW_ERROR_DUMP_TXCMD: last TX command data, structured as
76 * &struct iwl_fw_error_dump_txcmd packets
75 */ 77 */
76enum iwl_fw_error_dump_type { 78enum iwl_fw_error_dump_type {
77 IWL_FW_ERROR_DUMP_SRAM = 0, 79 IWL_FW_ERROR_DUMP_SRAM = 0,
78 IWL_FW_ERROR_DUMP_REG = 1, 80 IWL_FW_ERROR_DUMP_REG = 1,
79 IWL_FW_ERROR_DUMP_RXF = 2, 81 IWL_FW_ERROR_DUMP_RXF = 2,
82 IWL_FW_ERROR_DUMP_TXCMD = 3,
80 83
81 IWL_FW_ERROR_DUMP_MAX, 84 IWL_FW_ERROR_DUMP_MAX,
82}; 85};
@@ -105,4 +108,27 @@ struct iwl_fw_error_dump_file {
105 u8 data[0]; 108 u8 data[0];
106} __packed; 109} __packed;
107 110
111/**
112 * struct iwl_fw_error_dump_txcmd - TX command data
113 * @cmdlen: original length of command
114 * @caplen: captured length of command (may be less)
115 * @data: captured command data, @caplen bytes
116 */
117struct iwl_fw_error_dump_txcmd {
118 __le32 cmdlen;
119 __le32 caplen;
120 u8 data[];
121} __packed;
122
123/**
124 * iwl_mvm_fw_error_next_data - advance fw error dump data pointer
125 * @data: previous data block
126 * Returns: next data block
127 */
128static inline struct iwl_fw_error_dump_data *
129iwl_mvm_fw_error_next_data(struct iwl_fw_error_dump_data *data)
130{
131 return (void *)(data->data + le32_to_cpu(data->len));
132}
133
108#endif /* __fw_error_dump_h__ */ 134#endif /* __fw_error_dump_h__ */
diff --git a/drivers/net/wireless/iwlwifi/iwl-fw.h b/drivers/net/wireless/iwlwifi/iwl-fw.h
index f5927d0cf9b6..0aa7c0085c9f 100644
--- a/drivers/net/wireless/iwlwifi/iwl-fw.h
+++ b/drivers/net/wireless/iwlwifi/iwl-fw.h
@@ -74,7 +74,7 @@
74 * @IWL_UCODE_TLV_FLAGS_MFP: This uCode image supports MFP (802.11w). 74 * @IWL_UCODE_TLV_FLAGS_MFP: This uCode image supports MFP (802.11w).
75 * @IWL_UCODE_TLV_FLAGS_P2P: This uCode image supports P2P. 75 * @IWL_UCODE_TLV_FLAGS_P2P: This uCode image supports P2P.
76 * @IWL_UCODE_TLV_FLAGS_DW_BC_TABLE: The SCD byte count table is in DWORDS 76 * @IWL_UCODE_TLV_FLAGS_DW_BC_TABLE: The SCD byte count table is in DWORDS
77 * @IWL_UCODE_TLV_FLAGS_UAPSD: This uCode image supports uAPSD 77 * @IWL_UCODE_TLV_FLAGS_UAPSD_SUPPORT: This uCode image supports uAPSD
78 * @IWL_UCODE_TLV_FLAGS_SHORT_BL: 16 entries of black list instead of 64 in scan 78 * @IWL_UCODE_TLV_FLAGS_SHORT_BL: 16 entries of black list instead of 64 in scan
79 * offload profile config command. 79 * offload profile config command.
80 * @IWL_UCODE_TLV_FLAGS_D3_6_IPV6_ADDRS: D3 image supports up to six 80 * @IWL_UCODE_TLV_FLAGS_D3_6_IPV6_ADDRS: D3 image supports up to six
@@ -107,6 +107,7 @@ enum iwl_ucode_tlv_flag {
107 IWL_UCODE_TLV_FLAGS_P2P_PM = BIT(21), 107 IWL_UCODE_TLV_FLAGS_P2P_PM = BIT(21),
108 IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM = BIT(22), 108 IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM = BIT(22),
109 IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_SCM = BIT(23), 109 IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_SCM = BIT(23),
110 IWL_UCODE_TLV_FLAGS_UAPSD_SUPPORT = BIT(24),
110 IWL_UCODE_TLV_FLAGS_EBS_SUPPORT = BIT(25), 111 IWL_UCODE_TLV_FLAGS_EBS_SUPPORT = BIT(25),
111 IWL_UCODE_TLV_FLAGS_P2P_PS_UAPSD = BIT(26), 112 IWL_UCODE_TLV_FLAGS_P2P_PS_UAPSD = BIT(26),
112 IWL_UCODE_TLV_FLAGS_BCAST_FILTERING = BIT(29), 113 IWL_UCODE_TLV_FLAGS_BCAST_FILTERING = BIT(29),
@@ -116,9 +117,11 @@ enum iwl_ucode_tlv_flag {
116/** 117/**
117 * enum iwl_ucode_tlv_api - ucode api 118 * enum iwl_ucode_tlv_api - ucode api
118 * @IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID: wowlan config includes tid field. 119 * @IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID: wowlan config includes tid field.
120 * @IWL_UCODE_TLV_API_CSA_FLOW: ucode can do unbind-bind flow for CSA.
119 */ 121 */
120enum iwl_ucode_tlv_api { 122enum iwl_ucode_tlv_api {
121 IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID = BIT(0), 123 IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID = BIT(0),
124 IWL_UCODE_TLV_API_CSA_FLOW = BIT(4),
122}; 125};
123 126
124/** 127/**
@@ -194,6 +197,11 @@ struct fw_img {
194 bool is_dual_cpus; 197 bool is_dual_cpus;
195}; 198};
196 199
200struct iwl_sf_region {
201 u32 addr;
202 u32 size;
203};
204
197/* uCode version contains 4 values: Major/Minor/API/Serial */ 205/* uCode version contains 4 values: Major/Minor/API/Serial */
198#define IWL_UCODE_MAJOR(ver) (((ver) & 0xFF000000) >> 24) 206#define IWL_UCODE_MAJOR(ver) (((ver) & 0xFF000000) >> 24)
199#define IWL_UCODE_MINOR(ver) (((ver) & 0x00FF0000) >> 16) 207#define IWL_UCODE_MINOR(ver) (((ver) & 0x00FF0000) >> 16)
diff --git a/drivers/net/wireless/iwlwifi/iwl-io.c b/drivers/net/wireless/iwlwifi/iwl-io.c
index 44cc3cf45762..5eef4ae7333b 100644
--- a/drivers/net/wireless/iwlwifi/iwl-io.c
+++ b/drivers/net/wireless/iwlwifi/iwl-io.c
@@ -33,6 +33,7 @@
33#include "iwl-io.h" 33#include "iwl-io.h"
34#include "iwl-csr.h" 34#include "iwl-csr.h"
35#include "iwl-debug.h" 35#include "iwl-debug.h"
36#include "iwl-prph.h"
36#include "iwl-fh.h" 37#include "iwl-fh.h"
37 38
38#define IWL_POLL_INTERVAL 10 /* microseconds */ 39#define IWL_POLL_INTERVAL 10 /* microseconds */
@@ -183,6 +184,23 @@ void iwl_clear_bits_prph(struct iwl_trans *trans, u32 ofs, u32 mask)
183} 184}
184IWL_EXPORT_SYMBOL(iwl_clear_bits_prph); 185IWL_EXPORT_SYMBOL(iwl_clear_bits_prph);
185 186
187void iwl_force_nmi(struct iwl_trans *trans)
188{
189 /*
190 * In HW previous to the 8000 HW family, and in the 8000 HW family
191 * itself when the revision step==0, the DEVICE_SET_NMI_REG is used
192 * to force an NMI. Otherwise, a different register -
193 * DEVICE_SET_NMI_8000B_REG - is used.
194 */
195 if ((trans->cfg->device_family != IWL_DEVICE_FAMILY_8000) ||
196 ((trans->hw_rev & 0xc) == 0x0))
197 iwl_write_prph(trans, DEVICE_SET_NMI_REG, DEVICE_SET_NMI_VAL);
198 else
199 iwl_write_prph(trans, DEVICE_SET_NMI_8000B_REG,
200 DEVICE_SET_NMI_8000B_VAL);
201}
202IWL_EXPORT_SYMBOL(iwl_force_nmi);
203
186static const char *get_fh_string(int cmd) 204static const char *get_fh_string(int cmd)
187{ 205{
188#define IWL_CMD(x) case x: return #x 206#define IWL_CMD(x) case x: return #x
diff --git a/drivers/net/wireless/iwlwifi/iwl-io.h b/drivers/net/wireless/iwlwifi/iwl-io.h
index 665ddd9dbbc4..705d12c079e8 100644
--- a/drivers/net/wireless/iwlwifi/iwl-io.h
+++ b/drivers/net/wireless/iwlwifi/iwl-io.h
@@ -80,6 +80,7 @@ void iwl_set_bits_prph(struct iwl_trans *trans, u32 ofs, u32 mask);
80void iwl_set_bits_mask_prph(struct iwl_trans *trans, u32 ofs, 80void iwl_set_bits_mask_prph(struct iwl_trans *trans, u32 ofs,
81 u32 bits, u32 mask); 81 u32 bits, u32 mask);
82void iwl_clear_bits_prph(struct iwl_trans *trans, u32 ofs, u32 mask); 82void iwl_clear_bits_prph(struct iwl_trans *trans, u32 ofs, u32 mask);
83void iwl_force_nmi(struct iwl_trans *trans);
83 84
84/* Error handling */ 85/* Error handling */
85int iwl_dump_fh(struct iwl_trans *trans, char **buf); 86int iwl_dump_fh(struct iwl_trans *trans, char **buf);
diff --git a/drivers/net/wireless/iwlwifi/iwl-modparams.h b/drivers/net/wireless/iwlwifi/iwl-modparams.h
index d994317db85b..d051857729ab 100644
--- a/drivers/net/wireless/iwlwifi/iwl-modparams.h
+++ b/drivers/net/wireless/iwlwifi/iwl-modparams.h
@@ -119,6 +119,7 @@ struct iwl_mod_params {
119#endif 119#endif
120 int ant_coupling; 120 int ant_coupling;
121 char *nvm_file; 121 char *nvm_file;
122 bool uapsd_disable;
122}; 123};
123 124
124#endif /* #__iwl_modparams_h__ */ 125#endif /* #__iwl_modparams_h__ */
diff --git a/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c b/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c
index 4049c0d626ba..85eee79c495c 100644
--- a/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c
+++ b/drivers/net/wireless/iwlwifi/iwl-nvm-parse.c
@@ -62,6 +62,7 @@
62#include <linux/types.h> 62#include <linux/types.h>
63#include <linux/slab.h> 63#include <linux/slab.h>
64#include <linux/export.h> 64#include <linux/export.h>
65#include <linux/etherdevice.h>
65#include "iwl-drv.h" 66#include "iwl-drv.h"
66#include "iwl-modparams.h" 67#include "iwl-modparams.h"
67#include "iwl-nvm-parse.h" 68#include "iwl-nvm-parse.h"
@@ -127,7 +128,7 @@ static const u8 iwl_nvm_channels[] = {
127 128
128static const u8 iwl_nvm_channels_family_8000[] = { 129static const u8 iwl_nvm_channels_family_8000[] = {
129 /* 2.4 GHz */ 130 /* 2.4 GHz */
130 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 131 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
131 /* 5 GHz */ 132 /* 5 GHz */
132 36, 40, 44, 48, 52, 56, 60, 64, 68, 72, 76, 80, 84, 88, 92, 133 36, 40, 44, 48, 52, 56, 60, 64, 68, 72, 76, 80, 84, 88, 92,
133 96, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140, 144, 134 96, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140, 144,
@@ -137,7 +138,7 @@ static const u8 iwl_nvm_channels_family_8000[] = {
137#define IWL_NUM_CHANNELS ARRAY_SIZE(iwl_nvm_channels) 138#define IWL_NUM_CHANNELS ARRAY_SIZE(iwl_nvm_channels)
138#define IWL_NUM_CHANNELS_FAMILY_8000 ARRAY_SIZE(iwl_nvm_channels_family_8000) 139#define IWL_NUM_CHANNELS_FAMILY_8000 ARRAY_SIZE(iwl_nvm_channels_family_8000)
139#define NUM_2GHZ_CHANNELS 14 140#define NUM_2GHZ_CHANNELS 14
140#define NUM_2GHZ_CHANNELS_FAMILY_8000 13 141#define NUM_2GHZ_CHANNELS_FAMILY_8000 14
141#define FIRST_2GHZ_HT_MINUS 5 142#define FIRST_2GHZ_HT_MINUS 5
142#define LAST_2GHZ_HT_PLUS 9 143#define LAST_2GHZ_HT_PLUS 9
143#define LAST_5GHZ_HT 161 144#define LAST_5GHZ_HT 161
@@ -450,13 +451,7 @@ static void iwl_set_hw_address(const struct iwl_cfg *cfg,
450 struct iwl_nvm_data *data, 451 struct iwl_nvm_data *data,
451 const __le16 *nvm_sec) 452 const __le16 *nvm_sec)
452{ 453{
453 u8 hw_addr[ETH_ALEN]; 454 const u8 *hw_addr = (const u8 *)(nvm_sec + HW_ADDR);
454
455 if (cfg->device_family != IWL_DEVICE_FAMILY_8000)
456 memcpy(hw_addr, nvm_sec + HW_ADDR, ETH_ALEN);
457 else
458 memcpy(hw_addr, nvm_sec + MAC_ADDRESS_OVERRIDE_FAMILY_8000,
459 ETH_ALEN);
460 455
461 /* The byte order is little endian 16 bit, meaning 214365 */ 456 /* The byte order is little endian 16 bit, meaning 214365 */
462 data->hw_addr[0] = hw_addr[1]; 457 data->hw_addr[0] = hw_addr[1];
@@ -467,6 +462,41 @@ static void iwl_set_hw_address(const struct iwl_cfg *cfg,
467 data->hw_addr[5] = hw_addr[4]; 462 data->hw_addr[5] = hw_addr[4];
468} 463}
469 464
465static void iwl_set_hw_address_family_8000(const struct iwl_cfg *cfg,
466 struct iwl_nvm_data *data,
467 const __le16 *mac_override,
468 const __le16 *nvm_hw)
469{
470 const u8 *hw_addr;
471
472 if (mac_override) {
473 hw_addr = (const u8 *)(mac_override +
474 MAC_ADDRESS_OVERRIDE_FAMILY_8000);
475
476 /* The byte order is little endian 16 bit, meaning 214365 */
477 data->hw_addr[0] = hw_addr[1];
478 data->hw_addr[1] = hw_addr[0];
479 data->hw_addr[2] = hw_addr[3];
480 data->hw_addr[3] = hw_addr[2];
481 data->hw_addr[4] = hw_addr[5];
482 data->hw_addr[5] = hw_addr[4];
483
484 if (is_valid_ether_addr(hw_addr))
485 return;
486 }
487
488 /* take the MAC address from the OTP */
489 hw_addr = (const u8 *)(nvm_hw + HW_ADDR0_FAMILY_8000);
490 data->hw_addr[0] = hw_addr[3];
491 data->hw_addr[1] = hw_addr[2];
492 data->hw_addr[2] = hw_addr[1];
493 data->hw_addr[3] = hw_addr[0];
494
495 hw_addr = (const u8 *)(nvm_hw + HW_ADDR1_FAMILY_8000);
496 data->hw_addr[4] = hw_addr[1];
497 data->hw_addr[5] = hw_addr[0];
498}
499
470struct iwl_nvm_data * 500struct iwl_nvm_data *
471iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg, 501iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg,
472 const __le16 *nvm_hw, const __le16 *nvm_sw, 502 const __le16 *nvm_hw, const __le16 *nvm_sw,
@@ -526,7 +556,7 @@ iwl_parse_nvm_data(struct device *dev, const struct iwl_cfg *cfg,
526 rx_chains); 556 rx_chains);
527 } else { 557 } else {
528 /* MAC address in family 8000 */ 558 /* MAC address in family 8000 */
529 iwl_set_hw_address(cfg, data, mac_override); 559 iwl_set_hw_address_family_8000(cfg, data, mac_override, nvm_hw);
530 560
531 iwl_init_sbands(dev, cfg, data, regulatory, 561 iwl_init_sbands(dev, cfg, data, regulatory,
532 sku & NVM_SKU_CAP_11AC_ENABLE, tx_chains, 562 sku & NVM_SKU_CAP_11AC_ENABLE, tx_chains,
diff --git a/drivers/net/wireless/iwlwifi/iwl-phy-db.c b/drivers/net/wireless/iwlwifi/iwl-phy-db.c
index b761ac4822a3..d4fb5cad07ea 100644
--- a/drivers/net/wireless/iwlwifi/iwl-phy-db.c
+++ b/drivers/net/wireless/iwlwifi/iwl-phy-db.c
@@ -345,7 +345,6 @@ static int iwl_send_phy_db_cmd(struct iwl_phy_db *phy_db, u16 type,
345 struct iwl_phy_db_cmd phy_db_cmd; 345 struct iwl_phy_db_cmd phy_db_cmd;
346 struct iwl_host_cmd cmd = { 346 struct iwl_host_cmd cmd = {
347 .id = PHY_DB_CMD, 347 .id = PHY_DB_CMD,
348 .flags = CMD_SYNC,
349 }; 348 };
350 349
351 IWL_DEBUG_INFO(phy_db->trans, 350 IWL_DEBUG_INFO(phy_db->trans,
@@ -393,13 +392,13 @@ static int iwl_phy_db_send_all_channel_groups(
393 entry->data); 392 entry->data);
394 if (err) { 393 if (err) {
395 IWL_ERR(phy_db->trans, 394 IWL_ERR(phy_db->trans,
396 "Can't SEND phy_db section %d (%d), err %d", 395 "Can't SEND phy_db section %d (%d), err %d\n",
397 type, i, err); 396 type, i, err);
398 return err; 397 return err;
399 } 398 }
400 399
401 IWL_DEBUG_INFO(phy_db->trans, 400 IWL_DEBUG_INFO(phy_db->trans,
402 "Sent PHY_DB HCMD, type = %d num = %d", 401 "Sent PHY_DB HCMD, type = %d num = %d\n",
403 type, i); 402 type, i);
404 } 403 }
405 404
@@ -451,7 +450,7 @@ int iwl_send_phy_db_data(struct iwl_phy_db *phy_db)
451 IWL_NUM_PAPD_CH_GROUPS); 450 IWL_NUM_PAPD_CH_GROUPS);
452 if (err) { 451 if (err) {
453 IWL_ERR(phy_db->trans, 452 IWL_ERR(phy_db->trans,
454 "Cannot send channel specific PAPD groups"); 453 "Cannot send channel specific PAPD groups\n");
455 return err; 454 return err;
456 } 455 }
457 456
@@ -461,7 +460,7 @@ int iwl_send_phy_db_data(struct iwl_phy_db *phy_db)
461 IWL_NUM_TXP_CH_GROUPS); 460 IWL_NUM_TXP_CH_GROUPS);
462 if (err) { 461 if (err) {
463 IWL_ERR(phy_db->trans, 462 IWL_ERR(phy_db->trans,
464 "Cannot send channel specific TX power groups"); 463 "Cannot send channel specific TX power groups\n");
465 return err; 464 return err;
466 } 465 }
467 466
diff --git a/drivers/net/wireless/iwlwifi/iwl-prph.h b/drivers/net/wireless/iwlwifi/iwl-prph.h
index 779311080a9e..4997e27672b3 100644
--- a/drivers/net/wireless/iwlwifi/iwl-prph.h
+++ b/drivers/net/wireless/iwlwifi/iwl-prph.h
@@ -105,6 +105,9 @@
105 105
106/* Device NMI register */ 106/* Device NMI register */
107#define DEVICE_SET_NMI_REG 0x00a01c30 107#define DEVICE_SET_NMI_REG 0x00a01c30
108#define DEVICE_SET_NMI_VAL 0x1
109#define DEVICE_SET_NMI_8000B_REG 0x00a01c24
110#define DEVICE_SET_NMI_8000B_VAL 0x1000000
108 111
109/* Shared registers (0x0..0x3ff, via target indirect or periphery */ 112/* Shared registers (0x0..0x3ff, via target indirect or periphery */
110#define SHR_BASE 0x00a10000 113#define SHR_BASE 0x00a10000
diff --git a/drivers/net/wireless/iwlwifi/iwl-trans.h b/drivers/net/wireless/iwlwifi/iwl-trans.h
index 22fd94ec8048..34d49e171fb4 100644
--- a/drivers/net/wireless/iwlwifi/iwl-trans.h
+++ b/drivers/net/wireless/iwlwifi/iwl-trans.h
@@ -189,10 +189,9 @@ static inline u32 iwl_rx_packet_payload_len(const struct iwl_rx_packet *pkt)
189/** 189/**
190 * enum CMD_MODE - how to send the host commands ? 190 * enum CMD_MODE - how to send the host commands ?
191 * 191 *
192 * @CMD_SYNC: The caller will be stalled until the fw responds to the command
193 * @CMD_ASYNC: Return right away and don't wait for the response 192 * @CMD_ASYNC: Return right away and don't wait for the response
194 * @CMD_WANT_SKB: valid only with CMD_SYNC. The caller needs the buffer of the 193 * @CMD_WANT_SKB: Not valid with CMD_ASYNC. The caller needs the buffer of
195 * response. The caller needs to call iwl_free_resp when done. 194 * the response. The caller needs to call iwl_free_resp when done.
196 * @CMD_HIGH_PRIO: The command is high priority - it goes to the front of the 195 * @CMD_HIGH_PRIO: The command is high priority - it goes to the front of the
197 * command queue, but after other high priority commands. valid only 196 * command queue, but after other high priority commands. valid only
198 * with CMD_ASYNC. 197 * with CMD_ASYNC.
@@ -202,7 +201,6 @@ static inline u32 iwl_rx_packet_payload_len(const struct iwl_rx_packet *pkt)
202 * (i.e. mark it as non-idle). 201 * (i.e. mark it as non-idle).
203 */ 202 */
204enum CMD_MODE { 203enum CMD_MODE {
205 CMD_SYNC = 0,
206 CMD_ASYNC = BIT(0), 204 CMD_ASYNC = BIT(0),
207 CMD_WANT_SKB = BIT(1), 205 CMD_WANT_SKB = BIT(1),
208 CMD_SEND_IN_RFKILL = BIT(2), 206 CMD_SEND_IN_RFKILL = BIT(2),
@@ -427,7 +425,7 @@ struct iwl_trans;
427 * @send_cmd:send a host command. Must return -ERFKILL if RFkill is asserted. 425 * @send_cmd:send a host command. Must return -ERFKILL if RFkill is asserted.
428 * If RFkill is asserted in the middle of a SYNC host command, it must 426 * If RFkill is asserted in the middle of a SYNC host command, it must
429 * return -ERFKILL straight away. 427 * return -ERFKILL straight away.
430 * May sleep only if CMD_SYNC is set 428 * May sleep only if CMD_ASYNC is not set
431 * @tx: send an skb 429 * @tx: send an skb
432 * Must be atomic 430 * Must be atomic
433 * @reclaim: free packet until ssn. Returns a list of freed packets. 431 * @reclaim: free packet until ssn. Returns a list of freed packets.
@@ -463,6 +461,11 @@ struct iwl_trans;
463 * @unref: release a reference previously taken with @ref. Note that 461 * @unref: release a reference previously taken with @ref. Note that
464 * initially the reference count is 1, making an initial @unref 462 * initially the reference count is 1, making an initial @unref
465 * necessary to allow low power states. 463 * necessary to allow low power states.
464 * @dump_data: fill a data dump with debug data, maybe containing last
465 * TX'ed commands and similar. When called with a NULL buffer and
466 * zero buffer length, provide only the (estimated) required buffer
467 * length. Return the used buffer length.
468 * Note that the transport must fill in the proper file headers.
466 */ 469 */
467struct iwl_trans_ops { 470struct iwl_trans_ops {
468 471
@@ -470,6 +473,8 @@ struct iwl_trans_ops {
470 void (*op_mode_leave)(struct iwl_trans *iwl_trans); 473 void (*op_mode_leave)(struct iwl_trans *iwl_trans);
471 int (*start_fw)(struct iwl_trans *trans, const struct fw_img *fw, 474 int (*start_fw)(struct iwl_trans *trans, const struct fw_img *fw,
472 bool run_in_rfkill); 475 bool run_in_rfkill);
476 int (*update_sf)(struct iwl_trans *trans,
477 struct iwl_sf_region *st_fwrd_space);
473 void (*fw_alive)(struct iwl_trans *trans, u32 scd_addr); 478 void (*fw_alive)(struct iwl_trans *trans, u32 scd_addr);
474 void (*stop_device)(struct iwl_trans *trans); 479 void (*stop_device)(struct iwl_trans *trans);
475 480
@@ -511,6 +516,10 @@ struct iwl_trans_ops {
511 u32 value); 516 u32 value);
512 void (*ref)(struct iwl_trans *trans); 517 void (*ref)(struct iwl_trans *trans);
513 void (*unref)(struct iwl_trans *trans); 518 void (*unref)(struct iwl_trans *trans);
519
520#ifdef CONFIG_IWLWIFI_DEBUGFS
521 u32 (*dump_data)(struct iwl_trans *trans, void *buf, u32 buflen);
522#endif
514}; 523};
515 524
516/** 525/**
@@ -629,6 +638,17 @@ static inline int iwl_trans_start_fw(struct iwl_trans *trans,
629 return trans->ops->start_fw(trans, fw, run_in_rfkill); 638 return trans->ops->start_fw(trans, fw, run_in_rfkill);
630} 639}
631 640
641static inline int iwl_trans_update_sf(struct iwl_trans *trans,
642 struct iwl_sf_region *st_fwrd_space)
643{
644 might_sleep();
645
646 if (trans->ops->update_sf)
647 return trans->ops->update_sf(trans, st_fwrd_space);
648
649 return 0;
650}
651
632static inline void iwl_trans_stop_device(struct iwl_trans *trans) 652static inline void iwl_trans_stop_device(struct iwl_trans *trans)
633{ 653{
634 might_sleep(); 654 might_sleep();
@@ -664,6 +684,16 @@ static inline void iwl_trans_unref(struct iwl_trans *trans)
664 trans->ops->unref(trans); 684 trans->ops->unref(trans);
665} 685}
666 686
687#ifdef CONFIG_IWLWIFI_DEBUGFS
688static inline u32 iwl_trans_dump_data(struct iwl_trans *trans,
689 void *buf, u32 buflen)
690{
691 if (!trans->ops->dump_data)
692 return 0;
693 return trans->ops->dump_data(trans, buf, buflen);
694}
695#endif
696
667static inline int iwl_trans_send_cmd(struct iwl_trans *trans, 697static inline int iwl_trans_send_cmd(struct iwl_trans *trans,
668 struct iwl_host_cmd *cmd) 698 struct iwl_host_cmd *cmd)
669{ 699{
@@ -677,7 +707,7 @@ static inline int iwl_trans_send_cmd(struct iwl_trans *trans,
677 return -EIO; 707 return -EIO;
678 708
679 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE)) { 709 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE)) {
680 IWL_ERR(trans, "%s bad state = %d", __func__, trans->state); 710 IWL_ERR(trans, "%s bad state = %d\n", __func__, trans->state);
681 return -EIO; 711 return -EIO;
682 } 712 }
683 713
@@ -719,7 +749,7 @@ static inline int iwl_trans_tx(struct iwl_trans *trans, struct sk_buff *skb,
719 return -EIO; 749 return -EIO;
720 750
721 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE)) 751 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE))
722 IWL_ERR(trans, "%s bad state = %d", __func__, trans->state); 752 IWL_ERR(trans, "%s bad state = %d\n", __func__, trans->state);
723 753
724 return trans->ops->tx(trans, skb, dev_cmd, queue); 754 return trans->ops->tx(trans, skb, dev_cmd, queue);
725} 755}
@@ -728,7 +758,7 @@ static inline void iwl_trans_reclaim(struct iwl_trans *trans, int queue,
728 int ssn, struct sk_buff_head *skbs) 758 int ssn, struct sk_buff_head *skbs)
729{ 759{
730 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE)) 760 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE))
731 IWL_ERR(trans, "%s bad state = %d", __func__, trans->state); 761 IWL_ERR(trans, "%s bad state = %d\n", __func__, trans->state);
732 762
733 trans->ops->reclaim(trans, queue, ssn, skbs); 763 trans->ops->reclaim(trans, queue, ssn, skbs);
734} 764}
@@ -745,7 +775,7 @@ static inline void iwl_trans_txq_enable(struct iwl_trans *trans, int queue,
745 might_sleep(); 775 might_sleep();
746 776
747 if (unlikely((trans->state != IWL_TRANS_FW_ALIVE))) 777 if (unlikely((trans->state != IWL_TRANS_FW_ALIVE)))
748 IWL_ERR(trans, "%s bad state = %d", __func__, trans->state); 778 IWL_ERR(trans, "%s bad state = %d\n", __func__, trans->state);
749 779
750 trans->ops->txq_enable(trans, queue, fifo, sta_id, tid, 780 trans->ops->txq_enable(trans, queue, fifo, sta_id, tid,
751 frame_limit, ssn); 781 frame_limit, ssn);
@@ -762,7 +792,7 @@ static inline int iwl_trans_wait_tx_queue_empty(struct iwl_trans *trans,
762 u32 txq_bm) 792 u32 txq_bm)
763{ 793{
764 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE)) 794 if (unlikely(trans->state != IWL_TRANS_FW_ALIVE))
765 IWL_ERR(trans, "%s bad state = %d", __func__, trans->state); 795 IWL_ERR(trans, "%s bad state = %d\n", __func__, trans->state);
766 796
767 return trans->ops->wait_tx_queue_empty(trans, txq_bm); 797 return trans->ops->wait_tx_queue_empty(trans, txq_bm);
768} 798}
diff --git a/drivers/net/wireless/iwlwifi/mvm/Makefile b/drivers/net/wireless/iwlwifi/mvm/Makefile
index ccdd3b7c4cce..c30d7f64ec1e 100644
--- a/drivers/net/wireless/iwlwifi/mvm/Makefile
+++ b/drivers/net/wireless/iwlwifi/mvm/Makefile
@@ -3,8 +3,9 @@ iwlmvm-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 coex.o 5iwlmvm-y += power.o coex.o
6iwlmvm-y += led.o tt.o offloading.o 6iwlmvm-y += tt.o offloading.o
7iwlmvm-$(CONFIG_IWLWIFI_DEBUGFS) += debugfs.o debugfs-vif.o 7iwlmvm-$(CONFIG_IWLWIFI_DEBUGFS) += debugfs.o debugfs-vif.o
8iwlmvm-$(CONFIG_IWLWIFI_LEDS) += led.o
8iwlmvm-$(CONFIG_PM_SLEEP) += d3.o 9iwlmvm-$(CONFIG_PM_SLEEP) += d3.o
9 10
10ccflags-y += -D__CHECK_ENDIAN__ -I$(src)/../ 11ccflags-y += -D__CHECK_ENDIAN__ -I$(src)/../
diff --git a/drivers/net/wireless/iwlwifi/mvm/coex.c b/drivers/net/wireless/iwlwifi/mvm/coex.c
index 4284672d0397..c8c3b38228f0 100644
--- a/drivers/net/wireless/iwlwifi/mvm/coex.c
+++ b/drivers/net/wireless/iwlwifi/mvm/coex.c
@@ -106,7 +106,7 @@ static const u8 iwl_bt_prio_tbl[BT_COEX_PRIO_TBL_EVT_MAX] = {
106 106
107static int iwl_send_bt_prio_tbl(struct iwl_mvm *mvm) 107static int iwl_send_bt_prio_tbl(struct iwl_mvm *mvm)
108{ 108{
109 return iwl_mvm_send_cmd_pdu(mvm, BT_COEX_PRIO_TABLE, CMD_SYNC, 109 return iwl_mvm_send_cmd_pdu(mvm, BT_COEX_PRIO_TABLE, 0,
110 sizeof(struct iwl_bt_coex_prio_tbl_cmd), 110 sizeof(struct iwl_bt_coex_prio_tbl_cmd),
111 &iwl_bt_prio_tbl); 111 &iwl_bt_prio_tbl);
112} 112}
@@ -124,10 +124,10 @@ const u32 iwl_bt_cts_kill_msk[BT_KILL_MSK_MAX] = {
124}; 124};
125 125
126static const __le32 iwl_bt_prio_boost[BT_COEX_BOOST_SIZE] = { 126static const __le32 iwl_bt_prio_boost[BT_COEX_BOOST_SIZE] = {
127 cpu_to_le32(0xf0f0f0f0), 127 cpu_to_le32(0xf0f0f0f0), /* 50% */
128 cpu_to_le32(0xc0c0c0c0), 128 cpu_to_le32(0xc0c0c0c0), /* 25% */
129 cpu_to_le32(0xfcfcfcfc), 129 cpu_to_le32(0xfcfcfcfc), /* 75% */
130 cpu_to_le32(0xff00ff00), 130 cpu_to_le32(0xfefefefe), /* 87.5% */
131}; 131};
132 132
133static const __le32 iwl_single_shared_ant[BT_COEX_MAX_LUT][BT_COEX_LUT_SIZE] = { 133static const __le32 iwl_single_shared_ant[BT_COEX_MAX_LUT][BT_COEX_LUT_SIZE] = {
@@ -300,8 +300,8 @@ static const __le64 iwl_ci_mask[][3] = {
300}; 300};
301 301
302static const __le32 iwl_bt_mprio_lut[BT_COEX_MULTI_PRIO_LUT_SIZE] = { 302static const __le32 iwl_bt_mprio_lut[BT_COEX_MULTI_PRIO_LUT_SIZE] = {
303 cpu_to_le32(0x22002200), 303 cpu_to_le32(0x28412201),
304 cpu_to_le32(0x33113311), 304 cpu_to_le32(0x11118451),
305}; 305};
306 306
307struct corunning_block_luts { 307struct corunning_block_luts {
@@ -565,7 +565,6 @@ int iwl_send_bt_init_conf(struct iwl_mvm *mvm)
565 .id = BT_CONFIG, 565 .id = BT_CONFIG,
566 .len = { sizeof(*bt_cmd), }, 566 .len = { sizeof(*bt_cmd), },
567 .dataflags = { IWL_HCMD_DFL_NOCOPY, }, 567 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
568 .flags = CMD_SYNC,
569 }; 568 };
570 int ret; 569 int ret;
571 u32 flags; 570 u32 flags;
@@ -663,7 +662,6 @@ static int iwl_mvm_bt_udpate_ctrl_kill_msk(struct iwl_mvm *mvm,
663 .data[0] = &bt_cmd, 662 .data[0] = &bt_cmd,
664 .len = { sizeof(*bt_cmd), }, 663 .len = { sizeof(*bt_cmd), },
665 .dataflags = { IWL_HCMD_DFL_NOCOPY, }, 664 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
666 .flags = CMD_SYNC,
667 }; 665 };
668 int ret = 0; 666 int ret = 0;
669 667
@@ -717,7 +715,8 @@ static int iwl_mvm_bt_udpate_ctrl_kill_msk(struct iwl_mvm *mvm,
717 return ret; 715 return ret;
718} 716}
719 717
720int iwl_mvm_bt_coex_reduced_txp(struct iwl_mvm *mvm, u8 sta_id, bool enable) 718static int iwl_mvm_bt_coex_reduced_txp(struct iwl_mvm *mvm, u8 sta_id,
719 bool enable)
721{ 720{
722 struct iwl_bt_coex_cmd *bt_cmd; 721 struct iwl_bt_coex_cmd *bt_cmd;
723 /* Send ASYNC since this can be sent from an atomic context */ 722 /* Send ASYNC since this can be sent from an atomic context */
@@ -735,8 +734,7 @@ int iwl_mvm_bt_coex_reduced_txp(struct iwl_mvm *mvm, u8 sta_id, bool enable)
735 return 0; 734 return 0;
736 735
737 /* nothing to do */ 736 /* nothing to do */
738 if (mvmsta->bt_reduced_txpower_dbg || 737 if (mvmsta->bt_reduced_txpower == enable)
739 mvmsta->bt_reduced_txpower == enable)
740 return 0; 738 return 0;
741 739
742 bt_cmd = kzalloc(sizeof(*bt_cmd), GFP_ATOMIC); 740 bt_cmd = kzalloc(sizeof(*bt_cmd), GFP_ATOMIC);
@@ -803,23 +801,10 @@ static void iwl_mvm_bt_notif_iterator(void *_data, u8 *mac,
803 801
804 switch (vif->type) { 802 switch (vif->type) {
805 case NL80211_IFTYPE_STATION: 803 case NL80211_IFTYPE_STATION:
804 /* Count BSSes vifs */
805 data->num_bss_ifaces++;
806 /* default smps_mode for BSS / P2P client is AUTOMATIC */ 806 /* default smps_mode for BSS / P2P client is AUTOMATIC */
807 smps_mode = IEEE80211_SMPS_AUTOMATIC; 807 smps_mode = IEEE80211_SMPS_AUTOMATIC;
808 data->num_bss_ifaces++;
809
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; 808 break;
824 case NL80211_IFTYPE_AP: 809 case NL80211_IFTYPE_AP:
825 /* default smps_mode for AP / GO is OFF */ 810 /* default smps_mode for AP / GO is OFF */
@@ -845,8 +830,12 @@ static void iwl_mvm_bt_notif_iterator(void *_data, u8 *mac,
845 /* ... relax constraints and disable rssi events */ 830 /* ... relax constraints and disable rssi events */
846 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX, 831 iwl_mvm_update_smps(mvm, vif, IWL_MVM_SMPS_REQ_BT_COEX,
847 smps_mode); 832 smps_mode);
848 if (vif->type == NL80211_IFTYPE_STATION) 833 data->reduced_tx_power = false;
834 if (vif->type == NL80211_IFTYPE_STATION) {
835 iwl_mvm_bt_coex_reduced_txp(mvm, mvmvif->ap_sta_id,
836 false);
849 iwl_mvm_bt_coex_enable_rssi_event(mvm, vif, false, 0); 837 iwl_mvm_bt_coex_enable_rssi_event(mvm, vif, false, 0);
838 }
850 return; 839 return;
851 } 840 }
852 841
@@ -857,6 +846,11 @@ static void iwl_mvm_bt_notif_iterator(void *_data, u8 *mac,
857 smps_mode = vif->type == NL80211_IFTYPE_AP ? 846 smps_mode = vif->type == NL80211_IFTYPE_AP ?
858 IEEE80211_SMPS_OFF : 847 IEEE80211_SMPS_OFF :
859 IEEE80211_SMPS_DYNAMIC; 848 IEEE80211_SMPS_DYNAMIC;
849
850 /* relax SMPS contraints for next association */
851 if (!vif->bss_conf.assoc)
852 smps_mode = IEEE80211_SMPS_AUTOMATIC;
853
860 IWL_DEBUG_COEX(data->mvm, 854 IWL_DEBUG_COEX(data->mvm,
861 "mac %d: bt_status %d bt_activity_grading %d smps_req %d\n", 855 "mac %d: bt_status %d bt_activity_grading %d smps_req %d\n",
862 mvmvif->id, data->notif->bt_status, bt_activity_grading, 856 mvmvif->id, data->notif->bt_status, bt_activity_grading,
@@ -903,22 +897,18 @@ static void iwl_mvm_bt_notif_iterator(void *_data, u8 *mac,
903 /* if secondary is not NULL, it might be a GO */ 897 /* if secondary is not NULL, it might be a GO */
904 data->secondary = chanctx_conf; 898 data->secondary = chanctx_conf;
905 899
906 /* don't reduce the Tx power if in loose scheme */ 900 /*
901 * don't reduce the Tx power if one of these is true:
902 * we are in LOOSE
903 * single share antenna product
904 * BT is active
905 * we are associated
906 */
907 if (iwl_get_coex_type(mvm, vif) == BT_COEX_LOOSE_LUT || 907 if (iwl_get_coex_type(mvm, vif) == BT_COEX_LOOSE_LUT ||
908 mvm->cfg->bt_shared_single_ant) { 908 mvm->cfg->bt_shared_single_ant || !vif->bss_conf.assoc ||
909 data->reduced_tx_power = false; 909 !data->notif->bt_status) {
910 iwl_mvm_bt_coex_enable_rssi_event(mvm, vif, false, 0);
911 return;
912 }
913
914 /* reduced Txpower only if BT is on, so ...*/
915 if (!data->notif->bt_status) {
916 /* ... cancel reduced Tx power ... */
917 if (iwl_mvm_bt_coex_reduced_txp(mvm, mvmvif->ap_sta_id, false))
918 IWL_ERR(mvm, "Couldn't send BT_CONFIG cmd\n");
919 data->reduced_tx_power = false; 910 data->reduced_tx_power = false;
920 911 iwl_mvm_bt_coex_reduced_txp(mvm, mvmvif->ap_sta_id, false);
921 /* ... and there is no need to get reports on RSSI any more. */
922 iwl_mvm_bt_coex_enable_rssi_event(mvm, vif, false, 0); 912 iwl_mvm_bt_coex_enable_rssi_event(mvm, vif, false, 0);
923 return; 913 return;
924 } 914 }
@@ -1022,9 +1012,9 @@ static void iwl_mvm_bt_coex_notif_handle(struct iwl_mvm *mvm)
1022 1012
1023 /* Don't spam the fw with the same command over and over */ 1013 /* Don't spam the fw with the same command over and over */
1024 if (memcmp(&cmd, &mvm->last_bt_ci_cmd, sizeof(cmd))) { 1014 if (memcmp(&cmd, &mvm->last_bt_ci_cmd, sizeof(cmd))) {
1025 if (iwl_mvm_send_cmd_pdu(mvm, BT_COEX_CI, CMD_SYNC, 1015 if (iwl_mvm_send_cmd_pdu(mvm, BT_COEX_CI, 0,
1026 sizeof(cmd), &cmd)) 1016 sizeof(cmd), &cmd))
1027 IWL_ERR(mvm, "Failed to send BT_CI cmd"); 1017 IWL_ERR(mvm, "Failed to send BT_CI cmd\n");
1028 memcpy(&mvm->last_bt_ci_cmd, &cmd, sizeof(cmd)); 1018 memcpy(&mvm->last_bt_ci_cmd, &cmd, sizeof(cmd));
1029 } 1019 }
1030 1020
@@ -1039,7 +1029,6 @@ static void iwl_mvm_bt_coex_notif_handle(struct iwl_mvm *mvm)
1039 IWL_ERR(mvm, "Failed to update the ctrl_kill_msk\n"); 1029 IWL_ERR(mvm, "Failed to update the ctrl_kill_msk\n");
1040} 1030}
1041 1031
1042/* upon association, the fw will send in BT Coex notification */
1043int iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm, 1032int iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm,
1044 struct iwl_rx_cmd_buffer *rxb, 1033 struct iwl_rx_cmd_buffer *rxb,
1045 struct iwl_device_cmd *dev_cmd) 1034 struct iwl_device_cmd *dev_cmd)
@@ -1278,7 +1267,6 @@ int iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm,
1278 .id = BT_CONFIG, 1267 .id = BT_CONFIG,
1279 .len = { sizeof(*bt_cmd), }, 1268 .len = { sizeof(*bt_cmd), },
1280 .dataflags = { IWL_HCMD_DFL_NOCOPY, }, 1269 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
1281 .flags = CMD_SYNC,
1282 }; 1270 };
1283 1271
1284 if (!IWL_MVM_BT_COEX_CORUNNING) 1272 if (!IWL_MVM_BT_COEX_CORUNNING)
diff --git a/drivers/net/wireless/iwlwifi/mvm/d3.c b/drivers/net/wireless/iwlwifi/mvm/d3.c
index 7694472a303e..645b3cfc29a5 100644
--- a/drivers/net/wireless/iwlwifi/mvm/d3.c
+++ b/drivers/net/wireless/iwlwifi/mvm/d3.c
@@ -193,8 +193,7 @@ static void iwl_mvm_wowlan_program_keys(struct ieee80211_hw *hw,
193 wkc.wep_key.key_offset = data->wep_key_idx; 193 wkc.wep_key.key_offset = data->wep_key_idx;
194 } 194 }
195 195
196 ret = iwl_mvm_send_cmd_pdu(mvm, WEP_KEY, CMD_SYNC, 196 ret = iwl_mvm_send_cmd_pdu(mvm, WEP_KEY, 0, sizeof(wkc), &wkc);
197 sizeof(wkc), &wkc);
198 data->error = ret != 0; 197 data->error = ret != 0;
199 198
200 mvm->ptk_ivlen = key->iv_len; 199 mvm->ptk_ivlen = key->iv_len;
@@ -341,7 +340,6 @@ static int iwl_mvm_send_patterns(struct iwl_mvm *mvm,
341 struct iwl_host_cmd cmd = { 340 struct iwl_host_cmd cmd = {
342 .id = WOWLAN_PATTERNS, 341 .id = WOWLAN_PATTERNS,
343 .dataflags[0] = IWL_HCMD_DFL_NOCOPY, 342 .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
344 .flags = CMD_SYNC,
345 }; 343 };
346 int i, err; 344 int i, err;
347 345
@@ -518,7 +516,6 @@ static int iwl_mvm_send_remote_wake_cfg(struct iwl_mvm *mvm,
518 .id = REMOTE_WAKE_CONFIG_CMD, 516 .id = REMOTE_WAKE_CONFIG_CMD,
519 .len = { sizeof(*cfg), }, 517 .len = { sizeof(*cfg), },
520 .dataflags = { IWL_HCMD_DFL_NOCOPY, }, 518 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
521 .flags = CMD_SYNC,
522 }; 519 };
523 int ret; 520 int ret;
524 521
@@ -666,10 +663,8 @@ static int iwl_mvm_d3_reprogram(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
666 663
667 if (WARN_ON(!vif->bss_conf.assoc)) 664 if (WARN_ON(!vif->bss_conf.assoc))
668 return -EINVAL; 665 return -EINVAL;
669 /* hack */ 666
670 vif->bss_conf.assoc = false;
671 ret = iwl_mvm_mac_ctxt_add(mvm, vif); 667 ret = iwl_mvm_mac_ctxt_add(mvm, vif);
672 vif->bss_conf.assoc = true;
673 if (ret) 668 if (ret)
674 return ret; 669 return ret;
675 670
@@ -705,7 +700,7 @@ static int iwl_mvm_d3_reprogram(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
705 return ret; 700 return ret;
706 rcu_assign_pointer(mvm->fw_id_to_mac_id[mvmvif->ap_sta_id], ap_sta); 701 rcu_assign_pointer(mvm->fw_id_to_mac_id[mvmvif->ap_sta_id], ap_sta);
707 702
708 ret = iwl_mvm_mac_ctxt_changed(mvm, vif); 703 ret = iwl_mvm_mac_ctxt_changed(mvm, vif, false);
709 if (ret) 704 if (ret)
710 return ret; 705 return ret;
711 706
@@ -719,7 +714,7 @@ static int iwl_mvm_d3_reprogram(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
719 for (i = 1; i < MAX_BINDINGS; i++) 714 for (i = 1; i < MAX_BINDINGS; i++)
720 quota_cmd.quotas[i].id_and_color = cpu_to_le32(FW_CTXT_INVALID); 715 quota_cmd.quotas[i].id_and_color = cpu_to_le32(FW_CTXT_INVALID);
721 716
722 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_QUOTA_CMD, CMD_SYNC, 717 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_QUOTA_CMD, 0,
723 sizeof(quota_cmd), &quota_cmd); 718 sizeof(quota_cmd), &quota_cmd);
724 if (ret) 719 if (ret)
725 IWL_ERR(mvm, "Failed to send quota: %d\n", ret); 720 IWL_ERR(mvm, "Failed to send quota: %d\n", ret);
@@ -739,7 +734,7 @@ static int iwl_mvm_get_last_nonqos_seq(struct iwl_mvm *mvm,
739 }; 734 };
740 struct iwl_host_cmd cmd = { 735 struct iwl_host_cmd cmd = {
741 .id = NON_QOS_TX_COUNTER_CMD, 736 .id = NON_QOS_TX_COUNTER_CMD,
742 .flags = CMD_SYNC | CMD_WANT_SKB, 737 .flags = CMD_WANT_SKB,
743 }; 738 };
744 int err; 739 int err;
745 u32 size; 740 u32 size;
@@ -781,7 +776,7 @@ void iwl_mvm_set_last_nonqos_seq(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
781 776
782 mvmvif->seqno_valid = false; 777 mvmvif->seqno_valid = false;
783 778
784 if (iwl_mvm_send_cmd_pdu(mvm, NON_QOS_TX_COUNTER_CMD, CMD_SYNC, 779 if (iwl_mvm_send_cmd_pdu(mvm, NON_QOS_TX_COUNTER_CMD, 0,
785 sizeof(query_cmd), &query_cmd)) 780 sizeof(query_cmd), &query_cmd))
786 IWL_ERR(mvm, "failed to set non-QoS seqno\n"); 781 IWL_ERR(mvm, "failed to set non-QoS seqno\n");
787} 782}
@@ -796,7 +791,7 @@ iwl_mvm_send_wowlan_config_cmd(struct iwl_mvm *mvm,
796 if (mvm->fw->ucode_capa.api[0] & IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID) 791 if (mvm->fw->ucode_capa.api[0] & IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID)
797 cmd_len = sizeof(*cmd); 792 cmd_len = sizeof(*cmd);
798 793
799 return iwl_mvm_send_cmd_pdu(mvm, WOWLAN_CONFIGURATION, CMD_SYNC, 794 return iwl_mvm_send_cmd_pdu(mvm, WOWLAN_CONFIGURATION, 0,
800 cmd_len, cmd); 795 cmd_len, cmd);
801} 796}
802 797
@@ -825,7 +820,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
825 }; 820 };
826 struct iwl_host_cmd d3_cfg_cmd = { 821 struct iwl_host_cmd d3_cfg_cmd = {
827 .id = D3_CONFIG_CMD, 822 .id = D3_CONFIG_CMD,
828 .flags = CMD_SYNC | CMD_WANT_SKB, 823 .flags = CMD_WANT_SKB,
829 .data[0] = &d3_cfg_cmd_data, 824 .data[0] = &d3_cfg_cmd_data,
830 .len[0] = sizeof(d3_cfg_cmd_data), 825 .len[0] = sizeof(d3_cfg_cmd_data),
831 }; 826 };
@@ -975,7 +970,6 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
975 if (key_data.use_rsc_tsc) { 970 if (key_data.use_rsc_tsc) {
976 struct iwl_host_cmd rsc_tsc_cmd = { 971 struct iwl_host_cmd rsc_tsc_cmd = {
977 .id = WOWLAN_TSC_RSC_PARAM, 972 .id = WOWLAN_TSC_RSC_PARAM,
978 .flags = CMD_SYNC,
979 .data[0] = key_data.rsc_tsc, 973 .data[0] = key_data.rsc_tsc,
980 .dataflags[0] = IWL_HCMD_DFL_NOCOPY, 974 .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
981 .len[0] = sizeof(*key_data.rsc_tsc), 975 .len[0] = sizeof(*key_data.rsc_tsc),
@@ -989,7 +983,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
989 if (key_data.use_tkip) { 983 if (key_data.use_tkip) {
990 ret = iwl_mvm_send_cmd_pdu(mvm, 984 ret = iwl_mvm_send_cmd_pdu(mvm,
991 WOWLAN_TKIP_PARAM, 985 WOWLAN_TKIP_PARAM,
992 CMD_SYNC, sizeof(tkip_cmd), 986 0, sizeof(tkip_cmd),
993 &tkip_cmd); 987 &tkip_cmd);
994 if (ret) 988 if (ret)
995 goto out; 989 goto out;
@@ -1006,8 +1000,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1006 kek_kck_cmd.replay_ctr = mvmvif->rekey_data.replay_ctr; 1000 kek_kck_cmd.replay_ctr = mvmvif->rekey_data.replay_ctr;
1007 1001
1008 ret = iwl_mvm_send_cmd_pdu(mvm, 1002 ret = iwl_mvm_send_cmd_pdu(mvm,
1009 WOWLAN_KEK_KCK_MATERIAL, 1003 WOWLAN_KEK_KCK_MATERIAL, 0,
1010 CMD_SYNC,
1011 sizeof(kek_kck_cmd), 1004 sizeof(kek_kck_cmd),
1012 &kek_kck_cmd); 1005 &kek_kck_cmd);
1013 if (ret) 1006 if (ret)
@@ -1023,7 +1016,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1023 if (ret) 1016 if (ret)
1024 goto out; 1017 goto out;
1025 1018
1026 ret = iwl_mvm_send_proto_offload(mvm, vif, false, CMD_SYNC); 1019 ret = iwl_mvm_send_proto_offload(mvm, vif, false, 0);
1027 if (ret) 1020 if (ret)
1028 goto out; 1021 goto out;
1029 1022
@@ -1035,7 +1028,7 @@ static int __iwl_mvm_suspend(struct ieee80211_hw *hw,
1035 if (ret) 1028 if (ret)
1036 goto out; 1029 goto out;
1037 1030
1038 ret = iwl_mvm_power_update_mac(mvm, vif); 1031 ret = iwl_mvm_power_update_mac(mvm);
1039 if (ret) 1032 if (ret)
1040 goto out; 1033 goto out;
1041 1034
@@ -1466,7 +1459,7 @@ static bool iwl_mvm_query_wakeup_reasons(struct iwl_mvm *mvm,
1466 } err_info; 1459 } err_info;
1467 struct iwl_host_cmd cmd = { 1460 struct iwl_host_cmd cmd = {
1468 .id = WOWLAN_GET_STATUSES, 1461 .id = WOWLAN_GET_STATUSES,
1469 .flags = CMD_SYNC | CMD_WANT_SKB, 1462 .flags = CMD_WANT_SKB,
1470 }; 1463 };
1471 struct iwl_wowlan_status_data status; 1464 struct iwl_wowlan_status_data status;
1472 struct iwl_wowlan_status *fw_status; 1465 struct iwl_wowlan_status *fw_status;
@@ -1492,7 +1485,7 @@ static bool iwl_mvm_query_wakeup_reasons(struct iwl_mvm *mvm,
1492 } 1485 }
1493 1486
1494 /* only for tracing for now */ 1487 /* only for tracing for now */
1495 ret = iwl_mvm_send_cmd_pdu(mvm, OFFLOADS_QUERY_CMD, CMD_SYNC, 0, NULL); 1488 ret = iwl_mvm_send_cmd_pdu(mvm, OFFLOADS_QUERY_CMD, 0, 0, NULL);
1496 if (ret) 1489 if (ret)
1497 IWL_ERR(mvm, "failed to query offload statistics (%d)\n", ret); 1490 IWL_ERR(mvm, "failed to query offload statistics (%d)\n", ret);
1498 1491
diff --git a/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c b/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c
index 6047cfdafb95..2e90ff795c13 100644
--- a/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c
+++ b/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c
@@ -175,7 +175,7 @@ static ssize_t iwl_dbgfs_pm_params_write(struct ieee80211_vif *vif, char *buf,
175 175
176 mutex_lock(&mvm->mutex); 176 mutex_lock(&mvm->mutex);
177 iwl_dbgfs_update_pm(mvm, vif, param, val); 177 iwl_dbgfs_update_pm(mvm, vif, param, val);
178 ret = iwl_mvm_power_update_mac(mvm, vif); 178 ret = iwl_mvm_power_update_mac(mvm);
179 mutex_unlock(&mvm->mutex); 179 mutex_unlock(&mvm->mutex);
180 180
181 return ret ?: count; 181 return ret ?: count;
@@ -262,10 +262,9 @@ static ssize_t iwl_dbgfs_mac_params_read(struct file *file,
262 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv; 262 struct iwl_mvm_sta *mvm_sta = (void *)sta->drv_priv;
263 263
264 pos += scnprintf(buf+pos, bufsz-pos, 264 pos += scnprintf(buf+pos, bufsz-pos,
265 "ap_sta_id %d - reduced Tx power %d force %d\n", 265 "ap_sta_id %d - reduced Tx power %d\n",
266 ap_sta_id, 266 ap_sta_id,
267 mvm_sta->bt_reduced_txpower, 267 mvm_sta->bt_reduced_txpower);
268 mvm_sta->bt_reduced_txpower_dbg);
269 } 268 }
270 } 269 }
271 270
@@ -283,41 +282,6 @@ static ssize_t iwl_dbgfs_mac_params_read(struct file *file,
283 return simple_read_from_buffer(user_buf, count, ppos, buf, pos); 282 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
284} 283}
285 284
286static ssize_t iwl_dbgfs_reduced_txp_write(struct ieee80211_vif *vif,
287 char *buf, size_t count,
288 loff_t *ppos)
289{
290 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
291 struct iwl_mvm *mvm = mvmvif->mvm;
292 struct iwl_mvm_sta *mvmsta;
293 bool reduced_tx_power;
294 int ret;
295
296 if (mvmvif->ap_sta_id >= ARRAY_SIZE(mvm->fw_id_to_mac_id))
297 return -ENOTCONN;
298
299 if (strtobool(buf, &reduced_tx_power) != 0)
300 return -EINVAL;
301
302 mutex_lock(&mvm->mutex);
303
304 mvmsta = iwl_mvm_sta_from_staid_protected(mvm, mvmvif->ap_sta_id);
305 if (IS_ERR_OR_NULL(mvmsta)) {
306 mutex_unlock(&mvm->mutex);
307 return -ENOTCONN;
308 }
309
310 mvmsta->bt_reduced_txpower_dbg = false;
311 ret = iwl_mvm_bt_coex_reduced_txp(mvm, mvmvif->ap_sta_id,
312 reduced_tx_power);
313 if (!ret)
314 mvmsta->bt_reduced_txpower_dbg = true;
315
316 mutex_unlock(&mvm->mutex);
317
318 return ret ? : count;
319}
320
321static void iwl_dbgfs_update_bf(struct ieee80211_vif *vif, 285static void iwl_dbgfs_update_bf(struct ieee80211_vif *vif,
322 enum iwl_dbgfs_bf_mask param, int value) 286 enum iwl_dbgfs_bf_mask param, int value)
323{ 287{
@@ -452,9 +416,9 @@ static ssize_t iwl_dbgfs_bf_params_write(struct ieee80211_vif *vif, char *buf,
452 mutex_lock(&mvm->mutex); 416 mutex_lock(&mvm->mutex);
453 iwl_dbgfs_update_bf(vif, param, value); 417 iwl_dbgfs_update_bf(vif, param, value);
454 if (param == MVM_DEBUGFS_BF_ENABLE_BEACON_FILTER && !value) 418 if (param == MVM_DEBUGFS_BF_ENABLE_BEACON_FILTER && !value)
455 ret = iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC); 419 ret = iwl_mvm_disable_beacon_filter(mvm, vif, 0);
456 else 420 else
457 ret = iwl_mvm_enable_beacon_filter(mvm, vif, CMD_SYNC); 421 ret = iwl_mvm_enable_beacon_filter(mvm, vif, 0);
458 mutex_unlock(&mvm->mutex); 422 mutex_unlock(&mvm->mutex);
459 423
460 return ret ?: count; 424 return ret ?: count;
@@ -558,7 +522,6 @@ MVM_DEBUGFS_READ_FILE_OPS(mac_params);
558MVM_DEBUGFS_READ_WRITE_FILE_OPS(pm_params, 32); 522MVM_DEBUGFS_READ_WRITE_FILE_OPS(pm_params, 32);
559MVM_DEBUGFS_READ_WRITE_FILE_OPS(bf_params, 256); 523MVM_DEBUGFS_READ_WRITE_FILE_OPS(bf_params, 256);
560MVM_DEBUGFS_READ_WRITE_FILE_OPS(low_latency, 10); 524MVM_DEBUGFS_READ_WRITE_FILE_OPS(low_latency, 10);
561MVM_DEBUGFS_WRITE_FILE_OPS(reduced_txp, 10);
562 525
563void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif) 526void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
564{ 527{
@@ -590,7 +553,6 @@ void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
590 S_IRUSR); 553 S_IRUSR);
591 554
592 MVM_DEBUGFS_ADD_FILE_VIF(mac_params, mvmvif->dbgfs_dir, S_IRUSR); 555 MVM_DEBUGFS_ADD_FILE_VIF(mac_params, mvmvif->dbgfs_dir, S_IRUSR);
593 MVM_DEBUGFS_ADD_FILE_VIF(reduced_txp, mvmvif->dbgfs_dir, S_IWUSR);
594 MVM_DEBUGFS_ADD_FILE_VIF(low_latency, mvmvif->dbgfs_dir, 556 MVM_DEBUGFS_ADD_FILE_VIF(low_latency, mvmvif->dbgfs_dir,
595 S_IRUSR | S_IWUSR); 557 S_IRUSR | S_IWUSR);
596 558
diff --git a/drivers/net/wireless/iwlwifi/mvm/debugfs.c b/drivers/net/wireless/iwlwifi/mvm/debugfs.c
index f462c9baa2b5..29ca72695eaa 100644
--- a/drivers/net/wireless/iwlwifi/mvm/debugfs.c
+++ b/drivers/net/wireless/iwlwifi/mvm/debugfs.c
@@ -65,9 +65,8 @@
65#include "mvm.h" 65#include "mvm.h"
66#include "sta.h" 66#include "sta.h"
67#include "iwl-io.h" 67#include "iwl-io.h"
68#include "iwl-prph.h"
69#include "debugfs.h" 68#include "debugfs.h"
70#include "fw-error-dump.h" 69#include "iwl-fw-error-dump.h"
71 70
72static ssize_t iwl_dbgfs_tx_flush_write(struct iwl_mvm *mvm, char *buf, 71static ssize_t iwl_dbgfs_tx_flush_write(struct iwl_mvm *mvm, char *buf,
73 size_t count, loff_t *ppos) 72 size_t count, loff_t *ppos)
@@ -681,7 +680,7 @@ static ssize_t iwl_dbgfs_fw_restart_write(struct iwl_mvm *mvm, char *buf,
681 mvm->restart_fw++; 680 mvm->restart_fw++;
682 681
683 /* take the return value to make compiler happy - it will fail anyway */ 682 /* take the return value to make compiler happy - it will fail anyway */
684 ret = iwl_mvm_send_cmd_pdu(mvm, REPLY_ERROR, CMD_SYNC, 0, NULL); 683 ret = iwl_mvm_send_cmd_pdu(mvm, REPLY_ERROR, 0, 0, NULL);
685 684
686 mutex_unlock(&mvm->mutex); 685 mutex_unlock(&mvm->mutex);
687 686
@@ -691,7 +690,7 @@ static ssize_t iwl_dbgfs_fw_restart_write(struct iwl_mvm *mvm, char *buf,
691static ssize_t iwl_dbgfs_fw_nmi_write(struct iwl_mvm *mvm, char *buf, 690static ssize_t iwl_dbgfs_fw_nmi_write(struct iwl_mvm *mvm, char *buf,
692 size_t count, loff_t *ppos) 691 size_t count, loff_t *ppos)
693{ 692{
694 iwl_write_prph(mvm->trans, DEVICE_SET_NMI_REG, 1); 693 iwl_force_nmi(mvm->trans);
695 694
696 return count; 695 return count;
697} 696}
@@ -838,7 +837,7 @@ static ssize_t iwl_dbgfs_bcast_filters_write(struct iwl_mvm *mvm, char *buf,
838 /* send updated bcast filtering configuration */ 837 /* send updated bcast filtering configuration */
839 if (mvm->dbgfs_bcast_filtering.override && 838 if (mvm->dbgfs_bcast_filtering.override &&
840 iwl_mvm_bcast_filter_build_cmd(mvm, &cmd)) 839 iwl_mvm_bcast_filter_build_cmd(mvm, &cmd))
841 err = iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, CMD_SYNC, 840 err = iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, 0,
842 sizeof(cmd), &cmd); 841 sizeof(cmd), &cmd);
843 mutex_unlock(&mvm->mutex); 842 mutex_unlock(&mvm->mutex);
844 843
@@ -910,7 +909,7 @@ static ssize_t iwl_dbgfs_bcast_filters_macs_write(struct iwl_mvm *mvm,
910 /* send updated bcast filtering configuration */ 909 /* send updated bcast filtering configuration */
911 if (mvm->dbgfs_bcast_filtering.override && 910 if (mvm->dbgfs_bcast_filtering.override &&
912 iwl_mvm_bcast_filter_build_cmd(mvm, &cmd)) 911 iwl_mvm_bcast_filter_build_cmd(mvm, &cmd))
913 err = iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, CMD_SYNC, 912 err = iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, 0,
914 sizeof(cmd), &cmd); 913 sizeof(cmd), &cmd);
915 mutex_unlock(&mvm->mutex); 914 mutex_unlock(&mvm->mutex);
916 915
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw.c b/drivers/net/wireless/iwlwifi/mvm/fw.c
index 3d99cf564ba6..883e702152d5 100644
--- a/drivers/net/wireless/iwlwifi/mvm/fw.c
+++ b/drivers/net/wireless/iwlwifi/mvm/fw.c
@@ -99,7 +99,7 @@ static int iwl_send_tx_ant_cfg(struct iwl_mvm *mvm, u8 valid_tx_ant)
99 }; 99 };
100 100
101 IWL_DEBUG_FW(mvm, "select valid tx ant: %u\n", valid_tx_ant); 101 IWL_DEBUG_FW(mvm, "select valid tx ant: %u\n", valid_tx_ant);
102 return iwl_mvm_send_cmd_pdu(mvm, TX_ANT_CONFIGURATION_CMD, CMD_SYNC, 102 return iwl_mvm_send_cmd_pdu(mvm, TX_ANT_CONFIGURATION_CMD, 0,
103 sizeof(tx_ant_cmd), &tx_ant_cmd); 103 sizeof(tx_ant_cmd), &tx_ant_cmd);
104} 104}
105 105
@@ -137,6 +137,8 @@ static bool iwl_alive_fn(struct iwl_notif_wait_data *notif_wait,
137 alive_data->scd_base_addr = le32_to_cpu(palive2->scd_base_ptr); 137 alive_data->scd_base_addr = le32_to_cpu(palive2->scd_base_ptr);
138 mvm->umac_error_event_table = 138 mvm->umac_error_event_table =
139 le32_to_cpu(palive2->error_info_addr); 139 le32_to_cpu(palive2->error_info_addr);
140 mvm->sf_space.addr = le32_to_cpu(palive2->st_fwrd_addr);
141 mvm->sf_space.size = le32_to_cpu(palive2->st_fwrd_size);
140 142
141 alive_data->valid = le16_to_cpu(palive2->status) == 143 alive_data->valid = le16_to_cpu(palive2->status) ==
142 IWL_ALIVE_STATUS_OK; 144 IWL_ALIVE_STATUS_OK;
@@ -180,6 +182,7 @@ static int iwl_mvm_load_ucode_wait_alive(struct iwl_mvm *mvm,
180 int ret, i; 182 int ret, i;
181 enum iwl_ucode_type old_type = mvm->cur_ucode; 183 enum iwl_ucode_type old_type = mvm->cur_ucode;
182 static const u8 alive_cmd[] = { MVM_ALIVE }; 184 static const u8 alive_cmd[] = { MVM_ALIVE };
185 struct iwl_sf_region st_fwrd_space;
183 186
184 fw = iwl_get_ucode_image(mvm, ucode_type); 187 fw = iwl_get_ucode_image(mvm, ucode_type);
185 if (WARN_ON(!fw)) 188 if (WARN_ON(!fw))
@@ -215,6 +218,14 @@ static int iwl_mvm_load_ucode_wait_alive(struct iwl_mvm *mvm,
215 return -EIO; 218 return -EIO;
216 } 219 }
217 220
221 /*
222 * update the sdio allocation according to the pointer we get in the
223 * alive notification.
224 */
225 st_fwrd_space.addr = mvm->sf_space.addr;
226 st_fwrd_space.size = mvm->sf_space.size;
227 ret = iwl_trans_update_sf(mvm->trans, &st_fwrd_space);
228
218 iwl_trans_fw_alive(mvm->trans, alive_data.scd_base_addr); 229 iwl_trans_fw_alive(mvm->trans, alive_data.scd_base_addr);
219 230
220 /* 231 /*
@@ -256,7 +267,7 @@ static int iwl_send_phy_cfg_cmd(struct iwl_mvm *mvm)
256 IWL_DEBUG_INFO(mvm, "Sending Phy CFG command: 0x%x\n", 267 IWL_DEBUG_INFO(mvm, "Sending Phy CFG command: 0x%x\n",
257 phy_cfg_cmd.phy_cfg); 268 phy_cfg_cmd.phy_cfg);
258 269
259 return iwl_mvm_send_cmd_pdu(mvm, PHY_CONFIGURATION_CMD, CMD_SYNC, 270 return iwl_mvm_send_cmd_pdu(mvm, PHY_CONFIGURATION_CMD, 0,
260 sizeof(phy_cfg_cmd), &phy_cfg_cmd); 271 sizeof(phy_cfg_cmd), &phy_cfg_cmd);
261} 272}
262 273
@@ -295,7 +306,7 @@ int iwl_run_init_mvm_ucode(struct iwl_mvm *mvm, bool read_nvm)
295 /* Read the NVM only at driver load time, no need to do this twice */ 306 /* Read the NVM only at driver load time, no need to do this twice */
296 if (read_nvm) { 307 if (read_nvm) {
297 /* Read nvm */ 308 /* Read nvm */
298 ret = iwl_nvm_init(mvm); 309 ret = iwl_nvm_init(mvm, true);
299 if (ret) { 310 if (ret) {
300 IWL_ERR(mvm, "Failed to read NVM: %d\n", ret); 311 IWL_ERR(mvm, "Failed to read NVM: %d\n", ret);
301 goto error; 312 goto error;
@@ -303,7 +314,7 @@ int iwl_run_init_mvm_ucode(struct iwl_mvm *mvm, bool read_nvm)
303 } 314 }
304 315
305 /* In case we read the NVM from external file, load it to the NIC */ 316 /* In case we read the NVM from external file, load it to the NIC */
306 if (iwlwifi_mod_params.nvm_file) 317 if (mvm->nvm_file_name)
307 iwl_mvm_load_nvm_to_nic(mvm); 318 iwl_mvm_load_nvm_to_nic(mvm);
308 319
309 ret = iwl_nvm_check_version(mvm->nvm_data, mvm->trans); 320 ret = iwl_nvm_check_version(mvm->nvm_data, mvm->trans);
diff --git a/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c b/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c
index 7110ec2605d6..8b5302777632 100644
--- a/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c
+++ b/drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c
@@ -685,7 +685,7 @@ static void iwl_mvm_mac_ctxt_cmd_common(struct iwl_mvm *mvm,
685static int iwl_mvm_mac_ctxt_send_cmd(struct iwl_mvm *mvm, 685static int iwl_mvm_mac_ctxt_send_cmd(struct iwl_mvm *mvm,
686 struct iwl_mac_ctx_cmd *cmd) 686 struct iwl_mac_ctx_cmd *cmd)
687{ 687{
688 int ret = iwl_mvm_send_cmd_pdu(mvm, MAC_CONTEXT_CMD, CMD_SYNC, 688 int ret = iwl_mvm_send_cmd_pdu(mvm, MAC_CONTEXT_CMD, 0,
689 sizeof(*cmd), cmd); 689 sizeof(*cmd), cmd);
690 if (ret) 690 if (ret)
691 IWL_ERR(mvm, "Failed to send MAC context (action:%d): %d\n", 691 IWL_ERR(mvm, "Failed to send MAC context (action:%d): %d\n",
@@ -693,19 +693,39 @@ static int iwl_mvm_mac_ctxt_send_cmd(struct iwl_mvm *mvm,
693 return ret; 693 return ret;
694} 694}
695 695
696/* 696static int iwl_mvm_mac_ctxt_cmd_sta(struct iwl_mvm *mvm,
697 * Fill the specific data for mac context of type station or p2p client 697 struct ieee80211_vif *vif,
698 */ 698 u32 action, bool force_assoc_off)
699static void iwl_mvm_mac_ctxt_cmd_fill_sta(struct iwl_mvm *mvm,
700 struct ieee80211_vif *vif,
701 struct iwl_mac_data_sta *ctxt_sta,
702 bool force_assoc_off)
703{ 699{
700 struct iwl_mac_ctx_cmd cmd = {};
701 struct iwl_mac_data_sta *ctxt_sta;
702
703 WARN_ON(vif->type != NL80211_IFTYPE_STATION);
704
705 /* Fill the common data for all mac context types */
706 iwl_mvm_mac_ctxt_cmd_common(mvm, vif, &cmd, action);
707
708 if (vif->p2p) {
709 struct ieee80211_p2p_noa_attr *noa =
710 &vif->bss_conf.p2p_noa_attr;
711
712 cmd.p2p_sta.ctwin = cpu_to_le32(noa->oppps_ctwindow &
713 IEEE80211_P2P_OPPPS_CTWINDOW_MASK);
714 ctxt_sta = &cmd.p2p_sta.sta;
715 } else {
716 ctxt_sta = &cmd.sta;
717 }
718
704 /* We need the dtim_period to set the MAC as associated */ 719 /* We need the dtim_period to set the MAC as associated */
705 if (vif->bss_conf.assoc && vif->bss_conf.dtim_period && 720 if (vif->bss_conf.assoc && vif->bss_conf.dtim_period &&
706 !force_assoc_off) { 721 !force_assoc_off) {
707 u32 dtim_offs; 722 u32 dtim_offs;
708 723
724 /* Allow beacons to pass through as long as we are not
725 * associated, or we do not have dtim period information.
726 */
727 cmd.filter_flags |= cpu_to_le32(MAC_FILTER_IN_BEACON);
728
709 /* 729 /*
710 * The DTIM count counts down, so when it is N that means N 730 * The DTIM count counts down, so when it is N that means N
711 * more beacon intervals happen until the DTIM TBTT. Therefore 731 * more beacon intervals happen until the DTIM TBTT. Therefore
@@ -752,51 +772,6 @@ static void iwl_mvm_mac_ctxt_cmd_fill_sta(struct iwl_mvm *mvm,
752 772
753 ctxt_sta->listen_interval = cpu_to_le32(mvm->hw->conf.listen_interval); 773 ctxt_sta->listen_interval = cpu_to_le32(mvm->hw->conf.listen_interval);
754 ctxt_sta->assoc_id = cpu_to_le32(vif->bss_conf.aid); 774 ctxt_sta->assoc_id = cpu_to_le32(vif->bss_conf.aid);
755}
756
757static int iwl_mvm_mac_ctxt_cmd_station(struct iwl_mvm *mvm,
758 struct ieee80211_vif *vif,
759 u32 action)
760{
761 struct iwl_mac_ctx_cmd cmd = {};
762
763 WARN_ON(vif->type != NL80211_IFTYPE_STATION || vif->p2p);
764
765 /* Fill the common data for all mac context types */
766 iwl_mvm_mac_ctxt_cmd_common(mvm, vif, &cmd, action);
767
768 /* Allow beacons to pass through as long as we are not associated,or we
769 * do not have dtim period information */
770 if (!vif->bss_conf.assoc || !vif->bss_conf.dtim_period)
771 cmd.filter_flags |= cpu_to_le32(MAC_FILTER_IN_BEACON);
772 else
773 cmd.filter_flags &= ~cpu_to_le32(MAC_FILTER_IN_BEACON);
774
775 /* Fill the data specific for station mode */
776 iwl_mvm_mac_ctxt_cmd_fill_sta(mvm, vif, &cmd.sta,
777 action == FW_CTXT_ACTION_ADD);
778
779 return iwl_mvm_mac_ctxt_send_cmd(mvm, &cmd);
780}
781
782static int iwl_mvm_mac_ctxt_cmd_p2p_client(struct iwl_mvm *mvm,
783 struct ieee80211_vif *vif,
784 u32 action)
785{
786 struct iwl_mac_ctx_cmd cmd = {};
787 struct ieee80211_p2p_noa_attr *noa = &vif->bss_conf.p2p_noa_attr;
788
789 WARN_ON(vif->type != NL80211_IFTYPE_STATION || !vif->p2p);
790
791 /* Fill the common data for all mac context types */
792 iwl_mvm_mac_ctxt_cmd_common(mvm, vif, &cmd, action);
793
794 /* Fill the data specific for station mode */
795 iwl_mvm_mac_ctxt_cmd_fill_sta(mvm, vif, &cmd.p2p_sta.sta,
796 action == FW_CTXT_ACTION_ADD);
797
798 cmd.p2p_sta.ctwin = cpu_to_le32(noa->oppps_ctwindow &
799 IEEE80211_P2P_OPPPS_CTWINDOW_MASK);
800 775
801 return iwl_mvm_mac_ctxt_send_cmd(mvm, &cmd); 776 return iwl_mvm_mac_ctxt_send_cmd(mvm, &cmd);
802} 777}
@@ -1134,16 +1109,12 @@ static int iwl_mvm_mac_ctxt_cmd_go(struct iwl_mvm *mvm,
1134} 1109}
1135 1110
1136static int iwl_mvm_mac_ctx_send(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 1111static int iwl_mvm_mac_ctx_send(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
1137 u32 action) 1112 u32 action, bool force_assoc_off)
1138{ 1113{
1139 switch (vif->type) { 1114 switch (vif->type) {
1140 case NL80211_IFTYPE_STATION: 1115 case NL80211_IFTYPE_STATION:
1141 if (!vif->p2p) 1116 return iwl_mvm_mac_ctxt_cmd_sta(mvm, vif, action,
1142 return iwl_mvm_mac_ctxt_cmd_station(mvm, vif, 1117 force_assoc_off);
1143 action);
1144 else
1145 return iwl_mvm_mac_ctxt_cmd_p2p_client(mvm, vif,
1146 action);
1147 break; 1118 break;
1148 case NL80211_IFTYPE_AP: 1119 case NL80211_IFTYPE_AP:
1149 if (!vif->p2p) 1120 if (!vif->p2p)
@@ -1173,7 +1144,8 @@ int iwl_mvm_mac_ctxt_add(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
1173 vif->addr, ieee80211_vif_type_p2p(vif))) 1144 vif->addr, ieee80211_vif_type_p2p(vif)))
1174 return -EIO; 1145 return -EIO;
1175 1146
1176 ret = iwl_mvm_mac_ctx_send(mvm, vif, FW_CTXT_ACTION_ADD); 1147 ret = iwl_mvm_mac_ctx_send(mvm, vif, FW_CTXT_ACTION_ADD,
1148 true);
1177 if (ret) 1149 if (ret)
1178 return ret; 1150 return ret;
1179 1151
@@ -1184,7 +1156,8 @@ int iwl_mvm_mac_ctxt_add(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
1184 return 0; 1156 return 0;
1185} 1157}
1186 1158
1187int iwl_mvm_mac_ctxt_changed(struct iwl_mvm *mvm, struct ieee80211_vif *vif) 1159int iwl_mvm_mac_ctxt_changed(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
1160 bool force_assoc_off)
1188{ 1161{
1189 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 1162 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
1190 1163
@@ -1192,7 +1165,8 @@ int iwl_mvm_mac_ctxt_changed(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
1192 vif->addr, ieee80211_vif_type_p2p(vif))) 1165 vif->addr, ieee80211_vif_type_p2p(vif)))
1193 return -EIO; 1166 return -EIO;
1194 1167
1195 return iwl_mvm_mac_ctx_send(mvm, vif, FW_CTXT_ACTION_MODIFY); 1168 return iwl_mvm_mac_ctx_send(mvm, vif, FW_CTXT_ACTION_MODIFY,
1169 force_assoc_off);
1196} 1170}
1197 1171
1198int iwl_mvm_mac_ctxt_remove(struct iwl_mvm *mvm, struct ieee80211_vif *vif) 1172int iwl_mvm_mac_ctxt_remove(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
@@ -1211,7 +1185,7 @@ int iwl_mvm_mac_ctxt_remove(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
1211 mvmvif->color)); 1185 mvmvif->color));
1212 cmd.action = cpu_to_le32(FW_CTXT_ACTION_REMOVE); 1186 cmd.action = cpu_to_le32(FW_CTXT_ACTION_REMOVE);
1213 1187
1214 ret = iwl_mvm_send_cmd_pdu(mvm, MAC_CONTEXT_CMD, CMD_SYNC, 1188 ret = iwl_mvm_send_cmd_pdu(mvm, MAC_CONTEXT_CMD, 0,
1215 sizeof(cmd), &cmd); 1189 sizeof(cmd), &cmd);
1216 if (ret) { 1190 if (ret) {
1217 IWL_ERR(mvm, "Failed to remove MAC context: %d\n", ret); 1191 IWL_ERR(mvm, "Failed to remove MAC context: %d\n", ret);
@@ -1237,11 +1211,23 @@ int iwl_mvm_rx_beacon_notif(struct iwl_mvm *mvm,
1237 u32 rate __maybe_unused = 1211 u32 rate __maybe_unused =
1238 le32_to_cpu(beacon->beacon_notify_hdr.initial_rate); 1212 le32_to_cpu(beacon->beacon_notify_hdr.initial_rate);
1239 1213
1214 lockdep_assert_held(&mvm->mutex);
1215
1240 IWL_DEBUG_RX(mvm, "beacon status %#x retries:%d tsf:0x%16llX rate:%d\n", 1216 IWL_DEBUG_RX(mvm, "beacon status %#x retries:%d tsf:0x%16llX rate:%d\n",
1241 status & TX_STATUS_MSK, 1217 status & TX_STATUS_MSK,
1242 beacon->beacon_notify_hdr.failure_frame, 1218 beacon->beacon_notify_hdr.failure_frame,
1243 le64_to_cpu(beacon->tsf), 1219 le64_to_cpu(beacon->tsf),
1244 rate); 1220 rate);
1221
1222 if (unlikely(mvm->csa_vif && mvm->csa_vif->csa_active)) {
1223 if (!ieee80211_csa_is_complete(mvm->csa_vif)) {
1224 iwl_mvm_mac_ctxt_beacon_changed(mvm, mvm->csa_vif);
1225 } else {
1226 ieee80211_csa_finish(mvm->csa_vif);
1227 mvm->csa_vif = NULL;
1228 }
1229 }
1230
1245 return 0; 1231 return 0;
1246} 1232}
1247 1233
diff --git a/drivers/net/wireless/iwlwifi/mvm/mac80211.c b/drivers/net/wireless/iwlwifi/mvm/mac80211.c
index 32682edfe5a4..7215f5980186 100644
--- a/drivers/net/wireless/iwlwifi/mvm/mac80211.c
+++ b/drivers/net/wireless/iwlwifi/mvm/mac80211.c
@@ -276,7 +276,6 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
276 IEEE80211_HW_AMPDU_AGGREGATION | 276 IEEE80211_HW_AMPDU_AGGREGATION |
277 IEEE80211_HW_TIMING_BEACON_ONLY | 277 IEEE80211_HW_TIMING_BEACON_ONLY |
278 IEEE80211_HW_CONNECTION_MONITOR | 278 IEEE80211_HW_CONNECTION_MONITOR |
279 IEEE80211_HW_SUPPORTS_UAPSD |
280 IEEE80211_HW_SUPPORTS_DYNAMIC_SMPS | 279 IEEE80211_HW_SUPPORTS_DYNAMIC_SMPS |
281 IEEE80211_HW_SUPPORTS_STATIC_SMPS; 280 IEEE80211_HW_SUPPORTS_STATIC_SMPS;
282 281
@@ -286,8 +285,6 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
286 IEEE80211_RADIOTAP_MCS_HAVE_STBC; 285 IEEE80211_RADIOTAP_MCS_HAVE_STBC;
287 hw->radiotap_vht_details |= IEEE80211_RADIOTAP_VHT_KNOWN_STBC; 286 hw->radiotap_vht_details |= IEEE80211_RADIOTAP_VHT_KNOWN_STBC;
288 hw->rate_control_algorithm = "iwl-mvm-rs"; 287 hw->rate_control_algorithm = "iwl-mvm-rs";
289 hw->uapsd_queues = IWL_UAPSD_AC_INFO;
290 hw->uapsd_max_sp_len = IWL_UAPSD_MAX_SP;
291 288
292 /* 289 /*
293 * Enable 11w if advertised by firmware and software crypto 290 * Enable 11w if advertised by firmware and software crypto
@@ -298,9 +295,13 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
298 !iwlwifi_mod_params.sw_crypto) 295 !iwlwifi_mod_params.sw_crypto)
299 hw->flags |= IEEE80211_HW_MFP_CAPABLE; 296 hw->flags |= IEEE80211_HW_MFP_CAPABLE;
300 297
301 /* Disable uAPSD due to firmware issues */ 298 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_UAPSD_SUPPORT &&
302 if (true) 299 IWL_UCODE_API(mvm->fw->ucode_ver) >= 9 &&
303 hw->flags &= ~IEEE80211_HW_SUPPORTS_UAPSD; 300 !iwlwifi_mod_params.uapsd_disable) {
301 hw->flags |= IEEE80211_HW_SUPPORTS_UAPSD;
302 hw->uapsd_queues = IWL_UAPSD_AC_INFO;
303 hw->uapsd_max_sp_len = IWL_UAPSD_MAX_SP;
304 }
304 305
305 hw->sta_data_size = sizeof(struct iwl_mvm_sta); 306 hw->sta_data_size = sizeof(struct iwl_mvm_sta);
306 hw->vif_data_size = sizeof(struct iwl_mvm_vif); 307 hw->vif_data_size = sizeof(struct iwl_mvm_vif);
@@ -320,6 +321,9 @@ int iwl_mvm_mac_setup_register(struct iwl_mvm *mvm)
320 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_GO_UAPSD) 321 if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_GO_UAPSD)
321 hw->wiphy->flags |= WIPHY_FLAG_AP_UAPSD; 322 hw->wiphy->flags |= WIPHY_FLAG_AP_UAPSD;
322 323
324 if (mvm->fw->ucode_capa.api[0] & IWL_UCODE_TLV_API_CSA_FLOW)
325 hw->wiphy->flags |= WIPHY_FLAG_HAS_CHANNEL_SWITCH;
326
323 hw->wiphy->iface_combinations = iwl_mvm_iface_combinations; 327 hw->wiphy->iface_combinations = iwl_mvm_iface_combinations;
324 hw->wiphy->n_iface_combinations = 328 hw->wiphy->n_iface_combinations =
325 ARRAY_SIZE(iwl_mvm_iface_combinations); 329 ARRAY_SIZE(iwl_mvm_iface_combinations);
@@ -539,13 +543,22 @@ static int iwl_mvm_mac_ampdu_action(struct ieee80211_hw *hw,
539 return -EACCES; 543 return -EACCES;
540 544
541 /* return from D0i3 before starting a new Tx aggregation */ 545 /* return from D0i3 before starting a new Tx aggregation */
542 if (action == IEEE80211_AMPDU_TX_START) { 546 switch (action) {
547 case IEEE80211_AMPDU_TX_START:
548 case IEEE80211_AMPDU_TX_STOP_CONT:
549 case IEEE80211_AMPDU_TX_STOP_FLUSH:
550 case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT:
551 case IEEE80211_AMPDU_TX_OPERATIONAL:
543 iwl_mvm_ref(mvm, IWL_MVM_REF_TX_AGG); 552 iwl_mvm_ref(mvm, IWL_MVM_REF_TX_AGG);
544 tx_agg_ref = true; 553 tx_agg_ref = true;
545 554
546 /* 555 /*
547 * wait synchronously until D0i3 exit to get the correct 556 * for tx start, wait synchronously until D0i3 exit to
548 * sequence number for the tid 557 * get the correct sequence number for the tid.
558 * additionally, some other ampdu actions use direct
559 * target access, which is not handled automatically
560 * by the trans layer (unlike commands), so wait for
561 * d0i3 exit in these cases as well.
549 */ 562 */
550 if (!wait_event_timeout(mvm->d0i3_exit_waitq, 563 if (!wait_event_timeout(mvm->d0i3_exit_waitq,
551 !test_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status), HZ)) { 564 !test_bit(IWL_MVM_STATUS_IN_D0I3, &mvm->status), HZ)) {
@@ -553,6 +566,9 @@ static int iwl_mvm_mac_ampdu_action(struct ieee80211_hw *hw,
553 iwl_mvm_unref(mvm, IWL_MVM_REF_TX_AGG); 566 iwl_mvm_unref(mvm, IWL_MVM_REF_TX_AGG);
554 return -EIO; 567 return -EIO;
555 } 568 }
569 break;
570 default:
571 break;
556 } 572 }
557 573
558 mutex_lock(&mvm->mutex); 574 mutex_lock(&mvm->mutex);
@@ -757,7 +773,7 @@ static int iwl_mvm_set_tx_power(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
757 .pwr_restriction = cpu_to_le16(tx_power), 773 .pwr_restriction = cpu_to_le16(tx_power),
758 }; 774 };
759 775
760 return iwl_mvm_send_cmd_pdu(mvm, REDUCE_TX_POWER_CMD, CMD_SYNC, 776 return iwl_mvm_send_cmd_pdu(mvm, REDUCE_TX_POWER_CMD, 0,
761 sizeof(reduce_txpwr_cmd), 777 sizeof(reduce_txpwr_cmd),
762 &reduce_txpwr_cmd); 778 &reduce_txpwr_cmd);
763} 779}
@@ -816,12 +832,12 @@ static int iwl_mvm_mac_add_interface(struct ieee80211_hw *hw,
816 if (ret) 832 if (ret)
817 goto out_release; 833 goto out_release;
818 834
819 ret = iwl_mvm_power_update_mac(mvm, vif); 835 ret = iwl_mvm_power_update_mac(mvm);
820 if (ret) 836 if (ret)
821 goto out_release; 837 goto out_release;
822 838
823 /* beacon filtering */ 839 /* beacon filtering */
824 ret = iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC); 840 ret = iwl_mvm_disable_beacon_filter(mvm, vif, 0);
825 if (ret) 841 if (ret)
826 goto out_remove_mac; 842 goto out_remove_mac;
827 843
@@ -967,7 +983,7 @@ static void iwl_mvm_mac_remove_interface(struct ieee80211_hw *hw,
967 if (mvm->vif_count && vif->type != NL80211_IFTYPE_P2P_DEVICE) 983 if (mvm->vif_count && vif->type != NL80211_IFTYPE_P2P_DEVICE)
968 mvm->vif_count--; 984 mvm->vif_count--;
969 985
970 iwl_mvm_power_update_mac(mvm, vif); 986 iwl_mvm_power_update_mac(mvm);
971 iwl_mvm_mac_ctxt_remove(mvm, vif); 987 iwl_mvm_mac_ctxt_remove(mvm, vif);
972 988
973out_release: 989out_release:
@@ -1228,7 +1244,7 @@ static int iwl_mvm_configure_bcast_filter(struct iwl_mvm *mvm,
1228 if (!iwl_mvm_bcast_filter_build_cmd(mvm, &cmd)) 1244 if (!iwl_mvm_bcast_filter_build_cmd(mvm, &cmd))
1229 return 0; 1245 return 0;
1230 1246
1231 return iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, CMD_SYNC, 1247 return iwl_mvm_send_cmd_pdu(mvm, BCAST_FILTER_CMD, 0,
1232 sizeof(cmd), &cmd); 1248 sizeof(cmd), &cmd);
1233} 1249}
1234#else 1250#else
@@ -1255,7 +1271,7 @@ static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
1255 if (changes & BSS_CHANGED_ASSOC && bss_conf->assoc) 1271 if (changes & BSS_CHANGED_ASSOC && bss_conf->assoc)
1256 iwl_mvm_mac_ctxt_recalc_tsf_id(mvm, vif); 1272 iwl_mvm_mac_ctxt_recalc_tsf_id(mvm, vif);
1257 1273
1258 ret = iwl_mvm_mac_ctxt_changed(mvm, vif); 1274 ret = iwl_mvm_mac_ctxt_changed(mvm, vif, false);
1259 if (ret) 1275 if (ret)
1260 IWL_ERR(mvm, "failed to update MAC %pM\n", vif->addr); 1276 IWL_ERR(mvm, "failed to update MAC %pM\n", vif->addr);
1261 1277
@@ -1335,10 +1351,10 @@ static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
1335 iwl_mvm_remove_time_event(mvm, mvmvif, 1351 iwl_mvm_remove_time_event(mvm, mvmvif,
1336 &mvmvif->time_event_data); 1352 &mvmvif->time_event_data);
1337 iwl_mvm_sf_update(mvm, vif, false); 1353 iwl_mvm_sf_update(mvm, vif, false);
1338 WARN_ON(iwl_mvm_enable_beacon_filter(mvm, vif, CMD_SYNC)); 1354 WARN_ON(iwl_mvm_enable_beacon_filter(mvm, vif, 0));
1339 } else if (changes & (BSS_CHANGED_PS | BSS_CHANGED_P2P_PS | 1355 } else if (changes & (BSS_CHANGED_PS | BSS_CHANGED_P2P_PS |
1340 BSS_CHANGED_QOS)) { 1356 BSS_CHANGED_QOS)) {
1341 ret = iwl_mvm_power_update_mac(mvm, vif); 1357 ret = iwl_mvm_power_update_mac(mvm);
1342 if (ret) 1358 if (ret)
1343 IWL_ERR(mvm, "failed to update power mode\n"); 1359 IWL_ERR(mvm, "failed to update power mode\n");
1344 } 1360 }
@@ -1349,16 +1365,19 @@ static void iwl_mvm_bss_info_changed_station(struct iwl_mvm *mvm,
1349 } 1365 }
1350 1366
1351 if (changes & BSS_CHANGED_CQM) { 1367 if (changes & BSS_CHANGED_CQM) {
1352 IWL_DEBUG_MAC80211(mvm, "cqm info_changed"); 1368 IWL_DEBUG_MAC80211(mvm, "cqm info_changed\n");
1353 /* reset cqm events tracking */ 1369 /* reset cqm events tracking */
1354 mvmvif->bf_data.last_cqm_event = 0; 1370 mvmvif->bf_data.last_cqm_event = 0;
1355 ret = iwl_mvm_update_beacon_filter(mvm, vif, false, CMD_SYNC); 1371 if (mvmvif->bf_data.bf_enabled) {
1356 if (ret) 1372 ret = iwl_mvm_enable_beacon_filter(mvm, vif, 0);
1357 IWL_ERR(mvm, "failed to update CQM thresholds\n"); 1373 if (ret)
1374 IWL_ERR(mvm,
1375 "failed to update CQM thresholds\n");
1376 }
1358 } 1377 }
1359 1378
1360 if (changes & BSS_CHANGED_ARP_FILTER) { 1379 if (changes & BSS_CHANGED_ARP_FILTER) {
1361 IWL_DEBUG_MAC80211(mvm, "arp filter changed"); 1380 IWL_DEBUG_MAC80211(mvm, "arp filter changed\n");
1362 iwl_mvm_configure_bcast_filter(mvm, vif); 1381 iwl_mvm_configure_bcast_filter(mvm, vif);
1363 } 1382 }
1364} 1383}
@@ -1404,7 +1423,7 @@ static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw,
1404 mvmvif->ap_ibss_active = true; 1423 mvmvif->ap_ibss_active = true;
1405 1424
1406 /* power updated needs to be done before quotas */ 1425 /* power updated needs to be done before quotas */
1407 iwl_mvm_power_update_mac(mvm, vif); 1426 iwl_mvm_power_update_mac(mvm);
1408 1427
1409 ret = iwl_mvm_update_quotas(mvm, vif); 1428 ret = iwl_mvm_update_quotas(mvm, vif);
1410 if (ret) 1429 if (ret)
@@ -1412,7 +1431,7 @@ static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw,
1412 1431
1413 /* Need to update the P2P Device MAC (only GO, IBSS is single vif) */ 1432 /* Need to update the P2P Device MAC (only GO, IBSS is single vif) */
1414 if (vif->p2p && mvm->p2p_device_vif) 1433 if (vif->p2p && mvm->p2p_device_vif)
1415 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif); 1434 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif, false);
1416 1435
1417 iwl_mvm_ref(mvm, IWL_MVM_REF_AP_IBSS); 1436 iwl_mvm_ref(mvm, IWL_MVM_REF_AP_IBSS);
1418 1437
@@ -1422,7 +1441,7 @@ static int iwl_mvm_start_ap_ibss(struct ieee80211_hw *hw,
1422 return 0; 1441 return 0;
1423 1442
1424out_quota_failed: 1443out_quota_failed:
1425 iwl_mvm_power_update_mac(mvm, vif); 1444 iwl_mvm_power_update_mac(mvm);
1426 mvmvif->ap_ibss_active = false; 1445 mvmvif->ap_ibss_active = false;
1427 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta); 1446 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta);
1428out_unbind: 1447out_unbind:
@@ -1452,13 +1471,13 @@ static void iwl_mvm_stop_ap_ibss(struct ieee80211_hw *hw,
1452 1471
1453 /* Need to update the P2P Device MAC (only GO, IBSS is single vif) */ 1472 /* Need to update the P2P Device MAC (only GO, IBSS is single vif) */
1454 if (vif->p2p && mvm->p2p_device_vif) 1473 if (vif->p2p && mvm->p2p_device_vif)
1455 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif); 1474 iwl_mvm_mac_ctxt_changed(mvm, mvm->p2p_device_vif, false);
1456 1475
1457 iwl_mvm_update_quotas(mvm, NULL); 1476 iwl_mvm_update_quotas(mvm, NULL);
1458 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta); 1477 iwl_mvm_send_rm_bcast_sta(mvm, &mvmvif->bcast_sta);
1459 iwl_mvm_binding_remove_vif(mvm, vif); 1478 iwl_mvm_binding_remove_vif(mvm, vif);
1460 1479
1461 iwl_mvm_power_update_mac(mvm, vif); 1480 iwl_mvm_power_update_mac(mvm);
1462 1481
1463 iwl_mvm_mac_ctxt_remove(mvm, vif); 1482 iwl_mvm_mac_ctxt_remove(mvm, vif);
1464 1483
@@ -1479,7 +1498,7 @@ iwl_mvm_bss_info_changed_ap_ibss(struct iwl_mvm *mvm,
1479 1498
1480 if (changes & (BSS_CHANGED_ERP_CTS_PROT | BSS_CHANGED_HT | 1499 if (changes & (BSS_CHANGED_ERP_CTS_PROT | BSS_CHANGED_HT |
1481 BSS_CHANGED_BANDWIDTH) && 1500 BSS_CHANGED_BANDWIDTH) &&
1482 iwl_mvm_mac_ctxt_changed(mvm, vif)) 1501 iwl_mvm_mac_ctxt_changed(mvm, vif, false))
1483 IWL_ERR(mvm, "failed to update MAC %pM\n", vif->addr); 1502 IWL_ERR(mvm, "failed to update MAC %pM\n", vif->addr);
1484 1503
1485 /* Need to send a new beacon template to the FW */ 1504 /* Need to send a new beacon template to the FW */
@@ -1497,6 +1516,9 @@ static void iwl_mvm_bss_info_changed(struct ieee80211_hw *hw,
1497 1516
1498 mutex_lock(&mvm->mutex); 1517 mutex_lock(&mvm->mutex);
1499 1518
1519 if (changes & BSS_CHANGED_IDLE && !bss_conf->idle)
1520 iwl_mvm_sched_scan_stop(mvm, true);
1521
1500 switch (vif->type) { 1522 switch (vif->type) {
1501 case NL80211_IFTYPE_STATION: 1523 case NL80211_IFTYPE_STATION:
1502 iwl_mvm_bss_info_changed_station(mvm, vif, bss_conf, changes); 1524 iwl_mvm_bss_info_changed_station(mvm, vif, bss_conf, changes);
@@ -1527,7 +1549,7 @@ static int iwl_mvm_mac_hw_scan(struct ieee80211_hw *hw,
1527 1549
1528 switch (mvm->scan_status) { 1550 switch (mvm->scan_status) {
1529 case IWL_MVM_SCAN_SCHED: 1551 case IWL_MVM_SCAN_SCHED:
1530 ret = iwl_mvm_sched_scan_stop(mvm); 1552 ret = iwl_mvm_sched_scan_stop(mvm, true);
1531 if (ret) { 1553 if (ret) {
1532 ret = -EBUSY; 1554 ret = -EBUSY;
1533 goto out; 1555 goto out;
@@ -1715,14 +1737,12 @@ static int iwl_mvm_mac_sta_state(struct ieee80211_hw *hw,
1715 } else if (old_state == IEEE80211_STA_ASSOC && 1737 } else if (old_state == IEEE80211_STA_ASSOC &&
1716 new_state == IEEE80211_STA_AUTHORIZED) { 1738 new_state == IEEE80211_STA_AUTHORIZED) {
1717 /* enable beacon filtering */ 1739 /* enable beacon filtering */
1718 if (vif->bss_conf.dtim_period) 1740 WARN_ON(iwl_mvm_enable_beacon_filter(mvm, vif, 0));
1719 WARN_ON(iwl_mvm_enable_beacon_filter(mvm, vif,
1720 CMD_SYNC));
1721 ret = 0; 1741 ret = 0;
1722 } else if (old_state == IEEE80211_STA_AUTHORIZED && 1742 } else if (old_state == IEEE80211_STA_AUTHORIZED &&
1723 new_state == IEEE80211_STA_ASSOC) { 1743 new_state == IEEE80211_STA_ASSOC) {
1724 /* disable beacon filtering */ 1744 /* disable beacon filtering */
1725 WARN_ON(iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC)); 1745 WARN_ON(iwl_mvm_disable_beacon_filter(mvm, vif, 0));
1726 ret = 0; 1746 ret = 0;
1727 } else if (old_state == IEEE80211_STA_ASSOC && 1747 } else if (old_state == IEEE80211_STA_ASSOC &&
1728 new_state == IEEE80211_STA_AUTH) { 1748 new_state == IEEE80211_STA_AUTH) {
@@ -1779,7 +1799,7 @@ static int iwl_mvm_mac_conf_tx(struct ieee80211_hw *hw,
1779 int ret; 1799 int ret;
1780 1800
1781 mutex_lock(&mvm->mutex); 1801 mutex_lock(&mvm->mutex);
1782 ret = iwl_mvm_mac_ctxt_changed(mvm, vif); 1802 ret = iwl_mvm_mac_ctxt_changed(mvm, vif, false);
1783 mutex_unlock(&mvm->mutex); 1803 mutex_unlock(&mvm->mutex);
1784 return ret; 1804 return ret;
1785 } 1805 }
@@ -1872,7 +1892,7 @@ static int iwl_mvm_mac_sched_scan_stop(struct ieee80211_hw *hw,
1872 int ret; 1892 int ret;
1873 1893
1874 mutex_lock(&mvm->mutex); 1894 mutex_lock(&mvm->mutex);
1875 ret = iwl_mvm_sched_scan_stop(mvm); 1895 ret = iwl_mvm_sched_scan_stop(mvm, false);
1876 mutex_unlock(&mvm->mutex); 1896 mutex_unlock(&mvm->mutex);
1877 iwl_mvm_wait_for_async_handlers(mvm); 1897 iwl_mvm_wait_for_async_handlers(mvm);
1878 1898
@@ -2168,10 +2188,10 @@ static void iwl_mvm_change_chanctx(struct ieee80211_hw *hw,
2168 return; 2188 return;
2169 2189
2170 mutex_lock(&mvm->mutex); 2190 mutex_lock(&mvm->mutex);
2191 iwl_mvm_bt_coex_vif_change(mvm);
2171 iwl_mvm_phy_ctxt_changed(mvm, phy_ctxt, &ctx->min_def, 2192 iwl_mvm_phy_ctxt_changed(mvm, phy_ctxt, &ctx->min_def,
2172 ctx->rx_chains_static, 2193 ctx->rx_chains_static,
2173 ctx->rx_chains_dynamic); 2194 ctx->rx_chains_dynamic);
2174 iwl_mvm_bt_coex_vif_change(mvm);
2175 mutex_unlock(&mvm->mutex); 2195 mutex_unlock(&mvm->mutex);
2176} 2196}
2177 2197
@@ -2191,6 +2211,11 @@ static int iwl_mvm_assign_vif_chanctx(struct ieee80211_hw *hw,
2191 2211
2192 switch (vif->type) { 2212 switch (vif->type) {
2193 case NL80211_IFTYPE_AP: 2213 case NL80211_IFTYPE_AP:
2214 /* Unless it's a CSA flow we have nothing to do here */
2215 if (vif->csa_active) {
2216 mvmvif->ap_ibss_active = true;
2217 break;
2218 }
2194 case NL80211_IFTYPE_ADHOC: 2219 case NL80211_IFTYPE_ADHOC:
2195 /* 2220 /*
2196 * The AP binding flow is handled as part of the start_ap flow 2221 * The AP binding flow is handled as part of the start_ap flow
@@ -2214,7 +2239,7 @@ static int iwl_mvm_assign_vif_chanctx(struct ieee80211_hw *hw,
2214 * Power state must be updated before quotas, 2239 * Power state must be updated before quotas,
2215 * otherwise fw will complain. 2240 * otherwise fw will complain.
2216 */ 2241 */
2217 iwl_mvm_power_update_mac(mvm, vif); 2242 iwl_mvm_power_update_mac(mvm);
2218 2243
2219 /* Setting the quota at this stage is only required for monitor 2244 /* Setting the quota at this stage is only required for monitor
2220 * interfaces. For the other types, the bss_info changed flow 2245 * interfaces. For the other types, the bss_info changed flow
@@ -2227,11 +2252,17 @@ static int iwl_mvm_assign_vif_chanctx(struct ieee80211_hw *hw,
2227 goto out_remove_binding; 2252 goto out_remove_binding;
2228 } 2253 }
2229 2254
2255 /* Handle binding during CSA */
2256 if (vif->type == NL80211_IFTYPE_AP) {
2257 iwl_mvm_update_quotas(mvm, vif);
2258 iwl_mvm_mac_ctxt_changed(mvm, vif, false);
2259 }
2260
2230 goto out_unlock; 2261 goto out_unlock;
2231 2262
2232 out_remove_binding: 2263 out_remove_binding:
2233 iwl_mvm_binding_remove_vif(mvm, vif); 2264 iwl_mvm_binding_remove_vif(mvm, vif);
2234 iwl_mvm_power_update_mac(mvm, vif); 2265 iwl_mvm_power_update_mac(mvm);
2235 out_unlock: 2266 out_unlock:
2236 mutex_unlock(&mvm->mutex); 2267 mutex_unlock(&mvm->mutex);
2237 if (ret) 2268 if (ret)
@@ -2251,22 +2282,29 @@ static void iwl_mvm_unassign_vif_chanctx(struct ieee80211_hw *hw,
2251 iwl_mvm_remove_time_event(mvm, mvmvif, &mvmvif->time_event_data); 2282 iwl_mvm_remove_time_event(mvm, mvmvif, &mvmvif->time_event_data);
2252 2283
2253 switch (vif->type) { 2284 switch (vif->type) {
2254 case NL80211_IFTYPE_AP:
2255 case NL80211_IFTYPE_ADHOC: 2285 case NL80211_IFTYPE_ADHOC:
2256 goto out_unlock; 2286 goto out_unlock;
2257 case NL80211_IFTYPE_MONITOR: 2287 case NL80211_IFTYPE_MONITOR:
2258 mvmvif->monitor_active = false; 2288 mvmvif->monitor_active = false;
2259 iwl_mvm_update_quotas(mvm, NULL); 2289 iwl_mvm_update_quotas(mvm, NULL);
2260 break; 2290 break;
2291 case NL80211_IFTYPE_AP:
2292 /* This part is triggered only during CSA */
2293 if (!vif->csa_active || !mvmvif->ap_ibss_active)
2294 goto out_unlock;
2295
2296 mvmvif->ap_ibss_active = false;
2297 iwl_mvm_update_quotas(mvm, NULL);
2298 /*TODO: bt_coex notification here? */
2261 default: 2299 default:
2262 break; 2300 break;
2263 } 2301 }
2264 2302
2265 iwl_mvm_binding_remove_vif(mvm, vif); 2303 iwl_mvm_binding_remove_vif(mvm, vif);
2266 iwl_mvm_power_update_mac(mvm, vif);
2267 2304
2268out_unlock: 2305out_unlock:
2269 mvmvif->phy_ctxt = NULL; 2306 mvmvif->phy_ctxt = NULL;
2307 iwl_mvm_power_update_mac(mvm);
2270 mutex_unlock(&mvm->mutex); 2308 mutex_unlock(&mvm->mutex);
2271} 2309}
2272 2310
@@ -2330,9 +2368,8 @@ static int __iwl_mvm_mac_testmode_cmd(struct iwl_mvm *mvm,
2330 return -EINVAL; 2368 return -EINVAL;
2331 2369
2332 if (nla_get_u32(tb[IWL_MVM_TM_ATTR_BEACON_FILTER_STATE])) 2370 if (nla_get_u32(tb[IWL_MVM_TM_ATTR_BEACON_FILTER_STATE]))
2333 return iwl_mvm_enable_beacon_filter(mvm, vif, 2371 return iwl_mvm_enable_beacon_filter(mvm, vif, 0);
2334 CMD_SYNC); 2372 return iwl_mvm_disable_beacon_filter(mvm, vif, 0);
2335 return iwl_mvm_disable_beacon_filter(mvm, vif, CMD_SYNC);
2336 } 2373 }
2337 2374
2338 return -EOPNOTSUPP; 2375 return -EOPNOTSUPP;
@@ -2353,6 +2390,53 @@ static int iwl_mvm_mac_testmode_cmd(struct ieee80211_hw *hw,
2353} 2390}
2354#endif 2391#endif
2355 2392
2393static void iwl_mvm_channel_switch_beacon(struct ieee80211_hw *hw,
2394 struct ieee80211_vif *vif,
2395 struct cfg80211_chan_def *chandef)
2396{
2397 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
2398
2399 mutex_lock(&mvm->mutex);
2400 if (WARN(mvm->csa_vif && mvm->csa_vif->csa_active,
2401 "Another CSA is already in progress"))
2402 goto out_unlock;
2403
2404 IWL_DEBUG_MAC80211(mvm, "CSA started to freq %d\n",
2405 chandef->center_freq1);
2406 mvm->csa_vif = vif;
2407
2408out_unlock:
2409 mutex_unlock(&mvm->mutex);
2410}
2411
2412static void iwl_mvm_mac_flush(struct ieee80211_hw *hw,
2413 struct ieee80211_vif *vif, u32 queues, bool drop)
2414{
2415 struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw);
2416 struct iwl_mvm_vif *mvmvif;
2417 struct iwl_mvm_sta *mvmsta;
2418
2419 if (!vif || vif->type != NL80211_IFTYPE_STATION)
2420 return;
2421
2422 mutex_lock(&mvm->mutex);
2423 mvmvif = iwl_mvm_vif_from_mac80211(vif);
2424 mvmsta = iwl_mvm_sta_from_staid_protected(mvm, mvmvif->ap_sta_id);
2425
2426 if (WARN_ON_ONCE(!mvmsta))
2427 goto done;
2428
2429 if (drop) {
2430 if (iwl_mvm_flush_tx_path(mvm, mvmsta->tfd_queue_msk, true))
2431 IWL_ERR(mvm, "flush request fail\n");
2432 } else {
2433 iwl_trans_wait_tx_queue_empty(mvm->trans,
2434 mvmsta->tfd_queue_msk);
2435 }
2436done:
2437 mutex_unlock(&mvm->mutex);
2438}
2439
2356const struct ieee80211_ops iwl_mvm_hw_ops = { 2440const struct ieee80211_ops iwl_mvm_hw_ops = {
2357 .tx = iwl_mvm_mac_tx, 2441 .tx = iwl_mvm_mac_tx,
2358 .ampdu_action = iwl_mvm_mac_ampdu_action, 2442 .ampdu_action = iwl_mvm_mac_ampdu_action,
@@ -2376,6 +2460,7 @@ const struct ieee80211_ops iwl_mvm_hw_ops = {
2376 .sta_rc_update = iwl_mvm_sta_rc_update, 2460 .sta_rc_update = iwl_mvm_sta_rc_update,
2377 .conf_tx = iwl_mvm_mac_conf_tx, 2461 .conf_tx = iwl_mvm_mac_conf_tx,
2378 .mgd_prepare_tx = iwl_mvm_mac_mgd_prepare_tx, 2462 .mgd_prepare_tx = iwl_mvm_mac_mgd_prepare_tx,
2463 .flush = iwl_mvm_mac_flush,
2379 .sched_scan_start = iwl_mvm_mac_sched_scan_start, 2464 .sched_scan_start = iwl_mvm_mac_sched_scan_start,
2380 .sched_scan_stop = iwl_mvm_mac_sched_scan_stop, 2465 .sched_scan_stop = iwl_mvm_mac_sched_scan_stop,
2381 .set_key = iwl_mvm_mac_set_key, 2466 .set_key = iwl_mvm_mac_set_key,
@@ -2395,6 +2480,8 @@ const struct ieee80211_ops iwl_mvm_hw_ops = {
2395 2480
2396 .set_tim = iwl_mvm_set_tim, 2481 .set_tim = iwl_mvm_set_tim,
2397 2482
2483 .channel_switch_beacon = iwl_mvm_channel_switch_beacon,
2484
2398 CFG80211_TESTMODE_CMD(iwl_mvm_mac_testmode_cmd) 2485 CFG80211_TESTMODE_CMD(iwl_mvm_mac_testmode_cmd)
2399 2486
2400#ifdef CONFIG_PM_SLEEP 2487#ifdef CONFIG_PM_SLEEP
diff --git a/drivers/net/wireless/iwlwifi/mvm/mvm.h b/drivers/net/wireless/iwlwifi/mvm/mvm.h
index 107d864b3c0e..fcc6c29482d0 100644
--- a/drivers/net/wireless/iwlwifi/mvm/mvm.h
+++ b/drivers/net/wireless/iwlwifi/mvm/mvm.h
@@ -490,6 +490,7 @@ struct iwl_mvm {
490 u32 log_event_table; 490 u32 log_event_table;
491 u32 umac_error_event_table; 491 u32 umac_error_event_table;
492 bool support_umac_log; 492 bool support_umac_log;
493 struct iwl_sf_region sf_space;
493 494
494 u32 ampdu_ref; 495 u32 ampdu_ref;
495 496
@@ -501,6 +502,7 @@ struct iwl_mvm {
501 u8 queue_to_mac80211[IWL_MAX_HW_QUEUES]; 502 u8 queue_to_mac80211[IWL_MAX_HW_QUEUES];
502 atomic_t queue_stop_count[IWL_MAX_HW_QUEUES]; 503 atomic_t queue_stop_count[IWL_MAX_HW_QUEUES];
503 504
505 const char *nvm_file_name;
504 struct iwl_nvm_data *nvm_data; 506 struct iwl_nvm_data *nvm_data;
505 /* NVM sections */ 507 /* NVM sections */
506 struct iwl_nvm_section nvm_sections[NVM_MAX_NUM_SECTIONS]; 508 struct iwl_nvm_section nvm_sections[NVM_MAX_NUM_SECTIONS];
@@ -589,7 +591,9 @@ struct iwl_mvm {
589 u32 *fw_error_rxf; 591 u32 *fw_error_rxf;
590 u32 fw_error_rxf_len; 592 u32 fw_error_rxf_len;
591 593
594#ifdef CONFIG_IWLWIFI_LEDS
592 struct led_classdev led; 595 struct led_classdev led;
596#endif
593 597
594 struct ieee80211_vif *p2p_device_vif; 598 struct ieee80211_vif *p2p_device_vif;
595 599
@@ -642,6 +646,8 @@ struct iwl_mvm {
642 646
643 /* Indicate if device power save is allowed */ 647 /* Indicate if device power save is allowed */
644 bool ps_disabled; 648 bool ps_disabled;
649
650 struct ieee80211_vif *csa_vif;
645}; 651};
646 652
647/* Extract MVM priv from op_mode and _hw */ 653/* Extract MVM priv from op_mode and _hw */
@@ -757,7 +763,7 @@ int iwl_mvm_rx_statistics(struct iwl_mvm *mvm,
757 struct iwl_device_cmd *cmd); 763 struct iwl_device_cmd *cmd);
758 764
759/* NVM */ 765/* NVM */
760int iwl_nvm_init(struct iwl_mvm *mvm); 766int iwl_nvm_init(struct iwl_mvm *mvm, bool read_nvm_from_nic);
761int iwl_mvm_load_nvm_to_nic(struct iwl_mvm *mvm); 767int iwl_mvm_load_nvm_to_nic(struct iwl_mvm *mvm);
762 768
763int iwl_mvm_up(struct iwl_mvm *mvm); 769int iwl_mvm_up(struct iwl_mvm *mvm);
@@ -808,7 +814,8 @@ void iwl_mvm_phy_ctxt_unref(struct iwl_mvm *mvm,
808int iwl_mvm_mac_ctxt_init(struct iwl_mvm *mvm, struct ieee80211_vif *vif); 814int iwl_mvm_mac_ctxt_init(struct iwl_mvm *mvm, struct ieee80211_vif *vif);
809void iwl_mvm_mac_ctxt_release(struct iwl_mvm *mvm, struct ieee80211_vif *vif); 815void iwl_mvm_mac_ctxt_release(struct iwl_mvm *mvm, struct ieee80211_vif *vif);
810int iwl_mvm_mac_ctxt_add(struct iwl_mvm *mvm, struct ieee80211_vif *vif); 816int iwl_mvm_mac_ctxt_add(struct iwl_mvm *mvm, struct ieee80211_vif *vif);
811int iwl_mvm_mac_ctxt_changed(struct iwl_mvm *mvm, struct ieee80211_vif *vif); 817int iwl_mvm_mac_ctxt_changed(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
818 bool force_assoc_off);
812int iwl_mvm_mac_ctxt_remove(struct iwl_mvm *mvm, struct ieee80211_vif *vif); 819int iwl_mvm_mac_ctxt_remove(struct iwl_mvm *mvm, struct ieee80211_vif *vif);
813u32 iwl_mvm_mac_get_queues_mask(struct iwl_mvm *mvm, 820u32 iwl_mvm_mac_get_queues_mask(struct iwl_mvm *mvm,
814 struct ieee80211_vif *vif); 821 struct ieee80211_vif *vif);
@@ -852,7 +859,7 @@ int iwl_mvm_config_sched_scan_profiles(struct iwl_mvm *mvm,
852 struct cfg80211_sched_scan_request *req); 859 struct cfg80211_sched_scan_request *req);
853int iwl_mvm_sched_scan_start(struct iwl_mvm *mvm, 860int iwl_mvm_sched_scan_start(struct iwl_mvm *mvm,
854 struct cfg80211_sched_scan_request *req); 861 struct cfg80211_sched_scan_request *req);
855int iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm); 862int iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm, bool notify);
856int iwl_mvm_rx_sched_scan_results(struct iwl_mvm *mvm, 863int iwl_mvm_rx_sched_scan_results(struct iwl_mvm *mvm,
857 struct iwl_rx_cmd_buffer *rxb, 864 struct iwl_rx_cmd_buffer *rxb,
858 struct iwl_device_cmd *cmd); 865 struct iwl_device_cmd *cmd);
@@ -887,7 +894,7 @@ int rs_pretty_print_rate(char *buf, const u32 rate);
887 894
888/* power management */ 895/* power management */
889int iwl_mvm_power_update_device(struct iwl_mvm *mvm); 896int iwl_mvm_power_update_device(struct iwl_mvm *mvm);
890int iwl_mvm_power_update_mac(struct iwl_mvm *mvm, struct ieee80211_vif *vif); 897int iwl_mvm_power_update_mac(struct iwl_mvm *mvm);
891int iwl_mvm_power_mac_dbgfs_read(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 898int iwl_mvm_power_mac_dbgfs_read(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
892 char *buf, int bufsz); 899 char *buf, int bufsz);
893 900
@@ -896,8 +903,18 @@ int iwl_mvm_power_uapsd_misbehaving_ap_notif(struct iwl_mvm *mvm,
896 struct iwl_rx_cmd_buffer *rxb, 903 struct iwl_rx_cmd_buffer *rxb,
897 struct iwl_device_cmd *cmd); 904 struct iwl_device_cmd *cmd);
898 905
906#ifdef CONFIG_IWLWIFI_LEDS
899int iwl_mvm_leds_init(struct iwl_mvm *mvm); 907int iwl_mvm_leds_init(struct iwl_mvm *mvm);
900void iwl_mvm_leds_exit(struct iwl_mvm *mvm); 908void iwl_mvm_leds_exit(struct iwl_mvm *mvm);
909#else
910static inline int iwl_mvm_leds_init(struct iwl_mvm *mvm)
911{
912 return 0;
913}
914static inline void iwl_mvm_leds_exit(struct iwl_mvm *mvm)
915{
916}
917#endif
901 918
902/* D3 (WoWLAN, NetDetect) */ 919/* D3 (WoWLAN, NetDetect) */
903int iwl_mvm_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wowlan); 920int iwl_mvm_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wowlan);
@@ -950,7 +967,6 @@ bool iwl_mvm_bt_coex_is_tpc_allowed(struct iwl_mvm *mvm,
950 enum ieee80211_band band); 967 enum ieee80211_band band);
951u8 iwl_mvm_bt_coex_tx_prio(struct iwl_mvm *mvm, struct ieee80211_hdr *hdr, 968u8 iwl_mvm_bt_coex_tx_prio(struct iwl_mvm *mvm, struct ieee80211_hdr *hdr,
952 struct ieee80211_tx_info *info, u8 ac); 969 struct ieee80211_tx_info *info, u8 ac);
953int iwl_mvm_bt_coex_reduced_txp(struct iwl_mvm *mvm, u8 sta_id, bool enable);
954 970
955enum iwl_bt_kill_msk { 971enum iwl_bt_kill_msk {
956 BT_KILL_MSK_DEFAULT, 972 BT_KILL_MSK_DEFAULT,
@@ -981,17 +997,11 @@ int iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm,
981int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm, 997int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm,
982 struct ieee80211_vif *vif, 998 struct ieee80211_vif *vif,
983 u32 flags); 999 u32 flags);
984int iwl_mvm_update_beacon_abort(struct iwl_mvm *mvm,
985 struct ieee80211_vif *vif, bool enable);
986int iwl_mvm_update_beacon_filter(struct iwl_mvm *mvm,
987 struct ieee80211_vif *vif,
988 bool force,
989 u32 flags);
990
991/* SMPS */ 1000/* SMPS */
992void iwl_mvm_update_smps(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 1001void iwl_mvm_update_smps(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
993 enum iwl_mvm_smps_type_request req_type, 1002 enum iwl_mvm_smps_type_request req_type,
994 enum ieee80211_smps_mode smps_request); 1003 enum ieee80211_smps_mode smps_request);
1004bool iwl_mvm_rx_diversity_allowed(struct iwl_mvm *mvm);
995 1005
996/* Low latency */ 1006/* Low latency */
997int iwl_mvm_update_low_latency(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 1007int iwl_mvm_update_low_latency(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
diff --git a/drivers/net/wireless/iwlwifi/mvm/nvm.c b/drivers/net/wireless/iwlwifi/mvm/nvm.c
index cf2d09f53782..808f78f6fbf9 100644
--- a/drivers/net/wireless/iwlwifi/mvm/nvm.c
+++ b/drivers/net/wireless/iwlwifi/mvm/nvm.c
@@ -74,6 +74,12 @@
74#define NVM_WRITE_OPCODE 1 74#define NVM_WRITE_OPCODE 1
75#define NVM_READ_OPCODE 0 75#define NVM_READ_OPCODE 0
76 76
77/* load nvm chunk response */
78enum {
79 READ_NVM_CHUNK_SUCCEED = 0,
80 READ_NVM_CHUNK_NOT_VALID_ADDRESS = 1
81};
82
77/* 83/*
78 * prepare the NVM host command w/ the pointers to the nvm buffer 84 * prepare the NVM host command w/ the pointers to the nvm buffer
79 * and send it to fw 85 * and send it to fw
@@ -90,7 +96,7 @@ static int iwl_nvm_write_chunk(struct iwl_mvm *mvm, u16 section,
90 struct iwl_host_cmd cmd = { 96 struct iwl_host_cmd cmd = {
91 .id = NVM_ACCESS_CMD, 97 .id = NVM_ACCESS_CMD,
92 .len = { sizeof(struct iwl_nvm_access_cmd), length }, 98 .len = { sizeof(struct iwl_nvm_access_cmd), length },
93 .flags = CMD_SYNC | CMD_SEND_IN_RFKILL, 99 .flags = CMD_SEND_IN_RFKILL,
94 .data = { &nvm_access_cmd, data }, 100 .data = { &nvm_access_cmd, data },
95 /* data may come from vmalloc, so use _DUP */ 101 /* data may come from vmalloc, so use _DUP */
96 .dataflags = { 0, IWL_HCMD_DFL_DUP }, 102 .dataflags = { 0, IWL_HCMD_DFL_DUP },
@@ -112,7 +118,7 @@ static int iwl_nvm_read_chunk(struct iwl_mvm *mvm, u16 section,
112 struct iwl_rx_packet *pkt; 118 struct iwl_rx_packet *pkt;
113 struct iwl_host_cmd cmd = { 119 struct iwl_host_cmd cmd = {
114 .id = NVM_ACCESS_CMD, 120 .id = NVM_ACCESS_CMD,
115 .flags = CMD_SYNC | CMD_WANT_SKB | CMD_SEND_IN_RFKILL, 121 .flags = CMD_WANT_SKB | CMD_SEND_IN_RFKILL,
116 .data = { &nvm_access_cmd, }, 122 .data = { &nvm_access_cmd, },
117 }; 123 };
118 int ret, bytes_read, offset_read; 124 int ret, bytes_read, offset_read;
@@ -139,10 +145,26 @@ static int iwl_nvm_read_chunk(struct iwl_mvm *mvm, u16 section,
139 offset_read = le16_to_cpu(nvm_resp->offset); 145 offset_read = le16_to_cpu(nvm_resp->offset);
140 resp_data = nvm_resp->data; 146 resp_data = nvm_resp->data;
141 if (ret) { 147 if (ret) {
142 IWL_ERR(mvm, 148 if ((offset != 0) &&
143 "NVM access command failed with status %d (device: %s)\n", 149 (ret == READ_NVM_CHUNK_NOT_VALID_ADDRESS)) {
144 ret, mvm->cfg->name); 150 /*
145 ret = -EINVAL; 151 * meaning of NOT_VALID_ADDRESS:
152 * driver try to read chunk from address that is
153 * multiple of 2K and got an error since addr is empty.
154 * meaning of (offset != 0): driver already
155 * read valid data from another chunk so this case
156 * is not an error.
157 */
158 IWL_DEBUG_EEPROM(mvm->trans->dev,
159 "NVM access command failed on offset 0x%x since that section size is multiple 2K\n",
160 offset);
161 ret = 0;
162 } else {
163 IWL_DEBUG_EEPROM(mvm->trans->dev,
164 "NVM access command failed with status %d (device: %s)\n",
165 ret, mvm->cfg->name);
166 ret = -EIO;
167 }
146 goto exit; 168 goto exit;
147 } 169 }
148 170
@@ -211,9 +233,9 @@ static int iwl_nvm_read_section(struct iwl_mvm *mvm, u16 section,
211 while (ret == length) { 233 while (ret == length) {
212 ret = iwl_nvm_read_chunk(mvm, section, offset, length, data); 234 ret = iwl_nvm_read_chunk(mvm, section, offset, length, data);
213 if (ret < 0) { 235 if (ret < 0) {
214 IWL_ERR(mvm, 236 IWL_DEBUG_EEPROM(mvm->trans->dev,
215 "Cannot read NVM from section %d offset %d, length %d\n", 237 "Cannot read NVM from section %d offset %d, length %d\n",
216 section, offset, length); 238 section, offset, length);
217 return ret; 239 return ret;
218 } 240 }
219 offset += ret; 241 offset += ret;
@@ -238,13 +260,20 @@ iwl_parse_nvm_sections(struct iwl_mvm *mvm)
238 return NULL; 260 return NULL;
239 } 261 }
240 } else { 262 } else {
263 /* SW and REGULATORY sections are mandatory */
241 if (!mvm->nvm_sections[NVM_SECTION_TYPE_SW].data || 264 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) { 265 !mvm->nvm_sections[NVM_SECTION_TYPE_REGULATORY].data) {
244 IWL_ERR(mvm, 266 IWL_ERR(mvm,
245 "Can't parse empty family 8000 NVM sections\n"); 267 "Can't parse empty family 8000 NVM sections\n");
246 return NULL; 268 return NULL;
247 } 269 }
270 /* MAC_OVERRIDE or at least HW section must exist */
271 if (!mvm->nvm_sections[mvm->cfg->nvm_hw_section_num].data &&
272 !mvm->nvm_sections[NVM_SECTION_TYPE_MAC_OVERRIDE].data) {
273 IWL_ERR(mvm,
274 "Can't parse mac_address, empty sections\n");
275 return NULL;
276 }
248 } 277 }
249 278
250 if (WARN_ON(!mvm->cfg)) 279 if (WARN_ON(!mvm->cfg))
@@ -311,16 +340,16 @@ static int iwl_mvm_read_external_nvm(struct iwl_mvm *mvm)
311 * get here after that we assume the NVM request can be satisfied 340 * get here after that we assume the NVM request can be satisfied
312 * synchronously. 341 * synchronously.
313 */ 342 */
314 ret = request_firmware(&fw_entry, iwlwifi_mod_params.nvm_file, 343 ret = request_firmware(&fw_entry, mvm->nvm_file_name,
315 mvm->trans->dev); 344 mvm->trans->dev);
316 if (ret) { 345 if (ret) {
317 IWL_ERR(mvm, "ERROR: %s isn't available %d\n", 346 IWL_ERR(mvm, "ERROR: %s isn't available %d\n",
318 iwlwifi_mod_params.nvm_file, ret); 347 mvm->nvm_file_name, ret);
319 return ret; 348 return ret;
320 } 349 }
321 350
322 IWL_INFO(mvm, "Loaded NVM file %s (%zu bytes)\n", 351 IWL_INFO(mvm, "Loaded NVM file %s (%zu bytes)\n",
323 iwlwifi_mod_params.nvm_file, fw_entry->size); 352 mvm->nvm_file_name, fw_entry->size);
324 353
325 if (fw_entry->size < sizeof(*file_sec)) { 354 if (fw_entry->size < sizeof(*file_sec)) {
326 IWL_ERR(mvm, "NVM file too small\n"); 355 IWL_ERR(mvm, "NVM file too small\n");
@@ -427,53 +456,28 @@ int iwl_mvm_load_nvm_to_nic(struct iwl_mvm *mvm)
427 return ret; 456 return ret;
428} 457}
429 458
430int iwl_nvm_init(struct iwl_mvm *mvm) 459int iwl_nvm_init(struct iwl_mvm *mvm, bool read_nvm_from_nic)
431{ 460{
432 int ret, i, section; 461 int ret, section;
433 u8 *nvm_buffer, *temp; 462 u8 *nvm_buffer, *temp;
434 int nvm_to_read[NVM_MAX_NUM_SECTIONS];
435 int num_of_sections_to_read;
436 463
437 if (WARN_ON_ONCE(mvm->cfg->nvm_hw_section_num >= NVM_MAX_NUM_SECTIONS)) 464 if (WARN_ON_ONCE(mvm->cfg->nvm_hw_section_num >= NVM_MAX_NUM_SECTIONS))
438 return -EINVAL; 465 return -EINVAL;
439 466
440 /* load external NVM if configured */ 467 /* load NVM values from nic */
441 if (iwlwifi_mod_params.nvm_file) { 468 if (read_nvm_from_nic) {
442 /* move to External NVM flow */
443 ret = iwl_mvm_read_external_nvm(mvm);
444 if (ret)
445 return ret;
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
463 /* Read From FW NVM */ 469 /* Read From FW NVM */
464 IWL_DEBUG_EEPROM(mvm->trans->dev, "Read from NVM\n"); 470 IWL_DEBUG_EEPROM(mvm->trans->dev, "Read from NVM\n");
465 471
466 /* TODO: find correct NVM max size for a section */
467 nvm_buffer = kmalloc(mvm->cfg->base_params->eeprom_size, 472 nvm_buffer = kmalloc(mvm->cfg->base_params->eeprom_size,
468 GFP_KERNEL); 473 GFP_KERNEL);
469 if (!nvm_buffer) 474 if (!nvm_buffer)
470 return -ENOMEM; 475 return -ENOMEM;
471 for (i = 0; i < num_of_sections_to_read; i++) { 476 for (section = 0; section < NVM_MAX_NUM_SECTIONS; section++) {
472 section = nvm_to_read[i];
473 /* we override the constness for initial read */ 477 /* we override the constness for initial read */
474 ret = iwl_nvm_read_section(mvm, section, nvm_buffer); 478 ret = iwl_nvm_read_section(mvm, section, nvm_buffer);
475 if (ret < 0) 479 if (ret < 0)
476 break; 480 continue;
477 temp = kmemdup(nvm_buffer, ret, GFP_KERNEL); 481 temp = kmemdup(nvm_buffer, ret, GFP_KERNEL);
478 if (!temp) { 482 if (!temp) {
479 ret = -ENOMEM; 483 ret = -ENOMEM;
@@ -502,15 +506,21 @@ int iwl_nvm_init(struct iwl_mvm *mvm)
502 mvm->nvm_hw_blob.size = ret; 506 mvm->nvm_hw_blob.size = ret;
503 break; 507 break;
504 } 508 }
505 WARN(1, "section: %d", section);
506 } 509 }
507#endif 510#endif
508 } 511 }
509 kfree(nvm_buffer); 512 kfree(nvm_buffer);
510 if (ret < 0) 513 }
514
515 /* load external NVM if configured */
516 if (mvm->nvm_file_name) {
517 /* move to External NVM flow */
518 ret = iwl_mvm_read_external_nvm(mvm);
519 if (ret)
511 return ret; 520 return ret;
512 } 521 }
513 522
523 /* parse the relevant nvm sections */
514 mvm->nvm_data = iwl_parse_nvm_sections(mvm); 524 mvm->nvm_data = iwl_parse_nvm_sections(mvm);
515 if (!mvm->nvm_data) 525 if (!mvm->nvm_data)
516 return -ENODATA; 526 return -ENODATA;
diff --git a/drivers/net/wireless/iwlwifi/mvm/ops.c b/drivers/net/wireless/iwlwifi/mvm/ops.c
index 7a5a8bac5fd0..cc2f7de396de 100644
--- a/drivers/net/wireless/iwlwifi/mvm/ops.c
+++ b/drivers/net/wireless/iwlwifi/mvm/ops.c
@@ -79,8 +79,8 @@
79#include "iwl-prph.h" 79#include "iwl-prph.h"
80#include "rs.h" 80#include "rs.h"
81#include "fw-api-scan.h" 81#include "fw-api-scan.h"
82#include "fw-error-dump.h"
83#include "time-event.h" 82#include "time-event.h"
83#include "iwl-fw-error-dump.h"
84 84
85/* 85/*
86 * module name, copyright, version, etc. 86 * module name, copyright, version, etc.
@@ -220,7 +220,7 @@ static const struct iwl_rx_handlers iwl_mvm_rx_handlers[] = {
220 RX_HANDLER(BA_NOTIF, iwl_mvm_rx_ba_notif, false), 220 RX_HANDLER(BA_NOTIF, iwl_mvm_rx_ba_notif, false),
221 221
222 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),
223 RX_HANDLER(BEACON_NOTIFICATION, iwl_mvm_rx_beacon_notif, false), 223 RX_HANDLER(BEACON_NOTIFICATION, iwl_mvm_rx_beacon_notif, true),
224 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, 225 RX_HANDLER(ANTENNA_COUPLING_NOTIFICATION,
226 iwl_mvm_rx_ant_coupling_notif, true), 226 iwl_mvm_rx_ant_coupling_notif, true),
@@ -466,13 +466,24 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
466 466
467 min_backoff = calc_min_backoff(trans, cfg); 467 min_backoff = calc_min_backoff(trans, cfg);
468 iwl_mvm_tt_initialize(mvm, min_backoff); 468 iwl_mvm_tt_initialize(mvm, min_backoff);
469 /* set the nvm_file_name according to priority */
470 if (iwlwifi_mod_params.nvm_file)
471 mvm->nvm_file_name = iwlwifi_mod_params.nvm_file;
472 else
473 mvm->nvm_file_name = mvm->cfg->default_nvm_file;
474
475 if (WARN(cfg->no_power_up_nic_in_init && !mvm->nvm_file_name,
476 "not allowing power-up and not having nvm_file\n"))
477 goto out_free;
469 478
470 /* 479 /*
471 * If the NVM exists in an external file, 480 * Even if nvm exists in the nvm_file driver should read agin the nvm
472 * there is no need to unnecessarily power up the NIC at driver load 481 * from the nic because there might be entries that exist in the OTP
482 * and not in the file.
483 * for nics with no_power_up_nic_in_init: rely completley on nvm_file
473 */ 484 */
474 if (iwlwifi_mod_params.nvm_file) { 485 if (cfg->no_power_up_nic_in_init && mvm->nvm_file_name) {
475 err = iwl_nvm_init(mvm); 486 err = iwl_nvm_init(mvm, false);
476 if (err) 487 if (err)
477 goto out_free; 488 goto out_free;
478 } else { 489 } else {
@@ -519,7 +530,7 @@ iwl_op_mode_mvm_start(struct iwl_trans *trans, const struct iwl_cfg *cfg,
519 out_free: 530 out_free:
520 iwl_phy_db_free(mvm->phy_db); 531 iwl_phy_db_free(mvm->phy_db);
521 kfree(mvm->scan_cmd); 532 kfree(mvm->scan_cmd);
522 if (!iwlwifi_mod_params.nvm_file) 533 if (!cfg->no_power_up_nic_in_init || !mvm->nvm_file_name)
523 iwl_trans_op_mode_leave(trans); 534 iwl_trans_op_mode_leave(trans);
524 ieee80211_free_hw(mvm->hw); 535 ieee80211_free_hw(mvm->hw);
525 return NULL; 536 return NULL;
@@ -816,6 +827,7 @@ void iwl_mvm_fw_error_dump(struct iwl_mvm *mvm)
816 struct iwl_fw_error_dump_file *dump_file; 827 struct iwl_fw_error_dump_file *dump_file;
817 struct iwl_fw_error_dump_data *dump_data; 828 struct iwl_fw_error_dump_data *dump_data;
818 u32 file_len; 829 u32 file_len;
830 u32 trans_len;
819 831
820 lockdep_assert_held(&mvm->mutex); 832 lockdep_assert_held(&mvm->mutex);
821 833
@@ -827,6 +839,10 @@ void iwl_mvm_fw_error_dump(struct iwl_mvm *mvm)
827 sizeof(*dump_file) + 839 sizeof(*dump_file) +
828 sizeof(*dump_data) * 2; 840 sizeof(*dump_data) * 2;
829 841
842 trans_len = iwl_trans_dump_data(mvm->trans, NULL, 0);
843 if (trans_len)
844 file_len += trans_len;
845
830 dump_file = vmalloc(file_len); 846 dump_file = vmalloc(file_len);
831 if (!dump_file) 847 if (!dump_file)
832 return; 848 return;
@@ -840,7 +856,7 @@ void iwl_mvm_fw_error_dump(struct iwl_mvm *mvm)
840 dump_data->len = cpu_to_le32(mvm->fw_error_rxf_len); 856 dump_data->len = cpu_to_le32(mvm->fw_error_rxf_len);
841 memcpy(dump_data->data, mvm->fw_error_rxf, mvm->fw_error_rxf_len); 857 memcpy(dump_data->data, mvm->fw_error_rxf, mvm->fw_error_rxf_len);
842 858
843 dump_data = (void *)((u8 *)dump_data->data + mvm->fw_error_rxf_len); 859 dump_data = iwl_mvm_fw_error_next_data(dump_data);
844 dump_data->type = cpu_to_le32(IWL_FW_ERROR_DUMP_SRAM); 860 dump_data->type = cpu_to_le32(IWL_FW_ERROR_DUMP_SRAM);
845 dump_data->len = cpu_to_le32(mvm->fw_error_sram_len); 861 dump_data->len = cpu_to_le32(mvm->fw_error_sram_len);
846 862
@@ -858,6 +874,15 @@ void iwl_mvm_fw_error_dump(struct iwl_mvm *mvm)
858 kfree(mvm->fw_error_sram); 874 kfree(mvm->fw_error_sram);
859 mvm->fw_error_sram = NULL; 875 mvm->fw_error_sram = NULL;
860 mvm->fw_error_sram_len = 0; 876 mvm->fw_error_sram_len = 0;
877
878 if (trans_len) {
879 void *buf = iwl_mvm_fw_error_next_data(dump_data);
880 u32 real_trans_len = iwl_trans_dump_data(mvm->trans, buf,
881 trans_len);
882 dump_data = (void *)((u8 *)buf + real_trans_len);
883 dump_file->file_len =
884 cpu_to_le32(file_len - trans_len + real_trans_len);
885 }
861} 886}
862#endif 887#endif
863 888
@@ -1143,7 +1168,7 @@ static void iwl_mvm_d0i3_exit_work(struct work_struct *wk)
1143 struct iwl_mvm *mvm = container_of(wk, struct iwl_mvm, d0i3_exit_work); 1168 struct iwl_mvm *mvm = container_of(wk, struct iwl_mvm, d0i3_exit_work);
1144 struct iwl_host_cmd get_status_cmd = { 1169 struct iwl_host_cmd get_status_cmd = {
1145 .id = WOWLAN_GET_STATUSES, 1170 .id = WOWLAN_GET_STATUSES,
1146 .flags = CMD_SYNC | CMD_HIGH_PRIO | CMD_WANT_SKB, 1171 .flags = CMD_HIGH_PRIO | CMD_WANT_SKB,
1147 }; 1172 };
1148 struct iwl_wowlan_status *status; 1173 struct iwl_wowlan_status *status;
1149 int ret; 1174 int ret;
diff --git a/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c b/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c
index 237efe0ac1c4..539f3a942d43 100644
--- a/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c
+++ b/drivers/net/wireless/iwlwifi/mvm/phy-ctxt.c
@@ -156,6 +156,18 @@ 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 /* In scenarios where we only ever use a single-stream rates,
160 * i.e. legacy 11b/g/a associations, single-stream APs or even
161 * static SMPS, enable both chains to get diversity, improving
162 * the case where we're far enough from the AP that attenuation
163 * between the two antennas is sufficiently different to impact
164 * performance.
165 */
166 if (active_cnt == 1 && iwl_mvm_rx_diversity_allowed(mvm)) {
167 idle_cnt = 2;
168 active_cnt = 2;
169 }
170
159 cmd->rxchain_info = cpu_to_le32(mvm->fw->valid_rx_ant << 171 cmd->rxchain_info = cpu_to_le32(mvm->fw->valid_rx_ant <<
160 PHY_RX_CHAIN_VALID_POS); 172 PHY_RX_CHAIN_VALID_POS);
161 cmd->rxchain_info |= cpu_to_le32(idle_cnt << PHY_RX_CHAIN_CNT_POS); 173 cmd->rxchain_info |= cpu_to_le32(idle_cnt << PHY_RX_CHAIN_CNT_POS);
@@ -187,7 +199,7 @@ static int iwl_mvm_phy_ctxt_apply(struct iwl_mvm *mvm,
187 iwl_mvm_phy_ctxt_cmd_data(mvm, &cmd, chandef, 199 iwl_mvm_phy_ctxt_cmd_data(mvm, &cmd, chandef,
188 chains_static, chains_dynamic); 200 chains_static, chains_dynamic);
189 201
190 ret = iwl_mvm_send_cmd_pdu(mvm, PHY_CONTEXT_CMD, CMD_SYNC, 202 ret = iwl_mvm_send_cmd_pdu(mvm, PHY_CONTEXT_CMD, 0,
191 sizeof(struct iwl_phy_context_cmd), 203 sizeof(struct iwl_phy_context_cmd),
192 &cmd); 204 &cmd);
193 if (ret) 205 if (ret)
@@ -202,18 +214,15 @@ int iwl_mvm_phy_ctxt_add(struct iwl_mvm *mvm, struct iwl_mvm_phy_ctxt *ctxt,
202 struct cfg80211_chan_def *chandef, 214 struct cfg80211_chan_def *chandef,
203 u8 chains_static, u8 chains_dynamic) 215 u8 chains_static, u8 chains_dynamic)
204{ 216{
205 int ret;
206
207 WARN_ON(!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status) && 217 WARN_ON(!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status) &&
208 ctxt->ref); 218 ctxt->ref);
209 lockdep_assert_held(&mvm->mutex); 219 lockdep_assert_held(&mvm->mutex);
210 220
211 ctxt->channel = chandef->chan; 221 ctxt->channel = chandef->chan;
212 ret = iwl_mvm_phy_ctxt_apply(mvm, ctxt, chandef,
213 chains_static, chains_dynamic,
214 FW_CTXT_ACTION_ADD, 0);
215 222
216 return ret; 223 return iwl_mvm_phy_ctxt_apply(mvm, ctxt, chandef,
224 chains_static, chains_dynamic,
225 FW_CTXT_ACTION_ADD, 0);
217} 226}
218 227
219/* 228/*
diff --git a/drivers/net/wireless/iwlwifi/mvm/power.c b/drivers/net/wireless/iwlwifi/mvm/power.c
index 78309f7d0b7b..c182a8baf685 100644
--- a/drivers/net/wireless/iwlwifi/mvm/power.c
+++ b/drivers/net/wireless/iwlwifi/mvm/power.c
@@ -123,28 +123,6 @@ void iwl_mvm_beacon_filter_set_cqm_params(struct iwl_mvm *mvm,
123 cmd->ba_enable_beacon_abort = cpu_to_le32(mvmvif->bf_data.ba_enabled); 123 cmd->ba_enable_beacon_abort = cpu_to_le32(mvmvif->bf_data.ba_enabled);
124} 124}
125 125
126int iwl_mvm_update_beacon_abort(struct iwl_mvm *mvm,
127 struct ieee80211_vif *vif, bool enable)
128{
129 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
130 struct iwl_beacon_filter_cmd cmd = {
131 IWL_BF_CMD_CONFIG_DEFAULTS,
132 .bf_enable_beacon_filter = cpu_to_le32(1),
133 .ba_enable_beacon_abort = cpu_to_le32(enable),
134 };
135
136 if (!mvmvif->bf_data.bf_enabled)
137 return 0;
138
139 if (mvm->cur_ucode == IWL_UCODE_WOWLAN)
140 cmd.ba_escape_timer = cpu_to_le32(IWL_BA_ESCAPE_TIMER_D3);
141
142 mvmvif->bf_data.ba_enabled = enable;
143 iwl_mvm_beacon_filter_set_cqm_params(mvm, vif, &cmd);
144 iwl_mvm_beacon_filter_debugfs_parameters(vif, &cmd);
145 return iwl_mvm_beacon_filter_send_cmd(mvm, &cmd, CMD_SYNC);
146}
147
148static void iwl_mvm_power_log(struct iwl_mvm *mvm, 126static void iwl_mvm_power_log(struct iwl_mvm *mvm,
149 struct iwl_mac_power_cmd *cmd) 127 struct iwl_mac_power_cmd *cmd)
150{ 128{
@@ -268,10 +246,30 @@ static void iwl_mvm_power_configure_uapsd(struct iwl_mvm *mvm,
268 IWL_MVM_PS_HEAVY_RX_THLD_PERCENT; 246 IWL_MVM_PS_HEAVY_RX_THLD_PERCENT;
269} 247}
270 248
249static void iwl_mvm_binding_iterator(void *_data, u8 *mac,
250 struct ieee80211_vif *vif)
251{
252 unsigned long *data = _data;
253 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
254
255 if (!mvmvif->phy_ctxt)
256 return;
257
258 if (vif->type == NL80211_IFTYPE_STATION ||
259 vif->type == NL80211_IFTYPE_AP)
260 __set_bit(mvmvif->phy_ctxt->id, data);
261}
262
271static bool iwl_mvm_power_allow_uapsd(struct iwl_mvm *mvm, 263static bool iwl_mvm_power_allow_uapsd(struct iwl_mvm *mvm,
272 struct ieee80211_vif *vif) 264 struct ieee80211_vif *vif)
273{ 265{
274 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 266 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
267 unsigned long phy_ctxt_counter = 0;
268
269 ieee80211_iterate_active_interfaces_atomic(mvm->hw,
270 IEEE80211_IFACE_ITER_NORMAL,
271 iwl_mvm_binding_iterator,
272 &phy_ctxt_counter);
275 273
276 if (!memcmp(mvmvif->uapsd_misbehaving_bssid, vif->bss_conf.bssid, 274 if (!memcmp(mvmvif->uapsd_misbehaving_bssid, vif->bss_conf.bssid,
277 ETH_ALEN)) 275 ETH_ALEN))
@@ -289,6 +287,13 @@ static bool iwl_mvm_power_allow_uapsd(struct iwl_mvm *mvm,
289 IEEE80211_P2P_OPPPS_ENABLE_BIT)) 287 IEEE80211_P2P_OPPPS_ENABLE_BIT))
290 return false; 288 return false;
291 289
290 /*
291 * Avoid using uAPSD if client is in DCM -
292 * low latency issue in Miracast
293 */
294 if (hweight8(phy_ctxt_counter) >= 2)
295 return false;
296
292 return true; 297 return true;
293} 298}
294 299
@@ -429,7 +434,7 @@ static int iwl_mvm_power_send_cmd(struct iwl_mvm *mvm,
429 memcpy(&iwl_mvm_vif_from_mac80211(vif)->mac_pwr_cmd, &cmd, sizeof(cmd)); 434 memcpy(&iwl_mvm_vif_from_mac80211(vif)->mac_pwr_cmd, &cmd, sizeof(cmd));
430#endif 435#endif
431 436
432 return iwl_mvm_send_cmd_pdu(mvm, MAC_PM_POWER_TABLE, CMD_SYNC, 437 return iwl_mvm_send_cmd_pdu(mvm, MAC_PM_POWER_TABLE, 0,
433 sizeof(cmd), &cmd); 438 sizeof(cmd), &cmd);
434} 439}
435 440
@@ -455,7 +460,7 @@ int iwl_mvm_power_update_device(struct iwl_mvm *mvm)
455 "Sending device power command with flags = 0x%X\n", 460 "Sending device power command with flags = 0x%X\n",
456 cmd.flags); 461 cmd.flags);
457 462
458 return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, CMD_SYNC, sizeof(cmd), 463 return iwl_mvm_send_cmd_pdu(mvm, POWER_TABLE_CMD, 0, sizeof(cmd),
459 &cmd); 464 &cmd);
460} 465}
461 466
@@ -613,11 +618,15 @@ iwl_mvm_power_set_pm(struct iwl_mvm *mvm,
613 ap_same_channel = (bss_mvmvif->phy_ctxt->id == 618 ap_same_channel = (bss_mvmvif->phy_ctxt->id ==
614 ap_mvmvif->phy_ctxt->id); 619 ap_mvmvif->phy_ctxt->id);
615 620
616 /* bss is not stand alone: enable PM if alone on its channel */ 621 /* clients are not stand alone: enable PM if DCM */
617 if (vifs->bss_active && !(client_same_channel || ap_same_channel) && 622 if (!(client_same_channel || ap_same_channel) &&
618 (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM)) { 623 (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_BSS_P2P_PS_DCM)) {
624 if (vifs->bss_active)
619 bss_mvmvif->pm_enabled = true; 625 bss_mvmvif->pm_enabled = true;
620 return; 626 if (vifs->p2p_active &&
627 (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_P2P_PM))
628 p2p_mvmvif->pm_enabled = true;
629 return;
621 } 630 }
622 631
623 /* 632 /*
@@ -633,55 +642,6 @@ iwl_mvm_power_set_pm(struct iwl_mvm *mvm,
633 } 642 }
634} 643}
635 644
636int iwl_mvm_power_update_mac(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
637{
638 struct iwl_mvm_vif *mvmvif;
639 struct iwl_power_vifs vifs = {};
640 bool ba_enable;
641 int ret;
642
643 lockdep_assert_held(&mvm->mutex);
644
645 iwl_mvm_power_set_pm(mvm, &vifs);
646
647 /* disable PS if CAM */
648 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM) {
649 mvm->ps_disabled = true;
650 } else {
651 /* don't update device power state unless we add / remove monitor */
652 if (vifs.monitor_vif) {
653 if (vifs.monitor_active)
654 mvm->ps_disabled = true;
655 ret = iwl_mvm_power_update_device(mvm);
656 if (ret)
657 return ret;
658 }
659 }
660
661 if (vifs.bss_vif) {
662 ret = iwl_mvm_power_send_cmd(mvm, vifs.bss_vif);
663 if (ret)
664 return ret;
665 }
666
667 if (vifs.p2p_vif) {
668 ret = iwl_mvm_power_send_cmd(mvm, vifs.p2p_vif);
669 if (ret)
670 return ret;
671 }
672
673 if (!vifs.bf_vif)
674 return 0;
675
676 vif = vifs.bf_vif;
677 mvmvif = iwl_mvm_vif_from_mac80211(vif);
678
679 ba_enable = !(!mvmvif->pm_enabled || mvm->ps_disabled ||
680 !vif->bss_conf.ps || iwl_mvm_vif_low_latency(mvmvif));
681
682 return iwl_mvm_update_beacon_abort(mvm, vifs.bf_vif, ba_enable);
683}
684
685#ifdef CONFIG_IWLWIFI_DEBUGFS 645#ifdef CONFIG_IWLWIFI_DEBUGFS
686int iwl_mvm_power_mac_dbgfs_read(struct iwl_mvm *mvm, 646int iwl_mvm_power_mac_dbgfs_read(struct iwl_mvm *mvm,
687 struct ieee80211_vif *vif, char *buf, 647 struct ieee80211_vif *vif, char *buf,
@@ -801,7 +761,7 @@ static int _iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm,
801 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); 761 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
802 int ret; 762 int ret;
803 763
804 if (mvmvif != mvm->bf_allowed_vif || 764 if (mvmvif != mvm->bf_allowed_vif || !vif->bss_conf.dtim_period ||
805 vif->type != NL80211_IFTYPE_STATION || vif->p2p) 765 vif->type != NL80211_IFTYPE_STATION || vif->p2p)
806 return 0; 766 return 0;
807 767
@@ -829,6 +789,26 @@ int iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm,
829 return _iwl_mvm_enable_beacon_filter(mvm, vif, &cmd, flags, false); 789 return _iwl_mvm_enable_beacon_filter(mvm, vif, &cmd, flags, false);
830} 790}
831 791
792static int iwl_mvm_update_beacon_abort(struct iwl_mvm *mvm,
793 struct ieee80211_vif *vif,
794 bool enable)
795{
796 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
797 struct iwl_beacon_filter_cmd cmd = {
798 IWL_BF_CMD_CONFIG_DEFAULTS,
799 .bf_enable_beacon_filter = cpu_to_le32(1),
800 };
801
802 if (!mvmvif->bf_data.bf_enabled)
803 return 0;
804
805 if (mvm->cur_ucode == IWL_UCODE_WOWLAN)
806 cmd.ba_escape_timer = cpu_to_le32(IWL_BA_ESCAPE_TIMER_D3);
807
808 mvmvif->bf_data.ba_enabled = enable;
809 return _iwl_mvm_enable_beacon_filter(mvm, vif, &cmd, 0, false);
810}
811
832int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm, 812int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm,
833 struct ieee80211_vif *vif, 813 struct ieee80211_vif *vif,
834 u32 flags) 814 u32 flags)
@@ -848,6 +828,55 @@ int iwl_mvm_disable_beacon_filter(struct iwl_mvm *mvm,
848 return ret; 828 return ret;
849} 829}
850 830
831int iwl_mvm_power_update_mac(struct iwl_mvm *mvm)
832{
833 struct iwl_mvm_vif *mvmvif;
834 struct iwl_power_vifs vifs = {};
835 bool ba_enable;
836 int ret;
837
838 lockdep_assert_held(&mvm->mutex);
839
840 iwl_mvm_power_set_pm(mvm, &vifs);
841
842 /* disable PS if CAM */
843 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM) {
844 mvm->ps_disabled = true;
845 } else {
846 /* don't update device power state unless we add / remove monitor */
847 if (vifs.monitor_vif) {
848 if (vifs.monitor_active)
849 mvm->ps_disabled = true;
850 ret = iwl_mvm_power_update_device(mvm);
851 if (ret)
852 return ret;
853 }
854 }
855
856 if (vifs.bss_vif) {
857 ret = iwl_mvm_power_send_cmd(mvm, vifs.bss_vif);
858 if (ret)
859 return ret;
860 }
861
862 if (vifs.p2p_vif) {
863 ret = iwl_mvm_power_send_cmd(mvm, vifs.p2p_vif);
864 if (ret)
865 return ret;
866 }
867
868 if (!vifs.bf_vif)
869 return 0;
870
871 mvmvif = iwl_mvm_vif_from_mac80211(vifs.bf_vif);
872
873 ba_enable = !(!mvmvif->pm_enabled || mvm->ps_disabled ||
874 !vifs.bf_vif->bss_conf.ps ||
875 iwl_mvm_vif_low_latency(mvmvif));
876
877 return iwl_mvm_update_beacon_abort(mvm, vifs.bf_vif, ba_enable);
878}
879
851int iwl_mvm_update_d0i3_power_mode(struct iwl_mvm *mvm, 880int iwl_mvm_update_d0i3_power_mode(struct iwl_mvm *mvm,
852 struct ieee80211_vif *vif, 881 struct ieee80211_vif *vif,
853 bool enable, u32 flags) 882 bool enable, u32 flags)
@@ -871,9 +900,10 @@ int iwl_mvm_update_d0i3_power_mode(struct iwl_mvm *mvm,
871 if (WARN_ON(!dtimper_msec)) 900 if (WARN_ON(!dtimper_msec))
872 return 0; 901 return 0;
873 902
874 cmd.flags |=
875 cpu_to_le16(POWER_FLAGS_SKIP_OVER_DTIM_MSK);
876 cmd.skip_dtim_periods = 300 / dtimper_msec; 903 cmd.skip_dtim_periods = 300 / dtimper_msec;
904 if (cmd.skip_dtim_periods)
905 cmd.flags |=
906 cpu_to_le16(POWER_FLAGS_SKIP_OVER_DTIM_MSK);
877 } 907 }
878 iwl_mvm_power_log(mvm, &cmd); 908 iwl_mvm_power_log(mvm, &cmd);
879#ifdef CONFIG_IWLWIFI_DEBUGFS 909#ifdef CONFIG_IWLWIFI_DEBUGFS
@@ -904,23 +934,3 @@ int iwl_mvm_update_d0i3_power_mode(struct iwl_mvm *mvm,
904 934
905 return ret; 935 return ret;
906} 936}
907
908int iwl_mvm_update_beacon_filter(struct iwl_mvm *mvm,
909 struct ieee80211_vif *vif,
910 bool force,
911 u32 flags)
912{
913 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
914
915 if (mvmvif != mvm->bf_allowed_vif)
916 return 0;
917
918 if (!mvmvif->bf_data.bf_enabled) {
919 /* disable beacon filtering explicitly if force is true */
920 if (force)
921 return iwl_mvm_disable_beacon_filter(mvm, vif, flags);
922 return 0;
923 }
924
925 return iwl_mvm_enable_beacon_filter(mvm, vif, flags);
926}
diff --git a/drivers/net/wireless/iwlwifi/mvm/quota.c b/drivers/net/wireless/iwlwifi/mvm/quota.c
index 35e86e06dffd..ba68d7b84505 100644
--- a/drivers/net/wireless/iwlwifi/mvm/quota.c
+++ b/drivers/net/wireless/iwlwifi/mvm/quota.c
@@ -285,7 +285,7 @@ int iwl_mvm_update_quotas(struct iwl_mvm *mvm, struct ieee80211_vif *newvif)
285 285
286 iwl_mvm_adjust_quota_for_noa(mvm, &cmd); 286 iwl_mvm_adjust_quota_for_noa(mvm, &cmd);
287 287
288 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_QUOTA_CMD, CMD_SYNC, 288 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_QUOTA_CMD, 0,
289 sizeof(cmd), &cmd); 289 sizeof(cmd), &cmd);
290 if (ret) 290 if (ret)
291 IWL_ERR(mvm, "Failed to send quota: %d\n", ret); 291 IWL_ERR(mvm, "Failed to send quota: %d\n", ret);
diff --git a/drivers/net/wireless/iwlwifi/mvm/rs.c b/drivers/net/wireless/iwlwifi/mvm/rs.c
index 857ddaf6f48c..306a6caa4868 100644
--- a/drivers/net/wireless/iwlwifi/mvm/rs.c
+++ b/drivers/net/wireless/iwlwifi/mvm/rs.c
@@ -211,7 +211,7 @@ 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_INVALID, 215 RS_COLUMN_INVALID,
216 RS_COLUMN_INVALID, 216 RS_COLUMN_INVALID,
217 RS_COLUMN_INVALID, 217 RS_COLUMN_INVALID,
@@ -223,8 +223,8 @@ static const struct rs_tx_column rs_tx_columns[] = {
223 .ant = ANT_B, 223 .ant = ANT_B,
224 .next_columns = { 224 .next_columns = {
225 RS_COLUMN_LEGACY_ANT_A, 225 RS_COLUMN_LEGACY_ANT_A,
226 RS_COLUMN_SISO_ANT_A,
227 RS_COLUMN_SISO_ANT_B, 226 RS_COLUMN_SISO_ANT_B,
227 RS_COLUMN_MIMO2,
228 RS_COLUMN_INVALID, 228 RS_COLUMN_INVALID,
229 RS_COLUMN_INVALID, 229 RS_COLUMN_INVALID,
230 RS_COLUMN_INVALID, 230 RS_COLUMN_INVALID,
@@ -238,10 +238,10 @@ static const struct rs_tx_column rs_tx_columns[] = {
238 RS_COLUMN_SISO_ANT_B, 238 RS_COLUMN_SISO_ANT_B,
239 RS_COLUMN_MIMO2, 239 RS_COLUMN_MIMO2,
240 RS_COLUMN_SISO_ANT_A_SGI, 240 RS_COLUMN_SISO_ANT_A_SGI,
241 RS_COLUMN_SISO_ANT_B_SGI,
242 RS_COLUMN_LEGACY_ANT_A, 241 RS_COLUMN_LEGACY_ANT_A,
243 RS_COLUMN_LEGACY_ANT_B, 242 RS_COLUMN_LEGACY_ANT_B,
244 RS_COLUMN_INVALID, 243 RS_COLUMN_INVALID,
244 RS_COLUMN_INVALID,
245 }, 245 },
246 .checks = { 246 .checks = {
247 rs_siso_allow, 247 rs_siso_allow,
@@ -254,10 +254,10 @@ static const struct rs_tx_column rs_tx_columns[] = {
254 RS_COLUMN_SISO_ANT_A, 254 RS_COLUMN_SISO_ANT_A,
255 RS_COLUMN_MIMO2, 255 RS_COLUMN_MIMO2,
256 RS_COLUMN_SISO_ANT_B_SGI, 256 RS_COLUMN_SISO_ANT_B_SGI,
257 RS_COLUMN_SISO_ANT_A_SGI,
258 RS_COLUMN_LEGACY_ANT_A, 257 RS_COLUMN_LEGACY_ANT_A,
259 RS_COLUMN_LEGACY_ANT_B, 258 RS_COLUMN_LEGACY_ANT_B,
260 RS_COLUMN_INVALID, 259 RS_COLUMN_INVALID,
260 RS_COLUMN_INVALID,
261 }, 261 },
262 .checks = { 262 .checks = {
263 rs_siso_allow, 263 rs_siso_allow,
@@ -271,10 +271,10 @@ static const struct rs_tx_column rs_tx_columns[] = {
271 RS_COLUMN_SISO_ANT_B_SGI, 271 RS_COLUMN_SISO_ANT_B_SGI,
272 RS_COLUMN_MIMO2_SGI, 272 RS_COLUMN_MIMO2_SGI,
273 RS_COLUMN_SISO_ANT_A, 273 RS_COLUMN_SISO_ANT_A,
274 RS_COLUMN_SISO_ANT_B,
275 RS_COLUMN_MIMO2,
276 RS_COLUMN_LEGACY_ANT_A, 274 RS_COLUMN_LEGACY_ANT_A,
277 RS_COLUMN_LEGACY_ANT_B, 275 RS_COLUMN_LEGACY_ANT_B,
276 RS_COLUMN_INVALID,
277 RS_COLUMN_INVALID,
278 }, 278 },
279 .checks = { 279 .checks = {
280 rs_siso_allow, 280 rs_siso_allow,
@@ -289,10 +289,10 @@ static const struct rs_tx_column rs_tx_columns[] = {
289 RS_COLUMN_SISO_ANT_A_SGI, 289 RS_COLUMN_SISO_ANT_A_SGI,
290 RS_COLUMN_MIMO2_SGI, 290 RS_COLUMN_MIMO2_SGI,
291 RS_COLUMN_SISO_ANT_B, 291 RS_COLUMN_SISO_ANT_B,
292 RS_COLUMN_SISO_ANT_A,
293 RS_COLUMN_MIMO2,
294 RS_COLUMN_LEGACY_ANT_A, 292 RS_COLUMN_LEGACY_ANT_A,
295 RS_COLUMN_LEGACY_ANT_B, 293 RS_COLUMN_LEGACY_ANT_B,
294 RS_COLUMN_INVALID,
295 RS_COLUMN_INVALID,
296 }, 296 },
297 .checks = { 297 .checks = {
298 rs_siso_allow, 298 rs_siso_allow,
@@ -304,12 +304,12 @@ static const struct rs_tx_column rs_tx_columns[] = {
304 .ant = ANT_AB, 304 .ant = ANT_AB,
305 .next_columns = { 305 .next_columns = {
306 RS_COLUMN_SISO_ANT_A, 306 RS_COLUMN_SISO_ANT_A,
307 RS_COLUMN_SISO_ANT_B,
308 RS_COLUMN_SISO_ANT_A_SGI,
309 RS_COLUMN_SISO_ANT_B_SGI,
310 RS_COLUMN_MIMO2_SGI, 307 RS_COLUMN_MIMO2_SGI,
311 RS_COLUMN_LEGACY_ANT_A, 308 RS_COLUMN_LEGACY_ANT_A,
312 RS_COLUMN_LEGACY_ANT_B, 309 RS_COLUMN_LEGACY_ANT_B,
310 RS_COLUMN_INVALID,
311 RS_COLUMN_INVALID,
312 RS_COLUMN_INVALID,
313 }, 313 },
314 .checks = { 314 .checks = {
315 rs_mimo_allow, 315 rs_mimo_allow,
@@ -321,12 +321,12 @@ static const struct rs_tx_column rs_tx_columns[] = {
321 .sgi = true, 321 .sgi = true,
322 .next_columns = { 322 .next_columns = {
323 RS_COLUMN_SISO_ANT_A_SGI, 323 RS_COLUMN_SISO_ANT_A_SGI,
324 RS_COLUMN_SISO_ANT_B_SGI,
325 RS_COLUMN_SISO_ANT_A,
326 RS_COLUMN_SISO_ANT_B,
327 RS_COLUMN_MIMO2, 324 RS_COLUMN_MIMO2,
328 RS_COLUMN_LEGACY_ANT_A, 325 RS_COLUMN_LEGACY_ANT_A,
329 RS_COLUMN_LEGACY_ANT_B, 326 RS_COLUMN_LEGACY_ANT_B,
327 RS_COLUMN_INVALID,
328 RS_COLUMN_INVALID,
329 RS_COLUMN_INVALID,
330 }, 330 },
331 .checks = { 331 .checks = {
332 rs_mimo_allow, 332 rs_mimo_allow,
@@ -1335,105 +1335,50 @@ static void rs_set_expected_tpt_table(struct iwl_lq_sta *lq_sta,
1335 tbl->expected_tpt = rs_get_expected_tpt_table(lq_sta, column, rate->bw); 1335 tbl->expected_tpt = rs_get_expected_tpt_table(lq_sta, column, rate->bw);
1336} 1336}
1337 1337
1338/*
1339 * Find starting rate for new "search" high-throughput mode of modulation.
1340 * Goal is to find lowest expected rate (under perfect conditions) that is
1341 * above the current measured throughput of "active" mode, to give new mode
1342 * a fair chance to prove itself without too many challenges.
1343 *
1344 * This gets called when transitioning to more aggressive modulation
1345 * (i.e. legacy to SISO or MIMO, or SISO to MIMO), as well as less aggressive
1346 * (i.e. MIMO to SISO). When moving to MIMO, bit rate will typically need
1347 * to decrease to match "active" throughput. When moving from MIMO to SISO,
1348 * bit rate will typically need to increase, but not if performance was bad.
1349 */
1350static s32 rs_get_best_rate(struct iwl_mvm *mvm, 1338static s32 rs_get_best_rate(struct iwl_mvm *mvm,
1351 struct iwl_lq_sta *lq_sta, 1339 struct iwl_lq_sta *lq_sta,
1352 struct iwl_scale_tbl_info *tbl, /* "search" */ 1340 struct iwl_scale_tbl_info *tbl, /* "search" */
1353 u16 rate_mask, s8 index) 1341 unsigned long rate_mask, s8 index)
1354{ 1342{
1355 /* "active" values */
1356 struct iwl_scale_tbl_info *active_tbl = 1343 struct iwl_scale_tbl_info *active_tbl =
1357 &(lq_sta->lq_info[lq_sta->active_tbl]); 1344 &(lq_sta->lq_info[lq_sta->active_tbl]);
1358 s32 active_sr = active_tbl->win[index].success_ratio; 1345 s32 success_ratio = active_tbl->win[index].success_ratio;
1359 s32 active_tpt = active_tbl->expected_tpt[index]; 1346 u16 expected_current_tpt = active_tbl->expected_tpt[index];
1360 /* expected "search" throughput */
1361 const u16 *tpt_tbl = tbl->expected_tpt; 1347 const u16 *tpt_tbl = tbl->expected_tpt;
1362
1363 s32 new_rate, high, low, start_hi;
1364 u16 high_low; 1348 u16 high_low;
1365 s8 rate = index; 1349 u32 target_tpt;
1366 1350 int rate_idx;
1367 new_rate = high = low = start_hi = IWL_RATE_INVALID;
1368
1369 while (1) {
1370 high_low = rs_get_adjacent_rate(mvm, rate, rate_mask,
1371 tbl->rate.type);
1372
1373 low = high_low & 0xff;
1374 high = (high_low >> 8) & 0xff;
1375 1351
1376 /* 1352 if (success_ratio > RS_SR_NO_DECREASE) {
1377 * Lower the "search" bit rate, to give new "search" mode 1353 target_tpt = 100 * expected_current_tpt;
1378 * approximately the same throughput as "active" if: 1354 IWL_DEBUG_RATE(mvm,
1379 * 1355 "SR %d high. Find rate exceeding EXPECTED_CURRENT %d\n",
1380 * 1) "Active" mode has been working modestly well (but not 1356 success_ratio, target_tpt);
1381 * great), and expected "search" throughput (under perfect 1357 } else {
1382 * conditions) at candidate rate is above the actual 1358 target_tpt = lq_sta->last_tpt;
1383 * measured "active" throughput (but less than expected 1359 IWL_DEBUG_RATE(mvm,
1384 * "active" throughput under perfect conditions). 1360 "SR %d not thag good. Find rate exceeding ACTUAL_TPT %d\n",
1385 * OR 1361 success_ratio, target_tpt);
1386 * 2) "Active" mode has been working perfectly or very well 1362 }
1387 * and expected "search" throughput (under perfect
1388 * conditions) at candidate rate is above expected
1389 * "active" throughput (under perfect conditions).
1390 */
1391 if ((((100 * tpt_tbl[rate]) > lq_sta->last_tpt) &&
1392 ((active_sr > RS_SR_FORCE_DECREASE) &&
1393 (active_sr <= IWL_RATE_HIGH_TH) &&
1394 (tpt_tbl[rate] <= active_tpt))) ||
1395 ((active_sr >= IWL_RATE_SCALE_SWITCH) &&
1396 (tpt_tbl[rate] > active_tpt))) {
1397 /* (2nd or later pass)
1398 * If we've already tried to raise the rate, and are
1399 * now trying to lower it, use the higher rate. */
1400 if (start_hi != IWL_RATE_INVALID) {
1401 new_rate = start_hi;
1402 break;
1403 }
1404
1405 new_rate = rate;
1406
1407 /* Loop again with lower rate */
1408 if (low != IWL_RATE_INVALID)
1409 rate = low;
1410 1363
1411 /* Lower rate not available, use the original */ 1364 rate_idx = find_first_bit(&rate_mask, BITS_PER_LONG);
1412 else
1413 break;
1414 1365
1415 /* Else try to raise the "search" rate to match "active" */ 1366 while (rate_idx != IWL_RATE_INVALID) {
1416 } else { 1367 if (target_tpt < (100 * tpt_tbl[rate_idx]))
1417 /* (2nd or later pass) 1368 break;
1418 * If we've already tried to lower the rate, and are
1419 * now trying to raise it, use the lower rate. */
1420 if (new_rate != IWL_RATE_INVALID)
1421 break;
1422 1369
1423 /* Loop again with higher rate */ 1370 high_low = rs_get_adjacent_rate(mvm, rate_idx, rate_mask,
1424 else if (high != IWL_RATE_INVALID) { 1371 tbl->rate.type);
1425 start_hi = high;
1426 rate = high;
1427 1372
1428 /* Higher rate not available, use the original */ 1373 rate_idx = (high_low >> 8) & 0xff;
1429 } else {
1430 new_rate = rate;
1431 break;
1432 }
1433 }
1434 } 1374 }
1435 1375
1436 return new_rate; 1376 IWL_DEBUG_RATE(mvm, "Best rate found %d target_tp %d expected_new %d\n",
1377 rate_idx, target_tpt,
1378 rate_idx != IWL_RATE_INVALID ?
1379 100 * tpt_tbl[rate_idx] : IWL_INVALID_VALUE);
1380
1381 return rate_idx;
1437} 1382}
1438 1383
1439static u32 rs_bw_from_sta_bw(struct ieee80211_sta *sta) 1384static u32 rs_bw_from_sta_bw(struct ieee80211_sta *sta)
@@ -1608,7 +1553,7 @@ static enum rs_column rs_get_next_column(struct iwl_mvm *mvm,
1608 1553
1609 tpt = lq_sta->last_tpt / 100; 1554 tpt = lq_sta->last_tpt / 100;
1610 expected_tpt_tbl = rs_get_expected_tpt_table(lq_sta, next_col, 1555 expected_tpt_tbl = rs_get_expected_tpt_table(lq_sta, next_col,
1611 tbl->rate.bw); 1556 rs_bw_from_sta_bw(sta));
1612 if (WARN_ON_ONCE(!expected_tpt_tbl)) 1557 if (WARN_ON_ONCE(!expected_tpt_tbl))
1613 continue; 1558 continue;
1614 1559
@@ -1649,7 +1594,7 @@ static int rs_switch_to_column(struct iwl_mvm *mvm,
1649 const struct rs_tx_column *curr_column = &rs_tx_columns[tbl->column]; 1594 const struct rs_tx_column *curr_column = &rs_tx_columns[tbl->column];
1650 u32 sz = (sizeof(struct iwl_scale_tbl_info) - 1595 u32 sz = (sizeof(struct iwl_scale_tbl_info) -
1651 (sizeof(struct iwl_rate_scale_data) * IWL_RATE_COUNT)); 1596 (sizeof(struct iwl_rate_scale_data) * IWL_RATE_COUNT));
1652 u16 rate_mask = 0; 1597 unsigned long rate_mask = 0;
1653 u32 rate_idx = 0; 1598 u32 rate_idx = 0;
1654 1599
1655 memcpy(search_tbl, tbl, sz); 1600 memcpy(search_tbl, tbl, sz);
@@ -1691,7 +1636,7 @@ static int rs_switch_to_column(struct iwl_mvm *mvm,
1691 !(BIT(rate_idx) & rate_mask)) { 1636 !(BIT(rate_idx) & rate_mask)) {
1692 IWL_DEBUG_RATE(mvm, 1637 IWL_DEBUG_RATE(mvm,
1693 "can not switch with index %d" 1638 "can not switch with index %d"
1694 " rate mask %x\n", 1639 " rate mask %lx\n",
1695 rate_idx, rate_mask); 1640 rate_idx, rate_mask);
1696 1641
1697 goto err; 1642 goto err;
@@ -1805,16 +1750,21 @@ static void rs_get_adjacent_txp(struct iwl_mvm *mvm, int index,
1805 *stronger = TPC_INVALID; 1750 *stronger = TPC_INVALID;
1806} 1751}
1807 1752
1808static bool rs_tpc_allowed(struct iwl_mvm *mvm, struct rs_rate *rate, 1753static bool rs_tpc_allowed(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
1809 enum ieee80211_band band) 1754 struct rs_rate *rate, enum ieee80211_band band)
1810{ 1755{
1811 int index = rate->index; 1756 int index = rate->index;
1757 bool cam = (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM);
1758 bool sta_ps_disabled = (vif->type == NL80211_IFTYPE_STATION &&
1759 !vif->bss_conf.ps);
1812 1760
1761 IWL_DEBUG_RATE(mvm, "cam: %d sta_ps_disabled %d\n",
1762 cam, sta_ps_disabled);
1813 /* 1763 /*
1814 * allow tpc only if power management is enabled, or bt coex 1764 * allow tpc only if power management is enabled, or bt coex
1815 * activity grade allows it and we are on 2.4Ghz. 1765 * activity grade allows it and we are on 2.4Ghz.
1816 */ 1766 */
1817 if (iwlmvm_mod_params.power_scheme == IWL_POWER_SCHEME_CAM && 1767 if ((cam || sta_ps_disabled) &&
1818 !iwl_mvm_bt_coex_is_tpc_allowed(mvm, band)) 1768 !iwl_mvm_bt_coex_is_tpc_allowed(mvm, band))
1819 return false; 1769 return false;
1820 1770
@@ -1916,7 +1866,7 @@ static bool rs_tpc_perform(struct iwl_mvm *mvm,
1916 1866
1917#ifdef CONFIG_MAC80211_DEBUGFS 1867#ifdef CONFIG_MAC80211_DEBUGFS
1918 if (lq_sta->dbg_fixed_txp_reduction <= TPC_MAX_REDUCTION) { 1868 if (lq_sta->dbg_fixed_txp_reduction <= TPC_MAX_REDUCTION) {
1919 IWL_DEBUG_RATE(mvm, "fixed tpc: %d", 1869 IWL_DEBUG_RATE(mvm, "fixed tpc: %d\n",
1920 lq_sta->dbg_fixed_txp_reduction); 1870 lq_sta->dbg_fixed_txp_reduction);
1921 lq_sta->lq.reduced_tpc = lq_sta->dbg_fixed_txp_reduction; 1871 lq_sta->lq.reduced_tpc = lq_sta->dbg_fixed_txp_reduction;
1922 return cur != lq_sta->dbg_fixed_txp_reduction; 1872 return cur != lq_sta->dbg_fixed_txp_reduction;
@@ -1931,9 +1881,9 @@ static bool rs_tpc_perform(struct iwl_mvm *mvm,
1931 band = chanctx_conf->def.chan->band; 1881 band = chanctx_conf->def.chan->band;
1932 rcu_read_unlock(); 1882 rcu_read_unlock();
1933 1883
1934 if (!rs_tpc_allowed(mvm, rate, band)) { 1884 if (!rs_tpc_allowed(mvm, vif, rate, band)) {
1935 IWL_DEBUG_RATE(mvm, 1885 IWL_DEBUG_RATE(mvm,
1936 "tpc is not allowed. remove txp restrictions"); 1886 "tpc is not allowed. remove txp restrictions\n");
1937 lq_sta->lq.reduced_tpc = TPC_NO_REDUCTION; 1887 lq_sta->lq.reduced_tpc = TPC_NO_REDUCTION;
1938 return cur != TPC_NO_REDUCTION; 1888 return cur != TPC_NO_REDUCTION;
1939 } 1889 }
@@ -1959,12 +1909,12 @@ static bool rs_tpc_perform(struct iwl_mvm *mvm,
1959 1909
1960 /* override actions if we are on the edge */ 1910 /* override actions if we are on the edge */
1961 if (weak == TPC_INVALID && action == TPC_ACTION_DECREASE) { 1911 if (weak == TPC_INVALID && action == TPC_ACTION_DECREASE) {
1962 IWL_DEBUG_RATE(mvm, "already in lowest txp, stay"); 1912 IWL_DEBUG_RATE(mvm, "already in lowest txp, stay\n");
1963 action = TPC_ACTION_STAY; 1913 action = TPC_ACTION_STAY;
1964 } else if (strong == TPC_INVALID && 1914 } else if (strong == TPC_INVALID &&
1965 (action == TPC_ACTION_INCREASE || 1915 (action == TPC_ACTION_INCREASE ||
1966 action == TPC_ACTION_NO_RESTIRCTION)) { 1916 action == TPC_ACTION_NO_RESTIRCTION)) {
1967 IWL_DEBUG_RATE(mvm, "already in highest txp, stay"); 1917 IWL_DEBUG_RATE(mvm, "already in highest txp, stay\n");
1968 action = TPC_ACTION_STAY; 1918 action = TPC_ACTION_STAY;
1969 } 1919 }
1970 1920
@@ -2235,7 +2185,8 @@ static void rs_rate_scale_perform(struct iwl_mvm *mvm,
2235 break; 2185 break;
2236 case RS_ACTION_STAY: 2186 case RS_ACTION_STAY:
2237 /* No change */ 2187 /* No change */
2238 update_lq = rs_tpc_perform(mvm, sta, lq_sta, tbl); 2188 if (lq_sta->rs_state == RS_STATE_STAY_IN_COLUMN)
2189 update_lq = rs_tpc_perform(mvm, sta, lq_sta, tbl);
2239 break; 2190 break;
2240 default: 2191 default:
2241 break; 2192 break;
@@ -2489,10 +2440,6 @@ static void rs_vht_set_enabled_rates(struct ieee80211_sta *sta,
2489 if (i == IWL_RATE_9M_INDEX) 2440 if (i == IWL_RATE_9M_INDEX)
2490 continue; 2441 continue;
2491 2442
2492 /* Disable MCS9 as a workaround */
2493 if (i == IWL_RATE_MCS_9_INDEX)
2494 continue;
2495
2496 /* VHT MCS9 isn't valid for 20Mhz for NSS=1,2 */ 2443 /* VHT MCS9 isn't valid for 20Mhz for NSS=1,2 */
2497 if (i == IWL_RATE_MCS_9_INDEX && 2444 if (i == IWL_RATE_MCS_9_INDEX &&
2498 sta->bandwidth == IEEE80211_STA_RX_BW_20) 2445 sta->bandwidth == IEEE80211_STA_RX_BW_20)
@@ -2511,10 +2458,6 @@ static void rs_vht_set_enabled_rates(struct ieee80211_sta *sta,
2511 if (i == IWL_RATE_9M_INDEX) 2458 if (i == IWL_RATE_9M_INDEX)
2512 continue; 2459 continue;
2513 2460
2514 /* Disable MCS9 as a workaround */
2515 if (i == IWL_RATE_MCS_9_INDEX)
2516 continue;
2517
2518 /* VHT MCS9 isn't valid for 20Mhz for NSS=1,2 */ 2461 /* VHT MCS9 isn't valid for 20Mhz for NSS=1,2 */
2519 if (i == IWL_RATE_MCS_9_INDEX && 2462 if (i == IWL_RATE_MCS_9_INDEX &&
2520 sta->bandwidth == IEEE80211_STA_RX_BW_20) 2463 sta->bandwidth == IEEE80211_STA_RX_BW_20)
diff --git a/drivers/net/wireless/iwlwifi/mvm/scan.c b/drivers/net/wireless/iwlwifi/mvm/scan.c
index 36ae01a18dee..4b6c7d4bd199 100644
--- a/drivers/net/wireless/iwlwifi/mvm/scan.c
+++ b/drivers/net/wireless/iwlwifi/mvm/scan.c
@@ -306,7 +306,6 @@ int iwl_mvm_scan_request(struct iwl_mvm *mvm,
306 .id = SCAN_REQUEST_CMD, 306 .id = SCAN_REQUEST_CMD,
307 .len = { 0, }, 307 .len = { 0, },
308 .data = { mvm->scan_cmd, }, 308 .data = { mvm->scan_cmd, },
309 .flags = CMD_SYNC,
310 .dataflags = { IWL_HCMD_DFL_NOCOPY, }, 309 .dataflags = { IWL_HCMD_DFL_NOCOPY, },
311 }; 310 };
312 struct iwl_scan_cmd *cmd = mvm->scan_cmd; 311 struct iwl_scan_cmd *cmd = mvm->scan_cmd;
@@ -517,7 +516,7 @@ int iwl_mvm_cancel_scan(struct iwl_mvm *mvm)
517 ARRAY_SIZE(scan_abort_notif), 516 ARRAY_SIZE(scan_abort_notif),
518 iwl_mvm_scan_abort_notif, NULL); 517 iwl_mvm_scan_abort_notif, NULL);
519 518
520 ret = iwl_mvm_send_cmd_pdu(mvm, SCAN_ABORT_CMD, CMD_SYNC, 0, NULL); 519 ret = iwl_mvm_send_cmd_pdu(mvm, SCAN_ABORT_CMD, 0, 0, NULL);
521 if (ret) { 520 if (ret) {
522 IWL_ERR(mvm, "Couldn't send SCAN_ABORT_CMD: %d\n", ret); 521 IWL_ERR(mvm, "Couldn't send SCAN_ABORT_CMD: %d\n", ret);
523 /* mac80211's state will be cleaned in the nic_restart flow */ 522 /* mac80211's state will be cleaned in the nic_restart flow */
@@ -749,7 +748,6 @@ int iwl_mvm_config_sched_scan(struct iwl_mvm *mvm,
749 struct iwl_scan_offload_cfg *scan_cfg; 748 struct iwl_scan_offload_cfg *scan_cfg;
750 struct iwl_host_cmd cmd = { 749 struct iwl_host_cmd cmd = {
751 .id = SCAN_OFFLOAD_CONFIG_CMD, 750 .id = SCAN_OFFLOAD_CONFIG_CMD,
752 .flags = CMD_SYNC,
753 }; 751 };
754 struct iwl_mvm_scan_params params = {}; 752 struct iwl_mvm_scan_params params = {};
755 753
@@ -807,7 +805,6 @@ int iwl_mvm_config_sched_scan_profiles(struct iwl_mvm *mvm,
807 struct iwl_scan_offload_blacklist *blacklist; 805 struct iwl_scan_offload_blacklist *blacklist;
808 struct iwl_host_cmd cmd = { 806 struct iwl_host_cmd cmd = {
809 .id = SCAN_OFFLOAD_UPDATE_PROFILES_CMD, 807 .id = SCAN_OFFLOAD_UPDATE_PROFILES_CMD,
810 .flags = CMD_SYNC,
811 .len[1] = sizeof(*profile_cfg), 808 .len[1] = sizeof(*profile_cfg),
812 .dataflags[0] = IWL_HCMD_DFL_NOCOPY, 809 .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
813 .dataflags[1] = IWL_HCMD_DFL_NOCOPY, 810 .dataflags[1] = IWL_HCMD_DFL_NOCOPY,
@@ -898,7 +895,7 @@ int iwl_mvm_sched_scan_start(struct iwl_mvm *mvm,
898 scan_req.flags |= 895 scan_req.flags |=
899 cpu_to_le16(IWL_SCAN_OFFLOAD_FLAG_EBS_ACCURATE_MODE); 896 cpu_to_le16(IWL_SCAN_OFFLOAD_FLAG_EBS_ACCURATE_MODE);
900 897
901 return iwl_mvm_send_cmd_pdu(mvm, SCAN_OFFLOAD_REQUEST_CMD, CMD_SYNC, 898 return iwl_mvm_send_cmd_pdu(mvm, SCAN_OFFLOAD_REQUEST_CMD, 0,
902 sizeof(scan_req), &scan_req); 899 sizeof(scan_req), &scan_req);
903} 900}
904 901
@@ -907,7 +904,6 @@ static int iwl_mvm_send_sched_scan_abort(struct iwl_mvm *mvm)
907 int ret; 904 int ret;
908 struct iwl_host_cmd cmd = { 905 struct iwl_host_cmd cmd = {
909 .id = SCAN_OFFLOAD_ABORT_CMD, 906 .id = SCAN_OFFLOAD_ABORT_CMD,
910 .flags = CMD_SYNC,
911 }; 907 };
912 u32 status; 908 u32 status;
913 909
@@ -936,7 +932,7 @@ static int iwl_mvm_send_sched_scan_abort(struct iwl_mvm *mvm)
936 return ret; 932 return ret;
937} 933}
938 934
939int iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm) 935int iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm, bool notify)
940{ 936{
941 int ret; 937 int ret;
942 struct iwl_notification_wait wait_scan_done; 938 struct iwl_notification_wait wait_scan_done;
@@ -974,5 +970,8 @@ int iwl_mvm_sched_scan_stop(struct iwl_mvm *mvm)
974 */ 970 */
975 mvm->scan_status = IWL_MVM_SCAN_NONE; 971 mvm->scan_status = IWL_MVM_SCAN_NONE;
976 972
973 if (notify)
974 ieee80211_sched_scan_stopped(mvm->hw);
975
977 return 0; 976 return 0;
978} 977}
diff --git a/drivers/net/wireless/iwlwifi/mvm/sta.c b/drivers/net/wireless/iwlwifi/mvm/sta.c
index 3e11b9d802e7..1fb01ea2e704 100644
--- a/drivers/net/wireless/iwlwifi/mvm/sta.c
+++ b/drivers/net/wireless/iwlwifi/mvm/sta.c
@@ -327,7 +327,7 @@ static int iwl_mvm_rm_sta_common(struct iwl_mvm *mvm, u8 sta_id)
327 return -EINVAL; 327 return -EINVAL;
328 } 328 }
329 329
330 ret = iwl_mvm_send_cmd_pdu(mvm, REMOVE_STA, CMD_SYNC, 330 ret = iwl_mvm_send_cmd_pdu(mvm, REMOVE_STA, 0,
331 sizeof(rm_sta_cmd), &rm_sta_cmd); 331 sizeof(rm_sta_cmd), &rm_sta_cmd);
332 if (ret) { 332 if (ret) {
333 IWL_ERR(mvm, "Failed to remove station. Id=%d\n", sta_id); 333 IWL_ERR(mvm, "Failed to remove station. Id=%d\n", sta_id);
@@ -1053,12 +1053,12 @@ static int iwl_mvm_send_sta_key(struct iwl_mvm *mvm,
1053 cmd.sta_id = sta_id; 1053 cmd.sta_id = sta_id;
1054 1054
1055 status = ADD_STA_SUCCESS; 1055 status = ADD_STA_SUCCESS;
1056 if (cmd_flags == CMD_SYNC) 1056 if (cmd_flags & CMD_ASYNC)
1057 ret = iwl_mvm_send_cmd_pdu_status(mvm, ADD_STA_KEY, sizeof(cmd),
1058 &cmd, &status);
1059 else
1060 ret = iwl_mvm_send_cmd_pdu(mvm, ADD_STA_KEY, CMD_ASYNC, 1057 ret = iwl_mvm_send_cmd_pdu(mvm, ADD_STA_KEY, CMD_ASYNC,
1061 sizeof(cmd), &cmd); 1058 sizeof(cmd), &cmd);
1059 else
1060 ret = iwl_mvm_send_cmd_pdu_status(mvm, ADD_STA_KEY, sizeof(cmd),
1061 &cmd, &status);
1062 1062
1063 switch (status) { 1063 switch (status) {
1064 case ADD_STA_SUCCESS: 1064 case ADD_STA_SUCCESS:
@@ -1111,7 +1111,7 @@ static int iwl_mvm_send_sta_igtk(struct iwl_mvm *mvm,
1111 remove_key ? "removing" : "installing", 1111 remove_key ? "removing" : "installing",
1112 igtk_cmd.sta_id); 1112 igtk_cmd.sta_id);
1113 1113
1114 return iwl_mvm_send_cmd_pdu(mvm, MGMT_MCAST_KEY, CMD_SYNC, 1114 return iwl_mvm_send_cmd_pdu(mvm, MGMT_MCAST_KEY, 0,
1115 sizeof(igtk_cmd), &igtk_cmd); 1115 sizeof(igtk_cmd), &igtk_cmd);
1116} 1116}
1117 1117
@@ -1198,15 +1198,15 @@ int iwl_mvm_set_sta_key(struct iwl_mvm *mvm,
1198 ieee80211_get_key_rx_seq(keyconf, 0, &seq); 1198 ieee80211_get_key_rx_seq(keyconf, 0, &seq);
1199 ieee80211_get_tkip_rx_p1k(keyconf, addr, seq.tkip.iv32, p1k); 1199 ieee80211_get_tkip_rx_p1k(keyconf, addr, seq.tkip.iv32, p1k);
1200 ret = iwl_mvm_send_sta_key(mvm, mvm_sta, keyconf, sta_id, 1200 ret = iwl_mvm_send_sta_key(mvm, mvm_sta, keyconf, sta_id,
1201 seq.tkip.iv32, p1k, CMD_SYNC); 1201 seq.tkip.iv32, p1k, 0);
1202 break; 1202 break;
1203 case WLAN_CIPHER_SUITE_CCMP: 1203 case WLAN_CIPHER_SUITE_CCMP:
1204 ret = iwl_mvm_send_sta_key(mvm, mvm_sta, keyconf, sta_id, 1204 ret = iwl_mvm_send_sta_key(mvm, mvm_sta, keyconf, sta_id,
1205 0, NULL, CMD_SYNC); 1205 0, NULL, 0);
1206 break; 1206 break;
1207 default: 1207 default:
1208 ret = iwl_mvm_send_sta_key(mvm, mvm_sta, keyconf, 1208 ret = iwl_mvm_send_sta_key(mvm, mvm_sta, keyconf,
1209 sta_id, 0, NULL, CMD_SYNC); 1209 sta_id, 0, NULL, 0);
1210 } 1210 }
1211 1211
1212 if (ret) 1212 if (ret)
diff --git a/drivers/net/wireless/iwlwifi/mvm/sta.h b/drivers/net/wireless/iwlwifi/mvm/sta.h
index e5e3071ff252..d98e8a2142b8 100644
--- a/drivers/net/wireless/iwlwifi/mvm/sta.h
+++ b/drivers/net/wireless/iwlwifi/mvm/sta.h
@@ -287,8 +287,6 @@ static inline u16 iwl_mvm_tid_queued(struct iwl_mvm_tid_data *tid_data)
287 * @tid_disable_agg: bitmap: if bit(tid) is set, the fw won't send ampdus for 287 * @tid_disable_agg: bitmap: if bit(tid) is set, the fw won't send ampdus for
288 * tid. 288 * tid.
289 * @max_agg_bufsize: the maximal size of the AGG buffer for this station 289 * @max_agg_bufsize: the maximal size of the AGG buffer for this station
290 * @bt_reduced_txpower_dbg: debug mode in which %bt_reduced_txpower is forced
291 * by debugfs.
292 * @bt_reduced_txpower: is reduced tx power enabled for this station 290 * @bt_reduced_txpower: is reduced tx power enabled for this station
293 * @next_status_eosp: the next reclaimed packet is a PS-Poll response and 291 * @next_status_eosp: the next reclaimed packet is a PS-Poll response and
294 * we need to signal the EOSP 292 * we need to signal the EOSP
@@ -309,7 +307,6 @@ struct iwl_mvm_sta {
309 u32 mac_id_n_color; 307 u32 mac_id_n_color;
310 u16 tid_disable_agg; 308 u16 tid_disable_agg;
311 u8 max_agg_bufsize; 309 u8 max_agg_bufsize;
312 bool bt_reduced_txpower_dbg;
313 bool bt_reduced_txpower; 310 bool bt_reduced_txpower;
314 bool next_status_eosp; 311 bool next_status_eosp;
315 spinlock_t lock; 312 spinlock_t lock;
diff --git a/drivers/net/wireless/iwlwifi/mvm/time-event.c b/drivers/net/wireless/iwlwifi/mvm/time-event.c
index a9402937f767..80100f6cc12a 100644
--- a/drivers/net/wireless/iwlwifi/mvm/time-event.c
+++ b/drivers/net/wireless/iwlwifi/mvm/time-event.c
@@ -312,7 +312,7 @@ static int iwl_mvm_time_event_send_add(struct iwl_mvm *mvm,
312 ARRAY_SIZE(time_event_response), 312 ARRAY_SIZE(time_event_response),
313 iwl_mvm_time_event_response, te_data); 313 iwl_mvm_time_event_response, te_data);
314 314
315 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_EVENT_CMD, CMD_SYNC, 315 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_EVENT_CMD, 0,
316 sizeof(*te_cmd), te_cmd); 316 sizeof(*te_cmd), te_cmd);
317 if (ret) { 317 if (ret) {
318 IWL_ERR(mvm, "Couldn't send TIME_EVENT_CMD: %d\n", ret); 318 IWL_ERR(mvm, "Couldn't send TIME_EVENT_CMD: %d\n", ret);
@@ -434,7 +434,7 @@ void iwl_mvm_remove_time_event(struct iwl_mvm *mvm,
434 cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id, mvmvif->color)); 434 cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id, mvmvif->color));
435 435
436 IWL_DEBUG_TE(mvm, "Removing TE 0x%x\n", le32_to_cpu(time_cmd.id)); 436 IWL_DEBUG_TE(mvm, "Removing TE 0x%x\n", le32_to_cpu(time_cmd.id));
437 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_EVENT_CMD, CMD_SYNC, 437 ret = iwl_mvm_send_cmd_pdu(mvm, TIME_EVENT_CMD, 0,
438 sizeof(time_cmd), &time_cmd); 438 sizeof(time_cmd), &time_cmd);
439 if (WARN_ON(ret)) 439 if (WARN_ON(ret))
440 return; 440 return;
diff --git a/drivers/net/wireless/iwlwifi/mvm/tt.c b/drivers/net/wireless/iwlwifi/mvm/tt.c
index 39a3e03a0acd..868561512783 100644
--- a/drivers/net/wireless/iwlwifi/mvm/tt.c
+++ b/drivers/net/wireless/iwlwifi/mvm/tt.c
@@ -409,7 +409,6 @@ void iwl_mvm_tt_tx_backoff(struct iwl_mvm *mvm, u32 backoff)
409 .id = REPLY_THERMAL_MNG_BACKOFF, 409 .id = REPLY_THERMAL_MNG_BACKOFF,
410 .len = { sizeof(u32), }, 410 .len = { sizeof(u32), },
411 .data = { &backoff, }, 411 .data = { &backoff, },
412 .flags = CMD_SYNC,
413 }; 412 };
414 413
415 backoff = max(backoff, mvm->thermal_throttle.min_backoff); 414 backoff = max(backoff, mvm->thermal_throttle.min_backoff);
diff --git a/drivers/net/wireless/iwlwifi/mvm/tx.c b/drivers/net/wireless/iwlwifi/mvm/tx.c
index ff1b630e130e..3846a6c41eb1 100644
--- a/drivers/net/wireless/iwlwifi/mvm/tx.c
+++ b/drivers/net/wireless/iwlwifi/mvm/tx.c
@@ -958,7 +958,7 @@ int iwl_mvm_flush_tx_path(struct iwl_mvm *mvm, u32 tfd_msk, bool sync)
958 .flush_ctl = cpu_to_le16(DUMP_TX_FIFO_FLUSH), 958 .flush_ctl = cpu_to_le16(DUMP_TX_FIFO_FLUSH),
959 }; 959 };
960 960
961 u32 flags = sync ? CMD_SYNC : CMD_ASYNC; 961 u32 flags = sync ? 0 : CMD_ASYNC;
962 962
963 ret = iwl_mvm_send_cmd_pdu(mvm, TXPATH_FLUSH, flags, 963 ret = iwl_mvm_send_cmd_pdu(mvm, TXPATH_FLUSH, flags,
964 sizeof(flush_cmd), &flush_cmd); 964 sizeof(flush_cmd), &flush_cmd);
diff --git a/drivers/net/wireless/iwlwifi/mvm/utils.c b/drivers/net/wireless/iwlwifi/mvm/utils.c
index eb2ca64820fc..aa9fc77e8413 100644
--- a/drivers/net/wireless/iwlwifi/mvm/utils.c
+++ b/drivers/net/wireless/iwlwifi/mvm/utils.c
@@ -144,7 +144,7 @@ int iwl_mvm_send_cmd_status(struct iwl_mvm *mvm, struct iwl_host_cmd *cmd,
144 "cmd flags %x", cmd->flags)) 144 "cmd flags %x", cmd->flags))
145 return -EINVAL; 145 return -EINVAL;
146 146
147 cmd->flags |= CMD_SYNC | CMD_WANT_SKB; 147 cmd->flags |= CMD_WANT_SKB;
148 148
149 ret = iwl_trans_send_cmd(mvm->trans, cmd); 149 ret = iwl_trans_send_cmd(mvm->trans, cmd);
150 if (ret == -ERFKILL) { 150 if (ret == -ERFKILL) {
@@ -519,6 +519,7 @@ void iwl_mvm_dump_nic_error_log(struct iwl_mvm *mvm)
519 iwl_mvm_dump_umac_error_log(mvm); 519 iwl_mvm_dump_umac_error_log(mvm);
520} 520}
521 521
522#ifdef CONFIG_IWLWIFI_DEBUGFS
522void iwl_mvm_fw_error_sram_dump(struct iwl_mvm *mvm) 523void iwl_mvm_fw_error_sram_dump(struct iwl_mvm *mvm)
523{ 524{
524 const struct fw_img *img; 525 const struct fw_img *img;
@@ -581,6 +582,7 @@ void iwl_mvm_fw_error_rxf_dump(struct iwl_mvm *mvm)
581 } 582 }
582 iwl_trans_release_nic_access(mvm->trans, &flags); 583 iwl_trans_release_nic_access(mvm->trans, &flags);
583} 584}
585#endif
584 586
585/** 587/**
586 * iwl_mvm_send_lq_cmd() - Send link quality command 588 * iwl_mvm_send_lq_cmd() - Send link quality command
@@ -597,7 +599,7 @@ int iwl_mvm_send_lq_cmd(struct iwl_mvm *mvm, struct iwl_lq_cmd *lq, bool init)
597 struct iwl_host_cmd cmd = { 599 struct iwl_host_cmd cmd = {
598 .id = LQ_CMD, 600 .id = LQ_CMD,
599 .len = { sizeof(struct iwl_lq_cmd), }, 601 .len = { sizeof(struct iwl_lq_cmd), },
600 .flags = init ? CMD_SYNC : CMD_ASYNC, 602 .flags = init ? 0 : CMD_ASYNC,
601 .data = { lq, }, 603 .data = { lq, },
602 }; 604 };
603 605
@@ -648,6 +650,39 @@ void iwl_mvm_update_smps(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
648 ieee80211_request_smps(vif, smps_mode); 650 ieee80211_request_smps(vif, smps_mode);
649} 651}
650 652
653static void iwl_mvm_diversity_iter(void *_data, u8 *mac,
654 struct ieee80211_vif *vif)
655{
656 struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
657 bool *result = _data;
658 int i;
659
660 for (i = 0; i < NUM_IWL_MVM_SMPS_REQ; i++) {
661 if (mvmvif->smps_requests[i] == IEEE80211_SMPS_STATIC ||
662 mvmvif->smps_requests[i] == IEEE80211_SMPS_DYNAMIC)
663 *result = false;
664 }
665}
666
667bool iwl_mvm_rx_diversity_allowed(struct iwl_mvm *mvm)
668{
669 bool result = true;
670
671 lockdep_assert_held(&mvm->mutex);
672
673 if (num_of_ant(mvm->fw->valid_rx_ant) == 1)
674 return false;
675
676 if (!mvm->cfg->rx_with_siso_diversity)
677 return false;
678
679 ieee80211_iterate_active_interfaces_atomic(
680 mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
681 iwl_mvm_diversity_iter, &result);
682
683 return result;
684}
685
651int iwl_mvm_update_low_latency(struct iwl_mvm *mvm, struct ieee80211_vif *vif, 686int iwl_mvm_update_low_latency(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
652 bool value) 687 bool value)
653{ 688{
@@ -667,7 +702,7 @@ int iwl_mvm_update_low_latency(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
667 702
668 iwl_mvm_bt_coex_vif_change(mvm); 703 iwl_mvm_bt_coex_vif_change(mvm);
669 704
670 return iwl_mvm_power_update_mac(mvm, vif); 705 return iwl_mvm_power_update_mac(mvm);
671} 706}
672 707
673static void iwl_mvm_ll_iter(void *_data, u8 *mac, struct ieee80211_vif *vif) 708static void iwl_mvm_ll_iter(void *_data, u8 *mac, struct ieee80211_vif *vif)
diff --git a/drivers/net/wireless/iwlwifi/pcie/drv.c b/drivers/net/wireless/iwlwifi/pcie/drv.c
index 3d1d57f9f5bc..7091a18d5a72 100644
--- a/drivers/net/wireless/iwlwifi/pcie/drv.c
+++ b/drivers/net/wireless/iwlwifi/pcie/drv.c
@@ -417,7 +417,7 @@ static u64 splx_get_pwr_limit(struct iwl_trans *trans, union acpi_object *splx)
417 splx->package.count != 2 || 417 splx->package.count != 2 ||
418 splx->package.elements[0].type != ACPI_TYPE_INTEGER || 418 splx->package.elements[0].type != ACPI_TYPE_INTEGER ||
419 splx->package.elements[0].integer.value != 0) { 419 splx->package.elements[0].integer.value != 0) {
420 IWL_ERR(trans, "Unsupported splx structure"); 420 IWL_ERR(trans, "Unsupported splx structure\n");
421 return 0; 421 return 0;
422 } 422 }
423 423
@@ -426,14 +426,14 @@ static u64 splx_get_pwr_limit(struct iwl_trans *trans, union acpi_object *splx)
426 limits->package.count < 2 || 426 limits->package.count < 2 ||
427 limits->package.elements[0].type != ACPI_TYPE_INTEGER || 427 limits->package.elements[0].type != ACPI_TYPE_INTEGER ||
428 limits->package.elements[1].type != ACPI_TYPE_INTEGER) { 428 limits->package.elements[1].type != ACPI_TYPE_INTEGER) {
429 IWL_ERR(trans, "Invalid limits element"); 429 IWL_ERR(trans, "Invalid limits element\n");
430 return 0; 430 return 0;
431 } 431 }
432 432
433 domain_type = &limits->package.elements[0]; 433 domain_type = &limits->package.elements[0];
434 power_limit = &limits->package.elements[1]; 434 power_limit = &limits->package.elements[1];
435 if (!(domain_type->integer.value & SPL_DOMAINTYPE_WIFI)) { 435 if (!(domain_type->integer.value & SPL_DOMAINTYPE_WIFI)) {
436 IWL_DEBUG_INFO(trans, "WiFi power is not limited"); 436 IWL_DEBUG_INFO(trans, "WiFi power is not limited\n");
437 return 0; 437 return 0;
438 } 438 }
439 439
@@ -450,26 +450,26 @@ static void set_dflt_pwr_limit(struct iwl_trans *trans, struct pci_dev *pdev)
450 pxsx_handle = ACPI_HANDLE(&pdev->dev); 450 pxsx_handle = ACPI_HANDLE(&pdev->dev);
451 if (!pxsx_handle) { 451 if (!pxsx_handle) {
452 IWL_DEBUG_INFO(trans, 452 IWL_DEBUG_INFO(trans,
453 "Could not retrieve root port ACPI handle"); 453 "Could not retrieve root port ACPI handle\n");
454 return; 454 return;
455 } 455 }
456 456
457 /* Get the method's handle */ 457 /* Get the method's handle */
458 status = acpi_get_handle(pxsx_handle, (acpi_string)SPL_METHOD, &handle); 458 status = acpi_get_handle(pxsx_handle, (acpi_string)SPL_METHOD, &handle);
459 if (ACPI_FAILURE(status)) { 459 if (ACPI_FAILURE(status)) {
460 IWL_DEBUG_INFO(trans, "SPL method not found"); 460 IWL_DEBUG_INFO(trans, "SPL method not found\n");
461 return; 461 return;
462 } 462 }
463 463
464 /* Call SPLC with no arguments */ 464 /* Call SPLC with no arguments */
465 status = acpi_evaluate_object(handle, NULL, NULL, &splx); 465 status = acpi_evaluate_object(handle, NULL, NULL, &splx);
466 if (ACPI_FAILURE(status)) { 466 if (ACPI_FAILURE(status)) {
467 IWL_ERR(trans, "SPLC invocation failed (0x%x)", status); 467 IWL_ERR(trans, "SPLC invocation failed (0x%x)\n", status);
468 return; 468 return;
469 } 469 }
470 470
471 trans->dflt_pwr_limit = splx_get_pwr_limit(trans, splx.pointer); 471 trans->dflt_pwr_limit = splx_get_pwr_limit(trans, splx.pointer);
472 IWL_DEBUG_INFO(trans, "Default power limit set to %lld", 472 IWL_DEBUG_INFO(trans, "Default power limit set to %lld\n",
473 trans->dflt_pwr_limit); 473 trans->dflt_pwr_limit);
474 kfree(splx.pointer); 474 kfree(splx.pointer);
475} 475}
diff --git a/drivers/net/wireless/iwlwifi/pcie/internal.h b/drivers/net/wireless/iwlwifi/pcie/internal.h
index 1b95d856dfd5..6c22b23a2845 100644
--- a/drivers/net/wireless/iwlwifi/pcie/internal.h
+++ b/drivers/net/wireless/iwlwifi/pcie/internal.h
@@ -117,21 +117,19 @@ struct iwl_dma_ptr {
117/** 117/**
118 * iwl_queue_inc_wrap - increment queue index, wrap back to beginning 118 * iwl_queue_inc_wrap - increment queue index, wrap back to beginning
119 * @index -- current index 119 * @index -- current index
120 * @n_bd -- total number of entries in queue (must be power of 2)
121 */ 120 */
122static inline int iwl_queue_inc_wrap(int index, int n_bd) 121static inline int iwl_queue_inc_wrap(int index)
123{ 122{
124 return ++index & (n_bd - 1); 123 return ++index & (TFD_QUEUE_SIZE_MAX - 1);
125} 124}
126 125
127/** 126/**
128 * iwl_queue_dec_wrap - decrement queue index, wrap back to end 127 * iwl_queue_dec_wrap - decrement queue index, wrap back to end
129 * @index -- current index 128 * @index -- current index
130 * @n_bd -- total number of entries in queue (must be power of 2)
131 */ 129 */
132static inline int iwl_queue_dec_wrap(int index, int n_bd) 130static inline int iwl_queue_dec_wrap(int index)
133{ 131{
134 return --index & (n_bd - 1); 132 return --index & (TFD_QUEUE_SIZE_MAX - 1);
135} 133}
136 134
137struct iwl_cmd_meta { 135struct iwl_cmd_meta {
@@ -145,13 +143,13 @@ struct iwl_cmd_meta {
145 * 143 *
146 * Contains common data for Rx and Tx queues. 144 * Contains common data for Rx and Tx queues.
147 * 145 *
148 * Note the difference between n_bd and n_window: the hardware 146 * Note the difference between TFD_QUEUE_SIZE_MAX and n_window: the hardware
149 * always assumes 256 descriptors, so n_bd is always 256 (unless 147 * always assumes 256 descriptors, so TFD_QUEUE_SIZE_MAX is always 256 (unless
150 * there might be HW changes in the future). For the normal TX 148 * there might be HW changes in the future). For the normal TX
151 * queues, n_window, which is the size of the software queue data 149 * queues, n_window, which is the size of the software queue data
152 * is also 256; however, for the command queue, n_window is only 150 * is also 256; however, for the command queue, n_window is only
153 * 32 since we don't need so many commands pending. Since the HW 151 * 32 since we don't need so many commands pending. Since the HW
154 * still uses 256 BDs for DMA though, n_bd stays 256. As a result, 152 * still uses 256 BDs for DMA though, TFD_QUEUE_SIZE_MAX stays 256. As a result,
155 * the software buffers (in the variables @meta, @txb in struct 153 * the software buffers (in the variables @meta, @txb in struct
156 * iwl_txq) only have 32 entries, while the HW buffers (@tfds in 154 * iwl_txq) only have 32 entries, while the HW buffers (@tfds in
157 * the same struct) have 256. 155 * the same struct) have 256.
@@ -162,7 +160,6 @@ struct iwl_cmd_meta {
162 * data is a window overlayed over the HW queue. 160 * data is a window overlayed over the HW queue.
163 */ 161 */
164struct iwl_queue { 162struct iwl_queue {
165 int n_bd; /* number of BDs in this queue */
166 int write_ptr; /* 1-st empty entry (index) host_w*/ 163 int write_ptr; /* 1-st empty entry (index) host_w*/
167 int read_ptr; /* last used entry (index) host_r*/ 164 int read_ptr; /* last used entry (index) host_r*/
168 /* use for monitoring and recovering the stuck queue */ 165 /* use for monitoring and recovering the stuck queue */
@@ -373,6 +370,13 @@ void iwl_trans_pcie_reclaim(struct iwl_trans *trans, int txq_id, int ssn,
373 struct sk_buff_head *skbs); 370 struct sk_buff_head *skbs);
374void iwl_trans_pcie_tx_reset(struct iwl_trans *trans); 371void iwl_trans_pcie_tx_reset(struct iwl_trans *trans);
375 372
373static inline u16 iwl_pcie_tfd_tb_get_len(struct iwl_tfd *tfd, u8 idx)
374{
375 struct iwl_tfd_tb *tb = &tfd->tbs[idx];
376
377 return le16_to_cpu(tb->hi_n_len) >> 4;
378}
379
376/***************************************************** 380/*****************************************************
377* Error handling 381* Error handling
378******************************************************/ 382******************************************************/
diff --git a/drivers/net/wireless/iwlwifi/pcie/rx.c b/drivers/net/wireless/iwlwifi/pcie/rx.c
index 4a26a082a1ba..a2698e5e062c 100644
--- a/drivers/net/wireless/iwlwifi/pcie/rx.c
+++ b/drivers/net/wireless/iwlwifi/pcie/rx.c
@@ -850,7 +850,7 @@ static u32 iwl_pcie_int_cause_ict(struct iwl_trans *trans)
850 trans_pcie->ict_index, read); 850 trans_pcie->ict_index, read);
851 trans_pcie->ict_tbl[trans_pcie->ict_index] = 0; 851 trans_pcie->ict_tbl[trans_pcie->ict_index] = 0;
852 trans_pcie->ict_index = 852 trans_pcie->ict_index =
853 iwl_queue_inc_wrap(trans_pcie->ict_index, ICT_COUNT); 853 ((trans_pcie->ict_index + 1) & (ICT_COUNT - 1));
854 854
855 read = le32_to_cpu(trans_pcie->ict_tbl[trans_pcie->ict_index]); 855 read = le32_to_cpu(trans_pcie->ict_tbl[trans_pcie->ict_index]);
856 trace_iwlwifi_dev_ict_read(trans->dev, trans_pcie->ict_index, 856 trace_iwlwifi_dev_ict_read(trans->dev, trans_pcie->ict_index,
diff --git a/drivers/net/wireless/iwlwifi/pcie/trans.c b/drivers/net/wireless/iwlwifi/pcie/trans.c
index c76b148e1aba..788085bc65d7 100644
--- a/drivers/net/wireless/iwlwifi/pcie/trans.c
+++ b/drivers/net/wireless/iwlwifi/pcie/trans.c
@@ -73,6 +73,7 @@
73#include "iwl-csr.h" 73#include "iwl-csr.h"
74#include "iwl-prph.h" 74#include "iwl-prph.h"
75#include "iwl-agn-hw.h" 75#include "iwl-agn-hw.h"
76#include "iwl-fw-error-dump.h"
76#include "internal.h" 77#include "internal.h"
77 78
78static u32 iwl_trans_pcie_read_shr(struct iwl_trans *trans, u32 reg) 79static u32 iwl_trans_pcie_read_shr(struct iwl_trans *trans, u32 reg)
@@ -453,6 +454,7 @@ static int iwl_pcie_prepare_card_hw(struct iwl_trans *trans)
453{ 454{
454 int ret; 455 int ret;
455 int t = 0; 456 int t = 0;
457 int iter;
456 458
457 IWL_DEBUG_INFO(trans, "iwl_trans_prepare_card_hw enter\n"); 459 IWL_DEBUG_INFO(trans, "iwl_trans_prepare_card_hw enter\n");
458 460
@@ -461,18 +463,23 @@ static int iwl_pcie_prepare_card_hw(struct iwl_trans *trans)
461 if (ret >= 0) 463 if (ret >= 0)
462 return 0; 464 return 0;
463 465
464 /* If HW is not ready, prepare the conditions to check again */ 466 for (iter = 0; iter < 10; iter++) {
465 iwl_set_bit(trans, CSR_HW_IF_CONFIG_REG, 467 /* If HW is not ready, prepare the conditions to check again */
466 CSR_HW_IF_CONFIG_REG_PREPARE); 468 iwl_set_bit(trans, CSR_HW_IF_CONFIG_REG,
469 CSR_HW_IF_CONFIG_REG_PREPARE);
470
471 do {
472 ret = iwl_pcie_set_hw_ready(trans);
473 if (ret >= 0)
474 return 0;
467 475
468 do { 476 usleep_range(200, 1000);
469 ret = iwl_pcie_set_hw_ready(trans); 477 t += 200;
470 if (ret >= 0) 478 } while (t < 150000);
471 return 0; 479 msleep(25);
480 }
472 481
473 usleep_range(200, 1000); 482 IWL_DEBUG_INFO(trans, "got NIC after %d iterations\n", iter);
474 t += 200;
475 } while (t < 150000);
476 483
477 return ret; 484 return ret;
478} 485}
@@ -1337,8 +1344,8 @@ static int iwl_trans_pcie_wait_txq_empty(struct iwl_trans *trans, u32 txq_bm)
1337 IWL_ERR(trans, 1344 IWL_ERR(trans,
1338 "Q %d is %sactive and mapped to fifo %d ra_tid 0x%04x [%d,%d]\n", 1345 "Q %d is %sactive and mapped to fifo %d ra_tid 0x%04x [%d,%d]\n",
1339 cnt, active ? "" : "in", fifo, tbl_dw, 1346 cnt, active ? "" : "in", fifo, tbl_dw,
1340 iwl_read_prph(trans, 1347 iwl_read_prph(trans, SCD_QUEUE_RDPTR(cnt)) &
1341 SCD_QUEUE_RDPTR(cnt)) & (txq->q.n_bd - 1), 1348 (TFD_QUEUE_SIZE_MAX - 1),
1342 iwl_read_prph(trans, SCD_QUEUE_WRPTR(cnt))); 1349 iwl_read_prph(trans, SCD_QUEUE_WRPTR(cnt)));
1343 } 1350 }
1344 1351
@@ -1669,6 +1676,61 @@ err:
1669 IWL_ERR(trans, "failed to create the trans debugfs entry\n"); 1676 IWL_ERR(trans, "failed to create the trans debugfs entry\n");
1670 return -ENOMEM; 1677 return -ENOMEM;
1671} 1678}
1679
1680static u32 iwl_trans_pcie_get_cmdlen(struct iwl_tfd *tfd)
1681{
1682 u32 cmdlen = 0;
1683 int i;
1684
1685 for (i = 0; i < IWL_NUM_OF_TBS; i++)
1686 cmdlen += iwl_pcie_tfd_tb_get_len(tfd, i);
1687
1688 return cmdlen;
1689}
1690
1691static u32 iwl_trans_pcie_dump_data(struct iwl_trans *trans,
1692 void *buf, u32 buflen)
1693{
1694 struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans);
1695 struct iwl_fw_error_dump_data *data;
1696 struct iwl_txq *cmdq = &trans_pcie->txq[trans_pcie->cmd_queue];
1697 struct iwl_fw_error_dump_txcmd *txcmd;
1698 u32 len;
1699 int i, ptr;
1700
1701 if (!buf)
1702 return sizeof(*data) +
1703 cmdq->q.n_window * (sizeof(*txcmd) +
1704 TFD_MAX_PAYLOAD_SIZE);
1705
1706 len = 0;
1707 data = buf;
1708 data->type = cpu_to_le32(IWL_FW_ERROR_DUMP_TXCMD);
1709 txcmd = (void *)data->data;
1710 spin_lock_bh(&cmdq->lock);
1711 ptr = cmdq->q.write_ptr;
1712 for (i = 0; i < cmdq->q.n_window; i++) {
1713 u8 idx = get_cmd_index(&cmdq->q, ptr);
1714 u32 caplen, cmdlen;
1715
1716 cmdlen = iwl_trans_pcie_get_cmdlen(&cmdq->tfds[ptr]);
1717 caplen = min_t(u32, TFD_MAX_PAYLOAD_SIZE, cmdlen);
1718
1719 if (cmdlen) {
1720 len += sizeof(*txcmd) + caplen;
1721 txcmd->cmdlen = cpu_to_le32(cmdlen);
1722 txcmd->caplen = cpu_to_le32(caplen);
1723 memcpy(txcmd->data, cmdq->entries[idx].cmd, caplen);
1724 txcmd = (void *)((u8 *)txcmd->data + caplen);
1725 }
1726
1727 ptr = iwl_queue_dec_wrap(ptr);
1728 }
1729 spin_unlock_bh(&cmdq->lock);
1730
1731 data->len = cpu_to_le32(len);
1732 return sizeof(*data) + len;
1733}
1672#else 1734#else
1673static int iwl_trans_pcie_dbgfs_register(struct iwl_trans *trans, 1735static int iwl_trans_pcie_dbgfs_register(struct iwl_trans *trans,
1674 struct dentry *dir) 1736 struct dentry *dir)
@@ -1711,6 +1773,10 @@ static const struct iwl_trans_ops trans_ops_pcie = {
1711 .grab_nic_access = iwl_trans_pcie_grab_nic_access, 1773 .grab_nic_access = iwl_trans_pcie_grab_nic_access,
1712 .release_nic_access = iwl_trans_pcie_release_nic_access, 1774 .release_nic_access = iwl_trans_pcie_release_nic_access,
1713 .set_bits_mask = iwl_trans_pcie_set_bits_mask, 1775 .set_bits_mask = iwl_trans_pcie_set_bits_mask,
1776
1777#ifdef CONFIG_IWLWIFI_DEBUGFS
1778 .dump_data = iwl_trans_pcie_dump_data,
1779#endif
1714}; 1780};
1715 1781
1716struct iwl_trans *iwl_trans_pcie_alloc(struct pci_dev *pdev, 1782struct iwl_trans *iwl_trans_pcie_alloc(struct pci_dev *pdev,
diff --git a/drivers/net/wireless/iwlwifi/pcie/tx.c b/drivers/net/wireless/iwlwifi/pcie/tx.c
index dde6031f4257..038940afbdc5 100644
--- a/drivers/net/wireless/iwlwifi/pcie/tx.c
+++ b/drivers/net/wireless/iwlwifi/pcie/tx.c
@@ -70,20 +70,20 @@ static int iwl_queue_space(const struct iwl_queue *q)
70 70
71 /* 71 /*
72 * To avoid ambiguity between empty and completely full queues, there 72 * To avoid ambiguity between empty and completely full queues, there
73 * should always be less than q->n_bd elements in the queue. 73 * should always be less than TFD_QUEUE_SIZE_MAX elements in the queue.
74 * If q->n_window is smaller than q->n_bd, there is no need to reserve 74 * If q->n_window is smaller than TFD_QUEUE_SIZE_MAX, there is no need
75 * any queue entries for this purpose. 75 * to reserve any queue entries for this purpose.
76 */ 76 */
77 if (q->n_window < q->n_bd) 77 if (q->n_window < TFD_QUEUE_SIZE_MAX)
78 max = q->n_window; 78 max = q->n_window;
79 else 79 else
80 max = q->n_bd - 1; 80 max = TFD_QUEUE_SIZE_MAX - 1;
81 81
82 /* 82 /*
83 * q->n_bd is a power of 2, so the following is equivalent to modulo by 83 * TFD_QUEUE_SIZE_MAX is a power of 2, so the following is equivalent to
84 * q->n_bd and is well defined for negative dividends. 84 * modulo by TFD_QUEUE_SIZE_MAX and is well defined.
85 */ 85 */
86 used = (q->write_ptr - q->read_ptr) & (q->n_bd - 1); 86 used = (q->write_ptr - q->read_ptr) & (TFD_QUEUE_SIZE_MAX - 1);
87 87
88 if (WARN_ON(used > max)) 88 if (WARN_ON(used > max))
89 return 0; 89 return 0;
@@ -94,17 +94,11 @@ static int iwl_queue_space(const struct iwl_queue *q)
94/* 94/*
95 * iwl_queue_init - Initialize queue's high/low-water and read/write indexes 95 * iwl_queue_init - Initialize queue's high/low-water and read/write indexes
96 */ 96 */
97static int iwl_queue_init(struct iwl_queue *q, int count, int slots_num, u32 id) 97static int iwl_queue_init(struct iwl_queue *q, int slots_num, u32 id)
98{ 98{
99 q->n_bd = count;
100 q->n_window = slots_num; 99 q->n_window = slots_num;
101 q->id = id; 100 q->id = id;
102 101
103 /* count must be power-of-two size, otherwise iwl_queue_inc_wrap
104 * and iwl_queue_dec_wrap are broken. */
105 if (WARN_ON(!is_power_of_2(count)))
106 return -EINVAL;
107
108 /* slots_num must be power-of-two size, otherwise 102 /* slots_num must be power-of-two size, otherwise
109 * get_cmd_index is broken. */ 103 * get_cmd_index is broken. */
110 if (WARN_ON(!is_power_of_2(slots_num))) 104 if (WARN_ON(!is_power_of_2(slots_num)))
@@ -197,17 +191,17 @@ static void iwl_pcie_txq_stuck_timer(unsigned long data)
197 IWL_ERR(trans, 191 IWL_ERR(trans,
198 "Q %d is %sactive and mapped to fifo %d ra_tid 0x%04x [%d,%d]\n", 192 "Q %d is %sactive and mapped to fifo %d ra_tid 0x%04x [%d,%d]\n",
199 i, active ? "" : "in", fifo, tbl_dw, 193 i, active ? "" : "in", fifo, tbl_dw,
200 iwl_read_prph(trans, 194 iwl_read_prph(trans, SCD_QUEUE_RDPTR(i)) &
201 SCD_QUEUE_RDPTR(i)) & (txq->q.n_bd - 1), 195 (TFD_QUEUE_SIZE_MAX - 1),
202 iwl_read_prph(trans, SCD_QUEUE_WRPTR(i))); 196 iwl_read_prph(trans, SCD_QUEUE_WRPTR(i)));
203 } 197 }
204 198
205 for (i = q->read_ptr; i != q->write_ptr; 199 for (i = q->read_ptr; i != q->write_ptr;
206 i = iwl_queue_inc_wrap(i, q->n_bd)) 200 i = iwl_queue_inc_wrap(i))
207 IWL_ERR(trans, "scratch %d = 0x%08x\n", i, 201 IWL_ERR(trans, "scratch %d = 0x%08x\n", i,
208 le32_to_cpu(txq->scratchbufs[i].scratch)); 202 le32_to_cpu(txq->scratchbufs[i].scratch));
209 203
210 iwl_write_prph(trans, DEVICE_SET_NMI_REG, 1); 204 iwl_force_nmi(trans);
211} 205}
212 206
213/* 207/*
@@ -338,12 +332,12 @@ void iwl_pcie_txq_check_wrptrs(struct iwl_trans *trans)
338 for (i = 0; i < trans->cfg->base_params->num_of_queues; i++) { 332 for (i = 0; i < trans->cfg->base_params->num_of_queues; i++) {
339 struct iwl_txq *txq = &trans_pcie->txq[i]; 333 struct iwl_txq *txq = &trans_pcie->txq[i];
340 334
341 spin_lock(&txq->lock); 335 spin_lock_bh(&txq->lock);
342 if (trans_pcie->txq[i].need_update) { 336 if (trans_pcie->txq[i].need_update) {
343 iwl_pcie_txq_inc_wr_ptr(trans, txq); 337 iwl_pcie_txq_inc_wr_ptr(trans, txq);
344 trans_pcie->txq[i].need_update = false; 338 trans_pcie->txq[i].need_update = false;
345 } 339 }
346 spin_unlock(&txq->lock); 340 spin_unlock_bh(&txq->lock);
347 } 341 }
348} 342}
349 343
@@ -359,13 +353,6 @@ static inline dma_addr_t iwl_pcie_tfd_tb_get_addr(struct iwl_tfd *tfd, u8 idx)
359 return addr; 353 return addr;
360} 354}
361 355
362static inline u16 iwl_pcie_tfd_tb_get_len(struct iwl_tfd *tfd, u8 idx)
363{
364 struct iwl_tfd_tb *tb = &tfd->tbs[idx];
365
366 return le16_to_cpu(tb->hi_n_len) >> 4;
367}
368
369static inline void iwl_pcie_tfd_set_tb(struct iwl_tfd *tfd, u8 idx, 356static inline void iwl_pcie_tfd_set_tb(struct iwl_tfd *tfd, u8 idx,
370 dma_addr_t addr, u16 len) 357 dma_addr_t addr, u16 len)
371{ 358{
@@ -425,13 +412,17 @@ static void iwl_pcie_txq_free_tfd(struct iwl_trans *trans, struct iwl_txq *txq)
425{ 412{
426 struct iwl_tfd *tfd_tmp = txq->tfds; 413 struct iwl_tfd *tfd_tmp = txq->tfds;
427 414
428 /* rd_ptr is bounded by n_bd and idx is bounded by n_window */ 415 /* rd_ptr is bounded by TFD_QUEUE_SIZE_MAX and
416 * idx is bounded by n_window
417 */
429 int rd_ptr = txq->q.read_ptr; 418 int rd_ptr = txq->q.read_ptr;
430 int idx = get_cmd_index(&txq->q, rd_ptr); 419 int idx = get_cmd_index(&txq->q, rd_ptr);
431 420
432 lockdep_assert_held(&txq->lock); 421 lockdep_assert_held(&txq->lock);
433 422
434 /* We have only q->n_window txq->entries, but we use q->n_bd tfds */ 423 /* We have only q->n_window txq->entries, but we use
424 * TFD_QUEUE_SIZE_MAX tfds
425 */
435 iwl_pcie_tfd_unmap(trans, &txq->entries[idx].meta, &tfd_tmp[rd_ptr]); 426 iwl_pcie_tfd_unmap(trans, &txq->entries[idx].meta, &tfd_tmp[rd_ptr]);
436 427
437 /* free SKB */ 428 /* free SKB */
@@ -452,7 +443,7 @@ static void iwl_pcie_txq_free_tfd(struct iwl_trans *trans, struct iwl_txq *txq)
452} 443}
453 444
454static int iwl_pcie_txq_build_tfd(struct iwl_trans *trans, struct iwl_txq *txq, 445static int iwl_pcie_txq_build_tfd(struct iwl_trans *trans, struct iwl_txq *txq,
455 dma_addr_t addr, u16 len, u8 reset) 446 dma_addr_t addr, u16 len, bool reset)
456{ 447{
457 struct iwl_queue *q; 448 struct iwl_queue *q;
458 struct iwl_tfd *tfd, *tfd_tmp; 449 struct iwl_tfd *tfd, *tfd_tmp;
@@ -565,8 +556,7 @@ static int iwl_pcie_txq_init(struct iwl_trans *trans, struct iwl_txq *txq,
565 BUILD_BUG_ON(TFD_QUEUE_SIZE_MAX & (TFD_QUEUE_SIZE_MAX - 1)); 556 BUILD_BUG_ON(TFD_QUEUE_SIZE_MAX & (TFD_QUEUE_SIZE_MAX - 1));
566 557
567 /* Initialize queue's high/low-water marks, and head/tail indexes */ 558 /* Initialize queue's high/low-water marks, and head/tail indexes */
568 ret = iwl_queue_init(&txq->q, TFD_QUEUE_SIZE_MAX, slots_num, 559 ret = iwl_queue_init(&txq->q, slots_num, txq_id);
569 txq_id);
570 if (ret) 560 if (ret)
571 return ret; 561 return ret;
572 562
@@ -591,15 +581,12 @@ static void iwl_pcie_txq_unmap(struct iwl_trans *trans, int txq_id)
591 struct iwl_txq *txq = &trans_pcie->txq[txq_id]; 581 struct iwl_txq *txq = &trans_pcie->txq[txq_id];
592 struct iwl_queue *q = &txq->q; 582 struct iwl_queue *q = &txq->q;
593 583
594 if (!q->n_bd)
595 return;
596
597 spin_lock_bh(&txq->lock); 584 spin_lock_bh(&txq->lock);
598 while (q->write_ptr != q->read_ptr) { 585 while (q->write_ptr != q->read_ptr) {
599 IWL_DEBUG_TX_REPLY(trans, "Q %d Free %d\n", 586 IWL_DEBUG_TX_REPLY(trans, "Q %d Free %d\n",
600 txq_id, q->read_ptr); 587 txq_id, q->read_ptr);
601 iwl_pcie_txq_free_tfd(trans, txq); 588 iwl_pcie_txq_free_tfd(trans, txq);
602 q->read_ptr = iwl_queue_inc_wrap(q->read_ptr, q->n_bd); 589 q->read_ptr = iwl_queue_inc_wrap(q->read_ptr);
603 } 590 }
604 txq->active = false; 591 txq->active = false;
605 spin_unlock_bh(&txq->lock); 592 spin_unlock_bh(&txq->lock);
@@ -636,10 +623,12 @@ static void iwl_pcie_txq_free(struct iwl_trans *trans, int txq_id)
636 } 623 }
637 624
638 /* De-alloc circular buffer of TFDs */ 625 /* De-alloc circular buffer of TFDs */
639 if (txq->q.n_bd) { 626 if (txq->tfds) {
640 dma_free_coherent(dev, sizeof(struct iwl_tfd) * 627 dma_free_coherent(dev,
641 txq->q.n_bd, txq->tfds, txq->q.dma_addr); 628 sizeof(struct iwl_tfd) * TFD_QUEUE_SIZE_MAX,
629 txq->tfds, txq->q.dma_addr);
642 txq->q.dma_addr = 0; 630 txq->q.dma_addr = 0;
631 txq->tfds = NULL;
643 632
644 dma_free_coherent(dev, 633 dma_free_coherent(dev,
645 sizeof(*txq->scratchbufs) * txq->q.n_window, 634 sizeof(*txq->scratchbufs) * txq->q.n_window,
@@ -948,8 +937,7 @@ void iwl_trans_pcie_reclaim(struct iwl_trans *trans, int txq_id, int ssn,
948{ 937{
949 struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans); 938 struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans);
950 struct iwl_txq *txq = &trans_pcie->txq[txq_id]; 939 struct iwl_txq *txq = &trans_pcie->txq[txq_id];
951 /* n_bd is usually 256 => n_bd - 1 = 0xff */ 940 int tfd_num = ssn & (TFD_QUEUE_SIZE_MAX - 1);
952 int tfd_num = ssn & (txq->q.n_bd - 1);
953 struct iwl_queue *q = &txq->q; 941 struct iwl_queue *q = &txq->q;
954 int last_to_free; 942 int last_to_free;
955 943
@@ -973,12 +961,12 @@ void iwl_trans_pcie_reclaim(struct iwl_trans *trans, int txq_id, int ssn,
973 961
974 /*Since we free until index _not_ inclusive, the one before index is 962 /*Since we free until index _not_ inclusive, the one before index is
975 * the last we will free. This one must be used */ 963 * the last we will free. This one must be used */
976 last_to_free = iwl_queue_dec_wrap(tfd_num, q->n_bd); 964 last_to_free = iwl_queue_dec_wrap(tfd_num);
977 965
978 if (!iwl_queue_used(q, last_to_free)) { 966 if (!iwl_queue_used(q, last_to_free)) {
979 IWL_ERR(trans, 967 IWL_ERR(trans,
980 "%s: Read index for DMA queue txq id (%d), last_to_free %d is out of range [0-%d] %d %d.\n", 968 "%s: Read index for DMA queue txq id (%d), last_to_free %d is out of range [0-%d] %d %d.\n",
981 __func__, txq_id, last_to_free, q->n_bd, 969 __func__, txq_id, last_to_free, TFD_QUEUE_SIZE_MAX,
982 q->write_ptr, q->read_ptr); 970 q->write_ptr, q->read_ptr);
983 goto out; 971 goto out;
984 } 972 }
@@ -988,7 +976,7 @@ void iwl_trans_pcie_reclaim(struct iwl_trans *trans, int txq_id, int ssn,
988 976
989 for (; 977 for (;
990 q->read_ptr != tfd_num; 978 q->read_ptr != tfd_num;
991 q->read_ptr = iwl_queue_inc_wrap(q->read_ptr, q->n_bd)) { 979 q->read_ptr = iwl_queue_inc_wrap(q->read_ptr)) {
992 980
993 if (WARN_ON_ONCE(txq->entries[txq->q.read_ptr].skb == NULL)) 981 if (WARN_ON_ONCE(txq->entries[txq->q.read_ptr].skb == NULL))
994 continue; 982 continue;
@@ -1027,21 +1015,21 @@ static void iwl_pcie_cmdq_reclaim(struct iwl_trans *trans, int txq_id, int idx)
1027 1015
1028 lockdep_assert_held(&txq->lock); 1016 lockdep_assert_held(&txq->lock);
1029 1017
1030 if ((idx >= q->n_bd) || (!iwl_queue_used(q, idx))) { 1018 if ((idx >= TFD_QUEUE_SIZE_MAX) || (!iwl_queue_used(q, idx))) {
1031 IWL_ERR(trans, 1019 IWL_ERR(trans,
1032 "%s: Read index for DMA queue txq id (%d), index %d is out of range [0-%d] %d %d.\n", 1020 "%s: Read index for DMA queue txq id (%d), index %d is out of range [0-%d] %d %d.\n",
1033 __func__, txq_id, idx, q->n_bd, 1021 __func__, txq_id, idx, TFD_QUEUE_SIZE_MAX,
1034 q->write_ptr, q->read_ptr); 1022 q->write_ptr, q->read_ptr);
1035 return; 1023 return;
1036 } 1024 }
1037 1025
1038 for (idx = iwl_queue_inc_wrap(idx, q->n_bd); q->read_ptr != idx; 1026 for (idx = iwl_queue_inc_wrap(idx); q->read_ptr != idx;
1039 q->read_ptr = iwl_queue_inc_wrap(q->read_ptr, q->n_bd)) { 1027 q->read_ptr = iwl_queue_inc_wrap(q->read_ptr)) {
1040 1028
1041 if (nfreed++ > 0) { 1029 if (nfreed++ > 0) {
1042 IWL_ERR(trans, "HCMD skipped: index (%d) %d %d\n", 1030 IWL_ERR(trans, "HCMD skipped: index (%d) %d %d\n",
1043 idx, q->write_ptr, q->read_ptr); 1031 idx, q->write_ptr, q->read_ptr);
1044 iwl_write_prph(trans, DEVICE_SET_NMI_REG, 1); 1032 iwl_force_nmi(trans);
1045 } 1033 }
1046 } 1034 }
1047 1035
@@ -1327,28 +1315,39 @@ static int iwl_pcie_enqueue_hcmd(struct iwl_trans *trans,
1327 cmd_pos = offsetof(struct iwl_device_cmd, payload); 1315 cmd_pos = offsetof(struct iwl_device_cmd, payload);
1328 copy_size = sizeof(out_cmd->hdr); 1316 copy_size = sizeof(out_cmd->hdr);
1329 for (i = 0; i < IWL_MAX_CMD_TBS_PER_TFD; i++) { 1317 for (i = 0; i < IWL_MAX_CMD_TBS_PER_TFD; i++) {
1330 int copy = 0; 1318 int copy;
1331 1319
1332 if (!cmd->len[i]) 1320 if (!cmd->len[i])
1333 continue; 1321 continue;
1334 1322
1335 /* need at least IWL_HCMD_SCRATCHBUF_SIZE copied */
1336 if (copy_size < IWL_HCMD_SCRATCHBUF_SIZE) {
1337 copy = IWL_HCMD_SCRATCHBUF_SIZE - copy_size;
1338
1339 if (copy > cmd->len[i])
1340 copy = cmd->len[i];
1341 }
1342
1343 /* copy everything if not nocopy/dup */ 1323 /* copy everything if not nocopy/dup */
1344 if (!(cmd->dataflags[i] & (IWL_HCMD_DFL_NOCOPY | 1324 if (!(cmd->dataflags[i] & (IWL_HCMD_DFL_NOCOPY |
1345 IWL_HCMD_DFL_DUP))) 1325 IWL_HCMD_DFL_DUP))) {
1346 copy = cmd->len[i]; 1326 copy = cmd->len[i];
1347 1327
1348 if (copy) {
1349 memcpy((u8 *)out_cmd + cmd_pos, cmd->data[i], copy); 1328 memcpy((u8 *)out_cmd + cmd_pos, cmd->data[i], copy);
1350 cmd_pos += copy; 1329 cmd_pos += copy;
1351 copy_size += copy; 1330 copy_size += copy;
1331 continue;
1332 }
1333
1334 /*
1335 * Otherwise we need at least IWL_HCMD_SCRATCHBUF_SIZE copied
1336 * in total (for the scratchbuf handling), but copy up to what
1337 * we can fit into the payload for debug dump purposes.
1338 */
1339 copy = min_t(int, TFD_MAX_PAYLOAD_SIZE - cmd_pos, cmd->len[i]);
1340
1341 memcpy((u8 *)out_cmd + cmd_pos, cmd->data[i], copy);
1342 cmd_pos += copy;
1343
1344 /* However, treat copy_size the proper way, we need it below */
1345 if (copy_size < IWL_HCMD_SCRATCHBUF_SIZE) {
1346 copy = IWL_HCMD_SCRATCHBUF_SIZE - copy_size;
1347
1348 if (copy > cmd->len[i])
1349 copy = cmd->len[i];
1350 copy_size += copy;
1352 } 1351 }
1353 } 1352 }
1354 1353
@@ -1363,7 +1362,7 @@ static int iwl_pcie_enqueue_hcmd(struct iwl_trans *trans,
1363 memcpy(&txq->scratchbufs[q->write_ptr], &out_cmd->hdr, scratch_size); 1362 memcpy(&txq->scratchbufs[q->write_ptr], &out_cmd->hdr, scratch_size);
1364 iwl_pcie_txq_build_tfd(trans, txq, 1363 iwl_pcie_txq_build_tfd(trans, txq,
1365 iwl_pcie_get_scratchbuf_dma(txq, q->write_ptr), 1364 iwl_pcie_get_scratchbuf_dma(txq, q->write_ptr),
1366 scratch_size, 1); 1365 scratch_size, true);
1367 1366
1368 /* map first command fragment, if any remains */ 1367 /* map first command fragment, if any remains */
1369 if (copy_size > scratch_size) { 1368 if (copy_size > scratch_size) {
@@ -1379,7 +1378,7 @@ static int iwl_pcie_enqueue_hcmd(struct iwl_trans *trans,
1379 } 1378 }
1380 1379
1381 iwl_pcie_txq_build_tfd(trans, txq, phys_addr, 1380 iwl_pcie_txq_build_tfd(trans, txq, phys_addr,
1382 copy_size - scratch_size, 0); 1381 copy_size - scratch_size, false);
1383 } 1382 }
1384 1383
1385 /* map the remaining (adjusted) nocopy/dup fragments */ 1384 /* map the remaining (adjusted) nocopy/dup fragments */
@@ -1402,7 +1401,7 @@ static int iwl_pcie_enqueue_hcmd(struct iwl_trans *trans,
1402 goto out; 1401 goto out;
1403 } 1402 }
1404 1403
1405 iwl_pcie_txq_build_tfd(trans, txq, phys_addr, cmdlen[i], 0); 1404 iwl_pcie_txq_build_tfd(trans, txq, phys_addr, cmdlen[i], false);
1406 } 1405 }
1407 1406
1408 out_meta->flags = cmd->flags; 1407 out_meta->flags = cmd->flags;
@@ -1445,7 +1444,7 @@ static int iwl_pcie_enqueue_hcmd(struct iwl_trans *trans,
1445 } 1444 }
1446 1445
1447 /* Increment and update queue's write index */ 1446 /* Increment and update queue's write index */
1448 q->write_ptr = iwl_queue_inc_wrap(q->write_ptr, q->n_bd); 1447 q->write_ptr = iwl_queue_inc_wrap(q->write_ptr);
1449 iwl_pcie_txq_inc_wr_ptr(trans, txq); 1448 iwl_pcie_txq_inc_wr_ptr(trans, txq);
1450 1449
1451 spin_unlock_irqrestore(&trans_pcie->reg_lock, flags); 1450 spin_unlock_irqrestore(&trans_pcie->reg_lock, flags);
@@ -1601,7 +1600,7 @@ static int iwl_pcie_send_hcmd_sync(struct iwl_trans *trans,
1601 get_cmd_string(trans_pcie, cmd->id)); 1600 get_cmd_string(trans_pcie, cmd->id));
1602 ret = -ETIMEDOUT; 1601 ret = -ETIMEDOUT;
1603 1602
1604 iwl_write_prph(trans, DEVICE_SET_NMI_REG, 1); 1603 iwl_force_nmi(trans);
1605 iwl_trans_fw_error(trans); 1604 iwl_trans_fw_error(trans);
1606 1605
1607 goto cancel; 1606 goto cancel;
@@ -1740,7 +1739,7 @@ int iwl_trans_pcie_tx(struct iwl_trans *trans, struct sk_buff *skb,
1740 memcpy(&txq->scratchbufs[q->write_ptr], &dev_cmd->hdr, 1739 memcpy(&txq->scratchbufs[q->write_ptr], &dev_cmd->hdr,
1741 IWL_HCMD_SCRATCHBUF_SIZE); 1740 IWL_HCMD_SCRATCHBUF_SIZE);
1742 iwl_pcie_txq_build_tfd(trans, txq, tb0_phys, 1741 iwl_pcie_txq_build_tfd(trans, txq, tb0_phys,
1743 IWL_HCMD_SCRATCHBUF_SIZE, 1); 1742 IWL_HCMD_SCRATCHBUF_SIZE, true);
1744 1743
1745 /* there must be data left over for TB1 or this code must be changed */ 1744 /* there must be data left over for TB1 or this code must be changed */
1746 BUILD_BUG_ON(sizeof(struct iwl_tx_cmd) < IWL_HCMD_SCRATCHBUF_SIZE); 1745 BUILD_BUG_ON(sizeof(struct iwl_tx_cmd) < IWL_HCMD_SCRATCHBUF_SIZE);
@@ -1750,7 +1749,7 @@ int iwl_trans_pcie_tx(struct iwl_trans *trans, struct sk_buff *skb,
1750 tb1_phys = dma_map_single(trans->dev, tb1_addr, tb1_len, DMA_TO_DEVICE); 1749 tb1_phys = dma_map_single(trans->dev, tb1_addr, tb1_len, DMA_TO_DEVICE);
1751 if (unlikely(dma_mapping_error(trans->dev, tb1_phys))) 1750 if (unlikely(dma_mapping_error(trans->dev, tb1_phys)))
1752 goto out_err; 1751 goto out_err;
1753 iwl_pcie_txq_build_tfd(trans, txq, tb1_phys, tb1_len, 0); 1752 iwl_pcie_txq_build_tfd(trans, txq, tb1_phys, tb1_len, false);
1754 1753
1755 /* 1754 /*
1756 * Set up TFD's third entry to point directly to remainder 1755 * Set up TFD's third entry to point directly to remainder
@@ -1766,7 +1765,7 @@ int iwl_trans_pcie_tx(struct iwl_trans *trans, struct sk_buff *skb,
1766 &txq->tfds[q->write_ptr]); 1765 &txq->tfds[q->write_ptr]);
1767 goto out_err; 1766 goto out_err;
1768 } 1767 }
1769 iwl_pcie_txq_build_tfd(trans, txq, tb2_phys, tb2_len, 0); 1768 iwl_pcie_txq_build_tfd(trans, txq, tb2_phys, tb2_len, false);
1770 } 1769 }
1771 1770
1772 /* Set up entry for this TFD in Tx byte-count array */ 1771 /* Set up entry for this TFD in Tx byte-count array */
@@ -1788,7 +1787,7 @@ int iwl_trans_pcie_tx(struct iwl_trans *trans, struct sk_buff *skb,
1788 mod_timer(&txq->stuck_timer, jiffies + trans_pcie->wd_timeout); 1787 mod_timer(&txq->stuck_timer, jiffies + trans_pcie->wd_timeout);
1789 1788
1790 /* Tell device the write index *just past* this latest filled TFD */ 1789 /* Tell device the write index *just past* this latest filled TFD */
1791 q->write_ptr = iwl_queue_inc_wrap(q->write_ptr, q->n_bd); 1790 q->write_ptr = iwl_queue_inc_wrap(q->write_ptr);
1792 if (!wait_write_ptr) 1791 if (!wait_write_ptr)
1793 iwl_pcie_txq_inc_wr_ptr(trans, txq); 1792 iwl_pcie_txq_inc_wr_ptr(trans, txq);
1794 1793
diff --git a/drivers/net/wireless/libertas/cfg.c b/drivers/net/wireless/libertas/cfg.c
index 54e344aed6e0..47a998d8f99e 100644
--- a/drivers/net/wireless/libertas/cfg.c
+++ b/drivers/net/wireless/libertas/cfg.c
@@ -1006,9 +1006,8 @@ struct cmd_key_material {
1006} __packed; 1006} __packed;
1007 1007
1008static int lbs_set_key_material(struct lbs_private *priv, 1008static int lbs_set_key_material(struct lbs_private *priv,
1009 int key_type, 1009 int key_type, int key_info,
1010 int key_info, 1010 const u8 *key, u16 key_len)
1011 u8 *key, u16 key_len)
1012{ 1011{
1013 struct cmd_key_material cmd; 1012 struct cmd_key_material cmd;
1014 int ret; 1013 int ret;
@@ -1610,7 +1609,7 @@ static int lbs_cfg_del_key(struct wiphy *wiphy, struct net_device *netdev,
1610 */ 1609 */
1611 1610
1612static int lbs_cfg_get_station(struct wiphy *wiphy, struct net_device *dev, 1611static int lbs_cfg_get_station(struct wiphy *wiphy, struct net_device *dev,
1613 u8 *mac, struct station_info *sinfo) 1612 const u8 *mac, struct station_info *sinfo)
1614{ 1613{
1615 struct lbs_private *priv = wiphy_priv(wiphy); 1614 struct lbs_private *priv = wiphy_priv(wiphy);
1616 s8 signal, noise; 1615 s8 signal, noise;
diff --git a/drivers/net/wireless/libertas/defs.h b/drivers/net/wireless/libertas/defs.h
index ab966f08024a..407784aca627 100644
--- a/drivers/net/wireless/libertas/defs.h
+++ b/drivers/net/wireless/libertas/defs.h
@@ -90,7 +90,8 @@ do { if ((lbs_debug & (grp)) == (grp)) \
90#define lbs_deb_cfg80211(fmt, args...) LBS_DEB_LL(LBS_DEB_CFG80211, " cfg80211", fmt, ##args) 90#define lbs_deb_cfg80211(fmt, args...) LBS_DEB_LL(LBS_DEB_CFG80211, " cfg80211", fmt, ##args)
91 91
92#ifdef DEBUG 92#ifdef DEBUG
93static inline void lbs_deb_hex(unsigned int grp, const char *prompt, u8 *buf, int len) 93static inline void lbs_deb_hex(unsigned int grp, const char *prompt,
94 const u8 *buf, int len)
94{ 95{
95 int i = 0; 96 int i = 0;
96 97
diff --git a/drivers/net/wireless/libertas/rx.c b/drivers/net/wireless/libertas/rx.c
index c7366b07b568..e446fed7b345 100644
--- a/drivers/net/wireless/libertas/rx.c
+++ b/drivers/net/wireless/libertas/rx.c
@@ -71,8 +71,10 @@ int lbs_process_rxed_packet(struct lbs_private *priv, struct sk_buff *skb)
71 71
72 skb->ip_summed = CHECKSUM_NONE; 72 skb->ip_summed = CHECKSUM_NONE;
73 73
74 if (priv->wdev->iftype == NL80211_IFTYPE_MONITOR) 74 if (priv->wdev->iftype == NL80211_IFTYPE_MONITOR) {
75 return process_rxed_802_11_packet(priv, skb); 75 ret = process_rxed_802_11_packet(priv, skb);
76 goto done;
77 }
76 78
77 p_rx_pd = (struct rxpd *) skb->data; 79 p_rx_pd = (struct rxpd *) skb->data;
78 p_rx_pkt = (struct rxpackethdr *) ((u8 *)p_rx_pd + 80 p_rx_pkt = (struct rxpackethdr *) ((u8 *)p_rx_pd +
@@ -86,7 +88,7 @@ int lbs_process_rxed_packet(struct lbs_private *priv, struct sk_buff *skb)
86 if (skb->len < (ETH_HLEN + 8 + sizeof(struct rxpd))) { 88 if (skb->len < (ETH_HLEN + 8 + sizeof(struct rxpd))) {
87 lbs_deb_rx("rx err: frame received with bad length\n"); 89 lbs_deb_rx("rx err: frame received with bad length\n");
88 dev->stats.rx_length_errors++; 90 dev->stats.rx_length_errors++;
89 ret = 0; 91 ret = -EINVAL;
90 dev_kfree_skb(skb); 92 dev_kfree_skb(skb);
91 goto done; 93 goto done;
92 } 94 }
diff --git a/drivers/net/wireless/mwifiex/11n.c b/drivers/net/wireless/mwifiex/11n.c
index 2bd07d681c5e..e1c2f67ae85e 100644
--- a/drivers/net/wireless/mwifiex/11n.c
+++ b/drivers/net/wireless/mwifiex/11n.c
@@ -749,3 +749,45 @@ void mwifiex_set_ba_params(struct mwifiex_private *priv)
749 749
750 return; 750 return;
751} 751}
752
753u8 mwifiex_get_sec_chan_offset(int chan)
754{
755 u8 sec_offset;
756
757 switch (chan) {
758 case 36:
759 case 44:
760 case 52:
761 case 60:
762 case 100:
763 case 108:
764 case 116:
765 case 124:
766 case 132:
767 case 140:
768 case 149:
769 case 157:
770 sec_offset = IEEE80211_HT_PARAM_CHA_SEC_ABOVE;
771 break;
772 case 40:
773 case 48:
774 case 56:
775 case 64:
776 case 104:
777 case 112:
778 case 120:
779 case 128:
780 case 136:
781 case 144:
782 case 153:
783 case 161:
784 sec_offset = IEEE80211_HT_PARAM_CHA_SEC_BELOW;
785 break;
786 case 165:
787 default:
788 sec_offset = IEEE80211_HT_PARAM_CHA_SEC_NONE;
789 break;
790 }
791
792 return sec_offset;
793}
diff --git a/drivers/net/wireless/mwifiex/11n.h b/drivers/net/wireless/mwifiex/11n.h
index 40b007a00f4b..0b73fa08f5d4 100644
--- a/drivers/net/wireless/mwifiex/11n.h
+++ b/drivers/net/wireless/mwifiex/11n.h
@@ -63,6 +63,7 @@ int mwifiex_cmd_amsdu_aggr_ctrl(struct host_cmd_ds_command *cmd,
63 int cmd_action, 63 int cmd_action,
64 struct mwifiex_ds_11n_amsdu_aggr_ctrl *aa_ctrl); 64 struct mwifiex_ds_11n_amsdu_aggr_ctrl *aa_ctrl);
65void mwifiex_del_tx_ba_stream_tbl_by_ra(struct mwifiex_private *priv, u8 *ra); 65void mwifiex_del_tx_ba_stream_tbl_by_ra(struct mwifiex_private *priv, u8 *ra);
66u8 mwifiex_get_sec_chan_offset(int chan);
66 67
67static inline u8 68static inline u8
68mwifiex_is_station_ampdu_allowed(struct mwifiex_private *priv, 69mwifiex_is_station_ampdu_allowed(struct mwifiex_private *priv,
@@ -199,7 +200,7 @@ static inline int mwifiex_is_sta_11n_enabled(struct mwifiex_private *priv,
199} 200}
200 201
201static inline u8 202static inline u8
202mwifiex_tdls_peer_11n_enabled(struct mwifiex_private *priv, u8 *ra) 203mwifiex_tdls_peer_11n_enabled(struct mwifiex_private *priv, const u8 *ra)
203{ 204{
204 struct mwifiex_sta_node *node = mwifiex_get_sta_entry(priv, ra); 205 struct mwifiex_sta_node *node = mwifiex_get_sta_entry(priv, ra);
205 if (node) 206 if (node)
diff --git a/drivers/net/wireless/mwifiex/11n_aggr.c b/drivers/net/wireless/mwifiex/11n_aggr.c
index 860dfe71cf96..5b32106182f8 100644
--- a/drivers/net/wireless/mwifiex/11n_aggr.c
+++ b/drivers/net/wireless/mwifiex/11n_aggr.c
@@ -100,6 +100,7 @@ mwifiex_11n_form_amsdu_txpd(struct mwifiex_private *priv,
100 struct sk_buff *skb) 100 struct sk_buff *skb)
101{ 101{
102 struct txpd *local_tx_pd; 102 struct txpd *local_tx_pd;
103 struct mwifiex_txinfo *tx_info = MWIFIEX_SKB_TXCB(skb);
103 104
104 skb_push(skb, sizeof(*local_tx_pd)); 105 skb_push(skb, sizeof(*local_tx_pd));
105 106
@@ -118,6 +119,9 @@ mwifiex_11n_form_amsdu_txpd(struct mwifiex_private *priv,
118 local_tx_pd->tx_pkt_length = cpu_to_le16(skb->len - 119 local_tx_pd->tx_pkt_length = cpu_to_le16(skb->len -
119 sizeof(*local_tx_pd)); 120 sizeof(*local_tx_pd));
120 121
122 if (tx_info->flags & MWIFIEX_BUF_FLAG_TDLS_PKT)
123 local_tx_pd->flags |= MWIFIEX_TXPD_FLAGS_TDLS_PACKET;
124
121 if (local_tx_pd->tx_control == 0) 125 if (local_tx_pd->tx_control == 0)
122 /* TxCtrl set by user or default */ 126 /* TxCtrl set by user or default */
123 local_tx_pd->tx_control = cpu_to_le32(priv->pkt_tx_ctrl); 127 local_tx_pd->tx_control = cpu_to_le32(priv->pkt_tx_ctrl);
@@ -183,6 +187,9 @@ mwifiex_11n_aggregate_pkt(struct mwifiex_private *priv,
183 187
184 tx_info_aggr->bss_type = tx_info_src->bss_type; 188 tx_info_aggr->bss_type = tx_info_src->bss_type;
185 tx_info_aggr->bss_num = tx_info_src->bss_num; 189 tx_info_aggr->bss_num = tx_info_src->bss_num;
190
191 if (tx_info_src->flags & MWIFIEX_BUF_FLAG_TDLS_PKT)
192 tx_info_aggr->flags |= MWIFIEX_BUF_FLAG_TDLS_PKT;
186 skb_aggr->priority = skb_src->priority; 193 skb_aggr->priority = skb_src->priority;
187 194
188 do_gettimeofday(&tv); 195 do_gettimeofday(&tv);
diff --git a/drivers/net/wireless/mwifiex/cfg80211.c b/drivers/net/wireless/mwifiex/cfg80211.c
index 21ee27ab7b74..e95dec91a561 100644
--- a/drivers/net/wireless/mwifiex/cfg80211.c
+++ b/drivers/net/wireless/mwifiex/cfg80211.c
@@ -994,7 +994,7 @@ mwifiex_dump_station_info(struct mwifiex_private *priv,
994 */ 994 */
995static int 995static int
996mwifiex_cfg80211_get_station(struct wiphy *wiphy, struct net_device *dev, 996mwifiex_cfg80211_get_station(struct wiphy *wiphy, struct net_device *dev,
997 u8 *mac, struct station_info *sinfo) 997 const u8 *mac, struct station_info *sinfo)
998{ 998{
999 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev); 999 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1000 1000
@@ -1270,7 +1270,7 @@ static int mwifiex_cfg80211_change_beacon(struct wiphy *wiphy,
1270 */ 1270 */
1271static int 1271static int
1272mwifiex_cfg80211_del_station(struct wiphy *wiphy, struct net_device *dev, 1272mwifiex_cfg80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1273 u8 *mac) 1273 const u8 *mac)
1274{ 1274{
1275 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev); 1275 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1276 struct mwifiex_sta_node *sta_node; 1276 struct mwifiex_sta_node *sta_node;
@@ -2629,7 +2629,7 @@ static int mwifiex_cfg80211_set_coalesce(struct wiphy *wiphy,
2629 */ 2629 */
2630static int 2630static int
2631mwifiex_cfg80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev, 2631mwifiex_cfg80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev,
2632 u8 *peer, u8 action_code, u8 dialog_token, 2632 const u8 *peer, u8 action_code, u8 dialog_token,
2633 u16 status_code, u32 peer_capability, 2633 u16 status_code, u32 peer_capability,
2634 const u8 *extra_ies, size_t extra_ies_len) 2634 const u8 *extra_ies, size_t extra_ies_len)
2635{ 2635{
@@ -2701,7 +2701,7 @@ mwifiex_cfg80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev,
2701 2701
2702static int 2702static int
2703mwifiex_cfg80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev, 2703mwifiex_cfg80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev,
2704 u8 *peer, enum nl80211_tdls_operation action) 2704 const u8 *peer, enum nl80211_tdls_operation action)
2705{ 2705{
2706 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev); 2706 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2707 2707
@@ -2748,9 +2748,8 @@ mwifiex_cfg80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev,
2748} 2748}
2749 2749
2750static int 2750static int
2751mwifiex_cfg80211_add_station(struct wiphy *wiphy, 2751mwifiex_cfg80211_add_station(struct wiphy *wiphy, struct net_device *dev,
2752 struct net_device *dev, 2752 const u8 *mac, struct station_parameters *params)
2753 u8 *mac, struct station_parameters *params)
2754{ 2753{
2755 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev); 2754 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2756 2755
@@ -2765,9 +2764,9 @@ mwifiex_cfg80211_add_station(struct wiphy *wiphy,
2765} 2764}
2766 2765
2767static int 2766static int
2768mwifiex_cfg80211_change_station(struct wiphy *wiphy, 2767mwifiex_cfg80211_change_station(struct wiphy *wiphy, struct net_device *dev,
2769 struct net_device *dev, 2768 const u8 *mac,
2770 u8 *mac, struct station_parameters *params) 2769 struct station_parameters *params)
2771{ 2770{
2772 int ret; 2771 int ret;
2773 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev); 2772 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
diff --git a/drivers/net/wireless/mwifiex/fw.h b/drivers/net/wireless/mwifiex/fw.h
index b485dc1ae5eb..42eaeda1dc82 100644
--- a/drivers/net/wireless/mwifiex/fw.h
+++ b/drivers/net/wireless/mwifiex/fw.h
@@ -169,6 +169,7 @@ enum MWIFIEX_802_11_PRIVACY_FILTER {
169#define TLV_TYPE_GWK_CIPHER (PROPRIETARY_TLV_BASE_ID + 146) 169#define TLV_TYPE_GWK_CIPHER (PROPRIETARY_TLV_BASE_ID + 146)
170#define TLV_TYPE_COALESCE_RULE (PROPRIETARY_TLV_BASE_ID + 154) 170#define TLV_TYPE_COALESCE_RULE (PROPRIETARY_TLV_BASE_ID + 154)
171#define TLV_TYPE_KEY_PARAM_V2 (PROPRIETARY_TLV_BASE_ID + 156) 171#define TLV_TYPE_KEY_PARAM_V2 (PROPRIETARY_TLV_BASE_ID + 156)
172#define TLV_TYPE_TDLS_IDLE_TIMEOUT (PROPRIETARY_TLV_BASE_ID + 194)
172#define TLV_TYPE_FW_API_REV (PROPRIETARY_TLV_BASE_ID + 199) 173#define TLV_TYPE_FW_API_REV (PROPRIETARY_TLV_BASE_ID + 199)
173 174
174#define MWIFIEX_TX_DATA_BUF_SIZE_2K 2048 175#define MWIFIEX_TX_DATA_BUF_SIZE_2K 2048
@@ -229,6 +230,7 @@ enum MWIFIEX_802_11_PRIVACY_FILTER {
229#define ISENABLED_40MHZ_INTOLERANT(Dot11nDevCap) (Dot11nDevCap & BIT(8)) 230#define ISENABLED_40MHZ_INTOLERANT(Dot11nDevCap) (Dot11nDevCap & BIT(8))
230#define ISSUPP_RXLDPC(Dot11nDevCap) (Dot11nDevCap & BIT(22)) 231#define ISSUPP_RXLDPC(Dot11nDevCap) (Dot11nDevCap & BIT(22))
231#define ISSUPP_BEAMFORMING(Dot11nDevCap) (Dot11nDevCap & BIT(30)) 232#define ISSUPP_BEAMFORMING(Dot11nDevCap) (Dot11nDevCap & BIT(30))
233#define ISALLOWED_CHANWIDTH40(ht_param) (ht_param & BIT(2))
232 234
233/* httxcfg bitmap 235/* httxcfg bitmap
234 * 0 reserved 236 * 0 reserved
@@ -487,6 +489,7 @@ enum P2P_MODES {
487#define EVENT_UAP_MIC_COUNTERMEASURES 0x0000004c 489#define EVENT_UAP_MIC_COUNTERMEASURES 0x0000004c
488#define EVENT_HOSTWAKE_STAIE 0x0000004d 490#define EVENT_HOSTWAKE_STAIE 0x0000004d
489#define EVENT_CHANNEL_SWITCH_ANN 0x00000050 491#define EVENT_CHANNEL_SWITCH_ANN 0x00000050
492#define EVENT_TDLS_GENERIC_EVENT 0x00000052
490#define EVENT_EXT_SCAN_REPORT 0x00000058 493#define EVENT_EXT_SCAN_REPORT 0x00000058
491#define EVENT_REMAIN_ON_CHAN_EXPIRED 0x0000005f 494#define EVENT_REMAIN_ON_CHAN_EXPIRED 0x0000005f
492 495
@@ -519,6 +522,7 @@ enum P2P_MODES {
519#define ACT_TDLS_DELETE 0x00 522#define ACT_TDLS_DELETE 0x00
520#define ACT_TDLS_CREATE 0x01 523#define ACT_TDLS_CREATE 0x01
521#define ACT_TDLS_CONFIG 0x02 524#define ACT_TDLS_CONFIG 0x02
525#define TDLS_EVENT_LINK_TEAR_DOWN 3
522 526
523#define MWIFIEX_FW_V15 15 527#define MWIFIEX_FW_V15 15
524 528
@@ -535,6 +539,7 @@ struct mwifiex_ie_types_data {
535#define MWIFIEX_TxPD_POWER_MGMT_NULL_PACKET 0x01 539#define MWIFIEX_TxPD_POWER_MGMT_NULL_PACKET 0x01
536#define MWIFIEX_TxPD_POWER_MGMT_LAST_PACKET 0x08 540#define MWIFIEX_TxPD_POWER_MGMT_LAST_PACKET 0x08
537#define MWIFIEX_TXPD_FLAGS_TDLS_PACKET 0x10 541#define MWIFIEX_TXPD_FLAGS_TDLS_PACKET 0x10
542#define MWIFIEX_RXPD_FLAGS_TDLS_PACKET 0x01
538 543
539struct txpd { 544struct txpd {
540 u8 bss_type; 545 u8 bss_type;
@@ -577,7 +582,7 @@ struct rxpd {
577 * [Bit 7] Reserved 582 * [Bit 7] Reserved
578 */ 583 */
579 u8 ht_info; 584 u8 ht_info;
580 u8 reserved; 585 u8 flags;
581} __packed; 586} __packed;
582 587
583struct uap_txpd { 588struct uap_txpd {
@@ -708,6 +713,13 @@ struct mwifiex_ie_types_vendor_param_set {
708 u8 ie[MWIFIEX_MAX_VSIE_LEN]; 713 u8 ie[MWIFIEX_MAX_VSIE_LEN];
709}; 714};
710 715
716#define MWIFIEX_TDLS_IDLE_TIMEOUT 60
717
718struct mwifiex_ie_types_tdls_idle_timeout {
719 struct mwifiex_ie_types_header header;
720 __le16 value;
721} __packed;
722
711struct mwifiex_ie_types_rsn_param_set { 723struct mwifiex_ie_types_rsn_param_set {
712 struct mwifiex_ie_types_header header; 724 struct mwifiex_ie_types_header header;
713 u8 rsn_ie[1]; 725 u8 rsn_ie[1];
@@ -1745,6 +1757,15 @@ struct host_cmd_ds_802_11_subsc_evt {
1745 __le16 events; 1757 __le16 events;
1746} __packed; 1758} __packed;
1747 1759
1760struct mwifiex_tdls_generic_event {
1761 __le16 type;
1762 u8 peer_mac[ETH_ALEN];
1763 union {
1764 __le16 reason_code;
1765 __le16 reserved;
1766 } u;
1767} __packed;
1768
1748struct mwifiex_ie { 1769struct mwifiex_ie {
1749 __le16 ie_index; 1770 __le16 ie_index;
1750 __le16 mgmt_subtype_mask; 1771 __le16 mgmt_subtype_mask;
diff --git a/drivers/net/wireless/mwifiex/main.h b/drivers/net/wireless/mwifiex/main.h
index 34181192a666..3f25feb1508e 100644
--- a/drivers/net/wireless/mwifiex/main.h
+++ b/drivers/net/wireless/mwifiex/main.h
@@ -910,8 +910,6 @@ int mwifiex_handle_uap_rx_forward(struct mwifiex_private *priv,
910 struct sk_buff *skb); 910 struct sk_buff *skb);
911int mwifiex_process_sta_event(struct mwifiex_private *); 911int mwifiex_process_sta_event(struct mwifiex_private *);
912int mwifiex_process_uap_event(struct mwifiex_private *); 912int mwifiex_process_uap_event(struct mwifiex_private *);
913struct mwifiex_sta_node *
914mwifiex_get_sta_entry(struct mwifiex_private *priv, u8 *mac);
915void mwifiex_delete_all_station_list(struct mwifiex_private *priv); 913void mwifiex_delete_all_station_list(struct mwifiex_private *priv);
916void *mwifiex_process_sta_txpd(struct mwifiex_private *, struct sk_buff *skb); 914void *mwifiex_process_sta_txpd(struct mwifiex_private *, struct sk_buff *skb);
917void *mwifiex_process_uap_txpd(struct mwifiex_private *, struct sk_buff *skb); 915void *mwifiex_process_uap_txpd(struct mwifiex_private *, struct sk_buff *skb);
@@ -1220,26 +1218,26 @@ void mwifiex_dnld_txpwr_table(struct mwifiex_private *priv);
1220extern const struct ethtool_ops mwifiex_ethtool_ops; 1218extern const struct ethtool_ops mwifiex_ethtool_ops;
1221 1219
1222void mwifiex_del_all_sta_list(struct mwifiex_private *priv); 1220void mwifiex_del_all_sta_list(struct mwifiex_private *priv);
1223void mwifiex_del_sta_entry(struct mwifiex_private *priv, u8 *mac); 1221void mwifiex_del_sta_entry(struct mwifiex_private *priv, const u8 *mac);
1224void 1222void
1225mwifiex_set_sta_ht_cap(struct mwifiex_private *priv, const u8 *ies, 1223mwifiex_set_sta_ht_cap(struct mwifiex_private *priv, const u8 *ies,
1226 int ies_len, struct mwifiex_sta_node *node); 1224 int ies_len, struct mwifiex_sta_node *node);
1227struct mwifiex_sta_node * 1225struct mwifiex_sta_node *
1228mwifiex_add_sta_entry(struct mwifiex_private *priv, u8 *mac); 1226mwifiex_add_sta_entry(struct mwifiex_private *priv, const u8 *mac);
1229struct mwifiex_sta_node * 1227struct mwifiex_sta_node *
1230mwifiex_get_sta_entry(struct mwifiex_private *priv, u8 *mac); 1228mwifiex_get_sta_entry(struct mwifiex_private *priv, const u8 *mac);
1231int mwifiex_send_tdls_data_frame(struct mwifiex_private *priv, u8 *peer, 1229int mwifiex_send_tdls_data_frame(struct mwifiex_private *priv, const u8 *peer,
1232 u8 action_code, u8 dialog_token, 1230 u8 action_code, u8 dialog_token,
1233 u16 status_code, const u8 *extra_ies, 1231 u16 status_code, const u8 *extra_ies,
1234 size_t extra_ies_len); 1232 size_t extra_ies_len);
1235int mwifiex_send_tdls_action_frame(struct mwifiex_private *priv, 1233int mwifiex_send_tdls_action_frame(struct mwifiex_private *priv, const u8 *peer,
1236 u8 *peer, u8 action_code, u8 dialog_token, 1234 u8 action_code, u8 dialog_token,
1237 u16 status_code, const u8 *extra_ies, 1235 u16 status_code, const u8 *extra_ies,
1238 size_t extra_ies_len); 1236 size_t extra_ies_len);
1239void mwifiex_process_tdls_action_frame(struct mwifiex_private *priv, 1237void mwifiex_process_tdls_action_frame(struct mwifiex_private *priv,
1240 u8 *buf, int len); 1238 u8 *buf, int len);
1241int mwifiex_tdls_oper(struct mwifiex_private *priv, u8 *peer, u8 action); 1239int mwifiex_tdls_oper(struct mwifiex_private *priv, const u8 *peer, u8 action);
1242int mwifiex_get_tdls_link_status(struct mwifiex_private *priv, u8 *mac); 1240int mwifiex_get_tdls_link_status(struct mwifiex_private *priv, const u8 *mac);
1243void mwifiex_disable_all_tdls_links(struct mwifiex_private *priv); 1241void mwifiex_disable_all_tdls_links(struct mwifiex_private *priv);
1244bool mwifiex_is_bss_in_11ac_mode(struct mwifiex_private *priv); 1242bool mwifiex_is_bss_in_11ac_mode(struct mwifiex_private *priv);
1245u8 mwifiex_get_center_freq_index(struct mwifiex_private *priv, u8 band, 1243u8 mwifiex_get_center_freq_index(struct mwifiex_private *priv, u8 band,
diff --git a/drivers/net/wireless/mwifiex/pcie.c b/drivers/net/wireless/mwifiex/pcie.c
index c2cfeec466d8..574d4b597468 100644
--- a/drivers/net/wireless/mwifiex/pcie.c
+++ b/drivers/net/wireless/mwifiex/pcie.c
@@ -1071,6 +1071,7 @@ static int mwifiex_pcie_send_data_complete(struct mwifiex_adapter *adapter)
1071 * is mapped to PCI device memory. Tx ring pointers are advanced accordingly. 1071 * is mapped to PCI device memory. Tx ring pointers are advanced accordingly.
1072 * Download ready interrupt to FW is deffered if Tx ring is not full and 1072 * Download ready interrupt to FW is deffered if Tx ring is not full and
1073 * additional payload can be accomodated. 1073 * additional payload can be accomodated.
1074 * Caller must ensure tx_param parameter to this function is not NULL.
1074 */ 1075 */
1075static int 1076static int
1076mwifiex_pcie_send_data(struct mwifiex_adapter *adapter, struct sk_buff *skb, 1077mwifiex_pcie_send_data(struct mwifiex_adapter *adapter, struct sk_buff *skb,
diff --git a/drivers/net/wireless/mwifiex/sdio.c b/drivers/net/wireless/mwifiex/sdio.c
index a1773d3cb49f..4ce3d7b33991 100644
--- a/drivers/net/wireless/mwifiex/sdio.c
+++ b/drivers/net/wireless/mwifiex/sdio.c
@@ -1678,8 +1678,12 @@ static int mwifiex_sdio_host_to_card(struct mwifiex_adapter *adapter,
1678 if (ret) { 1678 if (ret) {
1679 if (type == MWIFIEX_TYPE_CMD) 1679 if (type == MWIFIEX_TYPE_CMD)
1680 adapter->cmd_sent = false; 1680 adapter->cmd_sent = false;
1681 if (type == MWIFIEX_TYPE_DATA) 1681 if (type == MWIFIEX_TYPE_DATA) {
1682 adapter->data_sent = false; 1682 adapter->data_sent = false;
1683 /* restore curr_wr_port in error cases */
1684 card->curr_wr_port = port;
1685 card->mp_wr_bitmap |= (u32)(1 << card->curr_wr_port);
1686 }
1683 } else { 1687 } else {
1684 if (type == MWIFIEX_TYPE_DATA) { 1688 if (type == MWIFIEX_TYPE_DATA) {
1685 if (!(card->mp_wr_bitmap & (1 << card->curr_wr_port))) 1689 if (!(card->mp_wr_bitmap & (1 << card->curr_wr_port)))
diff --git a/drivers/net/wireless/mwifiex/sta_cmd.c b/drivers/net/wireless/mwifiex/sta_cmd.c
index e3cac1495cc7..88202ce0c139 100644
--- a/drivers/net/wireless/mwifiex/sta_cmd.c
+++ b/drivers/net/wireless/mwifiex/sta_cmd.c
@@ -1546,6 +1546,7 @@ mwifiex_cmd_tdls_oper(struct mwifiex_private *priv,
1546 struct mwifiex_ie_types_extcap *extcap; 1546 struct mwifiex_ie_types_extcap *extcap;
1547 struct mwifiex_ie_types_vhtcap *vht_capab; 1547 struct mwifiex_ie_types_vhtcap *vht_capab;
1548 struct mwifiex_ie_types_aid *aid; 1548 struct mwifiex_ie_types_aid *aid;
1549 struct mwifiex_ie_types_tdls_idle_timeout *timeout;
1549 u8 *pos, qos_info; 1550 u8 *pos, qos_info;
1550 u16 config_len = 0; 1551 u16 config_len = 0;
1551 struct station_parameters *params = priv->sta_params; 1552 struct station_parameters *params = priv->sta_params;
@@ -1643,6 +1644,12 @@ mwifiex_cmd_tdls_oper(struct mwifiex_private *priv,
1643 config_len += sizeof(struct mwifiex_ie_types_aid); 1644 config_len += sizeof(struct mwifiex_ie_types_aid);
1644 } 1645 }
1645 1646
1647 timeout = (void *)(pos + config_len);
1648 timeout->header.type = cpu_to_le16(TLV_TYPE_TDLS_IDLE_TIMEOUT);
1649 timeout->header.len = cpu_to_le16(sizeof(timeout->value));
1650 timeout->value = cpu_to_le16(MWIFIEX_TDLS_IDLE_TIMEOUT);
1651 config_len += sizeof(struct mwifiex_ie_types_tdls_idle_timeout);
1652
1646 break; 1653 break;
1647 default: 1654 default:
1648 dev_err(priv->adapter->dev, "Unknown TDLS operation\n"); 1655 dev_err(priv->adapter->dev, "Unknown TDLS operation\n");
diff --git a/drivers/net/wireless/mwifiex/sta_cmdresp.c b/drivers/net/wireless/mwifiex/sta_cmdresp.c
index bfebb0144df5..577f2979ed8f 100644
--- a/drivers/net/wireless/mwifiex/sta_cmdresp.c
+++ b/drivers/net/wireless/mwifiex/sta_cmdresp.c
@@ -865,14 +865,20 @@ static int mwifiex_ret_tdls_oper(struct mwifiex_private *priv,
865 865
866 switch (action) { 866 switch (action) {
867 case ACT_TDLS_DELETE: 867 case ACT_TDLS_DELETE:
868 if (reason) 868 if (reason) {
869 dev_err(priv->adapter->dev, 869 if (!node || reason == TDLS_ERR_LINK_NONEXISTENT)
870 "TDLS link delete for %pM failed: reason %d\n", 870 dev_dbg(priv->adapter->dev,
871 cmd_tdls_oper->peer_mac, reason); 871 "TDLS link delete for %pM failed: reason %d\n",
872 else 872 cmd_tdls_oper->peer_mac, reason);
873 else
874 dev_err(priv->adapter->dev,
875 "TDLS link delete for %pM failed: reason %d\n",
876 cmd_tdls_oper->peer_mac, reason);
877 } else {
873 dev_dbg(priv->adapter->dev, 878 dev_dbg(priv->adapter->dev,
874 "TDLS link config for %pM successful\n", 879 "TDLS link delete for %pM successful\n",
875 cmd_tdls_oper->peer_mac); 880 cmd_tdls_oper->peer_mac);
881 }
876 break; 882 break;
877 case ACT_TDLS_CREATE: 883 case ACT_TDLS_CREATE:
878 if (reason) { 884 if (reason) {
diff --git a/drivers/net/wireless/mwifiex/sta_event.c b/drivers/net/wireless/mwifiex/sta_event.c
index 368450cc56c7..f6395ef11a72 100644
--- a/drivers/net/wireless/mwifiex/sta_event.c
+++ b/drivers/net/wireless/mwifiex/sta_event.c
@@ -134,6 +134,46 @@ mwifiex_reset_connect_state(struct mwifiex_private *priv, u16 reason_code)
134 netif_carrier_off(priv->netdev); 134 netif_carrier_off(priv->netdev);
135} 135}
136 136
137static int mwifiex_parse_tdls_event(struct mwifiex_private *priv,
138 struct sk_buff *event_skb)
139{
140 int ret = 0;
141 struct mwifiex_adapter *adapter = priv->adapter;
142 struct mwifiex_sta_node *sta_ptr;
143 struct mwifiex_tdls_generic_event *tdls_evt =
144 (void *)event_skb->data + sizeof(adapter->event_cause);
145
146 /* reserved 2 bytes are not mandatory in tdls event */
147 if (event_skb->len < (sizeof(struct mwifiex_tdls_generic_event) -
148 sizeof(u16) - sizeof(adapter->event_cause))) {
149 dev_err(adapter->dev, "Invalid event length!\n");
150 return -1;
151 }
152
153 sta_ptr = mwifiex_get_sta_entry(priv, tdls_evt->peer_mac);
154 if (!sta_ptr) {
155 dev_err(adapter->dev, "cannot get sta entry!\n");
156 return -1;
157 }
158
159 switch (le16_to_cpu(tdls_evt->type)) {
160 case TDLS_EVENT_LINK_TEAR_DOWN:
161 cfg80211_tdls_oper_request(priv->netdev,
162 tdls_evt->peer_mac,
163 NL80211_TDLS_TEARDOWN,
164 le16_to_cpu(tdls_evt->u.reason_code),
165 GFP_KERNEL);
166 ret = mwifiex_tdls_oper(priv, tdls_evt->peer_mac,
167 MWIFIEX_TDLS_DISABLE_LINK);
168 queue_work(adapter->workqueue, &adapter->main_work);
169 break;
170 default:
171 break;
172 }
173
174 return ret;
175}
176
137/* 177/*
138 * This function handles events generated by firmware. 178 * This function handles events generated by firmware.
139 * 179 *
@@ -459,6 +499,10 @@ int mwifiex_process_sta_event(struct mwifiex_private *priv)
459 false); 499 false);
460 break; 500 break;
461 501
502 case EVENT_TDLS_GENERIC_EVENT:
503 ret = mwifiex_parse_tdls_event(priv, adapter->event_skb);
504 break;
505
462 default: 506 default:
463 dev_dbg(adapter->dev, "event: unknown event id: %#x\n", 507 dev_dbg(adapter->dev, "event: unknown event id: %#x\n",
464 eventcause); 508 eventcause);
diff --git a/drivers/net/wireless/mwifiex/sta_rx.c b/drivers/net/wireless/mwifiex/sta_rx.c
index ed26387eccf5..8b639d7fe6df 100644
--- a/drivers/net/wireless/mwifiex/sta_rx.c
+++ b/drivers/net/wireless/mwifiex/sta_rx.c
@@ -183,6 +183,7 @@ int mwifiex_process_sta_rx_packet(struct mwifiex_private *priv,
183 struct rx_packet_hdr *rx_pkt_hdr; 183 struct rx_packet_hdr *rx_pkt_hdr;
184 u8 ta[ETH_ALEN]; 184 u8 ta[ETH_ALEN];
185 u16 rx_pkt_type, rx_pkt_offset, rx_pkt_length, seq_num; 185 u16 rx_pkt_type, rx_pkt_offset, rx_pkt_length, seq_num;
186 struct mwifiex_sta_node *sta_ptr;
186 187
187 local_rx_pd = (struct rxpd *) (skb->data); 188 local_rx_pd = (struct rxpd *) (skb->data);
188 rx_pkt_type = le16_to_cpu(local_rx_pd->rx_pkt_type); 189 rx_pkt_type = le16_to_cpu(local_rx_pd->rx_pkt_type);
@@ -213,14 +214,25 @@ int mwifiex_process_sta_rx_packet(struct mwifiex_private *priv,
213 * If the packet is not an unicast packet then send the packet 214 * If the packet is not an unicast packet then send the packet
214 * directly to os. Don't pass thru rx reordering 215 * directly to os. Don't pass thru rx reordering
215 */ 216 */
216 if (!IS_11N_ENABLED(priv) || 217 if ((!IS_11N_ENABLED(priv) &&
218 !(ISSUPP_TDLS_ENABLED(priv->adapter->fw_cap_info) &&
219 !(local_rx_pd->flags & MWIFIEX_RXPD_FLAGS_TDLS_PACKET))) ||
217 !ether_addr_equal_unaligned(priv->curr_addr, rx_pkt_hdr->eth803_hdr.h_dest)) { 220 !ether_addr_equal_unaligned(priv->curr_addr, rx_pkt_hdr->eth803_hdr.h_dest)) {
218 mwifiex_process_rx_packet(priv, skb); 221 mwifiex_process_rx_packet(priv, skb);
219 return ret; 222 return ret;
220 } 223 }
221 224
222 if (mwifiex_queuing_ra_based(priv)) { 225 if (mwifiex_queuing_ra_based(priv) ||
226 (ISSUPP_TDLS_ENABLED(priv->adapter->fw_cap_info) &&
227 local_rx_pd->flags & MWIFIEX_RXPD_FLAGS_TDLS_PACKET)) {
223 memcpy(ta, rx_pkt_hdr->eth803_hdr.h_source, ETH_ALEN); 228 memcpy(ta, rx_pkt_hdr->eth803_hdr.h_source, ETH_ALEN);
229 if (local_rx_pd->flags & MWIFIEX_RXPD_FLAGS_TDLS_PACKET &&
230 local_rx_pd->priority < MAX_NUM_TID) {
231 sta_ptr = mwifiex_get_sta_entry(priv, ta);
232 if (sta_ptr)
233 sta_ptr->rx_seq[local_rx_pd->priority] =
234 le16_to_cpu(local_rx_pd->seq_num);
235 }
224 } else { 236 } else {
225 if (rx_pkt_type != PKT_TYPE_BAR) 237 if (rx_pkt_type != PKT_TYPE_BAR)
226 priv->rx_seq[local_rx_pd->priority] = seq_num; 238 priv->rx_seq[local_rx_pd->priority] = seq_num;
diff --git a/drivers/net/wireless/mwifiex/sta_tx.c b/drivers/net/wireless/mwifiex/sta_tx.c
index 1236a5de7bca..5fce7e78a36e 100644
--- a/drivers/net/wireless/mwifiex/sta_tx.c
+++ b/drivers/net/wireless/mwifiex/sta_tx.c
@@ -128,6 +128,7 @@ int mwifiex_send_null_packet(struct mwifiex_private *priv, u8 flags)
128{ 128{
129 struct mwifiex_adapter *adapter = priv->adapter; 129 struct mwifiex_adapter *adapter = priv->adapter;
130 struct txpd *local_tx_pd; 130 struct txpd *local_tx_pd;
131 struct mwifiex_tx_param tx_param;
131/* sizeof(struct txpd) + Interface specific header */ 132/* sizeof(struct txpd) + Interface specific header */
132#define NULL_PACKET_HDR 64 133#define NULL_PACKET_HDR 64
133 u32 data_len = NULL_PACKET_HDR; 134 u32 data_len = NULL_PACKET_HDR;
@@ -168,8 +169,9 @@ int mwifiex_send_null_packet(struct mwifiex_private *priv, u8 flags)
168 skb, NULL); 169 skb, NULL);
169 } else { 170 } else {
170 skb_push(skb, INTF_HEADER_LEN); 171 skb_push(skb, INTF_HEADER_LEN);
172 tx_param.next_pkt_len = 0;
171 ret = adapter->if_ops.host_to_card(adapter, MWIFIEX_TYPE_DATA, 173 ret = adapter->if_ops.host_to_card(adapter, MWIFIEX_TYPE_DATA,
172 skb, NULL); 174 skb, &tx_param);
173 } 175 }
174 switch (ret) { 176 switch (ret) {
175 case -EBUSY: 177 case -EBUSY:
diff --git a/drivers/net/wireless/mwifiex/tdls.c b/drivers/net/wireless/mwifiex/tdls.c
index 97662a1ba58c..e73034fbbde9 100644
--- a/drivers/net/wireless/mwifiex/tdls.c
+++ b/drivers/net/wireless/mwifiex/tdls.c
@@ -25,8 +25,8 @@
25#define TDLS_RESP_FIX_LEN 8 25#define TDLS_RESP_FIX_LEN 8
26#define TDLS_CONFIRM_FIX_LEN 6 26#define TDLS_CONFIRM_FIX_LEN 6
27 27
28static void 28static void mwifiex_restore_tdls_packets(struct mwifiex_private *priv,
29mwifiex_restore_tdls_packets(struct mwifiex_private *priv, u8 *mac, u8 status) 29 const u8 *mac, u8 status)
30{ 30{
31 struct mwifiex_ra_list_tbl *ra_list; 31 struct mwifiex_ra_list_tbl *ra_list;
32 struct list_head *tid_list; 32 struct list_head *tid_list;
@@ -84,7 +84,8 @@ mwifiex_restore_tdls_packets(struct mwifiex_private *priv, u8 *mac, u8 status)
84 return; 84 return;
85} 85}
86 86
87static void mwifiex_hold_tdls_packets(struct mwifiex_private *priv, u8 *mac) 87static void mwifiex_hold_tdls_packets(struct mwifiex_private *priv,
88 const u8 *mac)
88{ 89{
89 struct mwifiex_ra_list_tbl *ra_list; 90 struct mwifiex_ra_list_tbl *ra_list;
90 struct list_head *ra_list_head; 91 struct list_head *ra_list_head;
@@ -185,8 +186,50 @@ static int mwifiex_tdls_add_vht_capab(struct mwifiex_private *priv,
185 return 0; 186 return 0;
186} 187}
187 188
189static int
190mwifiex_tdls_add_ht_oper(struct mwifiex_private *priv, const u8 *mac,
191 u8 vht_enabled, struct sk_buff *skb)
192{
193 struct ieee80211_ht_operation *ht_oper;
194 struct mwifiex_sta_node *sta_ptr;
195 struct mwifiex_bssdescriptor *bss_desc =
196 &priv->curr_bss_params.bss_descriptor;
197 u8 *pos;
198
199 sta_ptr = mwifiex_get_sta_entry(priv, mac);
200 if (unlikely(!sta_ptr)) {
201 dev_warn(priv->adapter->dev,
202 "TDLS peer station not found in list\n");
203 return -1;
204 }
205
206 pos = (void *)skb_put(skb, sizeof(struct ieee80211_ht_operation) + 2);
207 *pos++ = WLAN_EID_HT_OPERATION;
208 *pos++ = sizeof(struct ieee80211_ht_operation);
209 ht_oper = (void *)pos;
210
211 ht_oper->primary_chan = bss_desc->channel;
212
213 /* follow AP's channel bandwidth */
214 if (ISSUPP_CHANWIDTH40(priv->adapter->hw_dot_11n_dev_cap) &&
215 bss_desc->bcn_ht_cap &&
216 ISALLOWED_CHANWIDTH40(bss_desc->bcn_ht_oper->ht_param))
217 ht_oper->ht_param = bss_desc->bcn_ht_oper->ht_param;
218
219 if (vht_enabled) {
220 ht_oper->ht_param =
221 mwifiex_get_sec_chan_offset(bss_desc->channel);
222 ht_oper->ht_param |= BIT(2);
223 }
224
225 memcpy(&sta_ptr->tdls_cap.ht_oper, ht_oper,
226 sizeof(struct ieee80211_ht_operation));
227
228 return 0;
229}
230
188static int mwifiex_tdls_add_vht_oper(struct mwifiex_private *priv, 231static int mwifiex_tdls_add_vht_oper(struct mwifiex_private *priv,
189 u8 *mac, struct sk_buff *skb) 232 const u8 *mac, struct sk_buff *skb)
190{ 233{
191 struct mwifiex_bssdescriptor *bss_desc; 234 struct mwifiex_bssdescriptor *bss_desc;
192 struct ieee80211_vht_operation *vht_oper; 235 struct ieee80211_vht_operation *vht_oper;
@@ -325,8 +368,9 @@ static void mwifiex_tdls_add_qos_capab(struct sk_buff *skb)
325} 368}
326 369
327static int mwifiex_prep_tdls_encap_data(struct mwifiex_private *priv, 370static int mwifiex_prep_tdls_encap_data(struct mwifiex_private *priv,
328 u8 *peer, u8 action_code, u8 dialog_token, 371 const u8 *peer, u8 action_code,
329 u16 status_code, struct sk_buff *skb) 372 u8 dialog_token,
373 u16 status_code, struct sk_buff *skb)
330{ 374{
331 struct ieee80211_tdls_data *tf; 375 struct ieee80211_tdls_data *tf;
332 int ret; 376 int ret;
@@ -428,6 +472,17 @@ static int mwifiex_prep_tdls_encap_data(struct mwifiex_private *priv,
428 dev_kfree_skb_any(skb); 472 dev_kfree_skb_any(skb);
429 return ret; 473 return ret;
430 } 474 }
475 ret = mwifiex_tdls_add_ht_oper(priv, peer, 1, skb);
476 if (ret) {
477 dev_kfree_skb_any(skb);
478 return ret;
479 }
480 } else {
481 ret = mwifiex_tdls_add_ht_oper(priv, peer, 0, skb);
482 if (ret) {
483 dev_kfree_skb_any(skb);
484 return ret;
485 }
431 } 486 }
432 break; 487 break;
433 488
@@ -453,7 +508,8 @@ static int mwifiex_prep_tdls_encap_data(struct mwifiex_private *priv,
453} 508}
454 509
455static void 510static void
456mwifiex_tdls_add_link_ie(struct sk_buff *skb, u8 *src_addr, u8 *peer, u8 *bssid) 511mwifiex_tdls_add_link_ie(struct sk_buff *skb, const u8 *src_addr,
512 const u8 *peer, const u8 *bssid)
457{ 513{
458 struct ieee80211_tdls_lnkie *lnkid; 514 struct ieee80211_tdls_lnkie *lnkid;
459 515
@@ -467,8 +523,8 @@ mwifiex_tdls_add_link_ie(struct sk_buff *skb, u8 *src_addr, u8 *peer, u8 *bssid)
467 memcpy(lnkid->resp_sta, peer, ETH_ALEN); 523 memcpy(lnkid->resp_sta, peer, ETH_ALEN);
468} 524}
469 525
470int mwifiex_send_tdls_data_frame(struct mwifiex_private *priv, 526int mwifiex_send_tdls_data_frame(struct mwifiex_private *priv, const u8 *peer,
471 u8 *peer, u8 action_code, u8 dialog_token, 527 u8 action_code, u8 dialog_token,
472 u16 status_code, const u8 *extra_ies, 528 u16 status_code, const u8 *extra_ies,
473 size_t extra_ies_len) 529 size_t extra_ies_len)
474{ 530{
@@ -560,7 +616,8 @@ int mwifiex_send_tdls_data_frame(struct mwifiex_private *priv,
560} 616}
561 617
562static int 618static int
563mwifiex_construct_tdls_action_frame(struct mwifiex_private *priv, u8 *peer, 619mwifiex_construct_tdls_action_frame(struct mwifiex_private *priv,
620 const u8 *peer,
564 u8 action_code, u8 dialog_token, 621 u8 action_code, u8 dialog_token,
565 u16 status_code, struct sk_buff *skb) 622 u16 status_code, struct sk_buff *skb)
566{ 623{
@@ -638,10 +695,10 @@ mwifiex_construct_tdls_action_frame(struct mwifiex_private *priv, u8 *peer,
638 return 0; 695 return 0;
639} 696}
640 697
641int mwifiex_send_tdls_action_frame(struct mwifiex_private *priv, 698int mwifiex_send_tdls_action_frame(struct mwifiex_private *priv, const u8 *peer,
642 u8 *peer, u8 action_code, u8 dialog_token, 699 u8 action_code, u8 dialog_token,
643 u16 status_code, const u8 *extra_ies, 700 u16 status_code, const u8 *extra_ies,
644 size_t extra_ies_len) 701 size_t extra_ies_len)
645{ 702{
646 struct sk_buff *skb; 703 struct sk_buff *skb;
647 struct mwifiex_txinfo *tx_info; 704 struct mwifiex_txinfo *tx_info;
@@ -848,7 +905,7 @@ void mwifiex_process_tdls_action_frame(struct mwifiex_private *priv,
848} 905}
849 906
850static int 907static int
851mwifiex_tdls_process_config_link(struct mwifiex_private *priv, u8 *peer) 908mwifiex_tdls_process_config_link(struct mwifiex_private *priv, const u8 *peer)
852{ 909{
853 struct mwifiex_sta_node *sta_ptr; 910 struct mwifiex_sta_node *sta_ptr;
854 struct mwifiex_ds_tdls_oper tdls_oper; 911 struct mwifiex_ds_tdls_oper tdls_oper;
@@ -869,7 +926,7 @@ mwifiex_tdls_process_config_link(struct mwifiex_private *priv, u8 *peer)
869} 926}
870 927
871static int 928static int
872mwifiex_tdls_process_create_link(struct mwifiex_private *priv, u8 *peer) 929mwifiex_tdls_process_create_link(struct mwifiex_private *priv, const u8 *peer)
873{ 930{
874 struct mwifiex_sta_node *sta_ptr; 931 struct mwifiex_sta_node *sta_ptr;
875 struct mwifiex_ds_tdls_oper tdls_oper; 932 struct mwifiex_ds_tdls_oper tdls_oper;
@@ -896,7 +953,7 @@ mwifiex_tdls_process_create_link(struct mwifiex_private *priv, u8 *peer)
896} 953}
897 954
898static int 955static int
899mwifiex_tdls_process_disable_link(struct mwifiex_private *priv, u8 *peer) 956mwifiex_tdls_process_disable_link(struct mwifiex_private *priv, const u8 *peer)
900{ 957{
901 struct mwifiex_sta_node *sta_ptr; 958 struct mwifiex_sta_node *sta_ptr;
902 struct mwifiex_ds_tdls_oper tdls_oper; 959 struct mwifiex_ds_tdls_oper tdls_oper;
@@ -925,7 +982,7 @@ mwifiex_tdls_process_disable_link(struct mwifiex_private *priv, u8 *peer)
925} 982}
926 983
927static int 984static int
928mwifiex_tdls_process_enable_link(struct mwifiex_private *priv, u8 *peer) 985mwifiex_tdls_process_enable_link(struct mwifiex_private *priv, const u8 *peer)
929{ 986{
930 struct mwifiex_sta_node *sta_ptr; 987 struct mwifiex_sta_node *sta_ptr;
931 struct ieee80211_mcs_info mcs; 988 struct ieee80211_mcs_info mcs;
@@ -982,7 +1039,7 @@ mwifiex_tdls_process_enable_link(struct mwifiex_private *priv, u8 *peer)
982 return 0; 1039 return 0;
983} 1040}
984 1041
985int mwifiex_tdls_oper(struct mwifiex_private *priv, u8 *peer, u8 action) 1042int mwifiex_tdls_oper(struct mwifiex_private *priv, const u8 *peer, u8 action)
986{ 1043{
987 switch (action) { 1044 switch (action) {
988 case MWIFIEX_TDLS_ENABLE_LINK: 1045 case MWIFIEX_TDLS_ENABLE_LINK:
@@ -997,7 +1054,7 @@ int mwifiex_tdls_oper(struct mwifiex_private *priv, u8 *peer, u8 action)
997 return 0; 1054 return 0;
998} 1055}
999 1056
1000int mwifiex_get_tdls_link_status(struct mwifiex_private *priv, u8 *mac) 1057int mwifiex_get_tdls_link_status(struct mwifiex_private *priv, const u8 *mac)
1001{ 1058{
1002 struct mwifiex_sta_node *sta_ptr; 1059 struct mwifiex_sta_node *sta_ptr;
1003 1060
diff --git a/drivers/net/wireless/mwifiex/util.c b/drivers/net/wireless/mwifiex/util.c
index c3824e37f3f2..6da5abf52e61 100644
--- a/drivers/net/wireless/mwifiex/util.c
+++ b/drivers/net/wireless/mwifiex/util.c
@@ -259,7 +259,7 @@ int mwifiex_complete_cmd(struct mwifiex_adapter *adapter,
259 * NULL is returned if station entry is not found in associated STA list. 259 * NULL is returned if station entry is not found in associated STA list.
260 */ 260 */
261struct mwifiex_sta_node * 261struct mwifiex_sta_node *
262mwifiex_get_sta_entry(struct mwifiex_private *priv, u8 *mac) 262mwifiex_get_sta_entry(struct mwifiex_private *priv, const u8 *mac)
263{ 263{
264 struct mwifiex_sta_node *node; 264 struct mwifiex_sta_node *node;
265 265
@@ -280,7 +280,7 @@ mwifiex_get_sta_entry(struct mwifiex_private *priv, u8 *mac)
280 * If received mac address is NULL, NULL is returned. 280 * If received mac address is NULL, NULL is returned.
281 */ 281 */
282struct mwifiex_sta_node * 282struct mwifiex_sta_node *
283mwifiex_add_sta_entry(struct mwifiex_private *priv, u8 *mac) 283mwifiex_add_sta_entry(struct mwifiex_private *priv, const u8 *mac)
284{ 284{
285 struct mwifiex_sta_node *node; 285 struct mwifiex_sta_node *node;
286 unsigned long flags; 286 unsigned long flags;
@@ -332,7 +332,7 @@ mwifiex_set_sta_ht_cap(struct mwifiex_private *priv, const u8 *ies,
332} 332}
333 333
334/* This function will delete a station entry from station list */ 334/* This function will delete a station entry from station list */
335void mwifiex_del_sta_entry(struct mwifiex_private *priv, u8 *mac) 335void mwifiex_del_sta_entry(struct mwifiex_private *priv, const u8 *mac)
336{ 336{
337 struct mwifiex_sta_node *node; 337 struct mwifiex_sta_node *node;
338 unsigned long flags; 338 unsigned long flags;
diff --git a/drivers/net/wireless/mwifiex/wmm.c b/drivers/net/wireless/mwifiex/wmm.c
index 94b6c74ba727..6d9738a5dc31 100644
--- a/drivers/net/wireless/mwifiex/wmm.c
+++ b/drivers/net/wireless/mwifiex/wmm.c
@@ -92,7 +92,7 @@ mwifiex_wmm_ac_debug_print(const struct ieee_types_wmm_ac_parameters *ac_param)
92 * The function also initializes the list with the provided RA. 92 * The function also initializes the list with the provided RA.
93 */ 93 */
94static struct mwifiex_ra_list_tbl * 94static struct mwifiex_ra_list_tbl *
95mwifiex_wmm_allocate_ralist_node(struct mwifiex_adapter *adapter, u8 *ra) 95mwifiex_wmm_allocate_ralist_node(struct mwifiex_adapter *adapter, const u8 *ra)
96{ 96{
97 struct mwifiex_ra_list_tbl *ra_list; 97 struct mwifiex_ra_list_tbl *ra_list;
98 98
@@ -139,8 +139,7 @@ static u8 mwifiex_get_random_ba_threshold(void)
139 * This function allocates and adds a RA list for all TIDs 139 * This function allocates and adds a RA list for all TIDs
140 * with the given RA. 140 * with the given RA.
141 */ 141 */
142void 142void mwifiex_ralist_add(struct mwifiex_private *priv, const u8 *ra)
143mwifiex_ralist_add(struct mwifiex_private *priv, u8 *ra)
144{ 143{
145 int i; 144 int i;
146 struct mwifiex_ra_list_tbl *ra_list; 145 struct mwifiex_ra_list_tbl *ra_list;
@@ -566,7 +565,7 @@ mwifiex_clean_txrx(struct mwifiex_private *priv)
566 */ 565 */
567static struct mwifiex_ra_list_tbl * 566static struct mwifiex_ra_list_tbl *
568mwifiex_wmm_get_ralist_node(struct mwifiex_private *priv, u8 tid, 567mwifiex_wmm_get_ralist_node(struct mwifiex_private *priv, u8 tid,
569 u8 *ra_addr) 568 const u8 *ra_addr)
570{ 569{
571 struct mwifiex_ra_list_tbl *ra_list; 570 struct mwifiex_ra_list_tbl *ra_list;
572 571
@@ -587,7 +586,8 @@ mwifiex_wmm_get_ralist_node(struct mwifiex_private *priv, u8 tid,
587 * retrieved. 586 * retrieved.
588 */ 587 */
589struct mwifiex_ra_list_tbl * 588struct mwifiex_ra_list_tbl *
590mwifiex_wmm_get_queue_raptr(struct mwifiex_private *priv, u8 tid, u8 *ra_addr) 589mwifiex_wmm_get_queue_raptr(struct mwifiex_private *priv, u8 tid,
590 const u8 *ra_addr)
591{ 591{
592 struct mwifiex_ra_list_tbl *ra_list; 592 struct mwifiex_ra_list_tbl *ra_list;
593 593
@@ -648,7 +648,7 @@ mwifiex_wmm_add_buf_txqueue(struct mwifiex_private *priv,
648 if (ntohs(eth_hdr->h_proto) == ETH_P_TDLS) 648 if (ntohs(eth_hdr->h_proto) == ETH_P_TDLS)
649 dev_dbg(adapter->dev, 649 dev_dbg(adapter->dev,
650 "TDLS setup packet for %pM. Don't block\n", ra); 650 "TDLS setup packet for %pM. Don't block\n", ra);
651 else 651 else if (memcmp(priv->cfg_bssid, ra, ETH_ALEN))
652 tdls_status = mwifiex_get_tdls_link_status(priv, ra); 652 tdls_status = mwifiex_get_tdls_link_status(priv, ra);
653 } 653 }
654 654
diff --git a/drivers/net/wireless/mwifiex/wmm.h b/drivers/net/wireless/mwifiex/wmm.h
index 83e42083ebff..eca56e371a57 100644
--- a/drivers/net/wireless/mwifiex/wmm.h
+++ b/drivers/net/wireless/mwifiex/wmm.h
@@ -99,7 +99,7 @@ mwifiex_wmm_is_ra_list_empty(struct list_head *ra_list_hhead)
99 99
100void mwifiex_wmm_add_buf_txqueue(struct mwifiex_private *priv, 100void mwifiex_wmm_add_buf_txqueue(struct mwifiex_private *priv,
101 struct sk_buff *skb); 101 struct sk_buff *skb);
102void mwifiex_ralist_add(struct mwifiex_private *priv, u8 *ra); 102void mwifiex_ralist_add(struct mwifiex_private *priv, const u8 *ra);
103void mwifiex_rotate_priolists(struct mwifiex_private *priv, 103void mwifiex_rotate_priolists(struct mwifiex_private *priv,
104 struct mwifiex_ra_list_tbl *ra, int tid); 104 struct mwifiex_ra_list_tbl *ra, int tid);
105 105
@@ -123,7 +123,8 @@ void mwifiex_wmm_setup_ac_downgrade(struct mwifiex_private *priv);
123int mwifiex_ret_wmm_get_status(struct mwifiex_private *priv, 123int mwifiex_ret_wmm_get_status(struct mwifiex_private *priv,
124 const struct host_cmd_ds_command *resp); 124 const struct host_cmd_ds_command *resp);
125struct mwifiex_ra_list_tbl * 125struct mwifiex_ra_list_tbl *
126mwifiex_wmm_get_queue_raptr(struct mwifiex_private *priv, u8 tid, u8 *ra_addr); 126mwifiex_wmm_get_queue_raptr(struct mwifiex_private *priv, u8 tid,
127 const u8 *ra_addr);
127u8 mwifiex_wmm_downgrade_tid(struct mwifiex_private *priv, u32 tid); 128u8 mwifiex_wmm_downgrade_tid(struct mwifiex_private *priv, u32 tid);
128 129
129#endif /* !_MWIFIEX_WMM_H_ */ 130#endif /* !_MWIFIEX_WMM_H_ */
diff --git a/drivers/net/wireless/orinoco/hw.c b/drivers/net/wireless/orinoco/hw.c
index 49300d04efdf..e27e32851f1e 100644
--- a/drivers/net/wireless/orinoco/hw.c
+++ b/drivers/net/wireless/orinoco/hw.c
@@ -988,8 +988,8 @@ int __orinoco_hw_setup_enc(struct orinoco_private *priv)
988 * tsc must be NULL or up to 8 bytes 988 * tsc must be NULL or up to 8 bytes
989 */ 989 */
990int __orinoco_hw_set_tkip_key(struct orinoco_private *priv, int key_idx, 990int __orinoco_hw_set_tkip_key(struct orinoco_private *priv, int key_idx,
991 int set_tx, u8 *key, u8 *rsc, size_t rsc_len, 991 int set_tx, const u8 *key, const u8 *rsc,
992 u8 *tsc, size_t tsc_len) 992 size_t rsc_len, const u8 *tsc, size_t tsc_len)
993{ 993{
994 struct { 994 struct {
995 __le16 idx; 995 __le16 idx;
diff --git a/drivers/net/wireless/orinoco/hw.h b/drivers/net/wireless/orinoco/hw.h
index 8f6831f4e328..466d1ede76f1 100644
--- a/drivers/net/wireless/orinoco/hw.h
+++ b/drivers/net/wireless/orinoco/hw.h
@@ -38,8 +38,8 @@ int __orinoco_hw_set_wap(struct orinoco_private *priv);
38int __orinoco_hw_setup_wepkeys(struct orinoco_private *priv); 38int __orinoco_hw_setup_wepkeys(struct orinoco_private *priv);
39int __orinoco_hw_setup_enc(struct orinoco_private *priv); 39int __orinoco_hw_setup_enc(struct orinoco_private *priv);
40int __orinoco_hw_set_tkip_key(struct orinoco_private *priv, int key_idx, 40int __orinoco_hw_set_tkip_key(struct orinoco_private *priv, int key_idx,
41 int set_tx, u8 *key, u8 *rsc, size_t rsc_len, 41 int set_tx, const u8 *key, const u8 *rsc,
42 u8 *tsc, size_t tsc_len); 42 size_t rsc_len, const u8 *tsc, size_t tsc_len);
43int orinoco_clear_tkip_key(struct orinoco_private *priv, int key_idx); 43int orinoco_clear_tkip_key(struct orinoco_private *priv, int key_idx);
44int __orinoco_hw_set_multicast_list(struct orinoco_private *priv, 44int __orinoco_hw_set_multicast_list(struct orinoco_private *priv,
45 struct net_device *dev, 45 struct net_device *dev,
diff --git a/drivers/net/wireless/orinoco/orinoco_usb.c b/drivers/net/wireless/orinoco/orinoco_usb.c
index f9805c9353d2..1cbb7835806f 100644
--- a/drivers/net/wireless/orinoco/orinoco_usb.c
+++ b/drivers/net/wireless/orinoco/orinoco_usb.c
@@ -1687,7 +1687,7 @@ static int ezusb_probe(struct usb_interface *interface,
1687 firmware.code = fw_entry->data; 1687 firmware.code = fw_entry->data;
1688 } 1688 }
1689 if (firmware.size && firmware.code) { 1689 if (firmware.size && firmware.code) {
1690 if (ezusb_firmware_download(upriv, &firmware)) 1690 if (ezusb_firmware_download(upriv, &firmware) < 0)
1691 goto error; 1691 goto error;
1692 } else { 1692 } else {
1693 err("No firmware to download"); 1693 err("No firmware to download");
diff --git a/drivers/net/wireless/orinoco/wext.c b/drivers/net/wireless/orinoco/wext.c
index b7a867b50b94..6abdaf0aa052 100644
--- a/drivers/net/wireless/orinoco/wext.c
+++ b/drivers/net/wireless/orinoco/wext.c
@@ -52,9 +52,9 @@ static int orinoco_set_key(struct orinoco_private *priv, int index,
52 priv->keys[index].seq_len = seq_len; 52 priv->keys[index].seq_len = seq_len;
53 53
54 if (key_len) 54 if (key_len)
55 memcpy(priv->keys[index].key, key, key_len); 55 memcpy((void *)priv->keys[index].key, key, key_len);
56 if (seq_len) 56 if (seq_len)
57 memcpy(priv->keys[index].seq, seq, seq_len); 57 memcpy((void *)priv->keys[index].seq, seq, seq_len);
58 58
59 switch (alg) { 59 switch (alg) {
60 case ORINOCO_ALG_TKIP: 60 case ORINOCO_ALG_TKIP:
diff --git a/drivers/net/wireless/rndis_wlan.c b/drivers/net/wireless/rndis_wlan.c
index 39d22a154341..d2a9a08210be 100644
--- a/drivers/net/wireless/rndis_wlan.c
+++ b/drivers/net/wireless/rndis_wlan.c
@@ -517,7 +517,7 @@ static int rndis_set_default_key(struct wiphy *wiphy, struct net_device *netdev,
517 u8 key_index, bool unicast, bool multicast); 517 u8 key_index, bool unicast, bool multicast);
518 518
519static int rndis_get_station(struct wiphy *wiphy, struct net_device *dev, 519static int rndis_get_station(struct wiphy *wiphy, struct net_device *dev,
520 u8 *mac, struct station_info *sinfo); 520 const u8 *mac, struct station_info *sinfo);
521 521
522static int rndis_dump_station(struct wiphy *wiphy, struct net_device *dev, 522static int rndis_dump_station(struct wiphy *wiphy, struct net_device *dev,
523 int idx, u8 *mac, struct station_info *sinfo); 523 int idx, u8 *mac, struct station_info *sinfo);
@@ -2490,7 +2490,7 @@ static void rndis_fill_station_info(struct usbnet *usbdev,
2490} 2490}
2491 2491
2492static int rndis_get_station(struct wiphy *wiphy, struct net_device *dev, 2492static int rndis_get_station(struct wiphy *wiphy, struct net_device *dev,
2493 u8 *mac, struct station_info *sinfo) 2493 const u8 *mac, struct station_info *sinfo)
2494{ 2494{
2495 struct rndis_wlan_private *priv = wiphy_priv(wiphy); 2495 struct rndis_wlan_private *priv = wiphy_priv(wiphy);
2496 struct usbnet *usbdev = priv->usbdev; 2496 struct usbnet *usbdev = priv->usbdev;
diff --git a/drivers/net/wireless/rsi/rsi_91x_mac80211.c b/drivers/net/wireless/rsi/rsi_91x_mac80211.c
index 84164747ace0..54aaeb09debf 100644
--- a/drivers/net/wireless/rsi/rsi_91x_mac80211.c
+++ b/drivers/net/wireless/rsi/rsi_91x_mac80211.c
@@ -656,6 +656,7 @@ static int rsi_mac80211_ampdu_action(struct ieee80211_hw *hw,
656 case IEEE80211_AMPDU_TX_START: 656 case IEEE80211_AMPDU_TX_START:
657 common->vif_info[ii].seq_start = seq_no; 657 common->vif_info[ii].seq_start = seq_no;
658 ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, tid); 658 ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, tid);
659 status = 0;
659 break; 660 break;
660 661
661 case IEEE80211_AMPDU_TX_STOP_CONT: 662 case IEEE80211_AMPDU_TX_STOP_CONT:
diff --git a/drivers/net/wireless/rt2x00/rt2x00usb.c b/drivers/net/wireless/rt2x00/rt2x00usb.c
index 10572452cc21..86c43d112a4b 100644
--- a/drivers/net/wireless/rt2x00/rt2x00usb.c
+++ b/drivers/net/wireless/rt2x00/rt2x00usb.c
@@ -68,6 +68,12 @@ int rt2x00usb_vendor_request(struct rt2x00_dev *rt2x00dev,
68 } 68 }
69 } 69 }
70 70
71 /* If the port is powered down, we get a -EPROTO error, and this
72 * leads to a endless loop. So just say that the device is gone.
73 */
74 if (status == -EPROTO)
75 clear_bit(DEVICE_STATE_PRESENT, &rt2x00dev->flags);
76
71 rt2x00_err(rt2x00dev, 77 rt2x00_err(rt2x00dev,
72 "Vendor Request 0x%02x failed for offset 0x%04x with error %d\n", 78 "Vendor Request 0x%02x failed for offset 0x%04x with error %d\n",
73 request, offset, status); 79 request, offset, status);
diff --git a/drivers/net/wireless/rtl818x/rtl8180/dev.c b/drivers/net/wireless/rtl818x/rtl8180/dev.c
index 50d69b13f984..2c1c02bafa10 100644
--- a/drivers/net/wireless/rtl818x/rtl8180/dev.c
+++ b/drivers/net/wireless/rtl818x/rtl8180/dev.c
@@ -284,6 +284,8 @@ static void rtl8180_handle_rx(struct ieee80211_hw *dev)
284 rx_status.band = dev->conf.chandef.chan->band; 284 rx_status.band = dev->conf.chandef.chan->band;
285 rx_status.mactime = tsft; 285 rx_status.mactime = tsft;
286 rx_status.flag |= RX_FLAG_MACTIME_START; 286 rx_status.flag |= RX_FLAG_MACTIME_START;
287 if (flags & RTL818X_RX_DESC_FLAG_SPLCP)
288 rx_status.flag |= RX_FLAG_SHORTPRE;
287 if (flags & RTL818X_RX_DESC_FLAG_CRC32_ERR) 289 if (flags & RTL818X_RX_DESC_FLAG_CRC32_ERR)
288 rx_status.flag |= RX_FLAG_FAILED_FCS_CRC; 290 rx_status.flag |= RX_FLAG_FAILED_FCS_CRC;
289 291
@@ -461,18 +463,23 @@ static void rtl8180_tx(struct ieee80211_hw *dev,
461 RTL818X_TX_DESC_FLAG_NO_ENC; 463 RTL818X_TX_DESC_FLAG_NO_ENC;
462 464
463 rc_flags = info->control.rates[0].flags; 465 rc_flags = info->control.rates[0].flags;
466
467 /* HW will perform RTS-CTS when only RTS flags is set.
468 * HW will perform CTS-to-self when both RTS and CTS flags are set.
469 * RTS rate and RTS duration will be used also for CTS-to-self.
470 */
464 if (rc_flags & IEEE80211_TX_RC_USE_RTS_CTS) { 471 if (rc_flags & IEEE80211_TX_RC_USE_RTS_CTS) {
465 tx_flags |= RTL818X_TX_DESC_FLAG_RTS; 472 tx_flags |= RTL818X_TX_DESC_FLAG_RTS;
466 tx_flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19; 473 tx_flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
474 rts_duration = ieee80211_rts_duration(dev, priv->vif,
475 skb->len, info);
467 } else if (rc_flags & IEEE80211_TX_RC_USE_CTS_PROTECT) { 476 } else if (rc_flags & IEEE80211_TX_RC_USE_CTS_PROTECT) {
468 tx_flags |= RTL818X_TX_DESC_FLAG_CTS; 477 tx_flags |= RTL818X_TX_DESC_FLAG_RTS | RTL818X_TX_DESC_FLAG_CTS;
469 tx_flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19; 478 tx_flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
479 rts_duration = ieee80211_ctstoself_duration(dev, priv->vif,
480 skb->len, info);
470 } 481 }
471 482
472 if (rc_flags & IEEE80211_TX_RC_USE_RTS_CTS)
473 rts_duration = ieee80211_rts_duration(dev, priv->vif, skb->len,
474 info);
475
476 if (priv->chip_family == RTL818X_CHIP_FAMILY_RTL8180) { 483 if (priv->chip_family == RTL818X_CHIP_FAMILY_RTL8180) {
477 unsigned int remainder; 484 unsigned int remainder;
478 485
diff --git a/drivers/net/wireless/rtl818x/rtl8187/dev.c b/drivers/net/wireless/rtl818x/rtl8187/dev.c
index 0ca17cda48fa..629ad8cfa17b 100644
--- a/drivers/net/wireless/rtl818x/rtl8187/dev.c
+++ b/drivers/net/wireless/rtl818x/rtl8187/dev.c
@@ -253,14 +253,21 @@ static void rtl8187_tx(struct ieee80211_hw *dev,
253 flags |= ieee80211_get_tx_rate(dev, info)->hw_value << 24; 253 flags |= ieee80211_get_tx_rate(dev, info)->hw_value << 24;
254 if (ieee80211_has_morefrags(tx_hdr->frame_control)) 254 if (ieee80211_has_morefrags(tx_hdr->frame_control))
255 flags |= RTL818X_TX_DESC_FLAG_MOREFRAG; 255 flags |= RTL818X_TX_DESC_FLAG_MOREFRAG;
256
257 /* HW will perform RTS-CTS when only RTS flags is set.
258 * HW will perform CTS-to-self when both RTS and CTS flags are set.
259 * RTS rate and RTS duration will be used also for CTS-to-self.
260 */
256 if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_RTS_CTS) { 261 if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_RTS_CTS) {
257 flags |= RTL818X_TX_DESC_FLAG_RTS; 262 flags |= RTL818X_TX_DESC_FLAG_RTS;
258 flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19; 263 flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
259 rts_dur = ieee80211_rts_duration(dev, priv->vif, 264 rts_dur = ieee80211_rts_duration(dev, priv->vif,
260 skb->len, info); 265 skb->len, info);
261 } else if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_CTS_PROTECT) { 266 } else if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_CTS_PROTECT) {
262 flags |= RTL818X_TX_DESC_FLAG_CTS; 267 flags |= RTL818X_TX_DESC_FLAG_RTS | RTL818X_TX_DESC_FLAG_CTS;
263 flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19; 268 flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
269 rts_dur = ieee80211_ctstoself_duration(dev, priv->vif,
270 skb->len, info);
264 } 271 }
265 272
266 if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) { 273 if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) {
@@ -381,6 +388,8 @@ static void rtl8187_rx_cb(struct urb *urb)
381 rx_status.freq = dev->conf.chandef.chan->center_freq; 388 rx_status.freq = dev->conf.chandef.chan->center_freq;
382 rx_status.band = dev->conf.chandef.chan->band; 389 rx_status.band = dev->conf.chandef.chan->band;
383 rx_status.flag |= RX_FLAG_MACTIME_START; 390 rx_status.flag |= RX_FLAG_MACTIME_START;
391 if (flags & RTL818X_RX_DESC_FLAG_SPLCP)
392 rx_status.flag |= RX_FLAG_SHORTPRE;
384 if (flags & RTL818X_RX_DESC_FLAG_CRC32_ERR) 393 if (flags & RTL818X_RX_DESC_FLAG_CRC32_ERR)
385 rx_status.flag |= RX_FLAG_FAILED_FCS_CRC; 394 rx_status.flag |= RX_FLAG_FAILED_FCS_CRC;
386 memcpy(IEEE80211_SKB_RXCB(skb), &rx_status, sizeof(rx_status)); 395 memcpy(IEEE80211_SKB_RXCB(skb), &rx_status, sizeof(rx_status));
diff --git a/drivers/net/wireless/rtlwifi/rtl8188ee/hw.c b/drivers/net/wireless/rtlwifi/rtl8188ee/hw.c
index 94cd9df98381..b14cf5a10f44 100644
--- a/drivers/net/wireless/rtlwifi/rtl8188ee/hw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8188ee/hw.c
@@ -2515,23 +2515,3 @@ void rtl88ee_suspend(struct ieee80211_hw *hw)
2515void rtl88ee_resume(struct ieee80211_hw *hw) 2515void rtl88ee_resume(struct ieee80211_hw *hw)
2516{ 2516{
2517} 2517}
2518
2519/* Turn on AAP (RCR:bit 0) for promicuous mode. */
2520void rtl88ee_allow_all_destaddr(struct ieee80211_hw *hw,
2521 bool allow_all_da, bool write_into_reg)
2522{
2523 struct rtl_priv *rtlpriv = rtl_priv(hw);
2524 struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
2525
2526 if (allow_all_da) /* Set BIT0 */
2527 rtlpci->receive_config |= RCR_AAP;
2528 else /* Clear BIT0 */
2529 rtlpci->receive_config &= ~RCR_AAP;
2530
2531 if (write_into_reg)
2532 rtl_write_dword(rtlpriv, REG_RCR, rtlpci->receive_config);
2533
2534 RT_TRACE(rtlpriv, COMP_TURBO | COMP_INIT, DBG_LOUD,
2535 "receive_config = 0x%08X, write_into_reg =%d\n",
2536 rtlpci->receive_config, write_into_reg);
2537}
diff --git a/drivers/net/wireless/rtlwifi/rtl8188ee/hw.h b/drivers/net/wireless/rtlwifi/rtl8188ee/hw.h
index b4460a41bd01..1850fde881b5 100644
--- a/drivers/net/wireless/rtlwifi/rtl8188ee/hw.h
+++ b/drivers/net/wireless/rtlwifi/rtl8188ee/hw.h
@@ -61,8 +61,6 @@ void rtl8188ee_bt_reg_init(struct ieee80211_hw *hw);
61void rtl8188ee_bt_hw_init(struct ieee80211_hw *hw); 61void rtl8188ee_bt_hw_init(struct ieee80211_hw *hw);
62void rtl88ee_suspend(struct ieee80211_hw *hw); 62void rtl88ee_suspend(struct ieee80211_hw *hw);
63void rtl88ee_resume(struct ieee80211_hw *hw); 63void rtl88ee_resume(struct ieee80211_hw *hw);
64void rtl88ee_allow_all_destaddr(struct ieee80211_hw *hw,
65 bool allow_all_da, bool write_into_reg);
66void rtl88ee_fw_clk_off_timer_callback(unsigned long data); 64void rtl88ee_fw_clk_off_timer_callback(unsigned long data);
67 65
68#endif 66#endif
diff --git a/drivers/net/wireless/rtlwifi/rtl8188ee/sw.c b/drivers/net/wireless/rtlwifi/rtl8188ee/sw.c
index 347af1e4f438..842d69349a37 100644
--- a/drivers/net/wireless/rtlwifi/rtl8188ee/sw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8188ee/sw.c
@@ -93,6 +93,7 @@ int rtl88e_init_sw_vars(struct ieee80211_hw *hw)
93 u8 tid; 93 u8 tid;
94 94
95 rtl8188ee_bt_reg_init(hw); 95 rtl8188ee_bt_reg_init(hw);
96 rtlpci->msi_support = rtlpriv->cfg->mod_params->msi_support;
96 97
97 rtlpriv->dm.dm_initialgain_enable = 1; 98 rtlpriv->dm.dm_initialgain_enable = 1;
98 rtlpriv->dm.dm_flag = 0; 99 rtlpriv->dm.dm_flag = 0;
@@ -254,7 +255,6 @@ static struct rtl_hal_ops rtl8188ee_hal_ops = {
254 .enable_hw_sec = rtl88ee_enable_hw_security_config, 255 .enable_hw_sec = rtl88ee_enable_hw_security_config,
255 .set_key = rtl88ee_set_key, 256 .set_key = rtl88ee_set_key,
256 .init_sw_leds = rtl88ee_init_sw_leds, 257 .init_sw_leds = rtl88ee_init_sw_leds,
257 .allow_all_destaddr = rtl88ee_allow_all_destaddr,
258 .get_bbreg = rtl88e_phy_query_bb_reg, 258 .get_bbreg = rtl88e_phy_query_bb_reg,
259 .set_bbreg = rtl88e_phy_set_bb_reg, 259 .set_bbreg = rtl88e_phy_set_bb_reg,
260 .get_rfreg = rtl88e_phy_query_rf_reg, 260 .get_rfreg = rtl88e_phy_query_rf_reg,
@@ -266,6 +266,7 @@ static struct rtl_mod_params rtl88ee_mod_params = {
266 .inactiveps = true, 266 .inactiveps = true,
267 .swctrl_lps = false, 267 .swctrl_lps = false,
268 .fwctrl_lps = true, 268 .fwctrl_lps = true,
269 .msi_support = false,
269 .debug = DBG_EMERG, 270 .debug = DBG_EMERG,
270}; 271};
271 272
@@ -382,10 +383,12 @@ module_param_named(debug, rtl88ee_mod_params.debug, int, 0444);
382module_param_named(ips, rtl88ee_mod_params.inactiveps, bool, 0444); 383module_param_named(ips, rtl88ee_mod_params.inactiveps, bool, 0444);
383module_param_named(swlps, rtl88ee_mod_params.swctrl_lps, bool, 0444); 384module_param_named(swlps, rtl88ee_mod_params.swctrl_lps, bool, 0444);
384module_param_named(fwlps, rtl88ee_mod_params.fwctrl_lps, bool, 0444); 385module_param_named(fwlps, rtl88ee_mod_params.fwctrl_lps, bool, 0444);
386module_param_named(msi, rtl88ee_mod_params.msi_support, bool, 0444);
385MODULE_PARM_DESC(swenc, "Set to 1 for software crypto (default 0)\n"); 387MODULE_PARM_DESC(swenc, "Set to 1 for software crypto (default 0)\n");
386MODULE_PARM_DESC(ips, "Set to 0 to not use link power save (default 1)\n"); 388MODULE_PARM_DESC(ips, "Set to 0 to not use link power save (default 1)\n");
387MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 0)\n"); 389MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 0)\n");
388MODULE_PARM_DESC(fwlps, "Set to 1 to use FW control power save (default 1)\n"); 390MODULE_PARM_DESC(fwlps, "Set to 1 to use FW control power save (default 1)\n");
391MODULE_PARM_DESC(msi, "Set to 1 to use MSI interrupts mode (default 0)\n");
389MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)"); 392MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
390 393
391static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume); 394static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume);
diff --git a/drivers/net/wireless/rtlwifi/rtl8192ce/hw.c b/drivers/net/wireless/rtlwifi/rtl8192ce/hw.c
index 55adf043aef7..cdecb0fd4d8e 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192ce/hw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8192ce/hw.c
@@ -2423,24 +2423,3 @@ void rtl92ce_suspend(struct ieee80211_hw *hw)
2423void rtl92ce_resume(struct ieee80211_hw *hw) 2423void rtl92ce_resume(struct ieee80211_hw *hw)
2424{ 2424{
2425} 2425}
2426
2427/* Turn on AAP (RCR:bit 0) for promicuous mode. */
2428void rtl92ce_allow_all_destaddr(struct ieee80211_hw *hw,
2429 bool allow_all_da, bool write_into_reg)
2430{
2431 struct rtl_priv *rtlpriv = rtl_priv(hw);
2432 struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
2433
2434 if (allow_all_da) {/* Set BIT0 */
2435 rtlpci->receive_config |= RCR_AAP;
2436 } else {/* Clear BIT0 */
2437 rtlpci->receive_config &= ~RCR_AAP;
2438 }
2439
2440 if (write_into_reg)
2441 rtl_write_dword(rtlpriv, REG_RCR, rtlpci->receive_config);
2442
2443 RT_TRACE(rtlpriv, COMP_TURBO | COMP_INIT, DBG_LOUD,
2444 "receive_config=0x%08X, write_into_reg=%d\n",
2445 rtlpci->receive_config, write_into_reg);
2446}
diff --git a/drivers/net/wireless/rtlwifi/rtl8192ce/hw.h b/drivers/net/wireless/rtlwifi/rtl8192ce/hw.h
index 2d063b0c7760..5533070f266c 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192ce/hw.h
+++ b/drivers/net/wireless/rtlwifi/rtl8192ce/hw.h
@@ -76,7 +76,5 @@ void rtl8192ce_bt_reg_init(struct ieee80211_hw *hw);
76void rtl8192ce_bt_hw_init(struct ieee80211_hw *hw); 76void rtl8192ce_bt_hw_init(struct ieee80211_hw *hw);
77void rtl92ce_suspend(struct ieee80211_hw *hw); 77void rtl92ce_suspend(struct ieee80211_hw *hw);
78void rtl92ce_resume(struct ieee80211_hw *hw); 78void rtl92ce_resume(struct ieee80211_hw *hw);
79void rtl92ce_allow_all_destaddr(struct ieee80211_hw *hw,
80 bool allow_all_da, bool write_into_reg);
81 79
82#endif 80#endif
diff --git a/drivers/net/wireless/rtlwifi/rtl8192ce/sw.c b/drivers/net/wireless/rtlwifi/rtl8192ce/sw.c
index b790320d2030..12f21f4073e8 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192ce/sw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8192ce/sw.c
@@ -229,7 +229,6 @@ static struct rtl_hal_ops rtl8192ce_hal_ops = {
229 .enable_hw_sec = rtl92ce_enable_hw_security_config, 229 .enable_hw_sec = rtl92ce_enable_hw_security_config,
230 .set_key = rtl92ce_set_key, 230 .set_key = rtl92ce_set_key,
231 .init_sw_leds = rtl92ce_init_sw_leds, 231 .init_sw_leds = rtl92ce_init_sw_leds,
232 .allow_all_destaddr = rtl92ce_allow_all_destaddr,
233 .get_bbreg = rtl92c_phy_query_bb_reg, 232 .get_bbreg = rtl92c_phy_query_bb_reg,
234 .set_bbreg = rtl92c_phy_set_bb_reg, 233 .set_bbreg = rtl92c_phy_set_bb_reg,
235 .set_rfreg = rtl92ce_phy_set_rf_reg, 234 .set_rfreg = rtl92ce_phy_set_rf_reg,
diff --git a/drivers/net/wireless/rtlwifi/rtl8192cu/hw.c b/drivers/net/wireless/rtlwifi/rtl8192cu/hw.c
index 07cb06da6729..a903c2671b4d 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192cu/hw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8192cu/hw.c
@@ -511,7 +511,7 @@ static int _rtl92cu_init_power_on(struct ieee80211_hw *hw)
511 pr_info("MAC auto ON okay!\n"); 511 pr_info("MAC auto ON okay!\n");
512 break; 512 break;
513 } 513 }
514 if (pollingCount++ > 100) { 514 if (pollingCount++ > 1000) {
515 RT_TRACE(rtlpriv, COMP_INIT, DBG_EMERG, 515 RT_TRACE(rtlpriv, COMP_INIT, DBG_EMERG,
516 "Failed to polling REG_APS_FSMCO[APFM_ONMAC] done!\n"); 516 "Failed to polling REG_APS_FSMCO[APFM_ONMAC] done!\n");
517 return -ENODEV; 517 return -ENODEV;
diff --git a/drivers/net/wireless/rtlwifi/rtl8192se/hw.c b/drivers/net/wireless/rtlwifi/rtl8192se/hw.c
index 9098558d916d..1c7101bcd790 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192se/hw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8192se/hw.c
@@ -2544,23 +2544,3 @@ void rtl92se_resume(struct ieee80211_hw *hw)
2544 pci_write_config_dword(rtlpci->pdev, 0x40, 2544 pci_write_config_dword(rtlpci->pdev, 0x40,
2545 val & 0xffff00ff); 2545 val & 0xffff00ff);
2546} 2546}
2547
2548/* Turn on AAP (RCR:bit 0) for promicuous mode. */
2549void rtl92se_allow_all_destaddr(struct ieee80211_hw *hw,
2550 bool allow_all_da, bool write_into_reg)
2551{
2552 struct rtl_priv *rtlpriv = rtl_priv(hw);
2553 struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
2554
2555 if (allow_all_da) /* Set BIT0 */
2556 rtlpci->receive_config |= RCR_AAP;
2557 else /* Clear BIT0 */
2558 rtlpci->receive_config &= ~RCR_AAP;
2559
2560 if (write_into_reg)
2561 rtl_write_dword(rtlpriv, RCR, rtlpci->receive_config);
2562
2563 RT_TRACE(rtlpriv, COMP_TURBO | COMP_INIT, DBG_LOUD,
2564 "receive_config=0x%08X, write_into_reg=%d\n",
2565 rtlpci->receive_config, write_into_reg);
2566}
diff --git a/drivers/net/wireless/rtlwifi/rtl8192se/hw.h b/drivers/net/wireless/rtlwifi/rtl8192se/hw.h
index da48aa8cbe6f..4cacee10f31e 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192se/hw.h
+++ b/drivers/net/wireless/rtlwifi/rtl8192se/hw.h
@@ -74,7 +74,5 @@ void rtl92se_set_key(struct ieee80211_hw *hw,
74 u8 enc_algo, bool is_wepkey, bool clear_all); 74 u8 enc_algo, bool is_wepkey, bool clear_all);
75void rtl92se_suspend(struct ieee80211_hw *hw); 75void rtl92se_suspend(struct ieee80211_hw *hw);
76void rtl92se_resume(struct ieee80211_hw *hw); 76void rtl92se_resume(struct ieee80211_hw *hw);
77void rtl92se_allow_all_destaddr(struct ieee80211_hw *hw,
78 bool allow_all_da, bool write_into_reg);
79 77
80#endif 78#endif
diff --git a/drivers/net/wireless/rtlwifi/rtl8192se/sw.c b/drivers/net/wireless/rtlwifi/rtl8192se/sw.c
index 2e8e6f8d2d51..1bff2a0f7600 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192se/sw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8192se/sw.c
@@ -290,7 +290,6 @@ static struct rtl_hal_ops rtl8192se_hal_ops = {
290 .enable_hw_sec = rtl92se_enable_hw_security_config, 290 .enable_hw_sec = rtl92se_enable_hw_security_config,
291 .set_key = rtl92se_set_key, 291 .set_key = rtl92se_set_key,
292 .init_sw_leds = rtl92se_init_sw_leds, 292 .init_sw_leds = rtl92se_init_sw_leds,
293 .allow_all_destaddr = rtl92se_allow_all_destaddr,
294 .get_bbreg = rtl92s_phy_query_bb_reg, 293 .get_bbreg = rtl92s_phy_query_bb_reg,
295 .set_bbreg = rtl92s_phy_set_bb_reg, 294 .set_bbreg = rtl92s_phy_set_bb_reg,
296 .get_rfreg = rtl92s_phy_query_rf_reg, 295 .get_rfreg = rtl92s_phy_query_rf_reg,
diff --git a/drivers/net/wireless/rtlwifi/rtl8723ae/hw.c b/drivers/net/wireless/rtlwifi/rtl8723ae/hw.c
index 65c9e80e1f78..87f69166a7ed 100644
--- a/drivers/net/wireless/rtlwifi/rtl8723ae/hw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8723ae/hw.c
@@ -2383,24 +2383,3 @@ void rtl8723ae_suspend(struct ieee80211_hw *hw)
2383void rtl8723ae_resume(struct ieee80211_hw *hw) 2383void rtl8723ae_resume(struct ieee80211_hw *hw)
2384{ 2384{
2385} 2385}
2386
2387/* Turn on AAP (RCR:bit 0) for promicuous mode. */
2388void rtl8723ae_allow_all_destaddr(struct ieee80211_hw *hw,
2389 bool allow_all_da, bool write_into_reg)
2390{
2391 struct rtl_priv *rtlpriv = rtl_priv(hw);
2392 struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
2393
2394 if (allow_all_da) /* Set BIT0 */
2395 rtlpci->receive_config |= RCR_AAP;
2396 else /* Clear BIT0 */
2397 rtlpci->receive_config &= ~RCR_AAP;
2398
2399 if (write_into_reg)
2400 rtl_write_dword(rtlpriv, REG_RCR, rtlpci->receive_config);
2401
2402
2403 RT_TRACE(rtlpriv, COMP_TURBO | COMP_INIT, DBG_LOUD,
2404 "receive_config=0x%08X, write_into_reg=%d\n",
2405 rtlpci->receive_config, write_into_reg);
2406}
diff --git a/drivers/net/wireless/rtlwifi/rtl8723ae/hw.h b/drivers/net/wireless/rtlwifi/rtl8723ae/hw.h
index 6fa24f79b1d7..d3bc39fb27a5 100644
--- a/drivers/net/wireless/rtlwifi/rtl8723ae/hw.h
+++ b/drivers/net/wireless/rtlwifi/rtl8723ae/hw.h
@@ -67,7 +67,5 @@ void rtl8723ae_bt_reg_init(struct ieee80211_hw *hw);
67void rtl8723ae_bt_hw_init(struct ieee80211_hw *hw); 67void rtl8723ae_bt_hw_init(struct ieee80211_hw *hw);
68void rtl8723ae_suspend(struct ieee80211_hw *hw); 68void rtl8723ae_suspend(struct ieee80211_hw *hw);
69void rtl8723ae_resume(struct ieee80211_hw *hw); 69void rtl8723ae_resume(struct ieee80211_hw *hw);
70void rtl8723ae_allow_all_destaddr(struct ieee80211_hw *hw,
71 bool allow_all_da, bool write_into_reg);
72 70
73#endif 71#endif
diff --git a/drivers/net/wireless/rtlwifi/rtl8723ae/sw.c b/drivers/net/wireless/rtlwifi/rtl8723ae/sw.c
index 1087a3bd07fa..73cba1eec8cf 100644
--- a/drivers/net/wireless/rtlwifi/rtl8723ae/sw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8723ae/sw.c
@@ -238,7 +238,6 @@ static struct rtl_hal_ops rtl8723ae_hal_ops = {
238 .enable_hw_sec = rtl8723ae_enable_hw_security_config, 238 .enable_hw_sec = rtl8723ae_enable_hw_security_config,
239 .set_key = rtl8723ae_set_key, 239 .set_key = rtl8723ae_set_key,
240 .init_sw_leds = rtl8723ae_init_sw_leds, 240 .init_sw_leds = rtl8723ae_init_sw_leds,
241 .allow_all_destaddr = rtl8723ae_allow_all_destaddr,
242 .get_bbreg = rtl8723_phy_query_bb_reg, 241 .get_bbreg = rtl8723_phy_query_bb_reg,
243 .set_bbreg = rtl8723_phy_set_bb_reg, 242 .set_bbreg = rtl8723_phy_set_bb_reg,
244 .get_rfreg = rtl8723ae_phy_query_rf_reg, 243 .get_rfreg = rtl8723ae_phy_query_rf_reg,
diff --git a/drivers/net/wireless/rtlwifi/rtl8723be/hw.c b/drivers/net/wireless/rtlwifi/rtl8723be/hw.c
index 0fdf0909321f..3d555495b453 100644
--- a/drivers/net/wireless/rtlwifi/rtl8723be/hw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8723be/hw.c
@@ -2501,23 +2501,3 @@ void rtl8723be_suspend(struct ieee80211_hw *hw)
2501void rtl8723be_resume(struct ieee80211_hw *hw) 2501void rtl8723be_resume(struct ieee80211_hw *hw)
2502{ 2502{
2503} 2503}
2504
2505/* Turn on AAP (RCR:bit 0) for promicuous mode. */
2506void rtl8723be_allow_all_destaddr(struct ieee80211_hw *hw, bool allow_all_da,
2507 bool write_into_reg)
2508{
2509 struct rtl_priv *rtlpriv = rtl_priv(hw);
2510 struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
2511
2512 if (allow_all_da) /* Set BIT0 */
2513 rtlpci->receive_config |= RCR_AAP;
2514 else /* Clear BIT0 */
2515 rtlpci->receive_config &= ~RCR_AAP;
2516
2517 if (write_into_reg)
2518 rtl_write_dword(rtlpriv, REG_RCR, rtlpci->receive_config);
2519
2520 RT_TRACE(rtlpriv, COMP_TURBO | COMP_INIT, DBG_LOUD,
2521 "receive_config = 0x%08X, write_into_reg =%d\n",
2522 rtlpci->receive_config, write_into_reg);
2523}
diff --git a/drivers/net/wireless/rtlwifi/rtl8723be/hw.h b/drivers/net/wireless/rtlwifi/rtl8723be/hw.h
index b7449a9b57e4..64c7551af6b7 100644
--- a/drivers/net/wireless/rtlwifi/rtl8723be/hw.h
+++ b/drivers/net/wireless/rtlwifi/rtl8723be/hw.h
@@ -59,6 +59,4 @@ void rtl8723be_bt_reg_init(struct ieee80211_hw *hw);
59void rtl8723be_bt_hw_init(struct ieee80211_hw *hw); 59void rtl8723be_bt_hw_init(struct ieee80211_hw *hw);
60void rtl8723be_suspend(struct ieee80211_hw *hw); 60void rtl8723be_suspend(struct ieee80211_hw *hw);
61void rtl8723be_resume(struct ieee80211_hw *hw); 61void rtl8723be_resume(struct ieee80211_hw *hw);
62void rtl8723be_allow_all_destaddr(struct ieee80211_hw *hw, bool allow_all_da,
63 bool write_into_reg);
64#endif 62#endif
diff --git a/drivers/net/wireless/rtlwifi/rtl8723be/sw.c b/drivers/net/wireless/rtlwifi/rtl8723be/sw.c
index a07213645da0..ff12bf41644b 100644
--- a/drivers/net/wireless/rtlwifi/rtl8723be/sw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8723be/sw.c
@@ -92,7 +92,7 @@ int rtl8723be_init_sw_vars(struct ieee80211_hw *hw)
92 struct rtl_mac *mac = rtl_mac(rtl_priv(hw)); 92 struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
93 93
94 rtl8723be_bt_reg_init(hw); 94 rtl8723be_bt_reg_init(hw);
95 rtlpci->msi_support = false; 95 rtlpci->msi_support = rtlpriv->cfg->mod_params->msi_support;
96 rtlpriv->btcoexist.btc_ops = rtl_btc_get_ops_pointer(); 96 rtlpriv->btcoexist.btc_ops = rtl_btc_get_ops_pointer();
97 97
98 rtlpriv->dm.dm_initialgain_enable = 1; 98 rtlpriv->dm.dm_initialgain_enable = 1;
@@ -253,6 +253,7 @@ static struct rtl_mod_params rtl8723be_mod_params = {
253 .inactiveps = true, 253 .inactiveps = true,
254 .swctrl_lps = false, 254 .swctrl_lps = false,
255 .fwctrl_lps = true, 255 .fwctrl_lps = true,
256 .msi_support = false,
256 .debug = DBG_EMERG, 257 .debug = DBG_EMERG,
257}; 258};
258 259
@@ -365,9 +366,11 @@ module_param_named(debug, rtl8723be_mod_params.debug, int, 0444);
365module_param_named(ips, rtl8723be_mod_params.inactiveps, bool, 0444); 366module_param_named(ips, rtl8723be_mod_params.inactiveps, bool, 0444);
366module_param_named(swlps, rtl8723be_mod_params.swctrl_lps, bool, 0444); 367module_param_named(swlps, rtl8723be_mod_params.swctrl_lps, bool, 0444);
367module_param_named(fwlps, rtl8723be_mod_params.fwctrl_lps, bool, 0444); 368module_param_named(fwlps, rtl8723be_mod_params.fwctrl_lps, bool, 0444);
369module_param_named(msi, rtl8723be_mod_params.msi_support, bool, 0444);
368MODULE_PARM_DESC(swenc, "using hardware crypto (default 0 [hardware])\n"); 370MODULE_PARM_DESC(swenc, "using hardware crypto (default 0 [hardware])\n");
369MODULE_PARM_DESC(ips, "using no link power save (default 1 is open)\n"); 371MODULE_PARM_DESC(ips, "using no link power save (default 1 is open)\n");
370MODULE_PARM_DESC(fwlps, "using linked fw control power save (default 1 is open)\n"); 372MODULE_PARM_DESC(fwlps, "using linked fw control power save (default 1 is open)\n");
373MODULE_PARM_DESC(msi, "Set to 1 to use MSI interrupts mode (default 0)\n");
371MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)"); 374MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
372 375
373static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume); 376static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume);
diff --git a/drivers/net/wireless/rtlwifi/wifi.h b/drivers/net/wireless/rtlwifi/wifi.h
index 6965afdf572a..407a7936d364 100644
--- a/drivers/net/wireless/rtlwifi/wifi.h
+++ b/drivers/net/wireless/rtlwifi/wifi.h
@@ -1960,8 +1960,6 @@ struct rtl_hal_ops {
1960 u32 regaddr, u32 bitmask); 1960 u32 regaddr, u32 bitmask);
1961 void (*set_rfreg) (struct ieee80211_hw *hw, enum radio_path rfpath, 1961 void (*set_rfreg) (struct ieee80211_hw *hw, enum radio_path rfpath,
1962 u32 regaddr, u32 bitmask, u32 data); 1962 u32 regaddr, u32 bitmask, u32 data);
1963 void (*allow_all_destaddr)(struct ieee80211_hw *hw,
1964 bool allow_all_da, bool write_into_reg);
1965 void (*linked_set_reg) (struct ieee80211_hw *hw); 1963 void (*linked_set_reg) (struct ieee80211_hw *hw);
1966 void (*chk_switch_dmdp) (struct ieee80211_hw *hw); 1964 void (*chk_switch_dmdp) (struct ieee80211_hw *hw);
1967 void (*dualmac_easy_concurrent) (struct ieee80211_hw *hw); 1965 void (*dualmac_easy_concurrent) (struct ieee80211_hw *hw);
@@ -2030,6 +2028,10 @@ struct rtl_mod_params {
2030 2028
2031 /* default: 1 = using linked fw power save */ 2029 /* default: 1 = using linked fw power save */
2032 bool fwctrl_lps; 2030 bool fwctrl_lps;
2031
2032 /* default: 0 = not using MSI interrupts mode */
2033 /* submodules should set their own defalut value */
2034 bool msi_support;
2033}; 2035};
2034 2036
2035struct rtl_hal_usbint_cfg { 2037struct rtl_hal_usbint_cfg {
diff --git a/drivers/net/wireless/ti/wl1251/acx.c b/drivers/net/wireless/ti/wl1251/acx.c
index 5a4ec56c83d0..5695628757ee 100644
--- a/drivers/net/wireless/ti/wl1251/acx.c
+++ b/drivers/net/wireless/ti/wl1251/acx.c
@@ -2,7 +2,6 @@
2 2
3#include <linux/module.h> 3#include <linux/module.h>
4#include <linux/slab.h> 4#include <linux/slab.h>
5#include <linux/crc7.h>
6 5
7#include "wl1251.h" 6#include "wl1251.h"
8#include "reg.h" 7#include "reg.h"
diff --git a/drivers/net/wireless/ti/wl1251/cmd.c b/drivers/net/wireless/ti/wl1251/cmd.c
index bf1fa18b9786..ede31f048ef9 100644
--- a/drivers/net/wireless/ti/wl1251/cmd.c
+++ b/drivers/net/wireless/ti/wl1251/cmd.c
@@ -2,7 +2,6 @@
2 2
3#include <linux/module.h> 3#include <linux/module.h>
4#include <linux/slab.h> 4#include <linux/slab.h>
5#include <linux/crc7.h>
6#include <linux/etherdevice.h> 5#include <linux/etherdevice.h>
7 6
8#include "wl1251.h" 7#include "wl1251.h"
diff --git a/drivers/net/wireless/ti/wl1251/event.c b/drivers/net/wireless/ti/wl1251/event.c
index db0105313745..c98630394a1a 100644
--- a/drivers/net/wireless/ti/wl1251/event.c
+++ b/drivers/net/wireless/ti/wl1251/event.c
@@ -124,11 +124,12 @@ static int wl1251_event_process(struct wl1251 *wl, struct event_mailbox *mbox)
124 return ret; 124 return ret;
125 } 125 }
126 126
127 if (wl->vif && vector & SYNCHRONIZATION_TIMEOUT_EVENT_ID) { 127 if (vector & SYNCHRONIZATION_TIMEOUT_EVENT_ID) {
128 wl1251_debug(DEBUG_EVENT, "SYNCHRONIZATION_TIMEOUT_EVENT"); 128 wl1251_debug(DEBUG_EVENT, "SYNCHRONIZATION_TIMEOUT_EVENT");
129 129
130 /* indicate to the stack, that beacons have been lost */ 130 /* indicate to the stack, that beacons have been lost */
131 ieee80211_beacon_loss(wl->vif); 131 if (wl->vif && wl->vif->type == NL80211_IFTYPE_STATION)
132 ieee80211_beacon_loss(wl->vif);
132 } 133 }
133 134
134 if (vector & REGAINED_BSS_EVENT_ID) { 135 if (vector & REGAINED_BSS_EVENT_ID) {
diff --git a/drivers/net/wireless/ti/wl1251/main.c b/drivers/net/wireless/ti/wl1251/main.c
index 757e25784a8a..4e782f18ae34 100644
--- a/drivers/net/wireless/ti/wl1251/main.c
+++ b/drivers/net/wireless/ti/wl1251/main.c
@@ -550,6 +550,34 @@ static void wl1251_op_remove_interface(struct ieee80211_hw *hw,
550 mutex_unlock(&wl->mutex); 550 mutex_unlock(&wl->mutex);
551} 551}
552 552
553static int wl1251_build_null_data(struct wl1251 *wl)
554{
555 struct sk_buff *skb = NULL;
556 int size;
557 void *ptr;
558 int ret = -ENOMEM;
559
560 if (wl->bss_type == BSS_TYPE_IBSS) {
561 size = sizeof(struct wl12xx_null_data_template);
562 ptr = NULL;
563 } else {
564 skb = ieee80211_nullfunc_get(wl->hw, wl->vif);
565 if (!skb)
566 goto out;
567 size = skb->len;
568 ptr = skb->data;
569 }
570
571 ret = wl1251_cmd_template_set(wl, CMD_NULL_DATA, ptr, size);
572
573out:
574 dev_kfree_skb(skb);
575 if (ret)
576 wl1251_warning("cmd buld null data failed: %d", ret);
577
578 return ret;
579}
580
553static int wl1251_build_qos_null_data(struct wl1251 *wl) 581static int wl1251_build_qos_null_data(struct wl1251 *wl)
554{ 582{
555 struct ieee80211_qos_hdr template; 583 struct ieee80211_qos_hdr template;
@@ -687,16 +715,6 @@ static int wl1251_op_config(struct ieee80211_hw *hw, u32 changed)
687 wl->power_level = conf->power_level; 715 wl->power_level = conf->power_level;
688 } 716 }
689 717
690 /*
691 * Tell stack that connection is lost because hw encryption isn't
692 * supported in monitor mode.
693 * This requires temporary enabling of the hw connection monitor flag
694 */
695 if ((changed & IEEE80211_CONF_CHANGE_MONITOR) && wl->vif) {
696 wl->hw->flags |= IEEE80211_HW_CONNECTION_MONITOR;
697 ieee80211_connection_loss(wl->vif);
698 }
699
700out_sleep: 718out_sleep:
701 wl1251_ps_elp_sleep(wl); 719 wl1251_ps_elp_sleep(wl);
702 720
@@ -1103,24 +1121,19 @@ static void wl1251_op_bss_info_changed(struct ieee80211_hw *hw,
1103 wl->rssi_thold = bss_conf->cqm_rssi_thold; 1121 wl->rssi_thold = bss_conf->cqm_rssi_thold;
1104 } 1122 }
1105 1123
1106 if (changed & BSS_CHANGED_BSSID) { 1124 if ((changed & BSS_CHANGED_BSSID) &&
1125 memcmp(wl->bssid, bss_conf->bssid, ETH_ALEN)) {
1107 memcpy(wl->bssid, bss_conf->bssid, ETH_ALEN); 1126 memcpy(wl->bssid, bss_conf->bssid, ETH_ALEN);
1108 1127
1109 skb = ieee80211_nullfunc_get(wl->hw, wl->vif); 1128 if (!is_zero_ether_addr(wl->bssid)) {
1110 if (!skb) 1129 ret = wl1251_build_null_data(wl);
1111 goto out_sleep; 1130 if (ret < 0)
1112 1131 goto out_sleep;
1113 ret = wl1251_cmd_template_set(wl, CMD_NULL_DATA,
1114 skb->data, skb->len);
1115 dev_kfree_skb(skb);
1116 if (ret < 0)
1117 goto out_sleep;
1118 1132
1119 ret = wl1251_build_qos_null_data(wl); 1133 ret = wl1251_build_qos_null_data(wl);
1120 if (ret < 0) 1134 if (ret < 0)
1121 goto out; 1135 goto out_sleep;
1122 1136
1123 if (wl->bss_type != BSS_TYPE_IBSS) {
1124 ret = wl1251_join(wl, wl->bss_type, wl->channel, 1137 ret = wl1251_join(wl, wl->bss_type, wl->channel,
1125 wl->beacon_int, wl->dtim_period); 1138 wl->beacon_int, wl->dtim_period);
1126 if (ret < 0) 1139 if (ret < 0)
@@ -1129,9 +1142,6 @@ static void wl1251_op_bss_info_changed(struct ieee80211_hw *hw,
1129 } 1142 }
1130 1143
1131 if (changed & BSS_CHANGED_ASSOC) { 1144 if (changed & BSS_CHANGED_ASSOC) {
1132 /* Disable temporary enabled hw connection monitor flag */
1133 wl->hw->flags &= ~IEEE80211_HW_CONNECTION_MONITOR;
1134
1135 if (bss_conf->assoc) { 1145 if (bss_conf->assoc) {
1136 wl->beacon_int = bss_conf->beacon_int; 1146 wl->beacon_int = bss_conf->beacon_int;
1137 1147
@@ -1216,8 +1226,8 @@ static void wl1251_op_bss_info_changed(struct ieee80211_hw *hw,
1216 if (ret < 0) 1226 if (ret < 0)
1217 goto out_sleep; 1227 goto out_sleep;
1218 1228
1219 ret = wl1251_join(wl, wl->bss_type, wl->beacon_int, 1229 ret = wl1251_join(wl, wl->bss_type, wl->channel,
1220 wl->channel, wl->dtim_period); 1230 wl->beacon_int, wl->dtim_period);
1221 1231
1222 if (ret < 0) 1232 if (ret < 0)
1223 goto out_sleep; 1233 goto out_sleep;
diff --git a/drivers/net/wireless/ti/wl1251/spi.c b/drivers/net/wireless/ti/wl1251/spi.c
index b06d36d99362..a0aa8fa72392 100644
--- a/drivers/net/wireless/ti/wl1251/spi.c
+++ b/drivers/net/wireless/ti/wl1251/spi.c
@@ -23,6 +23,7 @@
23#include <linux/irq.h> 23#include <linux/irq.h>
24#include <linux/module.h> 24#include <linux/module.h>
25#include <linux/slab.h> 25#include <linux/slab.h>
26#include <linux/swab.h>
26#include <linux/crc7.h> 27#include <linux/crc7.h>
27#include <linux/spi/spi.h> 28#include <linux/spi/spi.h>
28#include <linux/wl12xx.h> 29#include <linux/wl12xx.h>
@@ -83,47 +84,44 @@ static void wl1251_spi_reset(struct wl1251 *wl)
83 84
84static void wl1251_spi_wake(struct wl1251 *wl) 85static void wl1251_spi_wake(struct wl1251 *wl)
85{ 86{
86 u8 crc[WSPI_INIT_CMD_CRC_LEN], *cmd;
87 struct spi_transfer t; 87 struct spi_transfer t;
88 struct spi_message m; 88 struct spi_message m;
89 u8 *cmd = kzalloc(WSPI_INIT_CMD_LEN, GFP_KERNEL);
89 90
90 cmd = kzalloc(WSPI_INIT_CMD_LEN, GFP_KERNEL);
91 if (!cmd) { 91 if (!cmd) {
92 wl1251_error("could not allocate cmd for spi init"); 92 wl1251_error("could not allocate cmd for spi init");
93 return; 93 return;
94 } 94 }
95 95
96 memset(crc, 0, sizeof(crc));
97 memset(&t, 0, sizeof(t)); 96 memset(&t, 0, sizeof(t));
98 spi_message_init(&m); 97 spi_message_init(&m);
99 98
100 /* Set WSPI_INIT_COMMAND 99 /* Set WSPI_INIT_COMMAND
101 * the data is being send from the MSB to LSB 100 * the data is being send from the MSB to LSB
102 */ 101 */
103 cmd[2] = 0xff; 102 cmd[0] = 0xff;
104 cmd[3] = 0xff; 103 cmd[1] = 0xff;
105 cmd[1] = WSPI_INIT_CMD_START | WSPI_INIT_CMD_TX; 104 cmd[2] = WSPI_INIT_CMD_START | WSPI_INIT_CMD_TX;
106 cmd[0] = 0; 105 cmd[3] = 0;
107 cmd[7] = 0; 106 cmd[4] = 0;
108 cmd[6] |= HW_ACCESS_WSPI_INIT_CMD_MASK << 3; 107 cmd[5] = HW_ACCESS_WSPI_INIT_CMD_MASK << 3;
109 cmd[6] |= HW_ACCESS_WSPI_FIXED_BUSY_LEN & WSPI_INIT_CMD_FIXEDBUSY_LEN; 108 cmd[5] |= HW_ACCESS_WSPI_FIXED_BUSY_LEN & WSPI_INIT_CMD_FIXEDBUSY_LEN;
109
110 cmd[6] = WSPI_INIT_CMD_IOD | WSPI_INIT_CMD_IP | WSPI_INIT_CMD_CS
111 | WSPI_INIT_CMD_WSPI | WSPI_INIT_CMD_WS;
110 112
111 if (HW_ACCESS_WSPI_FIXED_BUSY_LEN == 0) 113 if (HW_ACCESS_WSPI_FIXED_BUSY_LEN == 0)
112 cmd[5] |= WSPI_INIT_CMD_DIS_FIXEDBUSY; 114 cmd[6] |= WSPI_INIT_CMD_DIS_FIXEDBUSY;
113 else 115 else
114 cmd[5] |= WSPI_INIT_CMD_EN_FIXEDBUSY; 116 cmd[6] |= WSPI_INIT_CMD_EN_FIXEDBUSY;
115
116 cmd[5] |= WSPI_INIT_CMD_IOD | WSPI_INIT_CMD_IP | WSPI_INIT_CMD_CS
117 | WSPI_INIT_CMD_WSPI | WSPI_INIT_CMD_WS;
118
119 crc[0] = cmd[1];
120 crc[1] = cmd[0];
121 crc[2] = cmd[7];
122 crc[3] = cmd[6];
123 crc[4] = cmd[5];
124 117
125 cmd[4] |= crc7(0, crc, WSPI_INIT_CMD_CRC_LEN) << 1; 118 cmd[7] = crc7_be(0, cmd+2, WSPI_INIT_CMD_CRC_LEN) | WSPI_INIT_CMD_END;
126 cmd[4] |= WSPI_INIT_CMD_END; 119 /*
120 * The above is the logical order; it must actually be stored
121 * in the buffer byte-swapped.
122 */
123 __swab32s((u32 *)cmd);
124 __swab32s((u32 *)cmd+1);
127 125
128 t.tx_buf = cmd; 126 t.tx_buf = cmd;
129 t.len = WSPI_INIT_CMD_LEN; 127 t.len = WSPI_INIT_CMD_LEN;
diff --git a/drivers/net/wireless/ti/wlcore/debugfs.h b/drivers/net/wireless/ti/wlcore/debugfs.h
index f7381dd69009..0f2cfb0d2a9e 100644
--- a/drivers/net/wireless/ti/wlcore/debugfs.h
+++ b/drivers/net/wireless/ti/wlcore/debugfs.h
@@ -57,7 +57,7 @@ static const struct file_operations name## _ops = { \
57 wl, &name## _ops); \ 57 wl, &name## _ops); \
58 if (!entry || IS_ERR(entry)) \ 58 if (!entry || IS_ERR(entry)) \
59 goto err; \ 59 goto err; \
60 } while (0); 60 } while (0)
61 61
62 62
63#define DEBUGFS_ADD_PREFIX(prefix, name, parent) \ 63#define DEBUGFS_ADD_PREFIX(prefix, name, parent) \
@@ -66,7 +66,7 @@ static const struct file_operations name## _ops = { \
66 wl, &prefix## _## name## _ops); \ 66 wl, &prefix## _## name## _ops); \
67 if (!entry || IS_ERR(entry)) \ 67 if (!entry || IS_ERR(entry)) \
68 goto err; \ 68 goto err; \
69 } while (0); 69 } while (0)
70 70
71#define DEBUGFS_FWSTATS_FILE(sub, name, fmt, struct_type) \ 71#define DEBUGFS_FWSTATS_FILE(sub, name, fmt, struct_type) \
72static ssize_t sub## _ ##name## _read(struct file *file, \ 72static ssize_t sub## _ ##name## _read(struct file *file, \
diff --git a/drivers/net/wireless/ti/wlcore/main.c b/drivers/net/wireless/ti/wlcore/main.c
index 077eb5b9cd74..02c91d6db753 100644
--- a/drivers/net/wireless/ti/wlcore/main.c
+++ b/drivers/net/wireless/ti/wlcore/main.c
@@ -1416,7 +1416,7 @@ void wl1271_rx_filter_free(struct wl12xx_rx_filter *filter)
1416 1416
1417int wl1271_rx_filter_alloc_field(struct wl12xx_rx_filter *filter, 1417int wl1271_rx_filter_alloc_field(struct wl12xx_rx_filter *filter,
1418 u16 offset, u8 flags, 1418 u16 offset, u8 flags,
1419 u8 *pattern, u8 len) 1419 const u8 *pattern, u8 len)
1420{ 1420{
1421 struct wl12xx_rx_filter_field *field; 1421 struct wl12xx_rx_filter_field *field;
1422 1422
diff --git a/drivers/net/wireless/ti/wlcore/spi.c b/drivers/net/wireless/ti/wlcore/spi.c
index 5f3a389dd74c..392c882b28f0 100644
--- a/drivers/net/wireless/ti/wlcore/spi.c
+++ b/drivers/net/wireless/ti/wlcore/spi.c
@@ -24,11 +24,12 @@
24#include <linux/interrupt.h> 24#include <linux/interrupt.h>
25#include <linux/irq.h> 25#include <linux/irq.h>
26#include <linux/module.h> 26#include <linux/module.h>
27#include <linux/slab.h>
28#include <linux/swab.h>
27#include <linux/crc7.h> 29#include <linux/crc7.h>
28#include <linux/spi/spi.h> 30#include <linux/spi/spi.h>
29#include <linux/wl12xx.h> 31#include <linux/wl12xx.h>
30#include <linux/platform_device.h> 32#include <linux/platform_device.h>
31#include <linux/slab.h>
32 33
33#include "wlcore.h" 34#include "wlcore.h"
34#include "wl12xx_80211.h" 35#include "wl12xx_80211.h"
@@ -110,18 +111,16 @@ static void wl12xx_spi_reset(struct device *child)
110static void wl12xx_spi_init(struct device *child) 111static void wl12xx_spi_init(struct device *child)
111{ 112{
112 struct wl12xx_spi_glue *glue = dev_get_drvdata(child->parent); 113 struct wl12xx_spi_glue *glue = dev_get_drvdata(child->parent);
113 u8 crc[WSPI_INIT_CMD_CRC_LEN], *cmd;
114 struct spi_transfer t; 114 struct spi_transfer t;
115 struct spi_message m; 115 struct spi_message m;
116 u8 *cmd = kzalloc(WSPI_INIT_CMD_LEN, GFP_KERNEL);
116 117
117 cmd = kzalloc(WSPI_INIT_CMD_LEN, GFP_KERNEL);
118 if (!cmd) { 118 if (!cmd) {
119 dev_err(child->parent, 119 dev_err(child->parent,
120 "could not allocate cmd for spi init\n"); 120 "could not allocate cmd for spi init\n");
121 return; 121 return;
122 } 122 }
123 123
124 memset(crc, 0, sizeof(crc));
125 memset(&t, 0, sizeof(t)); 124 memset(&t, 0, sizeof(t));
126 spi_message_init(&m); 125 spi_message_init(&m);
127 126
@@ -129,30 +128,29 @@ static void wl12xx_spi_init(struct device *child)
129 * Set WSPI_INIT_COMMAND 128 * Set WSPI_INIT_COMMAND
130 * the data is being send from the MSB to LSB 129 * the data is being send from the MSB to LSB
131 */ 130 */
132 cmd[2] = 0xff; 131 cmd[0] = 0xff;
133 cmd[3] = 0xff; 132 cmd[1] = 0xff;
134 cmd[1] = WSPI_INIT_CMD_START | WSPI_INIT_CMD_TX; 133 cmd[2] = WSPI_INIT_CMD_START | WSPI_INIT_CMD_TX;
135 cmd[0] = 0; 134 cmd[3] = 0;
136 cmd[7] = 0; 135 cmd[4] = 0;
137 cmd[6] |= HW_ACCESS_WSPI_INIT_CMD_MASK << 3; 136 cmd[5] = HW_ACCESS_WSPI_INIT_CMD_MASK << 3;
138 cmd[6] |= HW_ACCESS_WSPI_FIXED_BUSY_LEN & WSPI_INIT_CMD_FIXEDBUSY_LEN; 137 cmd[5] |= HW_ACCESS_WSPI_FIXED_BUSY_LEN & WSPI_INIT_CMD_FIXEDBUSY_LEN;
138
139 cmd[6] = WSPI_INIT_CMD_IOD | WSPI_INIT_CMD_IP | WSPI_INIT_CMD_CS
140 | WSPI_INIT_CMD_WSPI | WSPI_INIT_CMD_WS;
139 141
140 if (HW_ACCESS_WSPI_FIXED_BUSY_LEN == 0) 142 if (HW_ACCESS_WSPI_FIXED_BUSY_LEN == 0)
141 cmd[5] |= WSPI_INIT_CMD_DIS_FIXEDBUSY; 143 cmd[6] |= WSPI_INIT_CMD_DIS_FIXEDBUSY;
142 else 144 else
143 cmd[5] |= WSPI_INIT_CMD_EN_FIXEDBUSY; 145 cmd[6] |= WSPI_INIT_CMD_EN_FIXEDBUSY;
144 146
145 cmd[5] |= WSPI_INIT_CMD_IOD | WSPI_INIT_CMD_IP | WSPI_INIT_CMD_CS 147 cmd[7] = crc7_be(0, cmd+2, WSPI_INIT_CMD_CRC_LEN) | WSPI_INIT_CMD_END;
146 | WSPI_INIT_CMD_WSPI | WSPI_INIT_CMD_WS; 148 /*
147 149 * The above is the logical order; it must actually be stored
148 crc[0] = cmd[1]; 150 * in the buffer byte-swapped.
149 crc[1] = cmd[0]; 151 */
150 crc[2] = cmd[7]; 152 __swab32s((u32 *)cmd);
151 crc[3] = cmd[6]; 153 __swab32s((u32 *)cmd+1);
152 crc[4] = cmd[5];
153
154 cmd[4] |= crc7(0, crc, WSPI_INIT_CMD_CRC_LEN) << 1;
155 cmd[4] |= WSPI_INIT_CMD_END;
156 154
157 t.tx_buf = cmd; 155 t.tx_buf = cmd;
158 t.len = WSPI_INIT_CMD_LEN; 156 t.len = WSPI_INIT_CMD_LEN;
diff --git a/drivers/net/wireless/ti/wlcore/wlcore_i.h b/drivers/net/wireless/ti/wlcore/wlcore_i.h
index 756e890bc5ee..c2c34a84ff3d 100644
--- a/drivers/net/wireless/ti/wlcore/wlcore_i.h
+++ b/drivers/net/wireless/ti/wlcore/wlcore_i.h
@@ -512,8 +512,8 @@ int wl1271_recalc_rx_streaming(struct wl1271 *wl, struct wl12xx_vif *wlvif);
512void wl12xx_queue_recovery_work(struct wl1271 *wl); 512void wl12xx_queue_recovery_work(struct wl1271 *wl);
513size_t wl12xx_copy_fwlog(struct wl1271 *wl, u8 *memblock, size_t maxlen); 513size_t wl12xx_copy_fwlog(struct wl1271 *wl, u8 *memblock, size_t maxlen);
514int wl1271_rx_filter_alloc_field(struct wl12xx_rx_filter *filter, 514int wl1271_rx_filter_alloc_field(struct wl12xx_rx_filter *filter,
515 u16 offset, u8 flags, 515 u16 offset, u8 flags,
516 u8 *pattern, u8 len); 516 const u8 *pattern, u8 len);
517void wl1271_rx_filter_free(struct wl12xx_rx_filter *filter); 517void wl1271_rx_filter_free(struct wl12xx_rx_filter *filter);
518struct wl12xx_rx_filter *wl1271_rx_filter_alloc(void); 518struct wl12xx_rx_filter *wl1271_rx_filter_alloc(void);
519int wl1271_rx_filter_get_fields_size(struct wl12xx_rx_filter *filter); 519int wl1271_rx_filter_get_fields_size(struct wl12xx_rx_filter *filter);
diff --git a/drivers/nfc/Kconfig b/drivers/nfc/Kconfig
index 65d4ca19d132..26c66a126551 100644
--- a/drivers/nfc/Kconfig
+++ b/drivers/nfc/Kconfig
@@ -71,5 +71,6 @@ config NFC_PORT100
71source "drivers/nfc/pn544/Kconfig" 71source "drivers/nfc/pn544/Kconfig"
72source "drivers/nfc/microread/Kconfig" 72source "drivers/nfc/microread/Kconfig"
73source "drivers/nfc/nfcmrvl/Kconfig" 73source "drivers/nfc/nfcmrvl/Kconfig"
74source "drivers/nfc/st21nfca/Kconfig"
74 75
75endmenu 76endmenu
diff --git a/drivers/nfc/Makefile b/drivers/nfc/Makefile
index ae42a3fa60c9..23225b0287fd 100644
--- a/drivers/nfc/Makefile
+++ b/drivers/nfc/Makefile
@@ -11,5 +11,6 @@ obj-$(CONFIG_NFC_SIM) += nfcsim.o
11obj-$(CONFIG_NFC_PORT100) += port100.o 11obj-$(CONFIG_NFC_PORT100) += port100.o
12obj-$(CONFIG_NFC_MRVL) += nfcmrvl/ 12obj-$(CONFIG_NFC_MRVL) += nfcmrvl/
13obj-$(CONFIG_NFC_TRF7970A) += trf7970a.o 13obj-$(CONFIG_NFC_TRF7970A) += trf7970a.o
14obj-$(CONFIG_NFC_ST21NFCA) += st21nfca/
14 15
15ccflags-$(CONFIG_NFC_DEBUG) := -DDEBUG 16ccflags-$(CONFIG_NFC_DEBUG) := -DDEBUG
diff --git a/drivers/nfc/pn544/i2c.c b/drivers/nfc/pn544/i2c.c
index f2acd85be86e..440291ab7263 100644
--- a/drivers/nfc/pn544/i2c.c
+++ b/drivers/nfc/pn544/i2c.c
@@ -22,6 +22,8 @@
22#include <linux/module.h> 22#include <linux/module.h>
23#include <linux/i2c.h> 23#include <linux/i2c.h>
24#include <linux/gpio.h> 24#include <linux/gpio.h>
25#include <linux/of_gpio.h>
26#include <linux/of_irq.h>
25#include <linux/miscdevice.h> 27#include <linux/miscdevice.h>
26#include <linux/interrupt.h> 28#include <linux/interrupt.h>
27#include <linux/delay.h> 29#include <linux/delay.h>
@@ -857,6 +859,92 @@ exit_state_wait_secure_write_answer:
857 } 859 }
858} 860}
859 861
862#ifdef CONFIG_OF
863
864static int pn544_hci_i2c_of_request_resources(struct i2c_client *client)
865{
866 struct pn544_i2c_phy *phy = i2c_get_clientdata(client);
867 struct device_node *pp;
868 int ret;
869
870 pp = client->dev.of_node;
871 if (!pp) {
872 ret = -ENODEV;
873 goto err_dt;
874 }
875
876 /* Obtention of EN GPIO from device tree */
877 ret = of_get_named_gpio(pp, "enable-gpios", 0);
878 if (ret < 0) {
879 if (ret != -EPROBE_DEFER)
880 nfc_err(&client->dev,
881 "Failed to get EN gpio, error: %d\n", ret);
882 goto err_dt;
883 }
884 phy->gpio_en = ret;
885
886 /* Configuration of EN GPIO */
887 ret = gpio_request(phy->gpio_en, "pn544_en");
888 if (ret) {
889 nfc_err(&client->dev, "Fail EN pin\n");
890 goto err_dt;
891 }
892 ret = gpio_direction_output(phy->gpio_en, 0);
893 if (ret) {
894 nfc_err(&client->dev, "Fail EN pin direction\n");
895 goto err_gpio_en;
896 }
897
898 /* Obtention of FW GPIO from device tree */
899 ret = of_get_named_gpio(pp, "firmware-gpios", 0);
900 if (ret < 0) {
901 if (ret != -EPROBE_DEFER)
902 nfc_err(&client->dev,
903 "Failed to get FW gpio, error: %d\n", ret);
904 goto err_gpio_en;
905 }
906 phy->gpio_fw = ret;
907
908 /* Configuration of FW GPIO */
909 ret = gpio_request(phy->gpio_fw, "pn544_fw");
910 if (ret) {
911 nfc_err(&client->dev, "Fail FW pin\n");
912 goto err_gpio_en;
913 }
914 ret = gpio_direction_output(phy->gpio_fw, 0);
915 if (ret) {
916 nfc_err(&client->dev, "Fail FW pin direction\n");
917 goto err_gpio_fw;
918 }
919
920 /* IRQ */
921 ret = irq_of_parse_and_map(pp, 0);
922 if (ret < 0) {
923 nfc_err(&client->dev,
924 "Unable to get irq, error: %d\n", ret);
925 goto err_gpio_fw;
926 }
927 client->irq = ret;
928
929 return 0;
930
931err_gpio_fw:
932 gpio_free(phy->gpio_fw);
933err_gpio_en:
934 gpio_free(phy->gpio_en);
935err_dt:
936 return ret;
937}
938
939#else
940
941static int pn544_hci_i2c_of_request_resources(struct i2c_client *client)
942{
943 return -ENODEV;
944}
945
946#endif
947
860static int pn544_hci_i2c_probe(struct i2c_client *client, 948static int pn544_hci_i2c_probe(struct i2c_client *client,
861 const struct i2c_device_id *id) 949 const struct i2c_device_id *id)
862{ 950{
@@ -887,25 +975,36 @@ static int pn544_hci_i2c_probe(struct i2c_client *client,
887 i2c_set_clientdata(client, phy); 975 i2c_set_clientdata(client, phy);
888 976
889 pdata = client->dev.platform_data; 977 pdata = client->dev.platform_data;
890 if (pdata == NULL) {
891 nfc_err(&client->dev, "No platform data\n");
892 return -EINVAL;
893 }
894 978
895 if (pdata->request_resources == NULL) { 979 /* No platform data, using device tree. */
896 nfc_err(&client->dev, "request_resources() missing\n"); 980 if (!pdata && client->dev.of_node) {
897 return -EINVAL; 981 r = pn544_hci_i2c_of_request_resources(client);
898 } 982 if (r) {
983 nfc_err(&client->dev, "No DT data\n");
984 return r;
985 }
986 /* Using platform data. */
987 } else if (pdata) {
899 988
900 r = pdata->request_resources(client); 989 if (pdata->request_resources == NULL) {
901 if (r) { 990 nfc_err(&client->dev, "request_resources() missing\n");
902 nfc_err(&client->dev, "Cannot get platform resources\n"); 991 return -EINVAL;
903 return r; 992 }
904 }
905 993
906 phy->gpio_en = pdata->get_gpio(NFC_GPIO_ENABLE); 994 r = pdata->request_resources(client);
907 phy->gpio_fw = pdata->get_gpio(NFC_GPIO_FW_RESET); 995 if (r) {
908 phy->gpio_irq = pdata->get_gpio(NFC_GPIO_IRQ); 996 nfc_err(&client->dev,
997 "Cannot get platform resources\n");
998 return r;
999 }
1000
1001 phy->gpio_en = pdata->get_gpio(NFC_GPIO_ENABLE);
1002 phy->gpio_fw = pdata->get_gpio(NFC_GPIO_FW_RESET);
1003 phy->gpio_irq = pdata->get_gpio(NFC_GPIO_IRQ);
1004 } else {
1005 nfc_err(&client->dev, "No platform data\n");
1006 return -EINVAL;
1007 }
909 1008
910 pn544_hci_i2c_platform_init(phy); 1009 pn544_hci_i2c_platform_init(phy);
911 1010
@@ -930,8 +1029,12 @@ err_hci:
930 free_irq(client->irq, phy); 1029 free_irq(client->irq, phy);
931 1030
932err_rti: 1031err_rti:
933 if (pdata->free_resources != NULL) 1032 if (!pdata) {
1033 gpio_free(phy->gpio_en);
1034 gpio_free(phy->gpio_fw);
1035 } else if (pdata->free_resources) {
934 pdata->free_resources(); 1036 pdata->free_resources();
1037 }
935 1038
936 return r; 1039 return r;
937} 1040}
@@ -953,15 +1056,30 @@ static int pn544_hci_i2c_remove(struct i2c_client *client)
953 pn544_hci_i2c_disable(phy); 1056 pn544_hci_i2c_disable(phy);
954 1057
955 free_irq(client->irq, phy); 1058 free_irq(client->irq, phy);
956 if (pdata->free_resources) 1059
1060 /* No platform data, GPIOs have been requested by this driver */
1061 if (!pdata) {
1062 gpio_free(phy->gpio_en);
1063 gpio_free(phy->gpio_fw);
1064 /* Using platform data */
1065 } else if (pdata->free_resources) {
957 pdata->free_resources(); 1066 pdata->free_resources();
1067 }
958 1068
959 return 0; 1069 return 0;
960} 1070}
961 1071
1072static const struct of_device_id of_pn544_i2c_match[] = {
1073 { .compatible = "nxp,pn544-i2c", },
1074 {},
1075};
1076MODULE_DEVICE_TABLE(of, of_pn544_i2c_match);
1077
962static struct i2c_driver pn544_hci_i2c_driver = { 1078static struct i2c_driver pn544_hci_i2c_driver = {
963 .driver = { 1079 .driver = {
964 .name = PN544_HCI_I2C_DRIVER_NAME, 1080 .name = PN544_HCI_I2C_DRIVER_NAME,
1081 .owner = THIS_MODULE,
1082 .of_match_table = of_match_ptr(of_pn544_i2c_match),
965 }, 1083 },
966 .probe = pn544_hci_i2c_probe, 1084 .probe = pn544_hci_i2c_probe,
967 .id_table = pn544_hci_i2c_id_table, 1085 .id_table = pn544_hci_i2c_id_table,
diff --git a/drivers/nfc/st21nfca/Kconfig b/drivers/nfc/st21nfca/Kconfig
new file mode 100644
index 000000000000..ee459f066ade
--- /dev/null
+++ b/drivers/nfc/st21nfca/Kconfig
@@ -0,0 +1,23 @@
1config NFC_ST21NFCA
2 tristate "STMicroelectronics ST21NFCA NFC driver"
3 depends on NFC_HCI
4 select CRC_CCITT
5 default n
6 ---help---
7 STMicroelectronics ST21NFCA core driver. It implements the chipset
8 HCI logic and hooks into the NFC kernel APIs. Physical layers will
9 register against it.
10
11 To compile this driver as a module, choose m here. The module will
12 be called st21nfca.
13 Say N if unsure.
14
15config NFC_ST21NFCA_I2C
16 tristate "NFC ST21NFCA i2c support"
17 depends on NFC_ST21NFCA && I2C && NFC_SHDLC
18 ---help---
19 This module adds support for the STMicroelectronics st21nfca i2c interface.
20 Select this if your platform is using the i2c bus.
21
22 If you choose to build a module, it'll be called st21nfca_i2c.
23 Say N if unsure.
diff --git a/drivers/nfc/st21nfca/Makefile b/drivers/nfc/st21nfca/Makefile
new file mode 100644
index 000000000000..038ed093a119
--- /dev/null
+++ b/drivers/nfc/st21nfca/Makefile
@@ -0,0 +1,8 @@
1#
2# Makefile for ST21NFCA HCI based NFC driver
3#
4
5st21nfca_i2c-objs = i2c.o
6
7obj-$(CONFIG_NFC_ST21NFCA) += st21nfca.o
8obj-$(CONFIG_NFC_ST21NFCA_I2C) += st21nfca_i2c.o
diff --git a/drivers/nfc/st21nfca/i2c.c b/drivers/nfc/st21nfca/i2c.c
new file mode 100644
index 000000000000..3f954ed86d98
--- /dev/null
+++ b/drivers/nfc/st21nfca/i2c.c
@@ -0,0 +1,724 @@
1/*
2 * I2C Link Layer for ST21NFCA HCI based Driver
3 * Copyright (C) 2014 STMicroelectronics SAS. All rights reserved.
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms and conditions of the GNU General Public License,
7 * version 2, as published by the Free Software Foundation.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, see <http://www.gnu.org/licenses/>.
16 */
17
18#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
19
20#include <linux/crc-ccitt.h>
21#include <linux/module.h>
22#include <linux/i2c.h>
23#include <linux/gpio.h>
24#include <linux/of_irq.h>
25#include <linux/of_gpio.h>
26#include <linux/miscdevice.h>
27#include <linux/interrupt.h>
28#include <linux/delay.h>
29#include <linux/nfc.h>
30#include <linux/firmware.h>
31#include <linux/unaligned/access_ok.h>
32#include <linux/platform_data/st21nfca.h>
33
34#include <net/nfc/hci.h>
35#include <net/nfc/llc.h>
36#include <net/nfc/nfc.h>
37
38#include "st21nfca.h"
39
40/*
41 * Every frame starts with ST21NFCA_SOF_EOF and ends with ST21NFCA_SOF_EOF.
42 * Because ST21NFCA_SOF_EOF is a possible data value, there is a mecanism
43 * called byte stuffing has been introduced.
44 *
45 * if byte == ST21NFCA_SOF_EOF or ST21NFCA_ESCAPE_BYTE_STUFFING
46 * - insert ST21NFCA_ESCAPE_BYTE_STUFFING (escape byte)
47 * - xor byte with ST21NFCA_BYTE_STUFFING_MASK
48 */
49#define ST21NFCA_SOF_EOF 0x7e
50#define ST21NFCA_BYTE_STUFFING_MASK 0x20
51#define ST21NFCA_ESCAPE_BYTE_STUFFING 0x7d
52
53/* SOF + 00 */
54#define ST21NFCA_FRAME_HEADROOM 2
55
56/* 2 bytes crc + EOF */
57#define ST21NFCA_FRAME_TAILROOM 3
58#define IS_START_OF_FRAME(buf) (buf[0] == ST21NFCA_SOF_EOF && \
59 buf[1] == 0)
60
61#define ST21NFCA_HCI_I2C_DRIVER_NAME "st21nfca_hci_i2c"
62
63static struct i2c_device_id st21nfca_hci_i2c_id_table[] = {
64 {ST21NFCA_HCI_DRIVER_NAME, 0},
65 {}
66};
67
68MODULE_DEVICE_TABLE(i2c, st21nfca_hci_i2c_id_table);
69
70struct st21nfca_i2c_phy {
71 struct i2c_client *i2c_dev;
72 struct nfc_hci_dev *hdev;
73
74 unsigned int gpio_ena;
75 unsigned int gpio_irq;
76 unsigned int irq_polarity;
77
78 struct sk_buff *pending_skb;
79 int current_read_len;
80 /*
81 * crc might have fail because i2c macro
82 * is disable due to other interface activity
83 */
84 int crc_trials;
85
86 int powered;
87 int run_mode;
88
89 /*
90 * < 0 if hardware error occured (e.g. i2c err)
91 * and prevents normal operation.
92 */
93 int hard_fault;
94 struct mutex phy_lock;
95};
96static u8 len_seq[] = { 13, 24, 15, 29 };
97static u16 wait_tab[] = { 2, 3, 5, 15, 20, 40};
98
99#define I2C_DUMP_SKB(info, skb) \
100do { \
101 pr_debug("%s:\n", info); \
102 print_hex_dump(KERN_DEBUG, "i2c: ", DUMP_PREFIX_OFFSET, \
103 16, 1, (skb)->data, (skb)->len, 0); \
104} while (0)
105
106/*
107 * In order to get the CLF in a known state we generate an internal reboot
108 * using a proprietary command.
109 * Once the reboot is completed, we expect to receive a ST21NFCA_SOF_EOF
110 * fill buffer.
111 */
112static int st21nfca_hci_platform_init(struct st21nfca_i2c_phy *phy)
113{
114 u16 wait_reboot[] = { 50, 300, 1000 };
115 char reboot_cmd[] = { 0x7E, 0x66, 0x48, 0xF6, 0x7E };
116 u8 tmp[ST21NFCA_HCI_LLC_MAX_SIZE];
117 int i, r = -1;
118
119 for (i = 0; i < ARRAY_SIZE(wait_reboot) && r < 0; i++) {
120 r = i2c_master_send(phy->i2c_dev, reboot_cmd,
121 sizeof(reboot_cmd));
122 if (r < 0)
123 msleep(wait_reboot[i]);
124 }
125 if (r < 0)
126 return r;
127
128 /* CLF is spending about 20ms to do an internal reboot */
129 msleep(20);
130 r = -1;
131 for (i = 0; i < ARRAY_SIZE(wait_reboot) && r < 0; i++) {
132 r = i2c_master_recv(phy->i2c_dev, tmp,
133 ST21NFCA_HCI_LLC_MAX_SIZE);
134 if (r < 0)
135 msleep(wait_reboot[i]);
136 }
137 if (r < 0)
138 return r;
139
140 for (i = 0; i < ST21NFCA_HCI_LLC_MAX_SIZE &&
141 tmp[i] == ST21NFCA_SOF_EOF; i++)
142 ;
143
144 if (r != ST21NFCA_HCI_LLC_MAX_SIZE)
145 return -ENODEV;
146
147 usleep_range(1000, 1500);
148 return 0;
149}
150
151static int st21nfca_hci_i2c_enable(void *phy_id)
152{
153 struct st21nfca_i2c_phy *phy = phy_id;
154
155 gpio_set_value(phy->gpio_ena, 1);
156 phy->powered = 1;
157 phy->run_mode = ST21NFCA_HCI_MODE;
158
159 usleep_range(10000, 15000);
160
161 return 0;
162}
163
164static void st21nfca_hci_i2c_disable(void *phy_id)
165{
166 struct st21nfca_i2c_phy *phy = phy_id;
167
168 pr_info("\n");
169 gpio_set_value(phy->gpio_ena, 0);
170
171 phy->powered = 0;
172}
173
174static void st21nfca_hci_add_len_crc(struct sk_buff *skb)
175{
176 u16 crc;
177 u8 tmp;
178
179 *skb_push(skb, 1) = 0;
180
181 crc = crc_ccitt(0xffff, skb->data, skb->len);
182 crc = ~crc;
183
184 tmp = crc & 0x00ff;
185 *skb_put(skb, 1) = tmp;
186
187 tmp = (crc >> 8) & 0x00ff;
188 *skb_put(skb, 1) = tmp;
189}
190
191static void st21nfca_hci_remove_len_crc(struct sk_buff *skb)
192{
193 skb_pull(skb, ST21NFCA_FRAME_HEADROOM);
194 skb_trim(skb, skb->len - ST21NFCA_FRAME_TAILROOM);
195}
196
197/*
198 * Writing a frame must not return the number of written bytes.
199 * It must return either zero for success, or <0 for error.
200 * In addition, it must not alter the skb
201 */
202static int st21nfca_hci_i2c_write(void *phy_id, struct sk_buff *skb)
203{
204 int r = -1, i, j;
205 struct st21nfca_i2c_phy *phy = phy_id;
206 struct i2c_client *client = phy->i2c_dev;
207 u8 tmp[ST21NFCA_HCI_LLC_MAX_SIZE * 2];
208
209 I2C_DUMP_SKB("st21nfca_hci_i2c_write", skb);
210
211
212 if (phy->hard_fault != 0)
213 return phy->hard_fault;
214
215 /*
216 * Compute CRC before byte stuffing computation on frame
217 * Note st21nfca_hci_add_len_crc is doing a byte stuffing
218 * on its own value
219 */
220 st21nfca_hci_add_len_crc(skb);
221
222 /* add ST21NFCA_SOF_EOF on tail */
223 *skb_put(skb, 1) = ST21NFCA_SOF_EOF;
224 /* add ST21NFCA_SOF_EOF on head */
225 *skb_push(skb, 1) = ST21NFCA_SOF_EOF;
226
227 /*
228 * Compute byte stuffing
229 * if byte == ST21NFCA_SOF_EOF or ST21NFCA_ESCAPE_BYTE_STUFFING
230 * insert ST21NFCA_ESCAPE_BYTE_STUFFING (escape byte)
231 * xor byte with ST21NFCA_BYTE_STUFFING_MASK
232 */
233 tmp[0] = skb->data[0];
234 for (i = 1, j = 1; i < skb->len - 1; i++, j++) {
235 if (skb->data[i] == ST21NFCA_SOF_EOF
236 || skb->data[i] == ST21NFCA_ESCAPE_BYTE_STUFFING) {
237 tmp[j] = ST21NFCA_ESCAPE_BYTE_STUFFING;
238 j++;
239 tmp[j] = skb->data[i] ^ ST21NFCA_BYTE_STUFFING_MASK;
240 } else {
241 tmp[j] = skb->data[i];
242 }
243 }
244 tmp[j] = skb->data[i];
245 j++;
246
247 /*
248 * Manage sleep mode
249 * Try 3 times to send data with delay between each
250 */
251 mutex_lock(&phy->phy_lock);
252 for (i = 0; i < ARRAY_SIZE(wait_tab) && r < 0; i++) {
253 r = i2c_master_send(client, tmp, j);
254 if (r < 0)
255 msleep(wait_tab[i]);
256 }
257 mutex_unlock(&phy->phy_lock);
258
259 if (r >= 0) {
260 if (r != j)
261 r = -EREMOTEIO;
262 else
263 r = 0;
264 }
265
266 st21nfca_hci_remove_len_crc(skb);
267
268 return r;
269}
270
271static int get_frame_size(u8 *buf, int buflen)
272{
273 int len = 0;
274 if (buf[len + 1] == ST21NFCA_SOF_EOF)
275 return 0;
276
277 for (len = 1; len < buflen && buf[len] != ST21NFCA_SOF_EOF; len++)
278 ;
279
280 return len;
281}
282
283static int check_crc(u8 *buf, int buflen)
284{
285 u16 crc;
286
287 crc = crc_ccitt(0xffff, buf, buflen - 2);
288 crc = ~crc;
289
290 if (buf[buflen - 2] != (crc & 0xff) || buf[buflen - 1] != (crc >> 8)) {
291 pr_err(ST21NFCA_HCI_DRIVER_NAME
292 ": CRC error 0x%x != 0x%x 0x%x\n", crc, buf[buflen - 1],
293 buf[buflen - 2]);
294
295 pr_info(DRIVER_DESC ": %s : BAD CRC\n", __func__);
296 print_hex_dump(KERN_DEBUG, "crc: ", DUMP_PREFIX_NONE,
297 16, 2, buf, buflen, false);
298 return -EPERM;
299 }
300 return 0;
301}
302
303/*
304 * Prepare received data for upper layer.
305 * Received data include byte stuffing, crc and sof/eof
306 * which is not usable by hci part.
307 * returns:
308 * frame size without sof/eof, header and byte stuffing
309 * -EBADMSG : frame was incorrect and discarded
310 */
311static int st21nfca_hci_i2c_repack(struct sk_buff *skb)
312{
313 int i, j, r, size;
314 if (skb->len < 1 || (skb->len > 1 && skb->data[1] != 0))
315 return -EBADMSG;
316
317 size = get_frame_size(skb->data, skb->len);
318 if (size > 0) {
319 skb_trim(skb, size);
320 /* remove ST21NFCA byte stuffing for upper layer */
321 for (i = 1, j = 0; i < skb->len; i++) {
322 if (skb->data[i + j] ==
323 (u8) ST21NFCA_ESCAPE_BYTE_STUFFING) {
324 skb->data[i] = skb->data[i + j + 1]
325 | ST21NFCA_BYTE_STUFFING_MASK;
326 i++;
327 j++;
328 }
329 skb->data[i] = skb->data[i + j];
330 }
331 /* remove byte stuffing useless byte */
332 skb_trim(skb, i - j);
333 /* remove ST21NFCA_SOF_EOF from head */
334 skb_pull(skb, 1);
335
336 r = check_crc(skb->data, skb->len);
337 if (r != 0) {
338 i = 0;
339 return -EBADMSG;
340 }
341
342 /* remove headbyte */
343 skb_pull(skb, 1);
344 /* remove crc. Byte Stuffing is already removed here */
345 skb_trim(skb, skb->len - 2);
346 return skb->len;
347 }
348 return 0;
349}
350
351/*
352 * Reads an shdlc frame and returns it in a newly allocated sk_buff. Guarantees
353 * that i2c bus will be flushed and that next read will start on a new frame.
354 * returned skb contains only LLC header and payload.
355 * returns:
356 * frame size : if received frame is complete (find ST21NFCA_SOF_EOF at
357 * end of read)
358 * -EAGAIN : if received frame is incomplete (not find ST21NFCA_SOF_EOF
359 * at end of read)
360 * -EREMOTEIO : i2c read error (fatal)
361 * -EBADMSG : frame was incorrect and discarded
362 * (value returned from st21nfca_hci_i2c_repack)
363 * -EIO : if no ST21NFCA_SOF_EOF is found after reaching
364 * the read length end sequence
365 */
366static int st21nfca_hci_i2c_read(struct st21nfca_i2c_phy *phy,
367 struct sk_buff *skb)
368{
369 int r, i;
370 u8 len;
371 u8 buf[ST21NFCA_HCI_LLC_MAX_PAYLOAD];
372 struct i2c_client *client = phy->i2c_dev;
373
374 if (phy->current_read_len < ARRAY_SIZE(len_seq)) {
375 len = len_seq[phy->current_read_len];
376
377 /*
378 * Add retry mecanism
379 * Operation on I2C interface may fail in case of operation on
380 * RF or SWP interface
381 */
382 r = 0;
383 mutex_lock(&phy->phy_lock);
384 for (i = 0; i < ARRAY_SIZE(wait_tab) && r <= 0; i++) {
385 r = i2c_master_recv(client, buf, len);
386 if (r < 0)
387 msleep(wait_tab[i]);
388 }
389 mutex_unlock(&phy->phy_lock);
390
391 if (r != len) {
392 phy->current_read_len = 0;
393 return -EREMOTEIO;
394 }
395
396 /*
397 * The first read sequence does not start with SOF.
398 * Data is corrupeted so we drop it.
399 */
400 if (!phy->current_read_len && buf[0] != ST21NFCA_SOF_EOF) {
401 skb_trim(skb, 0);
402 phy->current_read_len = 0;
403 return -EIO;
404 } else if (phy->current_read_len &&
405 IS_START_OF_FRAME(buf)) {
406 /*
407 * Previous frame transmission was interrupted and
408 * the frame got repeated.
409 * Received frame start with ST21NFCA_SOF_EOF + 00.
410 */
411 skb_trim(skb, 0);
412 phy->current_read_len = 0;
413 }
414
415 memcpy(skb_put(skb, len), buf, len);
416
417 if (skb->data[skb->len - 1] == ST21NFCA_SOF_EOF) {
418 phy->current_read_len = 0;
419 return st21nfca_hci_i2c_repack(skb);
420 }
421 phy->current_read_len++;
422 return -EAGAIN;
423 }
424 return -EIO;
425}
426
427/*
428 * Reads an shdlc frame from the chip. This is not as straightforward as it
429 * seems. The frame format is data-crc, and corruption can occur anywhere
430 * while transiting on i2c bus, such that we could read an invalid data.
431 * The tricky case is when we read a corrupted data or crc. We must detect
432 * this here in order to determine that data can be transmitted to the hci
433 * core. This is the reason why we check the crc here.
434 * The CLF will repeat a frame until we send a RR on that frame.
435 *
436 * On ST21NFCA, IRQ goes in idle when read starts. As no size information are
437 * available in the incoming data, other IRQ might come. Every IRQ will trigger
438 * a read sequence with different length and will fill the current frame.
439 * The reception is complete once we reach a ST21NFCA_SOF_EOF.
440 */
441static irqreturn_t st21nfca_hci_irq_thread_fn(int irq, void *phy_id)
442{
443 struct st21nfca_i2c_phy *phy = phy_id;
444 struct i2c_client *client;
445
446 int r;
447
448 if (!phy || irq != phy->i2c_dev->irq) {
449 WARN_ON_ONCE(1);
450 return IRQ_NONE;
451 }
452
453 client = phy->i2c_dev;
454 dev_dbg(&client->dev, "IRQ\n");
455
456 if (phy->hard_fault != 0)
457 return IRQ_HANDLED;
458
459 r = st21nfca_hci_i2c_read(phy, phy->pending_skb);
460 if (r == -EREMOTEIO) {
461 phy->hard_fault = r;
462
463 nfc_hci_recv_frame(phy->hdev, NULL);
464
465 return IRQ_HANDLED;
466 } else if (r == -EAGAIN || r == -EIO) {
467 return IRQ_HANDLED;
468 } else if (r == -EBADMSG && phy->crc_trials < ARRAY_SIZE(wait_tab)) {
469 /*
470 * With ST21NFCA, only one interface (I2C, RF or SWP)
471 * may be active at a time.
472 * Having incorrect crc is usually due to i2c macrocell
473 * deactivation in the middle of a transmission.
474 * It may generate corrupted data on i2c.
475 * We give sometime to get i2c back.
476 * The complete frame will be repeated.
477 */
478 msleep(wait_tab[phy->crc_trials]);
479 phy->crc_trials++;
480 phy->current_read_len = 0;
481 kfree_skb(phy->pending_skb);
482 } else if (r > 0) {
483 /*
484 * We succeeded to read data from the CLF and
485 * data is valid.
486 * Reset counter.
487 */
488 nfc_hci_recv_frame(phy->hdev, phy->pending_skb);
489 phy->crc_trials = 0;
490 }
491
492 phy->pending_skb = alloc_skb(ST21NFCA_HCI_LLC_MAX_SIZE * 2, GFP_KERNEL);
493 if (phy->pending_skb == NULL) {
494 phy->hard_fault = -ENOMEM;
495 nfc_hci_recv_frame(phy->hdev, NULL);
496 }
497
498 return IRQ_HANDLED;
499}
500
501static struct nfc_phy_ops i2c_phy_ops = {
502 .write = st21nfca_hci_i2c_write,
503 .enable = st21nfca_hci_i2c_enable,
504 .disable = st21nfca_hci_i2c_disable,
505};
506
507#ifdef CONFIG_OF
508static int st21nfca_hci_i2c_of_request_resources(struct i2c_client *client)
509{
510 struct st21nfca_i2c_phy *phy = i2c_get_clientdata(client);
511 struct device_node *pp;
512 int gpio;
513 int r;
514
515 pp = client->dev.of_node;
516 if (!pp)
517 return -ENODEV;
518
519 /* Get GPIO from device tree */
520 gpio = of_get_named_gpio(pp, "enable-gpios", 0);
521 if (gpio < 0) {
522 nfc_err(&client->dev, "Failed to retrieve enable-gpios from device tree\n");
523 return gpio;
524 }
525
526 /* GPIO request and configuration */
527 r = devm_gpio_request(&client->dev, gpio, "clf_enable");
528 if (r) {
529 nfc_err(&client->dev, "Failed to request enable pin\n");
530 return -ENODEV;
531 }
532
533 r = gpio_direction_output(gpio, 1);
534 if (r) {
535 nfc_err(&client->dev, "Failed to set enable pin direction as output\n");
536 return -ENODEV;
537 }
538 phy->gpio_ena = gpio;
539
540 /* IRQ */
541 r = irq_of_parse_and_map(pp, 0);
542 if (r < 0) {
543 nfc_err(&client->dev,
544 "Unable to get irq, error: %d\n", r);
545 return r;
546 }
547
548 phy->irq_polarity = irq_get_trigger_type(r);
549 client->irq = r;
550
551 return 0;
552}
553#else
554static int st21nfca_hci_i2c_of_request_resources(struct i2c_client *client)
555{
556 return -ENODEV;
557}
558#endif
559
560static int st21nfca_hci_i2c_request_resources(struct i2c_client *client)
561{
562 struct st21nfca_nfc_platform_data *pdata;
563 struct st21nfca_i2c_phy *phy = i2c_get_clientdata(client);
564 int r;
565 int irq;
566
567 pdata = client->dev.platform_data;
568 if (pdata == NULL) {
569 nfc_err(&client->dev, "No platform data\n");
570 return -EINVAL;
571 }
572
573 /* store for later use */
574 phy->gpio_irq = pdata->gpio_irq;
575 phy->gpio_ena = pdata->gpio_ena;
576 phy->irq_polarity = pdata->irq_polarity;
577
578 r = devm_gpio_request(&client->dev, phy->gpio_irq, "wake_up");
579 if (r) {
580 pr_err("%s : gpio_request failed\n", __FILE__);
581 return -ENODEV;
582 }
583
584 r = gpio_direction_input(phy->gpio_irq);
585 if (r) {
586 pr_err("%s : gpio_direction_input failed\n", __FILE__);
587 return -ENODEV;
588 }
589
590 if (phy->gpio_ena > 0) {
591 r = devm_gpio_request(&client->dev,
592 phy->gpio_ena, "clf_enable");
593 if (r) {
594 pr_err("%s : ena gpio_request failed\n", __FILE__);
595 return -ENODEV;
596 }
597 r = gpio_direction_output(phy->gpio_ena, 1);
598
599 if (r) {
600 pr_err("%s : ena gpio_direction_output failed\n",
601 __FILE__);
602 return -ENODEV;
603 }
604 }
605
606 /* IRQ */
607 irq = gpio_to_irq(phy->gpio_irq);
608 if (irq < 0) {
609 nfc_err(&client->dev,
610 "Unable to get irq number for GPIO %d error %d\n",
611 phy->gpio_irq, r);
612 return -ENODEV;
613 }
614 client->irq = irq;
615
616 return 0;
617}
618
619static int st21nfca_hci_i2c_probe(struct i2c_client *client,
620 const struct i2c_device_id *id)
621{
622 struct st21nfca_i2c_phy *phy;
623 struct st21nfca_nfc_platform_data *pdata;
624 int r;
625
626 dev_dbg(&client->dev, "%s\n", __func__);
627 dev_dbg(&client->dev, "IRQ: %d\n", client->irq);
628
629 if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
630 nfc_err(&client->dev, "Need I2C_FUNC_I2C\n");
631 return -ENODEV;
632 }
633
634 phy = devm_kzalloc(&client->dev, sizeof(struct st21nfca_i2c_phy),
635 GFP_KERNEL);
636 if (!phy) {
637 nfc_err(&client->dev,
638 "Cannot allocate memory for st21nfca i2c phy.\n");
639 return -ENOMEM;
640 }
641
642 phy->i2c_dev = client;
643 phy->pending_skb = alloc_skb(ST21NFCA_HCI_LLC_MAX_SIZE * 2, GFP_KERNEL);
644 if (phy->pending_skb == NULL)
645 return -ENOMEM;
646
647 phy->current_read_len = 0;
648 phy->crc_trials = 0;
649 mutex_init(&phy->phy_lock);
650 i2c_set_clientdata(client, phy);
651
652 pdata = client->dev.platform_data;
653 if (!pdata && client->dev.of_node) {
654 r = st21nfca_hci_i2c_of_request_resources(client);
655 if (r) {
656 nfc_err(&client->dev, "No platform data\n");
657 return r;
658 }
659 } else if (pdata) {
660 r = st21nfca_hci_i2c_request_resources(client);
661 if (r) {
662 nfc_err(&client->dev, "Cannot get platform resources\n");
663 return r;
664 }
665 } else {
666 nfc_err(&client->dev, "st21nfca platform resources not available\n");
667 return -ENODEV;
668 }
669
670 r = st21nfca_hci_platform_init(phy);
671 if (r < 0) {
672 nfc_err(&client->dev, "Unable to reboot st21nfca\n");
673 return -ENODEV;
674 }
675
676 r = devm_request_threaded_irq(&client->dev, client->irq, NULL,
677 st21nfca_hci_irq_thread_fn,
678 phy->irq_polarity | IRQF_ONESHOT,
679 ST21NFCA_HCI_DRIVER_NAME, phy);
680 if (r < 0) {
681 nfc_err(&client->dev, "Unable to register IRQ handler\n");
682 return r;
683 }
684
685 return st21nfca_hci_probe(phy, &i2c_phy_ops, LLC_SHDLC_NAME,
686 ST21NFCA_FRAME_HEADROOM, ST21NFCA_FRAME_TAILROOM,
687 ST21NFCA_HCI_LLC_MAX_PAYLOAD, &phy->hdev);
688}
689
690static int st21nfca_hci_i2c_remove(struct i2c_client *client)
691{
692 struct st21nfca_i2c_phy *phy = i2c_get_clientdata(client);
693
694 dev_dbg(&client->dev, "%s\n", __func__);
695
696 st21nfca_hci_remove(phy->hdev);
697
698 if (phy->powered)
699 st21nfca_hci_i2c_disable(phy);
700
701 return 0;
702}
703
704static const struct of_device_id of_st21nfca_i2c_match[] = {
705 { .compatible = "st,st21nfca_i2c", },
706 {}
707};
708
709static struct i2c_driver st21nfca_hci_i2c_driver = {
710 .driver = {
711 .owner = THIS_MODULE,
712 .name = ST21NFCA_HCI_I2C_DRIVER_NAME,
713 .owner = THIS_MODULE,
714 .of_match_table = of_match_ptr(of_st21nfca_i2c_match),
715 },
716 .probe = st21nfca_hci_i2c_probe,
717 .id_table = st21nfca_hci_i2c_id_table,
718 .remove = st21nfca_hci_i2c_remove,
719};
720
721module_i2c_driver(st21nfca_hci_i2c_driver);
722
723MODULE_LICENSE("GPL");
724MODULE_DESCRIPTION(DRIVER_DESC);
diff --git a/drivers/nfc/st21nfca/st21nfca.c b/drivers/nfc/st21nfca/st21nfca.c
new file mode 100644
index 000000000000..51e0f00b3a4f
--- /dev/null
+++ b/drivers/nfc/st21nfca/st21nfca.c
@@ -0,0 +1,698 @@
1/*
2 * HCI based Driver for STMicroelectronics NFC Chip
3 *
4 * Copyright (C) 2014 STMicroelectronics SAS. All rights reserved.
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, see <http://www.gnu.org/licenses/>.
17 */
18
19#include <linux/module.h>
20#include <linux/nfc.h>
21#include <net/nfc/hci.h>
22#include <net/nfc/llc.h>
23
24#include "st21nfca.h"
25
26#define DRIVER_DESC "HCI NFC driver for ST21NFCA"
27
28#define FULL_VERSION_LEN 3
29
30/* Proprietary gates, events, commands and registers */
31
32/* Commands that apply to all RF readers */
33#define ST21NFCA_RF_READER_CMD_PRESENCE_CHECK 0x30
34
35#define ST21NFCA_RF_READER_ISO15693_GATE 0x12
36#define ST21NFCA_RF_READER_ISO15693_INVENTORY 0x01
37
38/*
39 * Reader gate for communication with contact-less cards using Type A
40 * protocol ISO14443-3 but not compliant with ISO14443-4
41 */
42#define ST21NFCA_RF_READER_14443_3_A_GATE 0x15
43#define ST21NFCA_RF_READER_14443_3_A_UID 0x02
44#define ST21NFCA_RF_READER_14443_3_A_ATQA 0x03
45#define ST21NFCA_RF_READER_14443_3_A_SAK 0x04
46
47#define ST21NFCA_DEVICE_MGNT_GATE 0x01
48#define ST21NFCA_DEVICE_MGNT_PIPE 0x02
49
50#define ST21NFCA_DM_GETINFO 0x13
51#define ST21NFCA_DM_GETINFO_PIPE_LIST 0x02
52#define ST21NFCA_DM_GETINFO_PIPE_INFO 0x01
53#define ST21NFCA_DM_PIPE_CREATED 0x02
54#define ST21NFCA_DM_PIPE_OPEN 0x04
55#define ST21NFCA_DM_RF_ACTIVE 0x80
56
57#define ST21NFCA_DM_IS_PIPE_OPEN(p) \
58 ((p & 0x0f) == (ST21NFCA_DM_PIPE_CREATED | ST21NFCA_DM_PIPE_OPEN))
59
60#define ST21NFCA_NFC_MODE 0x03 /* NFC_MODE parameter*/
61
62static DECLARE_BITMAP(dev_mask, ST21NFCA_NUM_DEVICES);
63
64static struct nfc_hci_gate st21nfca_gates[] = {
65 {NFC_HCI_ADMIN_GATE, NFC_HCI_ADMIN_PIPE},
66 {NFC_HCI_LOOPBACK_GATE, NFC_HCI_INVALID_PIPE},
67 {NFC_HCI_ID_MGMT_GATE, NFC_HCI_INVALID_PIPE},
68 {NFC_HCI_LINK_MGMT_GATE, NFC_HCI_LINK_MGMT_PIPE},
69 {NFC_HCI_RF_READER_B_GATE, NFC_HCI_INVALID_PIPE},
70 {NFC_HCI_RF_READER_A_GATE, NFC_HCI_INVALID_PIPE},
71 {ST21NFCA_DEVICE_MGNT_GATE, ST21NFCA_DEVICE_MGNT_PIPE},
72 {ST21NFCA_RF_READER_F_GATE, NFC_HCI_INVALID_PIPE},
73 {ST21NFCA_RF_READER_14443_3_A_GATE, NFC_HCI_INVALID_PIPE},
74 {ST21NFCA_RF_READER_ISO15693_GATE, NFC_HCI_INVALID_PIPE},
75};
76
77struct st21nfca_pipe_info {
78 u8 pipe_state;
79 u8 src_host_id;
80 u8 src_gate_id;
81 u8 dst_host_id;
82 u8 dst_gate_id;
83} __packed;
84
85/* Largest headroom needed for outgoing custom commands */
86#define ST21NFCA_CMDS_HEADROOM 7
87
88static int st21nfca_hci_load_session(struct nfc_hci_dev *hdev)
89{
90 int i, j, r;
91 struct sk_buff *skb_pipe_list, *skb_pipe_info;
92 struct st21nfca_pipe_info *info;
93
94 u8 pipe_list[] = { ST21NFCA_DM_GETINFO_PIPE_LIST,
95 NFC_HCI_TERMINAL_HOST_ID
96 };
97 u8 pipe_info[] = { ST21NFCA_DM_GETINFO_PIPE_INFO,
98 NFC_HCI_TERMINAL_HOST_ID, 0
99 };
100
101 skb_pipe_list = alloc_skb(ST21NFCA_HCI_LLC_MAX_SIZE, GFP_KERNEL);
102 if (!skb_pipe_list) {
103 r = -ENOMEM;
104 goto free_list;
105 }
106
107 skb_pipe_info = alloc_skb(ST21NFCA_HCI_LLC_MAX_SIZE, GFP_KERNEL);
108 if (!skb_pipe_info) {
109 r = -ENOMEM;
110 goto free_info;
111 }
112
113 /* On ST21NFCA device pipes number are dynamics
114 * A maximum of 16 pipes can be created at the same time
115 * If pipes are already created, hci_dev_up will fail.
116 * Doing a clear all pipe is a bad idea because:
117 * - It does useless EEPROM cycling
118 * - It might cause issue for secure elements support
119 * (such as removing connectivity or APDU reader pipe)
120 * A better approach on ST21NFCA is to:
121 * - get a pipe list for each host.
122 * (eg: NFC_HCI_HOST_CONTROLLER_ID for now).
123 * (TODO Later on UICC HOST and eSE HOST)
124 * - get pipe information
125 * - match retrieved pipe list in st21nfca_gates
126 * ST21NFCA_DEVICE_MGNT_GATE is a proprietary gate
127 * with ST21NFCA_DEVICE_MGNT_PIPE.
128 * Pipe can be closed and need to be open.
129 */
130 r = nfc_hci_connect_gate(hdev, NFC_HCI_HOST_CONTROLLER_ID,
131 ST21NFCA_DEVICE_MGNT_GATE, ST21NFCA_DEVICE_MGNT_PIPE);
132 if (r < 0)
133 goto free_info;
134
135 /* Get pipe list */
136 r = nfc_hci_send_cmd(hdev, ST21NFCA_DEVICE_MGNT_GATE,
137 ST21NFCA_DM_GETINFO, pipe_list, sizeof(pipe_list),
138 &skb_pipe_list);
139 if (r < 0)
140 goto free_info;
141
142 /* Complete the existing gate_pipe table */
143 for (i = 0; i < skb_pipe_list->len; i++) {
144 pipe_info[2] = skb_pipe_list->data[i];
145 r = nfc_hci_send_cmd(hdev, ST21NFCA_DEVICE_MGNT_GATE,
146 ST21NFCA_DM_GETINFO, pipe_info,
147 sizeof(pipe_info), &skb_pipe_info);
148
149 if (r)
150 continue;
151
152 /*
153 * Match pipe ID and gate ID
154 * Output format from ST21NFC_DM_GETINFO is:
155 * - pipe state (1byte)
156 * - source hid (1byte)
157 * - source gid (1byte)
158 * - destination hid (1byte)
159 * - destination gid (1byte)
160 */
161 info = (struct st21nfca_pipe_info *) skb_pipe_info->data;
162 for (j = 0; (j < ARRAY_SIZE(st21nfca_gates)) &&
163 (st21nfca_gates[j].gate != info->dst_gate_id);
164 j++)
165 ;
166
167 if (j < ARRAY_SIZE(st21nfca_gates) &&
168 st21nfca_gates[j].gate == info->dst_gate_id &&
169 ST21NFCA_DM_IS_PIPE_OPEN(info->pipe_state)) {
170 st21nfca_gates[j].pipe = pipe_info[2];
171 hdev->gate2pipe[st21nfca_gates[j].gate] =
172 st21nfca_gates[j].pipe;
173 }
174 }
175
176 /*
177 * 3 gates have a well known pipe ID.
178 * They will never appear in the pipe list
179 */
180 if (skb_pipe_list->len + 3 < ARRAY_SIZE(st21nfca_gates)) {
181 for (i = skb_pipe_list->len + 3;
182 i < ARRAY_SIZE(st21nfca_gates); i++) {
183 r = nfc_hci_connect_gate(hdev,
184 NFC_HCI_HOST_CONTROLLER_ID,
185 st21nfca_gates[i].gate,
186 st21nfca_gates[i].pipe);
187 if (r < 0)
188 goto free_info;
189 }
190 }
191
192 memcpy(hdev->init_data.gates, st21nfca_gates, sizeof(st21nfca_gates));
193free_info:
194 kfree_skb(skb_pipe_info);
195free_list:
196 kfree_skb(skb_pipe_list);
197 return r;
198}
199
200static int st21nfca_hci_open(struct nfc_hci_dev *hdev)
201{
202 struct st21nfca_hci_info *info = nfc_hci_get_clientdata(hdev);
203 int r;
204
205 mutex_lock(&info->info_lock);
206
207 if (info->state != ST21NFCA_ST_COLD) {
208 r = -EBUSY;
209 goto out;
210 }
211
212 r = info->phy_ops->enable(info->phy_id);
213
214 if (r == 0)
215 info->state = ST21NFCA_ST_READY;
216
217out:
218 mutex_unlock(&info->info_lock);
219 return r;
220}
221
222static void st21nfca_hci_close(struct nfc_hci_dev *hdev)
223{
224 struct st21nfca_hci_info *info = nfc_hci_get_clientdata(hdev);
225
226 mutex_lock(&info->info_lock);
227
228 if (info->state == ST21NFCA_ST_COLD)
229 goto out;
230
231 info->phy_ops->disable(info->phy_id);
232 info->state = ST21NFCA_ST_COLD;
233
234out:
235 mutex_unlock(&info->info_lock);
236}
237
238static int st21nfca_hci_ready(struct nfc_hci_dev *hdev)
239{
240 struct sk_buff *skb;
241
242 u8 param;
243 int r;
244
245 param = NFC_HCI_UICC_HOST_ID;
246 r = nfc_hci_set_param(hdev, NFC_HCI_ADMIN_GATE,
247 NFC_HCI_ADMIN_WHITELIST, &param, 1);
248 if (r < 0)
249 return r;
250
251 /* Set NFC_MODE in device management gate to enable */
252 r = nfc_hci_get_param(hdev, ST21NFCA_DEVICE_MGNT_GATE,
253 ST21NFCA_NFC_MODE, &skb);
254 if (r < 0)
255 return r;
256
257 if (skb->data[0] == 0) {
258 kfree_skb(skb);
259 param = 1;
260
261 r = nfc_hci_set_param(hdev, ST21NFCA_DEVICE_MGNT_GATE,
262 ST21NFCA_NFC_MODE, &param, 1);
263 if (r < 0)
264 return r;
265 }
266
267 r = nfc_hci_send_event(hdev, NFC_HCI_RF_READER_A_GATE,
268 NFC_HCI_EVT_END_OPERATION, NULL, 0);
269 if (r < 0)
270 return r;
271
272 r = nfc_hci_get_param(hdev, NFC_HCI_ID_MGMT_GATE,
273 NFC_HCI_ID_MGMT_VERSION_SW, &skb);
274 if (r < 0)
275 return r;
276
277 if (skb->len != FULL_VERSION_LEN) {
278 kfree_skb(skb);
279 return -EINVAL;
280 }
281
282 print_hex_dump(KERN_DEBUG, "FULL VERSION SOFTWARE INFO: ",
283 DUMP_PREFIX_NONE, 16, 1,
284 skb->data, FULL_VERSION_LEN, false);
285
286 kfree_skb(skb);
287
288 return 0;
289}
290
291static int st21nfca_hci_xmit(struct nfc_hci_dev *hdev, struct sk_buff *skb)
292{
293 struct st21nfca_hci_info *info = nfc_hci_get_clientdata(hdev);
294
295 return info->phy_ops->write(info->phy_id, skb);
296}
297
298static int st21nfca_hci_start_poll(struct nfc_hci_dev *hdev,
299 u32 im_protocols, u32 tm_protocols)
300{
301 int r;
302
303 pr_info(DRIVER_DESC ": %s protocols 0x%x 0x%x\n",
304 __func__, im_protocols, tm_protocols);
305
306 r = nfc_hci_send_event(hdev, NFC_HCI_RF_READER_A_GATE,
307 NFC_HCI_EVT_END_OPERATION, NULL, 0);
308 if (r < 0)
309 return r;
310 if (im_protocols) {
311 /*
312 * enable polling according to im_protocols & tm_protocols
313 * - CLOSE pipe according to im_protocols & tm_protocols
314 */
315 if ((NFC_HCI_RF_READER_B_GATE & im_protocols) == 0) {
316 r = nfc_hci_disconnect_gate(hdev,
317 NFC_HCI_RF_READER_B_GATE);
318 if (r < 0)
319 return r;
320 }
321
322 if ((NFC_HCI_RF_READER_A_GATE & im_protocols) == 0) {
323 r = nfc_hci_disconnect_gate(hdev,
324 NFC_HCI_RF_READER_A_GATE);
325 if (r < 0)
326 return r;
327 }
328
329 if ((ST21NFCA_RF_READER_F_GATE & im_protocols) == 0) {
330 r = nfc_hci_disconnect_gate(hdev,
331 ST21NFCA_RF_READER_F_GATE);
332 if (r < 0)
333 return r;
334 }
335
336 if ((ST21NFCA_RF_READER_14443_3_A_GATE & im_protocols) == 0) {
337 r = nfc_hci_disconnect_gate(hdev,
338 ST21NFCA_RF_READER_14443_3_A_GATE);
339 if (r < 0)
340 return r;
341 }
342
343 if ((ST21NFCA_RF_READER_ISO15693_GATE & im_protocols) == 0) {
344 r = nfc_hci_disconnect_gate(hdev,
345 ST21NFCA_RF_READER_ISO15693_GATE);
346 if (r < 0)
347 return r;
348 }
349
350 r = nfc_hci_send_event(hdev, NFC_HCI_RF_READER_A_GATE,
351 NFC_HCI_EVT_READER_REQUESTED, NULL, 0);
352 if (r < 0)
353 nfc_hci_send_event(hdev, NFC_HCI_RF_READER_A_GATE,
354 NFC_HCI_EVT_END_OPERATION, NULL, 0);
355 }
356 return r;
357}
358
359static int st21nfca_get_iso14443_3_atqa(struct nfc_hci_dev *hdev, u16 *atqa)
360{
361 int r;
362 struct sk_buff *atqa_skb = NULL;
363
364 r = nfc_hci_get_param(hdev, ST21NFCA_RF_READER_14443_3_A_GATE,
365 ST21NFCA_RF_READER_14443_3_A_ATQA, &atqa_skb);
366 if (r < 0)
367 goto exit;
368
369 if (atqa_skb->len != 2) {
370 r = -EPROTO;
371 goto exit;
372 }
373
374 *atqa = be16_to_cpu(*(__be16 *) atqa_skb->data);
375
376exit:
377 kfree_skb(atqa_skb);
378 return r;
379}
380
381static int st21nfca_get_iso14443_3_sak(struct nfc_hci_dev *hdev, u8 *sak)
382{
383 int r;
384 struct sk_buff *sak_skb = NULL;
385
386 r = nfc_hci_get_param(hdev, ST21NFCA_RF_READER_14443_3_A_GATE,
387 ST21NFCA_RF_READER_14443_3_A_SAK, &sak_skb);
388 if (r < 0)
389 goto exit;
390
391 if (sak_skb->len != 1) {
392 r = -EPROTO;
393 goto exit;
394 }
395
396 *sak = sak_skb->data[0];
397
398exit:
399 kfree_skb(sak_skb);
400 return r;
401}
402
403static int st21nfca_get_iso14443_3_uid(struct nfc_hci_dev *hdev, u8 *gate,
404 int *len)
405{
406 int r;
407 struct sk_buff *uid_skb = NULL;
408
409 r = nfc_hci_get_param(hdev, ST21NFCA_RF_READER_14443_3_A_GATE,
410 ST21NFCA_RF_READER_14443_3_A_UID, &uid_skb);
411 if (r < 0)
412 goto exit;
413
414 if (uid_skb->len == 0 || uid_skb->len > NFC_NFCID1_MAXSIZE) {
415 r = -EPROTO;
416 goto exit;
417 }
418
419 gate = uid_skb->data;
420 *len = uid_skb->len;
421exit:
422 kfree_skb(uid_skb);
423 return r;
424}
425
426static int st21nfca_get_iso15693_inventory(struct nfc_hci_dev *hdev,
427 struct nfc_target *target)
428{
429 int r;
430 struct sk_buff *inventory_skb = NULL;
431
432 r = nfc_hci_get_param(hdev, ST21NFCA_RF_READER_ISO15693_GATE,
433 ST21NFCA_RF_READER_ISO15693_INVENTORY,
434 &inventory_skb);
435 if (r < 0)
436 goto exit;
437
438 skb_pull(inventory_skb, 2);
439
440 if (inventory_skb->len == 0 ||
441 inventory_skb->len > NFC_ISO15693_UID_MAXSIZE) {
442 r = -EPROTO;
443 goto exit;
444 }
445
446 memcpy(target->iso15693_uid, inventory_skb->data, inventory_skb->len);
447 target->iso15693_dsfid = inventory_skb->data[1];
448 target->is_iso15693 = 1;
449exit:
450 kfree_skb(inventory_skb);
451 return r;
452}
453
454static int st21nfca_hci_target_from_gate(struct nfc_hci_dev *hdev, u8 gate,
455 struct nfc_target *target)
456{
457 int r, len;
458 u16 atqa;
459 u8 sak;
460 u8 uid[NFC_NFCID1_MAXSIZE];
461
462 switch (gate) {
463 case ST21NFCA_RF_READER_F_GATE:
464 target->supported_protocols = NFC_PROTO_FELICA_MASK;
465 break;
466 case ST21NFCA_RF_READER_14443_3_A_GATE:
467 /* ISO14443-3 type 1 or 2 tags */
468 r = st21nfca_get_iso14443_3_atqa(hdev, &atqa);
469 if (r < 0)
470 return r;
471 if (atqa == 0x000c) {
472 target->supported_protocols = NFC_PROTO_JEWEL_MASK;
473 target->sens_res = 0x0c00;
474 } else {
475 r = st21nfca_get_iso14443_3_sak(hdev, &sak);
476 if (r < 0)
477 return r;
478
479 r = st21nfca_get_iso14443_3_uid(hdev, uid, &len);
480 if (r < 0)
481 return r;
482
483 target->supported_protocols =
484 nfc_hci_sak_to_protocol(sak);
485 if (target->supported_protocols == 0xffffffff)
486 return -EPROTO;
487
488 target->sens_res = atqa;
489 target->sel_res = sak;
490 memcpy(target->nfcid1, uid, len);
491 target->nfcid1_len = len;
492 }
493
494 break;
495 case ST21NFCA_RF_READER_ISO15693_GATE:
496 target->supported_protocols = NFC_PROTO_ISO15693_MASK;
497 r = st21nfca_get_iso15693_inventory(hdev, target);
498 if (r < 0)
499 return r;
500 break;
501 default:
502 return -EPROTO;
503 }
504
505 return 0;
506}
507
508#define ST21NFCA_CB_TYPE_READER_ISO15693 1
509static void st21nfca_hci_data_exchange_cb(void *context, struct sk_buff *skb,
510 int err)
511{
512 struct st21nfca_hci_info *info = context;
513
514 switch (info->async_cb_type) {
515 case ST21NFCA_CB_TYPE_READER_ISO15693:
516 if (err == 0)
517 skb_trim(skb, skb->len - 1);
518 info->async_cb(info->async_cb_context, skb, err);
519 break;
520 default:
521 if (err == 0)
522 kfree_skb(skb);
523 break;
524 }
525}
526
527/*
528 * Returns:
529 * <= 0: driver handled the data exchange
530 * 1: driver doesn't especially handle, please do standard processing
531 */
532static int st21nfca_hci_im_transceive(struct nfc_hci_dev *hdev,
533 struct nfc_target *target,
534 struct sk_buff *skb,
535 data_exchange_cb_t cb, void *cb_context)
536{
537 struct st21nfca_hci_info *info = nfc_hci_get_clientdata(hdev);
538
539 pr_info(DRIVER_DESC ": %s for gate=%d len=%d\n", __func__,
540 target->hci_reader_gate, skb->len);
541
542 switch (target->hci_reader_gate) {
543 case ST21NFCA_RF_READER_F_GATE:
544 *skb_push(skb, 1) = 0x1a;
545 return nfc_hci_send_cmd_async(hdev, target->hci_reader_gate,
546 ST21NFCA_WR_XCHG_DATA, skb->data,
547 skb->len, cb, cb_context);
548 case ST21NFCA_RF_READER_14443_3_A_GATE:
549 *skb_push(skb, 1) = 0x1a; /* CTR, see spec:10.2.2.1 */
550
551 return nfc_hci_send_cmd_async(hdev, target->hci_reader_gate,
552 ST21NFCA_WR_XCHG_DATA, skb->data,
553 skb->len, cb, cb_context);
554 case ST21NFCA_RF_READER_ISO15693_GATE:
555 info->async_cb_type = ST21NFCA_CB_TYPE_READER_ISO15693;
556 info->async_cb = cb;
557 info->async_cb_context = cb_context;
558
559 *skb_push(skb, 1) = 0x17;
560
561 return nfc_hci_send_cmd_async(hdev, target->hci_reader_gate,
562 ST21NFCA_WR_XCHG_DATA, skb->data,
563 skb->len,
564 st21nfca_hci_data_exchange_cb,
565 info);
566 break;
567 default:
568 return 1;
569 }
570}
571
572static int st21nfca_hci_check_presence(struct nfc_hci_dev *hdev,
573 struct nfc_target *target)
574{
575 u8 fwi = 0x11;
576 switch (target->hci_reader_gate) {
577 case NFC_HCI_RF_READER_A_GATE:
578 case NFC_HCI_RF_READER_B_GATE:
579 /*
580 * PRESENCE_CHECK on those gates is available
581 * However, the answer to this command is taking 3 * fwi
582 * if the card is no present.
583 * Instead, we send an empty I-Frame with a very short
584 * configurable fwi ~604µs.
585 */
586 return nfc_hci_send_cmd(hdev, target->hci_reader_gate,
587 ST21NFCA_WR_XCHG_DATA, &fwi, 1, NULL);
588 case ST21NFCA_RF_READER_14443_3_A_GATE:
589 return nfc_hci_send_cmd(hdev, target->hci_reader_gate,
590 ST21NFCA_RF_READER_CMD_PRESENCE_CHECK,
591 NULL, 0, NULL);
592 default:
593 return -EOPNOTSUPP;
594 }
595}
596
597static struct nfc_hci_ops st21nfca_hci_ops = {
598 .open = st21nfca_hci_open,
599 .close = st21nfca_hci_close,
600 .load_session = st21nfca_hci_load_session,
601 .hci_ready = st21nfca_hci_ready,
602 .xmit = st21nfca_hci_xmit,
603 .start_poll = st21nfca_hci_start_poll,
604 .target_from_gate = st21nfca_hci_target_from_gate,
605 .im_transceive = st21nfca_hci_im_transceive,
606 .check_presence = st21nfca_hci_check_presence,
607};
608
609int st21nfca_hci_probe(void *phy_id, struct nfc_phy_ops *phy_ops,
610 char *llc_name, int phy_headroom, int phy_tailroom,
611 int phy_payload, struct nfc_hci_dev **hdev)
612{
613 struct st21nfca_hci_info *info;
614 int r = 0;
615 int dev_num;
616 u32 protocols;
617 struct nfc_hci_init_data init_data;
618 unsigned long quirks = 0;
619
620 info = kzalloc(sizeof(struct st21nfca_hci_info), GFP_KERNEL);
621 if (!info) {
622 r = -ENOMEM;
623 goto err_alloc_hdev;
624 }
625
626 info->phy_ops = phy_ops;
627 info->phy_id = phy_id;
628 info->state = ST21NFCA_ST_COLD;
629 mutex_init(&info->info_lock);
630
631 init_data.gate_count = ARRAY_SIZE(st21nfca_gates);
632
633 memcpy(init_data.gates, st21nfca_gates, sizeof(st21nfca_gates));
634
635 /*
636 * Session id must include the driver name + i2c bus addr
637 * persistent info to discriminate 2 identical chips
638 */
639 dev_num = find_first_zero_bit(dev_mask, ST21NFCA_NUM_DEVICES);
640 if (dev_num >= ST21NFCA_NUM_DEVICES)
641 goto err_alloc_hdev;
642
643 scnprintf(init_data.session_id, sizeof(init_data.session_id), "%s%2x",
644 "ST21AH", dev_num);
645
646 protocols = NFC_PROTO_JEWEL_MASK |
647 NFC_PROTO_MIFARE_MASK |
648 NFC_PROTO_FELICA_MASK |
649 NFC_PROTO_ISO14443_MASK |
650 NFC_PROTO_ISO14443_B_MASK |
651 NFC_PROTO_ISO15693_MASK;
652
653 set_bit(NFC_HCI_QUIRK_SHORT_CLEAR, &quirks);
654
655 info->hdev =
656 nfc_hci_allocate_device(&st21nfca_hci_ops, &init_data, quirks,
657 protocols, llc_name,
658 phy_headroom + ST21NFCA_CMDS_HEADROOM,
659 phy_tailroom, phy_payload);
660
661 if (!info->hdev) {
662 pr_err("Cannot allocate nfc hdev.\n");
663 r = -ENOMEM;
664 goto err_alloc_hdev;
665 }
666
667 nfc_hci_set_clientdata(info->hdev, info);
668
669 r = nfc_hci_register_device(info->hdev);
670 if (r)
671 goto err_regdev;
672
673 *hdev = info->hdev;
674
675 return 0;
676
677err_regdev:
678 nfc_hci_free_device(info->hdev);
679
680err_alloc_hdev:
681 kfree(info);
682
683 return r;
684}
685EXPORT_SYMBOL(st21nfca_hci_probe);
686
687void st21nfca_hci_remove(struct nfc_hci_dev *hdev)
688{
689 struct st21nfca_hci_info *info = nfc_hci_get_clientdata(hdev);
690
691 nfc_hci_unregister_device(hdev);
692 nfc_hci_free_device(hdev);
693 kfree(info);
694}
695EXPORT_SYMBOL(st21nfca_hci_remove);
696
697MODULE_LICENSE("GPL");
698MODULE_DESCRIPTION(DRIVER_DESC);
diff --git a/drivers/nfc/st21nfca/st21nfca.h b/drivers/nfc/st21nfca/st21nfca.h
new file mode 100644
index 000000000000..334cd90bcc8c
--- /dev/null
+++ b/drivers/nfc/st21nfca/st21nfca.h
@@ -0,0 +1,87 @@
1/*
2 * Copyright (C) 2014 STMicroelectronics SAS. All rights reserved.
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program; if not, see <http://www.gnu.org/licenses/>.
15 */
16
17#ifndef __LOCAL_ST21NFCA_H_
18#define __LOCAL_ST21NFCA_H_
19
20#include <net/nfc/hci.h>
21
22#define HCI_MODE 0
23
24/* framing in HCI mode */
25#define ST21NFCA_SOF_EOF_LEN 2
26
27/* Almost every time value is 0 */
28#define ST21NFCA_HCI_LLC_LEN 1
29
30/* Size in worst case :
31 * In normal case CRC len = 2 but byte stuffing
32 * may appear in case one CRC byte = ST21NFCA_SOF_EOF
33 */
34#define ST21NFCA_HCI_LLC_CRC 4
35
36#define ST21NFCA_HCI_LLC_LEN_CRC (ST21NFCA_SOF_EOF_LEN + \
37 ST21NFCA_HCI_LLC_LEN + \
38 ST21NFCA_HCI_LLC_CRC)
39#define ST21NFCA_HCI_LLC_MIN_SIZE (1 + ST21NFCA_HCI_LLC_LEN_CRC)
40
41/* Worst case when adding byte stuffing between each byte */
42#define ST21NFCA_HCI_LLC_MAX_PAYLOAD 29
43#define ST21NFCA_HCI_LLC_MAX_SIZE (ST21NFCA_HCI_LLC_LEN_CRC + 1 + \
44 ST21NFCA_HCI_LLC_MAX_PAYLOAD)
45
46#define DRIVER_DESC "HCI NFC driver for ST21NFCA"
47
48#define ST21NFCA_HCI_MODE 0
49
50#define ST21NFCA_NUM_DEVICES 256
51
52int st21nfca_hci_probe(void *phy_id, struct nfc_phy_ops *phy_ops,
53 char *llc_name, int phy_headroom, int phy_tailroom,
54 int phy_payload, struct nfc_hci_dev **hdev);
55void st21nfca_hci_remove(struct nfc_hci_dev *hdev);
56
57enum st21nfca_state {
58 ST21NFCA_ST_COLD,
59 ST21NFCA_ST_READY,
60};
61
62struct st21nfca_hci_info {
63 struct nfc_phy_ops *phy_ops;
64 void *phy_id;
65
66 struct nfc_hci_dev *hdev;
67
68 enum st21nfca_state state;
69
70 struct mutex info_lock;
71
72 int async_cb_type;
73 data_exchange_cb_t async_cb;
74 void *async_cb_context;
75
76} __packed;
77
78/* Reader RF commands */
79#define ST21NFCA_WR_XCHG_DATA 0x10
80
81#define ST21NFCA_RF_READER_F_GATE 0x14
82#define ST21NFCA_RF_READER_F_DATARATE 0x01
83#define ST21NFCA_RF_READER_F_DATARATE_106 0x01
84#define ST21NFCA_RF_READER_F_DATARATE_212 0x02
85#define ST21NFCA_RF_READER_F_DATARATE_424 0x04
86
87#endif /* __LOCAL_ST21NFCA_H_ */
diff --git a/drivers/nfc/trf7970a.c b/drivers/nfc/trf7970a.c
index d9babe986473..efb36593ecb4 100644
--- a/drivers/nfc/trf7970a.c
+++ b/drivers/nfc/trf7970a.c
@@ -16,6 +16,7 @@
16#include <linux/device.h> 16#include <linux/device.h>
17#include <linux/netdevice.h> 17#include <linux/netdevice.h>
18#include <linux/interrupt.h> 18#include <linux/interrupt.h>
19#include <linux/pm_runtime.h>
19#include <linux/nfc.h> 20#include <linux/nfc.h>
20#include <linux/skbuff.h> 21#include <linux/skbuff.h>
21#include <linux/delay.h> 22#include <linux/delay.h>
@@ -67,14 +68,14 @@
67 * only the SRX bit set, it means that all of the data has been received 68 * only the SRX bit set, it means that all of the data has been received
68 * (once what's in the fifo has been read). However, depending on timing 69 * (once what's in the fifo has been read). However, depending on timing
69 * an interrupt status with only the SRX bit set may not be recived. In 70 * an interrupt status with only the SRX bit set may not be recived. In
70 * those cases, the timeout mechanism is used to wait 5 ms in case more 71 * those cases, the timeout mechanism is used to wait 20 ms in case more
71 * data arrives. After 5 ms, it is assumed that all of the data has been 72 * data arrives. After 20 ms, it is assumed that all of the data has been
72 * received and the accumulated rx data is sent upstream. The 73 * received and the accumulated rx data is sent upstream. The
73 * 'TRF7970A_ST_WAIT_FOR_RX_DATA_CONT' state is used for this purpose 74 * 'TRF7970A_ST_WAIT_FOR_RX_DATA_CONT' state is used for this purpose
74 * (i.e., it indicates that some data has been received but we're not sure 75 * (i.e., it indicates that some data has been received but we're not sure
75 * if there is more coming so a timeout in this state means all data has 76 * if there is more coming so a timeout in this state means all data has
76 * been received and there isn't an error). The delay is 5 ms since delays 77 * been received and there isn't an error). The delay is 20 ms since delays
77 * over 2 ms have been observed during testing (a little extra just in case). 78 * of ~16 ms have been observed during testing.
78 * 79 *
79 * Type 2 write and sector select commands respond with a 4-bit ACK or NACK. 80 * Type 2 write and sector select commands respond with a 4-bit ACK or NACK.
80 * Having only 4 bits in the FIFO won't normally generate an interrupt so 81 * Having only 4 bits in the FIFO won't normally generate an interrupt so
@@ -104,7 +105,9 @@
104 105
105#define TRF7970A_SUPPORTED_PROTOCOLS \ 106#define TRF7970A_SUPPORTED_PROTOCOLS \
106 (NFC_PROTO_MIFARE_MASK | NFC_PROTO_ISO14443_MASK | \ 107 (NFC_PROTO_MIFARE_MASK | NFC_PROTO_ISO14443_MASK | \
107 NFC_PROTO_ISO15693_MASK) 108 NFC_PROTO_ISO14443_B_MASK | NFC_PROTO_ISO15693_MASK)
109
110#define TRF7970A_AUTOSUSPEND_DELAY 30000 /* 30 seconds */
108 111
109/* TX data must be prefixed with a FIFO reset cmd, a cmd that depends 112/* TX data must be prefixed with a FIFO reset cmd, a cmd that depends
110 * on what the current framing is, the address of the TX length byte 1 113 * on what the current framing is, the address of the TX length byte 1
@@ -120,7 +123,7 @@
120/* TX length is 3 nibbles long ==> 4KB - 1 bytes max */ 123/* TX length is 3 nibbles long ==> 4KB - 1 bytes max */
121#define TRF7970A_TX_MAX (4096 - 1) 124#define TRF7970A_TX_MAX (4096 - 1)
122 125
123#define TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT 5 126#define TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT 20
124#define TRF7970A_WAIT_FOR_FIFO_DRAIN_TIMEOUT 3 127#define TRF7970A_WAIT_FOR_FIFO_DRAIN_TIMEOUT 3
125#define TRF7970A_WAIT_TO_ISSUE_ISO15693_EOF 20 128#define TRF7970A_WAIT_TO_ISSUE_ISO15693_EOF 20
126 129
@@ -330,13 +333,15 @@ struct trf7970a {
330 struct regulator *regulator; 333 struct regulator *regulator;
331 struct nfc_digital_dev *ddev; 334 struct nfc_digital_dev *ddev;
332 u32 quirks; 335 u32 quirks;
333 bool powering_up;
334 bool aborting; 336 bool aborting;
335 struct sk_buff *tx_skb; 337 struct sk_buff *tx_skb;
336 struct sk_buff *rx_skb; 338 struct sk_buff *rx_skb;
337 nfc_digital_cmd_complete_t cb; 339 nfc_digital_cmd_complete_t cb;
338 void *cb_arg; 340 void *cb_arg;
341 u8 chip_status_ctrl;
339 u8 iso_ctrl; 342 u8 iso_ctrl;
343 u8 iso_ctrl_tech;
344 u8 modulator_sys_clk_ctrl;
340 u8 special_fcn_reg1; 345 u8 special_fcn_reg1;
341 int technology; 346 int technology;
342 int framing; 347 int framing;
@@ -681,7 +686,9 @@ static irqreturn_t trf7970a_irq(int irq, void *dev_id)
681 trf->ignore_timeout = 686 trf->ignore_timeout =
682 !cancel_delayed_work(&trf->timeout_work); 687 !cancel_delayed_work(&trf->timeout_work);
683 trf7970a_drain_fifo(trf, status); 688 trf7970a_drain_fifo(trf, status);
684 } else if (!(status & TRF7970A_IRQ_STATUS_TX)) { 689 } else if (status == TRF7970A_IRQ_STATUS_TX) {
690 trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET);
691 } else {
685 trf7970a_send_err_upstream(trf, -EIO); 692 trf7970a_send_err_upstream(trf, -EIO);
686 } 693 }
687 break; 694 break;
@@ -757,8 +764,8 @@ static int trf7970a_init(struct trf7970a *trf)
757 if (ret) 764 if (ret)
758 goto err_out; 765 goto err_out;
759 766
760 ret = trf7970a_write(trf, TRF7970A_MODULATOR_SYS_CLK_CTRL, 767 /* Must clear NFC Target Detection Level reg due to erratum */
761 TRF7970A_MODULATOR_DEPTH_OOK); 768 ret = trf7970a_write(trf, TRF7970A_NFC_TARGET_LEVEL, 0);
762 if (ret) 769 if (ret)
763 goto err_out; 770 goto err_out;
764 771
@@ -774,12 +781,7 @@ static int trf7970a_init(struct trf7970a *trf)
774 781
775 trf->special_fcn_reg1 = 0; 782 trf->special_fcn_reg1 = 0;
776 783
777 ret = trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL, 784 trf->iso_ctrl = 0xff;
778 TRF7970A_CHIP_STATUS_RF_ON |
779 TRF7970A_CHIP_STATUS_VRS5_3);
780 if (ret)
781 goto err_out;
782
783 return 0; 785 return 0;
784 786
785err_out: 787err_out:
@@ -791,53 +793,29 @@ static void trf7970a_switch_rf_off(struct trf7970a *trf)
791{ 793{
792 dev_dbg(trf->dev, "Switching rf off\n"); 794 dev_dbg(trf->dev, "Switching rf off\n");
793 795
794 gpio_set_value(trf->en_gpio, 0); 796 trf->chip_status_ctrl &= ~TRF7970A_CHIP_STATUS_RF_ON;
795 gpio_set_value(trf->en2_gpio, 0); 797
798 trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL, trf->chip_status_ctrl);
796 799
797 trf->aborting = false; 800 trf->aborting = false;
798 trf->state = TRF7970A_ST_OFF; 801 trf->state = TRF7970A_ST_OFF;
802
803 pm_runtime_mark_last_busy(trf->dev);
804 pm_runtime_put_autosuspend(trf->dev);
799} 805}
800 806
801static int trf7970a_switch_rf_on(struct trf7970a *trf) 807static void trf7970a_switch_rf_on(struct trf7970a *trf)
802{ 808{
803 unsigned long delay;
804 int ret;
805
806 dev_dbg(trf->dev, "Switching rf on\n"); 809 dev_dbg(trf->dev, "Switching rf on\n");
807 810
808 if (trf->powering_up) 811 pm_runtime_get_sync(trf->dev);
809 usleep_range(5000, 6000);
810
811 gpio_set_value(trf->en2_gpio, 1);
812 usleep_range(1000, 2000);
813 gpio_set_value(trf->en_gpio, 1);
814 812
815 /* The delay between enabling the trf7970a and issuing the first 813 trf->state = TRF7970A_ST_IDLE;
816 * command is significantly longer the very first time after powering
817 * up. Make sure the longer delay is only done the first time.
818 */
819 if (trf->powering_up) {
820 delay = 20000;
821 trf->powering_up = false;
822 } else {
823 delay = 5000;
824 }
825
826 usleep_range(delay, delay + 1000);
827
828 ret = trf7970a_init(trf);
829 if (ret)
830 trf7970a_switch_rf_off(trf);
831 else
832 trf->state = TRF7970A_ST_IDLE;
833
834 return ret;
835} 814}
836 815
837static int trf7970a_switch_rf(struct nfc_digital_dev *ddev, bool on) 816static int trf7970a_switch_rf(struct nfc_digital_dev *ddev, bool on)
838{ 817{
839 struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 818 struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
840 int ret = 0;
841 819
842 dev_dbg(trf->dev, "Switching RF - state: %d, on: %d\n", trf->state, on); 820 dev_dbg(trf->dev, "Switching RF - state: %d, on: %d\n", trf->state, on);
843 821
@@ -846,7 +824,7 @@ static int trf7970a_switch_rf(struct nfc_digital_dev *ddev, bool on)
846 if (on) { 824 if (on) {
847 switch (trf->state) { 825 switch (trf->state) {
848 case TRF7970A_ST_OFF: 826 case TRF7970A_ST_OFF:
849 ret = trf7970a_switch_rf_on(trf); 827 trf7970a_switch_rf_on(trf);
850 break; 828 break;
851 case TRF7970A_ST_IDLE: 829 case TRF7970A_ST_IDLE:
852 case TRF7970A_ST_IDLE_RX_BLOCKED: 830 case TRF7970A_ST_IDLE_RX_BLOCKED:
@@ -871,7 +849,7 @@ static int trf7970a_switch_rf(struct nfc_digital_dev *ddev, bool on)
871 } 849 }
872 850
873 mutex_unlock(&trf->lock); 851 mutex_unlock(&trf->lock);
874 return ret; 852 return 0;
875} 853}
876 854
877static int trf7970a_config_rf_tech(struct trf7970a *trf, int tech) 855static int trf7970a_config_rf_tech(struct trf7970a *trf, int tech)
@@ -882,10 +860,16 @@ static int trf7970a_config_rf_tech(struct trf7970a *trf, int tech)
882 860
883 switch (tech) { 861 switch (tech) {
884 case NFC_DIGITAL_RF_TECH_106A: 862 case NFC_DIGITAL_RF_TECH_106A:
885 trf->iso_ctrl = TRF7970A_ISO_CTRL_14443A_106; 863 trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_14443A_106;
864 trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_OOK;
865 break;
866 case NFC_DIGITAL_RF_TECH_106B:
867 trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_14443B_106;
868 trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10;
886 break; 869 break;
887 case NFC_DIGITAL_RF_TECH_ISO15693: 870 case NFC_DIGITAL_RF_TECH_ISO15693:
888 trf->iso_ctrl = TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648; 871 trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648;
872 trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_OOK;
889 break; 873 break;
890 default: 874 default:
891 dev_dbg(trf->dev, "Unsupported rf technology: %d\n", tech); 875 dev_dbg(trf->dev, "Unsupported rf technology: %d\n", tech);
@@ -899,24 +883,29 @@ static int trf7970a_config_rf_tech(struct trf7970a *trf, int tech)
899 883
900static int trf7970a_config_framing(struct trf7970a *trf, int framing) 884static int trf7970a_config_framing(struct trf7970a *trf, int framing)
901{ 885{
886 u8 iso_ctrl = trf->iso_ctrl_tech;
887 int ret;
888
902 dev_dbg(trf->dev, "framing: %d\n", framing); 889 dev_dbg(trf->dev, "framing: %d\n", framing);
903 890
904 switch (framing) { 891 switch (framing) {
905 case NFC_DIGITAL_FRAMING_NFCA_SHORT: 892 case NFC_DIGITAL_FRAMING_NFCA_SHORT:
906 case NFC_DIGITAL_FRAMING_NFCA_STANDARD: 893 case NFC_DIGITAL_FRAMING_NFCA_STANDARD:
907 trf->tx_cmd = TRF7970A_CMD_TRANSMIT_NO_CRC; 894 trf->tx_cmd = TRF7970A_CMD_TRANSMIT_NO_CRC;
908 trf->iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N; 895 iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N;
909 break; 896 break;
910 case NFC_DIGITAL_FRAMING_NFCA_STANDARD_WITH_CRC_A: 897 case NFC_DIGITAL_FRAMING_NFCA_STANDARD_WITH_CRC_A:
911 case NFC_DIGITAL_FRAMING_NFCA_T4T: 898 case NFC_DIGITAL_FRAMING_NFCA_T4T:
899 case NFC_DIGITAL_FRAMING_NFCB:
900 case NFC_DIGITAL_FRAMING_NFCB_T4T:
912 case NFC_DIGITAL_FRAMING_ISO15693_INVENTORY: 901 case NFC_DIGITAL_FRAMING_ISO15693_INVENTORY:
913 case NFC_DIGITAL_FRAMING_ISO15693_T5T: 902 case NFC_DIGITAL_FRAMING_ISO15693_T5T:
914 trf->tx_cmd = TRF7970A_CMD_TRANSMIT; 903 trf->tx_cmd = TRF7970A_CMD_TRANSMIT;
915 trf->iso_ctrl &= ~TRF7970A_ISO_CTRL_RX_CRC_N; 904 iso_ctrl &= ~TRF7970A_ISO_CTRL_RX_CRC_N;
916 break; 905 break;
917 case NFC_DIGITAL_FRAMING_NFCA_T2T: 906 case NFC_DIGITAL_FRAMING_NFCA_T2T:
918 trf->tx_cmd = TRF7970A_CMD_TRANSMIT; 907 trf->tx_cmd = TRF7970A_CMD_TRANSMIT;
919 trf->iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N; 908 iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N;
920 break; 909 break;
921 default: 910 default:
922 dev_dbg(trf->dev, "Unsupported Framing: %d\n", framing); 911 dev_dbg(trf->dev, "Unsupported Framing: %d\n", framing);
@@ -925,24 +914,46 @@ static int trf7970a_config_framing(struct trf7970a *trf, int framing)
925 914
926 trf->framing = framing; 915 trf->framing = framing;
927 916
928 return trf7970a_write(trf, TRF7970A_ISO_CTRL, trf->iso_ctrl); 917 if (iso_ctrl != trf->iso_ctrl) {
918 ret = trf7970a_write(trf, TRF7970A_ISO_CTRL, iso_ctrl);
919 if (ret)
920 return ret;
921
922 trf->iso_ctrl = iso_ctrl;
923
924 ret = trf7970a_write(trf, TRF7970A_MODULATOR_SYS_CLK_CTRL,
925 trf->modulator_sys_clk_ctrl);
926 if (ret)
927 return ret;
928 }
929
930 if (!(trf->chip_status_ctrl & TRF7970A_CHIP_STATUS_RF_ON)) {
931 ret = trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL,
932 trf->chip_status_ctrl |
933 TRF7970A_CHIP_STATUS_RF_ON);
934 if (ret)
935 return ret;
936
937 trf->chip_status_ctrl |= TRF7970A_CHIP_STATUS_RF_ON;
938
939 usleep_range(5000, 6000);
940 }
941
942 return 0;
929} 943}
930 944
931static int trf7970a_in_configure_hw(struct nfc_digital_dev *ddev, int type, 945static int trf7970a_in_configure_hw(struct nfc_digital_dev *ddev, int type,
932 int param) 946 int param)
933{ 947{
934 struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 948 struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
935 int ret = 0; 949 int ret;
936 950
937 dev_dbg(trf->dev, "Configure hw - type: %d, param: %d\n", type, param); 951 dev_dbg(trf->dev, "Configure hw - type: %d, param: %d\n", type, param);
938 952
939 mutex_lock(&trf->lock); 953 mutex_lock(&trf->lock);
940 954
941 if (trf->state == TRF7970A_ST_OFF) { 955 if (trf->state == TRF7970A_ST_OFF)
942 ret = trf7970a_switch_rf_on(trf); 956 trf7970a_switch_rf_on(trf);
943 if (ret)
944 goto err_out;
945 }
946 957
947 switch (type) { 958 switch (type) {
948 case NFC_DIGITAL_CONFIG_RF_TECH: 959 case NFC_DIGITAL_CONFIG_RF_TECH:
@@ -956,7 +967,6 @@ static int trf7970a_in_configure_hw(struct nfc_digital_dev *ddev, int type,
956 ret = -EINVAL; 967 ret = -EINVAL;
957 } 968 }
958 969
959err_out:
960 mutex_unlock(&trf->lock); 970 mutex_unlock(&trf->lock);
961 return ret; 971 return ret;
962} 972}
@@ -1191,7 +1201,18 @@ static void trf7970a_abort_cmd(struct nfc_digital_dev *ddev)
1191 dev_dbg(trf->dev, "Abort process initiated\n"); 1201 dev_dbg(trf->dev, "Abort process initiated\n");
1192 1202
1193 mutex_lock(&trf->lock); 1203 mutex_lock(&trf->lock);
1194 trf->aborting = true; 1204
1205 switch (trf->state) {
1206 case TRF7970A_ST_WAIT_FOR_TX_FIFO:
1207 case TRF7970A_ST_WAIT_FOR_RX_DATA:
1208 case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT:
1209 case TRF7970A_ST_WAIT_TO_ISSUE_EOF:
1210 trf->aborting = true;
1211 break;
1212 default:
1213 break;
1214 }
1215
1195 mutex_unlock(&trf->lock); 1216 mutex_unlock(&trf->lock);
1196} 1217}
1197 1218
@@ -1206,12 +1227,25 @@ static struct nfc_digital_ops trf7970a_nfc_ops = {
1206 .abort_cmd = trf7970a_abort_cmd, 1227 .abort_cmd = trf7970a_abort_cmd,
1207}; 1228};
1208 1229
1230static int trf7970a_get_autosuspend_delay(struct device_node *np)
1231{
1232 int autosuspend_delay, ret;
1233
1234 ret = of_property_read_u32(np, "autosuspend-delay", &autosuspend_delay);
1235 if (ret)
1236 autosuspend_delay = TRF7970A_AUTOSUSPEND_DELAY;
1237
1238 of_node_put(np);
1239
1240 return autosuspend_delay;
1241}
1242
1209static int trf7970a_probe(struct spi_device *spi) 1243static int trf7970a_probe(struct spi_device *spi)
1210{ 1244{
1211 struct device_node *np = spi->dev.of_node; 1245 struct device_node *np = spi->dev.of_node;
1212 const struct spi_device_id *id = spi_get_device_id(spi); 1246 const struct spi_device_id *id = spi_get_device_id(spi);
1213 struct trf7970a *trf; 1247 struct trf7970a *trf;
1214 int ret; 1248 int uvolts, autosuspend_delay, ret;
1215 1249
1216 if (!np) { 1250 if (!np) {
1217 dev_err(&spi->dev, "No Device Tree entry\n"); 1251 dev_err(&spi->dev, "No Device Tree entry\n");
@@ -1281,7 +1315,10 @@ static int trf7970a_probe(struct spi_device *spi)
1281 goto err_destroy_lock; 1315 goto err_destroy_lock;
1282 } 1316 }
1283 1317
1284 trf->powering_up = true; 1318 uvolts = regulator_get_voltage(trf->regulator);
1319
1320 if (uvolts > 4000000)
1321 trf->chip_status_ctrl = TRF7970A_CHIP_STATUS_VRS5_3;
1285 1322
1286 trf->ddev = nfc_digital_allocate_device(&trf7970a_nfc_ops, 1323 trf->ddev = nfc_digital_allocate_device(&trf7970a_nfc_ops,
1287 TRF7970A_SUPPORTED_PROTOCOLS, 1324 TRF7970A_SUPPORTED_PROTOCOLS,
@@ -1297,6 +1334,12 @@ static int trf7970a_probe(struct spi_device *spi)
1297 nfc_digital_set_drvdata(trf->ddev, trf); 1334 nfc_digital_set_drvdata(trf->ddev, trf);
1298 spi_set_drvdata(spi, trf); 1335 spi_set_drvdata(spi, trf);
1299 1336
1337 autosuspend_delay = trf7970a_get_autosuspend_delay(np);
1338
1339 pm_runtime_set_autosuspend_delay(trf->dev, autosuspend_delay);
1340 pm_runtime_use_autosuspend(trf->dev);
1341 pm_runtime_enable(trf->dev);
1342
1300 ret = nfc_digital_register_device(trf->ddev); 1343 ret = nfc_digital_register_device(trf->ddev);
1301 if (ret) { 1344 if (ret) {
1302 dev_err(trf->dev, "Can't register NFC digital device: %d\n", 1345 dev_err(trf->dev, "Can't register NFC digital device: %d\n",
@@ -1307,6 +1350,7 @@ static int trf7970a_probe(struct spi_device *spi)
1307 return 0; 1350 return 0;
1308 1351
1309err_free_ddev: 1352err_free_ddev:
1353 pm_runtime_disable(trf->dev);
1310 nfc_digital_free_device(trf->ddev); 1354 nfc_digital_free_device(trf->ddev);
1311err_disable_regulator: 1355err_disable_regulator:
1312 regulator_disable(trf->regulator); 1356 regulator_disable(trf->regulator);
@@ -1321,15 +1365,16 @@ static int trf7970a_remove(struct spi_device *spi)
1321 1365
1322 mutex_lock(&trf->lock); 1366 mutex_lock(&trf->lock);
1323 1367
1324 trf7970a_switch_rf_off(trf);
1325 trf7970a_init(trf);
1326
1327 switch (trf->state) { 1368 switch (trf->state) {
1328 case TRF7970A_ST_WAIT_FOR_TX_FIFO: 1369 case TRF7970A_ST_WAIT_FOR_TX_FIFO:
1329 case TRF7970A_ST_WAIT_FOR_RX_DATA: 1370 case TRF7970A_ST_WAIT_FOR_RX_DATA:
1330 case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT: 1371 case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT:
1331 case TRF7970A_ST_WAIT_TO_ISSUE_EOF: 1372 case TRF7970A_ST_WAIT_TO_ISSUE_EOF:
1332 trf7970a_send_err_upstream(trf, -ECANCELED); 1373 trf7970a_send_err_upstream(trf, -ECANCELED);
1374 /* FALLTHROUGH */
1375 case TRF7970A_ST_IDLE:
1376 case TRF7970A_ST_IDLE_RX_BLOCKED:
1377 pm_runtime_put_sync(trf->dev);
1333 break; 1378 break;
1334 default: 1379 default:
1335 break; 1380 break;
@@ -1337,6 +1382,8 @@ static int trf7970a_remove(struct spi_device *spi)
1337 1382
1338 mutex_unlock(&trf->lock); 1383 mutex_unlock(&trf->lock);
1339 1384
1385 pm_runtime_disable(trf->dev);
1386
1340 nfc_digital_unregister_device(trf->ddev); 1387 nfc_digital_unregister_device(trf->ddev);
1341 nfc_digital_free_device(trf->ddev); 1388 nfc_digital_free_device(trf->ddev);
1342 1389
@@ -1347,6 +1394,70 @@ static int trf7970a_remove(struct spi_device *spi)
1347 return 0; 1394 return 0;
1348} 1395}
1349 1396
1397#ifdef CONFIG_PM_RUNTIME
1398static int trf7970a_pm_runtime_suspend(struct device *dev)
1399{
1400 struct spi_device *spi = container_of(dev, struct spi_device, dev);
1401 struct trf7970a *trf = spi_get_drvdata(spi);
1402 int ret;
1403
1404 dev_dbg(dev, "Runtime suspend\n");
1405
1406 if (trf->state != TRF7970A_ST_OFF) {
1407 dev_dbg(dev, "Can't suspend - not in OFF state (%d)\n",
1408 trf->state);
1409 return -EBUSY;
1410 }
1411
1412 gpio_set_value(trf->en_gpio, 0);
1413 gpio_set_value(trf->en2_gpio, 0);
1414
1415 ret = regulator_disable(trf->regulator);
1416 if (ret)
1417 dev_err(dev, "%s - Can't disable VIN: %d\n", __func__, ret);
1418
1419 return ret;
1420}
1421
1422static int trf7970a_pm_runtime_resume(struct device *dev)
1423{
1424 struct spi_device *spi = container_of(dev, struct spi_device, dev);
1425 struct trf7970a *trf = spi_get_drvdata(spi);
1426 int ret;
1427
1428 dev_dbg(dev, "Runtime resume\n");
1429
1430 ret = regulator_enable(trf->regulator);
1431 if (ret) {
1432 dev_err(dev, "%s - Can't enable VIN: %d\n", __func__, ret);
1433 return ret;
1434 }
1435
1436 usleep_range(5000, 6000);
1437
1438 gpio_set_value(trf->en2_gpio, 1);
1439 usleep_range(1000, 2000);
1440 gpio_set_value(trf->en_gpio, 1);
1441
1442 usleep_range(20000, 21000);
1443
1444 ret = trf7970a_init(trf);
1445 if (ret) {
1446 dev_err(dev, "%s - Can't initialize: %d\n", __func__, ret);
1447 return ret;
1448 }
1449
1450 pm_runtime_mark_last_busy(dev);
1451
1452 return 0;
1453}
1454#endif
1455
1456static const struct dev_pm_ops trf7970a_pm_ops = {
1457 SET_RUNTIME_PM_OPS(trf7970a_pm_runtime_suspend,
1458 trf7970a_pm_runtime_resume, NULL)
1459};
1460
1350static const struct spi_device_id trf7970a_id_table[] = { 1461static const struct spi_device_id trf7970a_id_table[] = {
1351 { "trf7970a", TRF7970A_QUIRK_IRQ_STATUS_READ_ERRATA }, 1462 { "trf7970a", TRF7970A_QUIRK_IRQ_STATUS_READ_ERRATA },
1352 { } 1463 { }
@@ -1360,6 +1471,7 @@ static struct spi_driver trf7970a_spi_driver = {
1360 .driver = { 1471 .driver = {
1361 .name = "trf7970a", 1472 .name = "trf7970a",
1362 .owner = THIS_MODULE, 1473 .owner = THIS_MODULE,
1474 .pm = &trf7970a_pm_ops,
1363 }, 1475 },
1364}; 1476};
1365 1477
diff --git a/drivers/staging/wlan-ng/cfg80211.c b/drivers/staging/wlan-ng/cfg80211.c
index f76f95c29617..723319ee08f3 100644
--- a/drivers/staging/wlan-ng/cfg80211.c
+++ b/drivers/staging/wlan-ng/cfg80211.c
@@ -84,7 +84,7 @@ static int prism2_domibset_uint32(wlandevice_t *wlandev, u32 did, u32 data)
84} 84}
85 85
86static int prism2_domibset_pstr32(wlandevice_t *wlandev, 86static int prism2_domibset_pstr32(wlandevice_t *wlandev,
87 u32 did, u8 len, u8 *data) 87 u32 did, u8 len, const u8 *data)
88{ 88{
89 struct p80211msg_dot11req_mibset msg; 89 struct p80211msg_dot11req_mibset msg;
90 p80211item_pstr32_t *mibitem = 90 p80211item_pstr32_t *mibitem =
@@ -298,7 +298,7 @@ static int prism2_set_default_key(struct wiphy *wiphy, struct net_device *dev,
298 298
299 299
300static int prism2_get_station(struct wiphy *wiphy, struct net_device *dev, 300static int prism2_get_station(struct wiphy *wiphy, struct net_device *dev,
301 u8 *mac, struct station_info *sinfo) 301 const u8 *mac, struct station_info *sinfo)
302{ 302{
303 wlandevice_t *wlandev = dev->ml_priv; 303 wlandevice_t *wlandev = dev->ml_priv;
304 struct p80211msg_lnxreq_commsquality quality; 304 struct p80211msg_lnxreq_commsquality quality;
diff --git a/include/linux/ath9k_platform.h b/include/linux/ath9k_platform.h
index 8598f8eacb20..a495a959e8a7 100644
--- a/include/linux/ath9k_platform.h
+++ b/include/linux/ath9k_platform.h
@@ -36,6 +36,8 @@ struct ath9k_platform_data {
36 36
37 int (*get_mac_revision)(void); 37 int (*get_mac_revision)(void);
38 int (*external_reset)(void); 38 int (*external_reset)(void);
39
40 bool use_eeprom;
39}; 41};
40 42
41#endif /* _LINUX_ATH9K_PLATFORM_H */ 43#endif /* _LINUX_ATH9K_PLATFORM_H */
diff --git a/include/linux/crc7.h b/include/linux/crc7.h
index 1786e772d5c6..d590765106f3 100644
--- a/include/linux/crc7.h
+++ b/include/linux/crc7.h
@@ -2,13 +2,13 @@
2#define _LINUX_CRC7_H 2#define _LINUX_CRC7_H
3#include <linux/types.h> 3#include <linux/types.h>
4 4
5extern const u8 crc7_syndrome_table[256]; 5extern const u8 crc7_be_syndrome_table[256];
6 6
7static inline u8 crc7_byte(u8 crc, u8 data) 7static inline u8 crc7_be_byte(u8 crc, u8 data)
8{ 8{
9 return crc7_syndrome_table[(crc << 1) ^ data]; 9 return crc7_be_syndrome_table[crc ^ data];
10} 10}
11 11
12extern u8 crc7(u8 crc, const u8 *buffer, size_t len); 12extern u8 crc7_be(u8 crc, const u8 *buffer, size_t len);
13 13
14#endif 14#endif
diff --git a/include/linux/platform_data/st21nfca.h b/include/linux/platform_data/st21nfca.h
new file mode 100644
index 000000000000..1730312398ff
--- /dev/null
+++ b/include/linux/platform_data/st21nfca.h
@@ -0,0 +1,32 @@
1/*
2 * Driver include for the ST21NFCA NFC chip.
3 *
4 * Copyright (C) 2014 STMicroelectronics SAS. All rights reserved.
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, see <http://www.gnu.org/licenses/>.
17 */
18
19#ifndef _ST21NFCA_HCI_H_
20#define _ST21NFCA_HCI_H_
21
22#include <linux/i2c.h>
23
24#define ST21NFCA_HCI_DRIVER_NAME "st21nfca_hci"
25
26struct st21nfca_nfc_platform_data {
27 unsigned int gpio_irq;
28 unsigned int gpio_ena;
29 unsigned int irq_polarity;
30};
31
32#endif /* _ST21NFCA_HCI_H_ */
diff --git a/include/linux/rfkill-gpio.h b/include/linux/rfkill-gpio.h
index 4d09f6eab359..20bcb55498cd 100644
--- a/include/linux/rfkill-gpio.h
+++ b/include/linux/rfkill-gpio.h
@@ -27,21 +27,11 @@
27 * struct rfkill_gpio_platform_data - platform data for rfkill gpio device. 27 * struct rfkill_gpio_platform_data - platform data for rfkill gpio device.
28 * for unused gpio's, the expected value is -1. 28 * for unused gpio's, the expected value is -1.
29 * @name: name for the gpio rf kill instance 29 * @name: name for the gpio rf kill instance
30 * @reset_gpio: GPIO which is used for reseting rfkill switch
31 * @shutdown_gpio: GPIO which is used for shutdown of rfkill switch
32 * @power_clk_name: [optional] name of clk to turn off while blocked
33 * @gpio_runtime_close: clean up platform specific gpio configuration
34 * @gpio_runtime_setup: set up platform specific gpio configuration
35 */ 30 */
36 31
37struct rfkill_gpio_platform_data { 32struct rfkill_gpio_platform_data {
38 char *name; 33 char *name;
39 int reset_gpio;
40 int shutdown_gpio;
41 const char *power_clk_name;
42 enum rfkill_type type; 34 enum rfkill_type type;
43 void (*gpio_runtime_close)(struct platform_device *);
44 int (*gpio_runtime_setup)(struct platform_device *);
45}; 35};
46 36
47#endif /* __RFKILL_GPIO_H */ 37#endif /* __RFKILL_GPIO_H */
diff --git a/include/linux/ssb/ssb.h b/include/linux/ssb/ssb.h
index 07ef9b82b66d..4568a5cc9ab8 100644
--- a/include/linux/ssb/ssb.h
+++ b/include/linux/ssb/ssb.h
@@ -33,6 +33,7 @@ struct ssb_sprom {
33 u8 et1phyaddr; /* MII address for enet1 */ 33 u8 et1phyaddr; /* MII address for enet1 */
34 u8 et0mdcport; /* MDIO for enet0 */ 34 u8 et0mdcport; /* MDIO for enet0 */
35 u8 et1mdcport; /* MDIO for enet1 */ 35 u8 et1mdcport; /* MDIO for enet1 */
36 u16 dev_id; /* Device ID overriding e.g. PCI ID */
36 u16 board_rev; /* Board revision number from SPROM. */ 37 u16 board_rev; /* Board revision number from SPROM. */
37 u16 board_num; /* Board number from SPROM. */ 38 u16 board_num; /* Board number from SPROM. */
38 u16 board_type; /* Board type from SPROM. */ 39 u16 board_type; /* Board type from SPROM. */
diff --git a/include/net/cfg80211.h b/include/net/cfg80211.h
index f2c318655519..e46c437944f7 100644
--- a/include/net/cfg80211.h
+++ b/include/net/cfg80211.h
@@ -341,8 +341,8 @@ struct vif_params {
341 * @seq_len: length of @seq. 341 * @seq_len: length of @seq.
342 */ 342 */
343struct key_params { 343struct key_params {
344 u8 *key; 344 const u8 *key;
345 u8 *seq; 345 const u8 *seq;
346 int key_len; 346 int key_len;
347 int seq_len; 347 int seq_len;
348 u32 cipher; 348 u32 cipher;
@@ -458,7 +458,7 @@ bool cfg80211_chandef_usable(struct wiphy *wiphy,
458 */ 458 */
459int cfg80211_chandef_dfs_required(struct wiphy *wiphy, 459int cfg80211_chandef_dfs_required(struct wiphy *wiphy,
460 const struct cfg80211_chan_def *chandef, 460 const struct cfg80211_chan_def *chandef,
461 enum nl80211_iftype); 461 enum nl80211_iftype iftype);
462 462
463/** 463/**
464 * ieee80211_chandef_rate_flags - returns rate flags for a channel 464 * ieee80211_chandef_rate_flags - returns rate flags for a channel
@@ -694,8 +694,10 @@ struct cfg80211_ap_settings {
694 * 694 *
695 * @chandef: defines the channel to use after the switch 695 * @chandef: defines the channel to use after the switch
696 * @beacon_csa: beacon data while performing the switch 696 * @beacon_csa: beacon data while performing the switch
697 * @counter_offset_beacon: offset for the counter within the beacon (tail) 697 * @counter_offsets_beacon: offsets of the counters within the beacon (tail)
698 * @counter_offset_presp: offset for the counter within the probe response 698 * @counter_offsets_presp: offsets of the counters within the probe response
699 * @n_counter_offsets_beacon: number of csa counters the beacon (tail)
700 * @n_counter_offsets_presp: number of csa counters in the probe response
699 * @beacon_after: beacon data to be used on the new channel 701 * @beacon_after: beacon data to be used on the new channel
700 * @radar_required: whether radar detection is required on the new channel 702 * @radar_required: whether radar detection is required on the new channel
701 * @block_tx: whether transmissions should be blocked while changing 703 * @block_tx: whether transmissions should be blocked while changing
@@ -704,7 +706,10 @@ struct cfg80211_ap_settings {
704struct cfg80211_csa_settings { 706struct cfg80211_csa_settings {
705 struct cfg80211_chan_def chandef; 707 struct cfg80211_chan_def chandef;
706 struct cfg80211_beacon_data beacon_csa; 708 struct cfg80211_beacon_data beacon_csa;
707 u16 counter_offset_beacon, counter_offset_presp; 709 const u16 *counter_offsets_beacon;
710 const u16 *counter_offsets_presp;
711 unsigned int n_counter_offsets_beacon;
712 unsigned int n_counter_offsets_presp;
708 struct cfg80211_beacon_data beacon_after; 713 struct cfg80211_beacon_data beacon_after;
709 bool radar_required; 714 bool radar_required;
710 bool block_tx; 715 bool block_tx;
@@ -868,36 +873,38 @@ int cfg80211_check_station_change(struct wiphy *wiphy,
868 * @STATION_INFO_NONPEER_PM: @nonpeer_pm filled 873 * @STATION_INFO_NONPEER_PM: @nonpeer_pm filled
869 * @STATION_INFO_CHAIN_SIGNAL: @chain_signal filled 874 * @STATION_INFO_CHAIN_SIGNAL: @chain_signal filled
870 * @STATION_INFO_CHAIN_SIGNAL_AVG: @chain_signal_avg filled 875 * @STATION_INFO_CHAIN_SIGNAL_AVG: @chain_signal_avg filled
876 * @STATION_INFO_EXPECTED_THROUGHPUT: @expected_throughput filled
871 */ 877 */
872enum station_info_flags { 878enum station_info_flags {
873 STATION_INFO_INACTIVE_TIME = 1<<0, 879 STATION_INFO_INACTIVE_TIME = BIT(0),
874 STATION_INFO_RX_BYTES = 1<<1, 880 STATION_INFO_RX_BYTES = BIT(1),
875 STATION_INFO_TX_BYTES = 1<<2, 881 STATION_INFO_TX_BYTES = BIT(2),
876 STATION_INFO_LLID = 1<<3, 882 STATION_INFO_LLID = BIT(3),
877 STATION_INFO_PLID = 1<<4, 883 STATION_INFO_PLID = BIT(4),
878 STATION_INFO_PLINK_STATE = 1<<5, 884 STATION_INFO_PLINK_STATE = BIT(5),
879 STATION_INFO_SIGNAL = 1<<6, 885 STATION_INFO_SIGNAL = BIT(6),
880 STATION_INFO_TX_BITRATE = 1<<7, 886 STATION_INFO_TX_BITRATE = BIT(7),
881 STATION_INFO_RX_PACKETS = 1<<8, 887 STATION_INFO_RX_PACKETS = BIT(8),
882 STATION_INFO_TX_PACKETS = 1<<9, 888 STATION_INFO_TX_PACKETS = BIT(9),
883 STATION_INFO_TX_RETRIES = 1<<10, 889 STATION_INFO_TX_RETRIES = BIT(10),
884 STATION_INFO_TX_FAILED = 1<<11, 890 STATION_INFO_TX_FAILED = BIT(11),
885 STATION_INFO_RX_DROP_MISC = 1<<12, 891 STATION_INFO_RX_DROP_MISC = BIT(12),
886 STATION_INFO_SIGNAL_AVG = 1<<13, 892 STATION_INFO_SIGNAL_AVG = BIT(13),
887 STATION_INFO_RX_BITRATE = 1<<14, 893 STATION_INFO_RX_BITRATE = BIT(14),
888 STATION_INFO_BSS_PARAM = 1<<15, 894 STATION_INFO_BSS_PARAM = BIT(15),
889 STATION_INFO_CONNECTED_TIME = 1<<16, 895 STATION_INFO_CONNECTED_TIME = BIT(16),
890 STATION_INFO_ASSOC_REQ_IES = 1<<17, 896 STATION_INFO_ASSOC_REQ_IES = BIT(17),
891 STATION_INFO_STA_FLAGS = 1<<18, 897 STATION_INFO_STA_FLAGS = BIT(18),
892 STATION_INFO_BEACON_LOSS_COUNT = 1<<19, 898 STATION_INFO_BEACON_LOSS_COUNT = BIT(19),
893 STATION_INFO_T_OFFSET = 1<<20, 899 STATION_INFO_T_OFFSET = BIT(20),
894 STATION_INFO_LOCAL_PM = 1<<21, 900 STATION_INFO_LOCAL_PM = BIT(21),
895 STATION_INFO_PEER_PM = 1<<22, 901 STATION_INFO_PEER_PM = BIT(22),
896 STATION_INFO_NONPEER_PM = 1<<23, 902 STATION_INFO_NONPEER_PM = BIT(23),
897 STATION_INFO_RX_BYTES64 = 1<<24, 903 STATION_INFO_RX_BYTES64 = BIT(24),
898 STATION_INFO_TX_BYTES64 = 1<<25, 904 STATION_INFO_TX_BYTES64 = BIT(25),
899 STATION_INFO_CHAIN_SIGNAL = 1<<26, 905 STATION_INFO_CHAIN_SIGNAL = BIT(26),
900 STATION_INFO_CHAIN_SIGNAL_AVG = 1<<27, 906 STATION_INFO_CHAIN_SIGNAL_AVG = BIT(27),
907 STATION_INFO_EXPECTED_THROUGHPUT = BIT(28),
901}; 908};
902 909
903/** 910/**
@@ -1019,6 +1026,8 @@ struct sta_bss_parameters {
1019 * @local_pm: local mesh STA power save mode 1026 * @local_pm: local mesh STA power save mode
1020 * @peer_pm: peer mesh STA power save mode 1027 * @peer_pm: peer mesh STA power save mode
1021 * @nonpeer_pm: non-peer mesh STA power save mode 1028 * @nonpeer_pm: non-peer mesh STA power save mode
1029 * @expected_throughput: expected throughput in kbps (including 802.11 headers)
1030 * towards this station.
1022 */ 1031 */
1023struct station_info { 1032struct station_info {
1024 u32 filled; 1033 u32 filled;
@@ -1057,6 +1066,8 @@ struct station_info {
1057 enum nl80211_mesh_power_mode peer_pm; 1066 enum nl80211_mesh_power_mode peer_pm;
1058 enum nl80211_mesh_power_mode nonpeer_pm; 1067 enum nl80211_mesh_power_mode nonpeer_pm;
1059 1068
1069 u32 expected_throughput;
1070
1060 /* 1071 /*
1061 * Note: Add a new enum station_info_flags value for each new field and 1072 * Note: Add a new enum station_info_flags value for each new field and
1062 * use it to check which fields are initialized. 1073 * use it to check which fields are initialized.
@@ -1064,6 +1075,19 @@ struct station_info {
1064}; 1075};
1065 1076
1066/** 1077/**
1078 * cfg80211_get_station - retrieve information about a given station
1079 * @dev: the device where the station is supposed to be connected to
1080 * @mac_addr: the mac address of the station of interest
1081 * @sinfo: pointer to the structure to fill with the information
1082 *
1083 * Returns 0 on success and sinfo is filled with the available information
1084 * otherwise returns a negative error code and the content of sinfo has to be
1085 * considered undefined.
1086 */
1087int cfg80211_get_station(struct net_device *dev, const u8 *mac_addr,
1088 struct station_info *sinfo);
1089
1090/**
1067 * enum monitor_flags - monitor flags 1091 * enum monitor_flags - monitor flags
1068 * 1092 *
1069 * Monitor interface configuration flags. Note that these must be the bits 1093 * Monitor interface configuration flags. Note that these must be the bits
@@ -1164,7 +1188,7 @@ struct bss_parameters {
1164 int use_cts_prot; 1188 int use_cts_prot;
1165 int use_short_preamble; 1189 int use_short_preamble;
1166 int use_short_slot_time; 1190 int use_short_slot_time;
1167 u8 *basic_rates; 1191 const u8 *basic_rates;
1168 u8 basic_rates_len; 1192 u8 basic_rates_len;
1169 int ap_isolate; 1193 int ap_isolate;
1170 int ht_opmode; 1194 int ht_opmode;
@@ -1694,10 +1718,10 @@ struct cfg80211_disassoc_request {
1694 * @ht_capa_mask: The bits of ht_capa which are to be used. 1718 * @ht_capa_mask: The bits of ht_capa which are to be used.
1695 */ 1719 */
1696struct cfg80211_ibss_params { 1720struct cfg80211_ibss_params {
1697 u8 *ssid; 1721 const u8 *ssid;
1698 u8 *bssid; 1722 const u8 *bssid;
1699 struct cfg80211_chan_def chandef; 1723 struct cfg80211_chan_def chandef;
1700 u8 *ie; 1724 const u8 *ie;
1701 u8 ssid_len, ie_len; 1725 u8 ssid_len, ie_len;
1702 u16 beacon_interval; 1726 u16 beacon_interval;
1703 u32 basic_rates; 1727 u32 basic_rates;
@@ -1806,8 +1830,8 @@ struct cfg80211_bitrate_mask {
1806 * @pmkid: The PMK material itself. 1830 * @pmkid: The PMK material itself.
1807 */ 1831 */
1808struct cfg80211_pmksa { 1832struct cfg80211_pmksa {
1809 u8 *bssid; 1833 const u8 *bssid;
1810 u8 *pmkid; 1834 const u8 *pmkid;
1811}; 1835};
1812 1836
1813/** 1837/**
@@ -1822,7 +1846,7 @@ struct cfg80211_pmksa {
1822 * memory, free @mask only! 1846 * memory, free @mask only!
1823 */ 1847 */
1824struct cfg80211_pkt_pattern { 1848struct cfg80211_pkt_pattern {
1825 u8 *mask, *pattern; 1849 const u8 *mask, *pattern;
1826 int pattern_len; 1850 int pattern_len;
1827 int pkt_offset; 1851 int pkt_offset;
1828}; 1852};
@@ -1986,6 +2010,8 @@ struct cfg80211_update_ft_ies_params {
1986 * @len: buffer length 2010 * @len: buffer length
1987 * @no_cck: don't use cck rates for this frame 2011 * @no_cck: don't use cck rates for this frame
1988 * @dont_wait_for_ack: tells the low level not to wait for an ack 2012 * @dont_wait_for_ack: tells the low level not to wait for an ack
2013 * @n_csa_offsets: length of csa_offsets array
2014 * @csa_offsets: array of all the csa offsets in the frame
1989 */ 2015 */
1990struct cfg80211_mgmt_tx_params { 2016struct cfg80211_mgmt_tx_params {
1991 struct ieee80211_channel *chan; 2017 struct ieee80211_channel *chan;
@@ -1995,6 +2021,8 @@ struct cfg80211_mgmt_tx_params {
1995 size_t len; 2021 size_t len;
1996 bool no_cck; 2022 bool no_cck;
1997 bool dont_wait_for_ack; 2023 bool dont_wait_for_ack;
2024 int n_csa_offsets;
2025 const u16 *csa_offsets;
1998}; 2026};
1999 2027
2000/** 2028/**
@@ -2336,28 +2364,29 @@ struct cfg80211_ops {
2336 2364
2337 2365
2338 int (*add_station)(struct wiphy *wiphy, struct net_device *dev, 2366 int (*add_station)(struct wiphy *wiphy, struct net_device *dev,
2339 u8 *mac, struct station_parameters *params); 2367 const u8 *mac,
2368 struct station_parameters *params);
2340 int (*del_station)(struct wiphy *wiphy, struct net_device *dev, 2369 int (*del_station)(struct wiphy *wiphy, struct net_device *dev,
2341 u8 *mac); 2370 const u8 *mac);
2342 int (*change_station)(struct wiphy *wiphy, struct net_device *dev, 2371 int (*change_station)(struct wiphy *wiphy, struct net_device *dev,
2343 u8 *mac, struct station_parameters *params); 2372 const u8 *mac,
2373 struct station_parameters *params);
2344 int (*get_station)(struct wiphy *wiphy, struct net_device *dev, 2374 int (*get_station)(struct wiphy *wiphy, struct net_device *dev,
2345 u8 *mac, struct station_info *sinfo); 2375 const u8 *mac, struct station_info *sinfo);
2346 int (*dump_station)(struct wiphy *wiphy, struct net_device *dev, 2376 int (*dump_station)(struct wiphy *wiphy, struct net_device *dev,
2347 int idx, u8 *mac, struct station_info *sinfo); 2377 int idx, u8 *mac, struct station_info *sinfo);
2348 2378
2349 int (*add_mpath)(struct wiphy *wiphy, struct net_device *dev, 2379 int (*add_mpath)(struct wiphy *wiphy, struct net_device *dev,
2350 u8 *dst, u8 *next_hop); 2380 const u8 *dst, const u8 *next_hop);
2351 int (*del_mpath)(struct wiphy *wiphy, struct net_device *dev, 2381 int (*del_mpath)(struct wiphy *wiphy, struct net_device *dev,
2352 u8 *dst); 2382 const u8 *dst);
2353 int (*change_mpath)(struct wiphy *wiphy, struct net_device *dev, 2383 int (*change_mpath)(struct wiphy *wiphy, struct net_device *dev,
2354 u8 *dst, u8 *next_hop); 2384 const u8 *dst, const u8 *next_hop);
2355 int (*get_mpath)(struct wiphy *wiphy, struct net_device *dev, 2385 int (*get_mpath)(struct wiphy *wiphy, struct net_device *dev,
2356 u8 *dst, u8 *next_hop, 2386 u8 *dst, u8 *next_hop, struct mpath_info *pinfo);
2357 struct mpath_info *pinfo);
2358 int (*dump_mpath)(struct wiphy *wiphy, struct net_device *dev, 2387 int (*dump_mpath)(struct wiphy *wiphy, struct net_device *dev,
2359 int idx, u8 *dst, u8 *next_hop, 2388 int idx, u8 *dst, u8 *next_hop,
2360 struct mpath_info *pinfo); 2389 struct mpath_info *pinfo);
2361 int (*get_mesh_config)(struct wiphy *wiphy, 2390 int (*get_mesh_config)(struct wiphy *wiphy,
2362 struct net_device *dev, 2391 struct net_device *dev,
2363 struct mesh_config *conf); 2392 struct mesh_config *conf);
@@ -2487,11 +2516,11 @@ struct cfg80211_ops {
2487 struct cfg80211_gtk_rekey_data *data); 2516 struct cfg80211_gtk_rekey_data *data);
2488 2517
2489 int (*tdls_mgmt)(struct wiphy *wiphy, struct net_device *dev, 2518 int (*tdls_mgmt)(struct wiphy *wiphy, struct net_device *dev,
2490 u8 *peer, u8 action_code, u8 dialog_token, 2519 const u8 *peer, u8 action_code, u8 dialog_token,
2491 u16 status_code, u32 peer_capability, 2520 u16 status_code, u32 peer_capability,
2492 const u8 *buf, size_t len); 2521 const u8 *buf, size_t len);
2493 int (*tdls_oper)(struct wiphy *wiphy, struct net_device *dev, 2522 int (*tdls_oper)(struct wiphy *wiphy, struct net_device *dev,
2494 u8 *peer, enum nl80211_tdls_operation oper); 2523 const u8 *peer, enum nl80211_tdls_operation oper);
2495 2524
2496 int (*probe_client)(struct wiphy *wiphy, struct net_device *dev, 2525 int (*probe_client)(struct wiphy *wiphy, struct net_device *dev,
2497 const u8 *peer, u64 *cookie); 2526 const u8 *peer, u64 *cookie);
@@ -2638,6 +2667,7 @@ struct ieee80211_iface_limit {
2638 * between infrastructure and AP types must match. This is required 2667 * between infrastructure and AP types must match. This is required
2639 * only in special cases. 2668 * only in special cases.
2640 * @radar_detect_widths: bitmap of channel widths supported for radar detection 2669 * @radar_detect_widths: bitmap of channel widths supported for radar detection
2670 * @radar_detect_regions: bitmap of regions supported for radar detection
2641 * 2671 *
2642 * With this structure the driver can describe which interface 2672 * With this structure the driver can describe which interface
2643 * combinations it supports concurrently. 2673 * combinations it supports concurrently.
@@ -2695,6 +2725,7 @@ struct ieee80211_iface_combination {
2695 u8 n_limits; 2725 u8 n_limits;
2696 bool beacon_int_infra_match; 2726 bool beacon_int_infra_match;
2697 u8 radar_detect_widths; 2727 u8 radar_detect_widths;
2728 u8 radar_detect_regions;
2698}; 2729};
2699 2730
2700struct ieee80211_txrx_stypes { 2731struct ieee80211_txrx_stypes {
@@ -2925,6 +2956,17 @@ struct wiphy_vendor_command {
2925 * (including P2P GO) or 0 to indicate no such limit is advertised. The 2956 * (including P2P GO) or 0 to indicate no such limit is advertised. The
2926 * driver is allowed to advertise a theoretical limit that it can reach in 2957 * driver is allowed to advertise a theoretical limit that it can reach in
2927 * some cases, but may not always reach. 2958 * some cases, but may not always reach.
2959 *
2960 * @max_num_csa_counters: Number of supported csa_counters in beacons
2961 * and probe responses. This value should be set if the driver
2962 * wishes to limit the number of csa counters. Default (0) means
2963 * infinite.
2964 * @max_adj_channel_rssi_comp: max offset of between the channel on which the
2965 * frame was sent and the channel on which the frame was heard for which
2966 * the reported rssi is still valid. If a driver is able to compensate the
2967 * low rssi when a frame is heard on different channel, then it should set
2968 * this variable to the maximal offset for which it can compensate.
2969 * This value should be set in MHz.
2928 */ 2970 */
2929struct wiphy { 2971struct wiphy {
2930 /* assign these fields before you register the wiphy */ 2972 /* assign these fields before you register the wiphy */
@@ -3042,6 +3084,9 @@ struct wiphy {
3042 3084
3043 u16 max_ap_assoc_sta; 3085 u16 max_ap_assoc_sta;
3044 3086
3087 u8 max_num_csa_counters;
3088 u8 max_adj_channel_rssi_comp;
3089
3045 char priv[0] __aligned(NETDEV_ALIGN); 3090 char priv[0] __aligned(NETDEV_ALIGN);
3046}; 3091};
3047 3092
@@ -3270,7 +3315,7 @@ struct wireless_dev {
3270 struct cfg80211_ibss_params ibss; 3315 struct cfg80211_ibss_params ibss;
3271 struct cfg80211_connect_params connect; 3316 struct cfg80211_connect_params connect;
3272 struct cfg80211_cached_keys *keys; 3317 struct cfg80211_cached_keys *keys;
3273 u8 *ie; 3318 const u8 *ie;
3274 size_t ie_len; 3319 size_t ie_len;
3275 u8 bssid[ETH_ALEN], prev_bssid[ETH_ALEN]; 3320 u8 bssid[ETH_ALEN], prev_bssid[ETH_ALEN];
3276 u8 ssid[IEEE80211_MAX_SSID_LEN]; 3321 u8 ssid[IEEE80211_MAX_SSID_LEN];
@@ -3511,7 +3556,8 @@ int ieee80211_data_to_8023(struct sk_buff *skb, const u8 *addr,
3511 * Return: 0 on success, or a negative error code. 3556 * Return: 0 on success, or a negative error code.
3512 */ 3557 */
3513int ieee80211_data_from_8023(struct sk_buff *skb, const u8 *addr, 3558int ieee80211_data_from_8023(struct sk_buff *skb, const u8 *addr,
3514 enum nl80211_iftype iftype, u8 *bssid, bool qos); 3559 enum nl80211_iftype iftype, const u8 *bssid,
3560 bool qos);
3515 3561
3516/** 3562/**
3517 * ieee80211_amsdu_to_8023s - decode an IEEE 802.11n A-MSDU frame 3563 * ieee80211_amsdu_to_8023s - decode an IEEE 802.11n A-MSDU frame
@@ -4312,7 +4358,7 @@ void cfg80211_roamed_bss(struct net_device *dev, struct cfg80211_bss *bss,
4312 * and not try to connect to any AP any more. 4358 * and not try to connect to any AP any more.
4313 */ 4359 */
4314void cfg80211_disconnected(struct net_device *dev, u16 reason, 4360void cfg80211_disconnected(struct net_device *dev, u16 reason,
4315 u8 *ie, size_t ie_len, gfp_t gfp); 4361 const u8 *ie, size_t ie_len, gfp_t gfp);
4316 4362
4317/** 4363/**
4318 * cfg80211_ready_on_channel - notification of remain_on_channel start 4364 * cfg80211_ready_on_channel - notification of remain_on_channel start
@@ -4768,6 +4814,35 @@ int cfg80211_iter_combinations(struct wiphy *wiphy,
4768 void *data), 4814 void *data),
4769 void *data); 4815 void *data);
4770 4816
4817/*
4818 * cfg80211_stop_iface - trigger interface disconnection
4819 *
4820 * @wiphy: the wiphy
4821 * @wdev: wireless device
4822 * @gfp: context flags
4823 *
4824 * Trigger interface to be stopped as if AP was stopped, IBSS/mesh left, STA
4825 * disconnected.
4826 *
4827 * Note: This doesn't need any locks and is asynchronous.
4828 */
4829void cfg80211_stop_iface(struct wiphy *wiphy, struct wireless_dev *wdev,
4830 gfp_t gfp);
4831
4832/**
4833 * cfg80211_shutdown_all_interfaces - shut down all interfaces for a wiphy
4834 * @wiphy: the wiphy to shut down
4835 *
4836 * This function shuts down all interfaces belonging to this wiphy by
4837 * calling dev_close() (and treating non-netdev interfaces as needed).
4838 * It shouldn't really be used unless there are some fatal device errors
4839 * that really can't be recovered in any other way.
4840 *
4841 * Callers must hold the RTNL and be able to deal with callbacks into
4842 * the driver while the function is running.
4843 */
4844void cfg80211_shutdown_all_interfaces(struct wiphy *wiphy);
4845
4771/* Logging, debugging and troubleshooting/diagnostic helpers. */ 4846/* Logging, debugging and troubleshooting/diagnostic helpers. */
4772 4847
4773/* wiphy_printk helpers, similar to dev_printk */ 4848/* wiphy_printk helpers, similar to dev_printk */
diff --git a/include/net/mac80211.h b/include/net/mac80211.h
index 451c1bf00df9..2c78997bc48d 100644
--- a/include/net/mac80211.h
+++ b/include/net/mac80211.h
@@ -1113,7 +1113,9 @@ enum ieee80211_vif_flags {
1113 * @addr: address of this interface 1113 * @addr: address of this interface
1114 * @p2p: indicates whether this AP or STA interface is a p2p 1114 * @p2p: indicates whether this AP or STA interface is a p2p
1115 * interface, i.e. a GO or p2p-sta respectively 1115 * interface, i.e. a GO or p2p-sta respectively
1116 * @csa_active: marks whether a channel switch is going on 1116 * @csa_active: marks whether a channel switch is going on. Internally it is
1117 * write-protected by sdata_lock and local->mtx so holding either is fine
1118 * for read access.
1117 * @driver_flags: flags/capabilities the driver has for this interface, 1119 * @driver_flags: flags/capabilities the driver has for this interface,
1118 * these need to be set (or cleared) when the interface is added 1120 * these need to be set (or cleared) when the interface is added
1119 * or, if supported by the driver, the interface type is changed 1121 * or, if supported by the driver, the interface type is changed
@@ -1374,6 +1376,7 @@ struct ieee80211_sta_rates {
1374 * the station moves to associated state. 1376 * the station moves to associated state.
1375 * @smps_mode: current SMPS mode (off, static or dynamic) 1377 * @smps_mode: current SMPS mode (off, static or dynamic)
1376 * @rates: rate control selection table 1378 * @rates: rate control selection table
1379 * @tdls: indicates whether the STA is a TDLS peer
1377 */ 1380 */
1378struct ieee80211_sta { 1381struct ieee80211_sta {
1379 u32 supp_rates[IEEE80211_NUM_BANDS]; 1382 u32 supp_rates[IEEE80211_NUM_BANDS];
@@ -1388,6 +1391,7 @@ struct ieee80211_sta {
1388 enum ieee80211_sta_rx_bandwidth bandwidth; 1391 enum ieee80211_sta_rx_bandwidth bandwidth;
1389 enum ieee80211_smps_mode smps_mode; 1392 enum ieee80211_smps_mode smps_mode;
1390 struct ieee80211_sta_rates __rcu *rates; 1393 struct ieee80211_sta_rates __rcu *rates;
1394 bool tdls;
1391 1395
1392 /* must be last */ 1396 /* must be last */
1393 u8 drv_priv[0] __aligned(sizeof(void *)); 1397 u8 drv_priv[0] __aligned(sizeof(void *));
@@ -2765,6 +2769,10 @@ enum ieee80211_roc_type {
2765 * information in bss_conf is set up and the beacon can be retrieved. A 2769 * information in bss_conf is set up and the beacon can be retrieved. A
2766 * channel context is bound before this is called. 2770 * channel context is bound before this is called.
2767 * @leave_ibss: Leave the IBSS again. 2771 * @leave_ibss: Leave the IBSS again.
2772 *
2773 * @get_expected_throughput: extract the expected throughput towards the
2774 * specified station. The returned value is expressed in Kbps. It returns 0
2775 * if the RC algorithm does not have proper data to provide.
2768 */ 2776 */
2769struct ieee80211_ops { 2777struct ieee80211_ops {
2770 void (*tx)(struct ieee80211_hw *hw, 2778 void (*tx)(struct ieee80211_hw *hw,
@@ -2958,6 +2966,7 @@ struct ieee80211_ops {
2958 2966
2959 int (*join_ibss)(struct ieee80211_hw *hw, struct ieee80211_vif *vif); 2967 int (*join_ibss)(struct ieee80211_hw *hw, struct ieee80211_vif *vif);
2960 void (*leave_ibss)(struct ieee80211_hw *hw, struct ieee80211_vif *vif); 2968 void (*leave_ibss)(struct ieee80211_hw *hw, struct ieee80211_vif *vif);
2969 u32 (*get_expected_throughput)(struct ieee80211_sta *sta);
2961}; 2970};
2962 2971
2963/** 2972/**
@@ -3407,6 +3416,47 @@ void ieee80211_tx_status_irqsafe(struct ieee80211_hw *hw,
3407 */ 3416 */
3408void ieee80211_report_low_ack(struct ieee80211_sta *sta, u32 num_packets); 3417void ieee80211_report_low_ack(struct ieee80211_sta *sta, u32 num_packets);
3409 3418
3419#define IEEE80211_MAX_CSA_COUNTERS_NUM 2
3420
3421/**
3422 * struct ieee80211_mutable_offsets - mutable beacon offsets
3423 * @tim_offset: position of TIM element
3424 * @tim_length: size of TIM element
3425 * @csa_counter_offs: array of IEEE80211_MAX_CSA_COUNTERS_NUM offsets
3426 * to CSA counters. This array can contain zero values which
3427 * should be ignored.
3428 */
3429struct ieee80211_mutable_offsets {
3430 u16 tim_offset;
3431 u16 tim_length;
3432
3433 u16 csa_counter_offs[IEEE80211_MAX_CSA_COUNTERS_NUM];
3434};
3435
3436/**
3437 * ieee80211_beacon_get_template - beacon template generation function
3438 * @hw: pointer obtained from ieee80211_alloc_hw().
3439 * @vif: &struct ieee80211_vif pointer from the add_interface callback.
3440 * @offs: &struct ieee80211_mutable_offsets pointer to struct that will
3441 * receive the offsets that may be updated by the driver.
3442 *
3443 * If the driver implements beaconing modes, it must use this function to
3444 * obtain the beacon template.
3445 *
3446 * This function should be used if the beacon frames are generated by the
3447 * device, and then the driver must use the returned beacon as the template
3448 * The driver or the device are responsible to update the DTIM and, when
3449 * applicable, the CSA count.
3450 *
3451 * The driver is responsible for freeing the returned skb.
3452 *
3453 * Return: The beacon template. %NULL on error.
3454 */
3455struct sk_buff *
3456ieee80211_beacon_get_template(struct ieee80211_hw *hw,
3457 struct ieee80211_vif *vif,
3458 struct ieee80211_mutable_offsets *offs);
3459
3410/** 3460/**
3411 * ieee80211_beacon_get_tim - beacon generation function 3461 * ieee80211_beacon_get_tim - beacon generation function
3412 * @hw: pointer obtained from ieee80211_alloc_hw(). 3462 * @hw: pointer obtained from ieee80211_alloc_hw().
@@ -3418,16 +3468,12 @@ void ieee80211_report_low_ack(struct ieee80211_sta *sta, u32 num_packets);
3418 * Set to 0 if invalid (in non-AP modes). 3468 * Set to 0 if invalid (in non-AP modes).
3419 * 3469 *
3420 * If the driver implements beaconing modes, it must use this function to 3470 * If the driver implements beaconing modes, it must use this function to
3421 * obtain the beacon frame/template. 3471 * obtain the beacon frame.
3422 * 3472 *
3423 * If the beacon frames are generated by the host system (i.e., not in 3473 * If the beacon frames are generated by the host system (i.e., not in
3424 * hardware/firmware), the driver uses this function to get each beacon 3474 * hardware/firmware), the driver uses this function to get each beacon
3425 * frame from mac80211 -- it is responsible for calling this function 3475 * frame from mac80211 -- it is responsible for calling this function exactly
3426 * before the beacon is needed (e.g. based on hardware interrupt). 3476 * once before the beacon is needed (e.g. based on hardware interrupt).
3427 *
3428 * If the beacon frames are generated by the device, then the driver
3429 * must use the returned beacon as the template and change the TIM IE
3430 * according to the current DTIM parameters/TIM bitmap.
3431 * 3477 *
3432 * The driver is responsible for freeing the returned skb. 3478 * The driver is responsible for freeing the returned skb.
3433 * 3479 *
@@ -3453,6 +3499,20 @@ static inline struct sk_buff *ieee80211_beacon_get(struct ieee80211_hw *hw,
3453} 3499}
3454 3500
3455/** 3501/**
3502 * ieee80211_csa_update_counter - request mac80211 to decrement the csa counter
3503 * @vif: &struct ieee80211_vif pointer from the add_interface callback.
3504 *
3505 * The csa counter should be updated after each beacon transmission.
3506 * This function is called implicitly when
3507 * ieee80211_beacon_get/ieee80211_beacon_get_tim are called, however if the
3508 * beacon frames are generated by the device, the driver should call this
3509 * function after each beacon transmission to sync mac80211's csa counters.
3510 *
3511 * Return: new csa counter value
3512 */
3513u8 ieee80211_csa_update_counter(struct ieee80211_vif *vif);
3514
3515/**
3456 * ieee80211_csa_finish - notify mac80211 about channel switch 3516 * ieee80211_csa_finish - notify mac80211 about channel switch
3457 * @vif: &struct ieee80211_vif pointer from the add_interface callback. 3517 * @vif: &struct ieee80211_vif pointer from the add_interface callback.
3458 * 3518 *
@@ -4480,6 +4540,8 @@ struct rate_control_ops {
4480 void (*add_sta_debugfs)(void *priv, void *priv_sta, 4540 void (*add_sta_debugfs)(void *priv, void *priv_sta,
4481 struct dentry *dir); 4541 struct dentry *dir);
4482 void (*remove_sta_debugfs)(void *priv, void *priv_sta); 4542 void (*remove_sta_debugfs)(void *priv, void *priv_sta);
4543
4544 u32 (*get_expected_throughput)(void *priv_sta);
4483}; 4545};
4484 4546
4485static inline int rate_supported(struct ieee80211_sta *sta, 4547static inline int rate_supported(struct ieee80211_sta *sta,
diff --git a/include/net/nfc/digital.h b/include/net/nfc/digital.h
index 7655cfe27c34..bdf55c3b7a19 100644
--- a/include/net/nfc/digital.h
+++ b/include/net/nfc/digital.h
@@ -36,6 +36,7 @@ enum {
36 NFC_DIGITAL_RF_TECH_212F, 36 NFC_DIGITAL_RF_TECH_212F,
37 NFC_DIGITAL_RF_TECH_424F, 37 NFC_DIGITAL_RF_TECH_424F,
38 NFC_DIGITAL_RF_TECH_ISO15693, 38 NFC_DIGITAL_RF_TECH_ISO15693,
39 NFC_DIGITAL_RF_TECH_106B,
39 40
40 NFC_DIGITAL_RF_TECH_LAST, 41 NFC_DIGITAL_RF_TECH_LAST,
41}; 42};
@@ -62,6 +63,9 @@ enum {
62 NFC_DIGITAL_FRAMING_ISO15693_INVENTORY, 63 NFC_DIGITAL_FRAMING_ISO15693_INVENTORY,
63 NFC_DIGITAL_FRAMING_ISO15693_T5T, 64 NFC_DIGITAL_FRAMING_ISO15693_T5T,
64 65
66 NFC_DIGITAL_FRAMING_NFCB,
67 NFC_DIGITAL_FRAMING_NFCB_T4T,
68
65 NFC_DIGITAL_FRAMING_LAST, 69 NFC_DIGITAL_FRAMING_LAST,
66}; 70};
67 71
diff --git a/include/net/nfc/hci.h b/include/net/nfc/hci.h
index 03c4650b548c..61286db54388 100644
--- a/include/net/nfc/hci.h
+++ b/include/net/nfc/hci.h
@@ -27,6 +27,7 @@ struct nfc_hci_dev;
27struct nfc_hci_ops { 27struct nfc_hci_ops {
28 int (*open) (struct nfc_hci_dev *hdev); 28 int (*open) (struct nfc_hci_dev *hdev);
29 void (*close) (struct nfc_hci_dev *hdev); 29 void (*close) (struct nfc_hci_dev *hdev);
30 int (*load_session) (struct nfc_hci_dev *hdev);
30 int (*hci_ready) (struct nfc_hci_dev *hdev); 31 int (*hci_ready) (struct nfc_hci_dev *hdev);
31 /* 32 /*
32 * xmit must always send the complete buffer before 33 * xmit must always send the complete buffer before
diff --git a/include/net/nfc/nfc.h b/include/net/nfc/nfc.h
index 2e8b40c16274..6c583e244de2 100644
--- a/include/net/nfc/nfc.h
+++ b/include/net/nfc/nfc.h
@@ -264,4 +264,7 @@ int nfc_add_se(struct nfc_dev *dev, u32 se_idx, u16 type);
264int nfc_remove_se(struct nfc_dev *dev, u32 se_idx); 264int nfc_remove_se(struct nfc_dev *dev, u32 se_idx);
265struct nfc_se *nfc_find_se(struct nfc_dev *dev, u32 se_idx); 265struct nfc_se *nfc_find_se(struct nfc_dev *dev, u32 se_idx);
266 266
267void nfc_send_to_raw_sock(struct nfc_dev *dev, struct sk_buff *skb,
268 u8 payload_type, u8 direction);
269
267#endif /* __NET_NFC_H */ 270#endif /* __NET_NFC_H */
diff --git a/include/uapi/linux/nfc.h b/include/uapi/linux/nfc.h
index 9789dc95b6a8..9b19b4461928 100644
--- a/include/uapi/linux/nfc.h
+++ b/include/uapi/linux/nfc.h
@@ -273,11 +273,19 @@ struct sockaddr_nfc_llcp {
273 * First byte is the adapter index 273 * First byte is the adapter index
274 * Second byte contains flags 274 * Second byte contains flags
275 * - 0x01 - Direction (0=RX, 1=TX) 275 * - 0x01 - Direction (0=RX, 1=TX)
276 * - 0x02-0x80 - Reserved 276 * - 0x02-0x04 - Payload type (000=LLCP, 001=NCI, 010=HCI, 011=Digital,
277 * 100=Proprietary)
278 * - 0x05-0x80 - Reserved
277 **/ 279 **/
278#define NFC_LLCP_RAW_HEADER_SIZE 2 280#define NFC_RAW_HEADER_SIZE 2
279#define NFC_LLCP_DIRECTION_RX 0x00 281#define NFC_DIRECTION_RX 0x00
280#define NFC_LLCP_DIRECTION_TX 0x01 282#define NFC_DIRECTION_TX 0x01
283
284#define RAW_PAYLOAD_LLCP 0
285#define RAW_PAYLOAD_NCI 1
286#define RAW_PAYLOAD_HCI 2
287#define RAW_PAYLOAD_DIGITAL 3
288#define RAW_PAYLOAD_PROPRIETARY 4
281 289
282/* socket option names */ 290/* socket option names */
283#define NFC_LLCP_RW 0 291#define NFC_LLCP_RW 0
diff --git a/include/uapi/linux/nl80211.h b/include/uapi/linux/nl80211.h
index 9922b9b828a2..be9519b52bb1 100644
--- a/include/uapi/linux/nl80211.h
+++ b/include/uapi/linux/nl80211.h
@@ -503,6 +503,9 @@
503 * TX status event pertaining to the TX request. 503 * TX status event pertaining to the TX request.
504 * %NL80211_ATTR_TX_NO_CCK_RATE is used to decide whether to send the 504 * %NL80211_ATTR_TX_NO_CCK_RATE is used to decide whether to send the
505 * management frames at CCK rate or not in 2GHz band. 505 * management frames at CCK rate or not in 2GHz band.
506 * %NL80211_ATTR_CSA_C_OFFSETS_TX is an array of offsets to CSA
507 * counters which will be updated to the current value. This attribute
508 * is used during CSA period.
506 * @NL80211_CMD_FRAME_WAIT_CANCEL: When an off-channel TX was requested, this 509 * @NL80211_CMD_FRAME_WAIT_CANCEL: When an off-channel TX was requested, this
507 * command may be used with the corresponding cookie to cancel the wait 510 * command may be used with the corresponding cookie to cancel the wait
508 * time if it is known that it is no longer necessary. 511 * time if it is known that it is no longer necessary.
@@ -1525,10 +1528,10 @@ enum nl80211_commands {
1525 * operation). 1528 * operation).
1526 * @NL80211_ATTR_CSA_IES: Nested set of attributes containing the IE information 1529 * @NL80211_ATTR_CSA_IES: Nested set of attributes containing the IE information
1527 * for the time while performing a channel switch. 1530 * for the time while performing a channel switch.
1528 * @NL80211_ATTR_CSA_C_OFF_BEACON: Offset of the channel switch counter 1531 * @NL80211_ATTR_CSA_C_OFF_BEACON: An array of offsets (u16) to the channel
1529 * field in the beacons tail (%NL80211_ATTR_BEACON_TAIL). 1532 * switch counters in the beacons tail (%NL80211_ATTR_BEACON_TAIL).
1530 * @NL80211_ATTR_CSA_C_OFF_PRESP: Offset of the channel switch counter 1533 * @NL80211_ATTR_CSA_C_OFF_PRESP: An array of offsets (u16) to the channel
1531 * field in the probe response (%NL80211_ATTR_PROBE_RESP). 1534 * switch counters in the probe response (%NL80211_ATTR_PROBE_RESP).
1532 * 1535 *
1533 * @NL80211_ATTR_RXMGMT_FLAGS: flags for nl80211_send_mgmt(), u32. 1536 * @NL80211_ATTR_RXMGMT_FLAGS: flags for nl80211_send_mgmt(), u32.
1534 * As specified in the &enum nl80211_rxmgmt_flags. 1537 * As specified in the &enum nl80211_rxmgmt_flags.
@@ -1576,6 +1579,11 @@ enum nl80211_commands {
1576 * advertise values that cannot always be met. In such cases, an attempt 1579 * advertise values that cannot always be met. In such cases, an attempt
1577 * to add a new station entry with @NL80211_CMD_NEW_STATION may fail. 1580 * to add a new station entry with @NL80211_CMD_NEW_STATION may fail.
1578 * 1581 *
1582 * @NL80211_ATTR_CSA_C_OFFSETS_TX: An array of csa counter offsets (u16) which
1583 * should be updated when the frame is transmitted.
1584 * @NL80211_ATTR_MAX_CSA_COUNTERS: U8 attribute used to advertise the maximum
1585 * supported number of csa counters.
1586 *
1579 * @NL80211_ATTR_TDLS_PEER_CAPABILITY: flags for TDLS peer capabilities, u32. 1587 * @NL80211_ATTR_TDLS_PEER_CAPABILITY: flags for TDLS peer capabilities, u32.
1580 * As specified in the &enum nl80211_tdls_peer_capability. 1588 * As specified in the &enum nl80211_tdls_peer_capability.
1581 * 1589 *
@@ -1920,6 +1928,9 @@ enum nl80211_attrs {
1920 1928
1921 NL80211_ATTR_IFACE_SOCKET_OWNER, 1929 NL80211_ATTR_IFACE_SOCKET_OWNER,
1922 1930
1931 NL80211_ATTR_CSA_C_OFFSETS_TX,
1932 NL80211_ATTR_MAX_CSA_COUNTERS,
1933
1923 /* add attributes here, update the policy in nl80211.c */ 1934 /* add attributes here, update the policy in nl80211.c */
1924 1935
1925 __NL80211_ATTR_AFTER_LAST, 1936 __NL80211_ATTR_AFTER_LAST,
@@ -2188,6 +2199,8 @@ enum nl80211_sta_bss_param {
2188 * Contains a nested array of signal strength attributes (u8, dBm) 2199 * Contains a nested array of signal strength attributes (u8, dBm)
2189 * @NL80211_STA_INFO_CHAIN_SIGNAL_AVG: per-chain signal strength average 2200 * @NL80211_STA_INFO_CHAIN_SIGNAL_AVG: per-chain signal strength average
2190 * Same format as NL80211_STA_INFO_CHAIN_SIGNAL. 2201 * Same format as NL80211_STA_INFO_CHAIN_SIGNAL.
2202 * @NL80211_STA_EXPECTED_THROUGHPUT: expected throughput considering also the
2203 * 802.11 header (u32, kbps)
2191 * @__NL80211_STA_INFO_AFTER_LAST: internal 2204 * @__NL80211_STA_INFO_AFTER_LAST: internal
2192 * @NL80211_STA_INFO_MAX: highest possible station info attribute 2205 * @NL80211_STA_INFO_MAX: highest possible station info attribute
2193 */ 2206 */
@@ -2219,6 +2232,7 @@ enum nl80211_sta_info {
2219 NL80211_STA_INFO_TX_BYTES64, 2232 NL80211_STA_INFO_TX_BYTES64,
2220 NL80211_STA_INFO_CHAIN_SIGNAL, 2233 NL80211_STA_INFO_CHAIN_SIGNAL,
2221 NL80211_STA_INFO_CHAIN_SIGNAL_AVG, 2234 NL80211_STA_INFO_CHAIN_SIGNAL_AVG,
2235 NL80211_STA_INFO_EXPECTED_THROUGHPUT,
2222 2236
2223 /* keep last */ 2237 /* keep last */
2224 __NL80211_STA_INFO_AFTER_LAST, 2238 __NL80211_STA_INFO_AFTER_LAST,
@@ -3688,6 +3702,8 @@ enum nl80211_iface_limit_attrs {
3688 * different channels may be used within this group. 3702 * different channels may be used within this group.
3689 * @NL80211_IFACE_COMB_RADAR_DETECT_WIDTHS: u32 attribute containing the bitmap 3703 * @NL80211_IFACE_COMB_RADAR_DETECT_WIDTHS: u32 attribute containing the bitmap
3690 * of supported channel widths for radar detection. 3704 * of supported channel widths for radar detection.
3705 * @NL80211_IFACE_COMB_RADAR_DETECT_REGIONS: u32 attribute containing the bitmap
3706 * of supported regulatory regions for radar detection.
3691 * @NUM_NL80211_IFACE_COMB: number of attributes 3707 * @NUM_NL80211_IFACE_COMB: number of attributes
3692 * @MAX_NL80211_IFACE_COMB: highest attribute number 3708 * @MAX_NL80211_IFACE_COMB: highest attribute number
3693 * 3709 *
@@ -3721,6 +3737,7 @@ enum nl80211_if_combination_attrs {
3721 NL80211_IFACE_COMB_STA_AP_BI_MATCH, 3737 NL80211_IFACE_COMB_STA_AP_BI_MATCH,
3722 NL80211_IFACE_COMB_NUM_CHANNELS, 3738 NL80211_IFACE_COMB_NUM_CHANNELS,
3723 NL80211_IFACE_COMB_RADAR_DETECT_WIDTHS, 3739 NL80211_IFACE_COMB_RADAR_DETECT_WIDTHS,
3740 NL80211_IFACE_COMB_RADAR_DETECT_REGIONS,
3724 3741
3725 /* keep last */ 3742 /* keep last */
3726 NUM_NL80211_IFACE_COMB, 3743 NUM_NL80211_IFACE_COMB,
diff --git a/lib/crc7.c b/lib/crc7.c
index f1c3a144cec1..bf6255e23919 100644
--- a/lib/crc7.c
+++ b/lib/crc7.c
@@ -10,42 +10,47 @@
10#include <linux/crc7.h> 10#include <linux/crc7.h>
11 11
12 12
13/* Table for CRC-7 (polynomial x^7 + x^3 + 1) */ 13/*
14const u8 crc7_syndrome_table[256] = { 14 * Table for CRC-7 (polynomial x^7 + x^3 + 1).
15 0x00, 0x09, 0x12, 0x1b, 0x24, 0x2d, 0x36, 0x3f, 15 * This is a big-endian CRC (msbit is highest power of x),
16 0x48, 0x41, 0x5a, 0x53, 0x6c, 0x65, 0x7e, 0x77, 16 * aligned so the msbit of the byte is the x^6 coefficient
17 0x19, 0x10, 0x0b, 0x02, 0x3d, 0x34, 0x2f, 0x26, 17 * and the lsbit is not used.
18 0x51, 0x58, 0x43, 0x4a, 0x75, 0x7c, 0x67, 0x6e, 18 */
19 0x32, 0x3b, 0x20, 0x29, 0x16, 0x1f, 0x04, 0x0d, 19const u8 crc7_be_syndrome_table[256] = {
20 0x7a, 0x73, 0x68, 0x61, 0x5e, 0x57, 0x4c, 0x45, 20 0x00, 0x12, 0x24, 0x36, 0x48, 0x5a, 0x6c, 0x7e,
21 0x2b, 0x22, 0x39, 0x30, 0x0f, 0x06, 0x1d, 0x14, 21 0x90, 0x82, 0xb4, 0xa6, 0xd8, 0xca, 0xfc, 0xee,
22 0x63, 0x6a, 0x71, 0x78, 0x47, 0x4e, 0x55, 0x5c, 22 0x32, 0x20, 0x16, 0x04, 0x7a, 0x68, 0x5e, 0x4c,
23 0x64, 0x6d, 0x76, 0x7f, 0x40, 0x49, 0x52, 0x5b, 23 0xa2, 0xb0, 0x86, 0x94, 0xea, 0xf8, 0xce, 0xdc,
24 0x2c, 0x25, 0x3e, 0x37, 0x08, 0x01, 0x1a, 0x13, 24 0x64, 0x76, 0x40, 0x52, 0x2c, 0x3e, 0x08, 0x1a,
25 0x7d, 0x74, 0x6f, 0x66, 0x59, 0x50, 0x4b, 0x42, 25 0xf4, 0xe6, 0xd0, 0xc2, 0xbc, 0xae, 0x98, 0x8a,
26 0x35, 0x3c, 0x27, 0x2e, 0x11, 0x18, 0x03, 0x0a, 26 0x56, 0x44, 0x72, 0x60, 0x1e, 0x0c, 0x3a, 0x28,
27 0x56, 0x5f, 0x44, 0x4d, 0x72, 0x7b, 0x60, 0x69, 27 0xc6, 0xd4, 0xe2, 0xf0, 0x8e, 0x9c, 0xaa, 0xb8,
28 0x1e, 0x17, 0x0c, 0x05, 0x3a, 0x33, 0x28, 0x21, 28 0xc8, 0xda, 0xec, 0xfe, 0x80, 0x92, 0xa4, 0xb6,
29 0x4f, 0x46, 0x5d, 0x54, 0x6b, 0x62, 0x79, 0x70, 29 0x58, 0x4a, 0x7c, 0x6e, 0x10, 0x02, 0x34, 0x26,
30 0x07, 0x0e, 0x15, 0x1c, 0x23, 0x2a, 0x31, 0x38, 30 0xfa, 0xe8, 0xde, 0xcc, 0xb2, 0xa0, 0x96, 0x84,
31 0x41, 0x48, 0x53, 0x5a, 0x65, 0x6c, 0x77, 0x7e, 31 0x6a, 0x78, 0x4e, 0x5c, 0x22, 0x30, 0x06, 0x14,
32 0x09, 0x00, 0x1b, 0x12, 0x2d, 0x24, 0x3f, 0x36, 32 0xac, 0xbe, 0x88, 0x9a, 0xe4, 0xf6, 0xc0, 0xd2,
33 0x58, 0x51, 0x4a, 0x43, 0x7c, 0x75, 0x6e, 0x67, 33 0x3c, 0x2e, 0x18, 0x0a, 0x74, 0x66, 0x50, 0x42,
34 0x10, 0x19, 0x02, 0x0b, 0x34, 0x3d, 0x26, 0x2f, 34 0x9e, 0x8c, 0xba, 0xa8, 0xd6, 0xc4, 0xf2, 0xe0,
35 0x73, 0x7a, 0x61, 0x68, 0x57, 0x5e, 0x45, 0x4c, 35 0x0e, 0x1c, 0x2a, 0x38, 0x46, 0x54, 0x62, 0x70,
36 0x3b, 0x32, 0x29, 0x20, 0x1f, 0x16, 0x0d, 0x04, 36 0x82, 0x90, 0xa6, 0xb4, 0xca, 0xd8, 0xee, 0xfc,
37 0x6a, 0x63, 0x78, 0x71, 0x4e, 0x47, 0x5c, 0x55, 37 0x12, 0x00, 0x36, 0x24, 0x5a, 0x48, 0x7e, 0x6c,
38 0x22, 0x2b, 0x30, 0x39, 0x06, 0x0f, 0x14, 0x1d, 38 0xb0, 0xa2, 0x94, 0x86, 0xf8, 0xea, 0xdc, 0xce,
39 0x25, 0x2c, 0x37, 0x3e, 0x01, 0x08, 0x13, 0x1a, 39 0x20, 0x32, 0x04, 0x16, 0x68, 0x7a, 0x4c, 0x5e,
40 0x6d, 0x64, 0x7f, 0x76, 0x49, 0x40, 0x5b, 0x52, 40 0xe6, 0xf4, 0xc2, 0xd0, 0xae, 0xbc, 0x8a, 0x98,
41 0x3c, 0x35, 0x2e, 0x27, 0x18, 0x11, 0x0a, 0x03, 41 0x76, 0x64, 0x52, 0x40, 0x3e, 0x2c, 0x1a, 0x08,
42 0x74, 0x7d, 0x66, 0x6f, 0x50, 0x59, 0x42, 0x4b, 42 0xd4, 0xc6, 0xf0, 0xe2, 0x9c, 0x8e, 0xb8, 0xaa,
43 0x17, 0x1e, 0x05, 0x0c, 0x33, 0x3a, 0x21, 0x28, 43 0x44, 0x56, 0x60, 0x72, 0x0c, 0x1e, 0x28, 0x3a,
44 0x5f, 0x56, 0x4d, 0x44, 0x7b, 0x72, 0x69, 0x60, 44 0x4a, 0x58, 0x6e, 0x7c, 0x02, 0x10, 0x26, 0x34,
45 0x0e, 0x07, 0x1c, 0x15, 0x2a, 0x23, 0x38, 0x31, 45 0xda, 0xc8, 0xfe, 0xec, 0x92, 0x80, 0xb6, 0xa4,
46 0x46, 0x4f, 0x54, 0x5d, 0x62, 0x6b, 0x70, 0x79 46 0x78, 0x6a, 0x5c, 0x4e, 0x30, 0x22, 0x14, 0x06,
47 0xe8, 0xfa, 0xcc, 0xde, 0xa0, 0xb2, 0x84, 0x96,
48 0x2e, 0x3c, 0x0a, 0x18, 0x66, 0x74, 0x42, 0x50,
49 0xbe, 0xac, 0x9a, 0x88, 0xf6, 0xe4, 0xd2, 0xc0,
50 0x1c, 0x0e, 0x38, 0x2a, 0x54, 0x46, 0x70, 0x62,
51 0x8c, 0x9e, 0xa8, 0xba, 0xc4, 0xd6, 0xe0, 0xf2
47}; 52};
48EXPORT_SYMBOL(crc7_syndrome_table); 53EXPORT_SYMBOL(crc7_be_syndrome_table);
49 54
50/** 55/**
51 * crc7 - update the CRC7 for the data buffer 56 * crc7 - update the CRC7 for the data buffer
@@ -55,14 +60,17 @@ EXPORT_SYMBOL(crc7_syndrome_table);
55 * Context: any 60 * Context: any
56 * 61 *
57 * Returns the updated CRC7 value. 62 * Returns the updated CRC7 value.
63 * The CRC7 is left-aligned in the byte (the lsbit is always 0), as that
64 * makes the computation easier, and all callers want it in that form.
65 *
58 */ 66 */
59u8 crc7(u8 crc, const u8 *buffer, size_t len) 67u8 crc7_be(u8 crc, const u8 *buffer, size_t len)
60{ 68{
61 while (len--) 69 while (len--)
62 crc = crc7_byte(crc, *buffer++); 70 crc = crc7_be_byte(crc, *buffer++);
63 return crc; 71 return crc;
64} 72}
65EXPORT_SYMBOL(crc7); 73EXPORT_SYMBOL(crc7_be);
66 74
67MODULE_DESCRIPTION("CRC7 calculations"); 75MODULE_DESCRIPTION("CRC7 calculations");
68MODULE_LICENSE("GPL"); 76MODULE_LICENSE("GPL");
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index a1e5bb7d06e8..dc4d301d3a72 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -7519,9 +7519,9 @@ int __init l2cap_init(void)
7519 l2cap_debugfs = debugfs_create_file("l2cap", 0444, bt_debugfs, 7519 l2cap_debugfs = debugfs_create_file("l2cap", 0444, bt_debugfs,
7520 NULL, &l2cap_debugfs_fops); 7520 NULL, &l2cap_debugfs_fops);
7521 7521
7522 debugfs_create_u16("l2cap_le_max_credits", 0466, bt_debugfs, 7522 debugfs_create_u16("l2cap_le_max_credits", 0644, bt_debugfs,
7523 &le_max_credits); 7523 &le_max_credits);
7524 debugfs_create_u16("l2cap_le_default_mps", 0466, bt_debugfs, 7524 debugfs_create_u16("l2cap_le_default_mps", 0644, bt_debugfs,
7525 &le_default_mps); 7525 &le_default_mps);
7526 7526
7527 bt_6lowpan_init(); 7527 bt_6lowpan_init();
diff --git a/net/mac80211/Makefile b/net/mac80211/Makefile
index 9d7d840aac6d..1e46ffa69167 100644
--- a/net/mac80211/Makefile
+++ b/net/mac80211/Makefile
@@ -25,7 +25,8 @@ mac80211-y := \
25 wme.o \ 25 wme.o \
26 event.o \ 26 event.o \
27 chan.o \ 27 chan.o \
28 trace.o mlme.o 28 trace.o mlme.o \
29 tdls.o
29 30
30mac80211-$(CONFIG_MAC80211_LEDS) += led.o 31mac80211-$(CONFIG_MAC80211_LEDS) += led.o
31mac80211-$(CONFIG_MAC80211_DEBUGFS) += \ 32mac80211-$(CONFIG_MAC80211_DEBUGFS) += \
diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c
index 7b8d3cf89574..d7513a503be1 100644
--- a/net/mac80211/cfg.c
+++ b/net/mac80211/cfg.c
@@ -472,8 +472,10 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
472{ 472{
473 struct ieee80211_sub_if_data *sdata = sta->sdata; 473 struct ieee80211_sub_if_data *sdata = sta->sdata;
474 struct ieee80211_local *local = sdata->local; 474 struct ieee80211_local *local = sdata->local;
475 struct rate_control_ref *ref = local->rate_ctrl;
475 struct timespec uptime; 476 struct timespec uptime;
476 u64 packets = 0; 477 u64 packets = 0;
478 u32 thr = 0;
477 int i, ac; 479 int i, ac;
478 480
479 sinfo->generation = sdata->local->sta_generation; 481 sinfo->generation = sdata->local->sta_generation;
@@ -587,6 +589,17 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
587 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_ASSOCIATED); 589 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_ASSOCIATED);
588 if (test_sta_flag(sta, WLAN_STA_TDLS_PEER)) 590 if (test_sta_flag(sta, WLAN_STA_TDLS_PEER))
589 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_TDLS_PEER); 591 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_TDLS_PEER);
592
593 /* check if the driver has a SW RC implementation */
594 if (ref && ref->ops->get_expected_throughput)
595 thr = ref->ops->get_expected_throughput(sta->rate_ctrl_priv);
596 else
597 thr = drv_get_expected_throughput(local, &sta->sta);
598
599 if (thr != 0) {
600 sinfo->filled |= STATION_INFO_EXPECTED_THROUGHPUT;
601 sinfo->expected_throughput = thr;
602 }
590} 603}
591 604
592static const char ieee80211_gstrings_sta_stats[][ETH_GSTRING_LEN] = { 605static const char ieee80211_gstrings_sta_stats[][ETH_GSTRING_LEN] = {
@@ -777,7 +790,7 @@ static void ieee80211_get_et_strings(struct wiphy *wiphy,
777} 790}
778 791
779static int ieee80211_dump_station(struct wiphy *wiphy, struct net_device *dev, 792static int ieee80211_dump_station(struct wiphy *wiphy, struct net_device *dev,
780 int idx, u8 *mac, struct station_info *sinfo) 793 int idx, u8 *mac, struct station_info *sinfo)
781{ 794{
782 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 795 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
783 struct ieee80211_local *local = sdata->local; 796 struct ieee80211_local *local = sdata->local;
@@ -807,7 +820,7 @@ static int ieee80211_dump_survey(struct wiphy *wiphy, struct net_device *dev,
807} 820}
808 821
809static int ieee80211_get_station(struct wiphy *wiphy, struct net_device *dev, 822static int ieee80211_get_station(struct wiphy *wiphy, struct net_device *dev,
810 u8 *mac, struct station_info *sinfo) 823 const u8 *mac, struct station_info *sinfo)
811{ 824{
812 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 825 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
813 struct ieee80211_local *local = sdata->local; 826 struct ieee80211_local *local = sdata->local;
@@ -1084,6 +1097,31 @@ static int ieee80211_change_beacon(struct wiphy *wiphy, struct net_device *dev,
1084 return 0; 1097 return 0;
1085} 1098}
1086 1099
1100bool ieee80211_csa_needs_block_tx(struct ieee80211_local *local)
1101{
1102 struct ieee80211_sub_if_data *sdata;
1103
1104 lockdep_assert_held(&local->mtx);
1105
1106 rcu_read_lock();
1107 list_for_each_entry_rcu(sdata, &local->interfaces, list) {
1108 if (!ieee80211_sdata_running(sdata))
1109 continue;
1110
1111 if (!sdata->vif.csa_active)
1112 continue;
1113
1114 if (!sdata->csa_block_tx)
1115 continue;
1116
1117 rcu_read_unlock();
1118 return true;
1119 }
1120 rcu_read_unlock();
1121
1122 return false;
1123}
1124
1087static int ieee80211_stop_ap(struct wiphy *wiphy, struct net_device *dev) 1125static int ieee80211_stop_ap(struct wiphy *wiphy, struct net_device *dev)
1088{ 1126{
1089 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 1127 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
@@ -1101,7 +1139,14 @@ static int ieee80211_stop_ap(struct wiphy *wiphy, struct net_device *dev)
1101 old_probe_resp = sdata_dereference(sdata->u.ap.probe_resp, sdata); 1139 old_probe_resp = sdata_dereference(sdata->u.ap.probe_resp, sdata);
1102 1140
1103 /* abort any running channel switch */ 1141 /* abort any running channel switch */
1142 mutex_lock(&local->mtx);
1104 sdata->vif.csa_active = false; 1143 sdata->vif.csa_active = false;
1144 if (!ieee80211_csa_needs_block_tx(local))
1145 ieee80211_wake_queues_by_reason(&local->hw,
1146 IEEE80211_MAX_QUEUE_MAP,
1147 IEEE80211_QUEUE_STOP_REASON_CSA);
1148 mutex_unlock(&local->mtx);
1149
1105 kfree(sdata->u.ap.next_beacon); 1150 kfree(sdata->u.ap.next_beacon);
1106 sdata->u.ap.next_beacon = NULL; 1151 sdata->u.ap.next_beacon = NULL;
1107 1152
@@ -1425,7 +1470,8 @@ static int sta_apply_parameters(struct ieee80211_local *local,
1425} 1470}
1426 1471
1427static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev, 1472static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev,
1428 u8 *mac, struct station_parameters *params) 1473 const u8 *mac,
1474 struct station_parameters *params)
1429{ 1475{
1430 struct ieee80211_local *local = wiphy_priv(wiphy); 1476 struct ieee80211_local *local = wiphy_priv(wiphy);
1431 struct sta_info *sta; 1477 struct sta_info *sta;
@@ -1459,6 +1505,8 @@ static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev,
1459 if (!(params->sta_flags_set & BIT(NL80211_STA_FLAG_TDLS_PEER))) { 1505 if (!(params->sta_flags_set & BIT(NL80211_STA_FLAG_TDLS_PEER))) {
1460 sta_info_pre_move_state(sta, IEEE80211_STA_AUTH); 1506 sta_info_pre_move_state(sta, IEEE80211_STA_AUTH);
1461 sta_info_pre_move_state(sta, IEEE80211_STA_ASSOC); 1507 sta_info_pre_move_state(sta, IEEE80211_STA_ASSOC);
1508 } else {
1509 sta->sta.tdls = true;
1462 } 1510 }
1463 1511
1464 err = sta_apply_parameters(local, sta, params); 1512 err = sta_apply_parameters(local, sta, params);
@@ -1492,7 +1540,7 @@ static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev,
1492} 1540}
1493 1541
1494static int ieee80211_del_station(struct wiphy *wiphy, struct net_device *dev, 1542static int ieee80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1495 u8 *mac) 1543 const u8 *mac)
1496{ 1544{
1497 struct ieee80211_sub_if_data *sdata; 1545 struct ieee80211_sub_if_data *sdata;
1498 1546
@@ -1506,7 +1554,7 @@ static int ieee80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1506} 1554}
1507 1555
1508static int ieee80211_change_station(struct wiphy *wiphy, 1556static int ieee80211_change_station(struct wiphy *wiphy,
1509 struct net_device *dev, u8 *mac, 1557 struct net_device *dev, const u8 *mac,
1510 struct station_parameters *params) 1558 struct station_parameters *params)
1511{ 1559{
1512 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 1560 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
@@ -1631,7 +1679,7 @@ out_err:
1631 1679
1632#ifdef CONFIG_MAC80211_MESH 1680#ifdef CONFIG_MAC80211_MESH
1633static int ieee80211_add_mpath(struct wiphy *wiphy, struct net_device *dev, 1681static int ieee80211_add_mpath(struct wiphy *wiphy, struct net_device *dev,
1634 u8 *dst, u8 *next_hop) 1682 const u8 *dst, const u8 *next_hop)
1635{ 1683{
1636 struct ieee80211_sub_if_data *sdata; 1684 struct ieee80211_sub_if_data *sdata;
1637 struct mesh_path *mpath; 1685 struct mesh_path *mpath;
@@ -1659,7 +1707,7 @@ static int ieee80211_add_mpath(struct wiphy *wiphy, struct net_device *dev,
1659} 1707}
1660 1708
1661static int ieee80211_del_mpath(struct wiphy *wiphy, struct net_device *dev, 1709static int ieee80211_del_mpath(struct wiphy *wiphy, struct net_device *dev,
1662 u8 *dst) 1710 const u8 *dst)
1663{ 1711{
1664 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 1712 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
1665 1713
@@ -1670,9 +1718,8 @@ static int ieee80211_del_mpath(struct wiphy *wiphy, struct net_device *dev,
1670 return 0; 1718 return 0;
1671} 1719}
1672 1720
1673static int ieee80211_change_mpath(struct wiphy *wiphy, 1721static int ieee80211_change_mpath(struct wiphy *wiphy, struct net_device *dev,
1674 struct net_device *dev, 1722 const u8 *dst, const u8 *next_hop)
1675 u8 *dst, u8 *next_hop)
1676{ 1723{
1677 struct ieee80211_sub_if_data *sdata; 1724 struct ieee80211_sub_if_data *sdata;
1678 struct mesh_path *mpath; 1725 struct mesh_path *mpath;
@@ -1764,8 +1811,8 @@ static int ieee80211_get_mpath(struct wiphy *wiphy, struct net_device *dev,
1764} 1811}
1765 1812
1766static int ieee80211_dump_mpath(struct wiphy *wiphy, struct net_device *dev, 1813static int ieee80211_dump_mpath(struct wiphy *wiphy, struct net_device *dev,
1767 int idx, u8 *dst, u8 *next_hop, 1814 int idx, u8 *dst, u8 *next_hop,
1768 struct mpath_info *pinfo) 1815 struct mpath_info *pinfo)
1769{ 1816{
1770 struct ieee80211_sub_if_data *sdata; 1817 struct ieee80211_sub_if_data *sdata;
1771 struct mesh_path *mpath; 1818 struct mesh_path *mpath;
@@ -3019,26 +3066,11 @@ void ieee80211_csa_finish(struct ieee80211_vif *vif)
3019} 3066}
3020EXPORT_SYMBOL(ieee80211_csa_finish); 3067EXPORT_SYMBOL(ieee80211_csa_finish);
3021 3068
3022static void ieee80211_csa_finalize(struct ieee80211_sub_if_data *sdata) 3069static int ieee80211_set_after_csa_beacon(struct ieee80211_sub_if_data *sdata,
3070 u32 *changed)
3023{ 3071{
3024 struct ieee80211_local *local = sdata->local; 3072 int err;
3025 int err, changed = 0;
3026
3027 sdata_assert_lock(sdata);
3028
3029 mutex_lock(&local->mtx);
3030 sdata->radar_required = sdata->csa_radar_required;
3031 err = ieee80211_vif_change_channel(sdata, &changed);
3032 mutex_unlock(&local->mtx);
3033 if (WARN_ON(err < 0))
3034 return;
3035
3036 if (!local->use_chanctx) {
3037 local->_oper_chandef = sdata->csa_chandef;
3038 ieee80211_hw_config(local, 0);
3039 }
3040 3073
3041 sdata->vif.csa_active = false;
3042 switch (sdata->vif.type) { 3074 switch (sdata->vif.type) {
3043 case NL80211_IFTYPE_AP: 3075 case NL80211_IFTYPE_AP:
3044 err = ieee80211_assign_beacon(sdata, sdata->u.ap.next_beacon); 3076 err = ieee80211_assign_beacon(sdata, sdata->u.ap.next_beacon);
@@ -3046,35 +3078,74 @@ static void ieee80211_csa_finalize(struct ieee80211_sub_if_data *sdata)
3046 sdata->u.ap.next_beacon = NULL; 3078 sdata->u.ap.next_beacon = NULL;
3047 3079
3048 if (err < 0) 3080 if (err < 0)
3049 return; 3081 return err;
3050 changed |= err; 3082 *changed |= err;
3051 break; 3083 break;
3052 case NL80211_IFTYPE_ADHOC: 3084 case NL80211_IFTYPE_ADHOC:
3053 err = ieee80211_ibss_finish_csa(sdata); 3085 err = ieee80211_ibss_finish_csa(sdata);
3054 if (err < 0) 3086 if (err < 0)
3055 return; 3087 return err;
3056 changed |= err; 3088 *changed |= err;
3057 break; 3089 break;
3058#ifdef CONFIG_MAC80211_MESH 3090#ifdef CONFIG_MAC80211_MESH
3059 case NL80211_IFTYPE_MESH_POINT: 3091 case NL80211_IFTYPE_MESH_POINT:
3060 err = ieee80211_mesh_finish_csa(sdata); 3092 err = ieee80211_mesh_finish_csa(sdata);
3061 if (err < 0) 3093 if (err < 0)
3062 return; 3094 return err;
3063 changed |= err; 3095 *changed |= err;
3064 break; 3096 break;
3065#endif 3097#endif
3066 default: 3098 default:
3067 WARN_ON(1); 3099 WARN_ON(1);
3068 return; 3100 return -EINVAL;
3101 }
3102
3103 return 0;
3104}
3105
3106static int __ieee80211_csa_finalize(struct ieee80211_sub_if_data *sdata)
3107{
3108 struct ieee80211_local *local = sdata->local;
3109 u32 changed = 0;
3110 int err;
3111
3112 sdata_assert_lock(sdata);
3113 lockdep_assert_held(&local->mtx);
3114
3115 sdata->radar_required = sdata->csa_radar_required;
3116 err = ieee80211_vif_change_channel(sdata, &changed);
3117 if (err < 0)
3118 return err;
3119
3120 if (!local->use_chanctx) {
3121 local->_oper_chandef = sdata->csa_chandef;
3122 ieee80211_hw_config(local, 0);
3069 } 3123 }
3070 3124
3125 sdata->vif.csa_active = false;
3126
3127 err = ieee80211_set_after_csa_beacon(sdata, &changed);
3128 if (err)
3129 return err;
3130
3071 ieee80211_bss_info_change_notify(sdata, changed); 3131 ieee80211_bss_info_change_notify(sdata, changed);
3132 cfg80211_ch_switch_notify(sdata->dev, &sdata->csa_chandef);
3072 3133
3073 ieee80211_wake_queues_by_reason(&sdata->local->hw, 3134 if (!ieee80211_csa_needs_block_tx(local))
3135 ieee80211_wake_queues_by_reason(&local->hw,
3074 IEEE80211_MAX_QUEUE_MAP, 3136 IEEE80211_MAX_QUEUE_MAP,
3075 IEEE80211_QUEUE_STOP_REASON_CSA); 3137 IEEE80211_QUEUE_STOP_REASON_CSA);
3076 3138
3077 cfg80211_ch_switch_notify(sdata->dev, &sdata->csa_chandef); 3139 return 0;
3140}
3141
3142static void ieee80211_csa_finalize(struct ieee80211_sub_if_data *sdata)
3143{
3144 if (__ieee80211_csa_finalize(sdata)) {
3145 sdata_info(sdata, "failed to finalize CSA, disconnecting\n");
3146 cfg80211_stop_iface(sdata->local->hw.wiphy, &sdata->wdev,
3147 GFP_KERNEL);
3148 }
3078} 3149}
3079 3150
3080void ieee80211_csa_finalize_work(struct work_struct *work) 3151void ieee80211_csa_finalize_work(struct work_struct *work)
@@ -3082,8 +3153,11 @@ void ieee80211_csa_finalize_work(struct work_struct *work)
3082 struct ieee80211_sub_if_data *sdata = 3153 struct ieee80211_sub_if_data *sdata =
3083 container_of(work, struct ieee80211_sub_if_data, 3154 container_of(work, struct ieee80211_sub_if_data,
3084 csa_finalize_work); 3155 csa_finalize_work);
3156 struct ieee80211_local *local = sdata->local;
3085 3157
3086 sdata_lock(sdata); 3158 sdata_lock(sdata);
3159 mutex_lock(&local->mtx);
3160
3087 /* AP might have been stopped while waiting for the lock. */ 3161 /* AP might have been stopped while waiting for the lock. */
3088 if (!sdata->vif.csa_active) 3162 if (!sdata->vif.csa_active)
3089 goto unlock; 3163 goto unlock;
@@ -3094,6 +3168,7 @@ void ieee80211_csa_finalize_work(struct work_struct *work)
3094 ieee80211_csa_finalize(sdata); 3168 ieee80211_csa_finalize(sdata);
3095 3169
3096unlock: 3170unlock:
3171 mutex_unlock(&local->mtx);
3097 sdata_unlock(sdata); 3172 sdata_unlock(sdata);
3098} 3173}
3099 3174
@@ -3129,9 +3204,25 @@ static int ieee80211_set_csa_beacon(struct ieee80211_sub_if_data *sdata,
3129 if (params->count <= 1) 3204 if (params->count <= 1)
3130 break; 3205 break;
3131 3206
3132 sdata->csa_counter_offset_beacon = 3207 if ((params->n_counter_offsets_beacon >
3133 params->counter_offset_beacon; 3208 IEEE80211_MAX_CSA_COUNTERS_NUM) ||
3134 sdata->csa_counter_offset_presp = params->counter_offset_presp; 3209 (params->n_counter_offsets_presp >
3210 IEEE80211_MAX_CSA_COUNTERS_NUM))
3211 return -EINVAL;
3212
3213 /* make sure we don't have garbage in other counters */
3214 memset(sdata->csa_counter_offset_beacon, 0,
3215 sizeof(sdata->csa_counter_offset_beacon));
3216 memset(sdata->csa_counter_offset_presp, 0,
3217 sizeof(sdata->csa_counter_offset_presp));
3218
3219 memcpy(sdata->csa_counter_offset_beacon,
3220 params->counter_offsets_beacon,
3221 params->n_counter_offsets_beacon * sizeof(u16));
3222 memcpy(sdata->csa_counter_offset_presp,
3223 params->counter_offsets_presp,
3224 params->n_counter_offsets_presp * sizeof(u16));
3225
3135 err = ieee80211_assign_beacon(sdata, &params->beacon_csa); 3226 err = ieee80211_assign_beacon(sdata, &params->beacon_csa);
3136 if (err < 0) { 3227 if (err < 0) {
3137 kfree(sdata->u.ap.next_beacon); 3228 kfree(sdata->u.ap.next_beacon);
@@ -3220,8 +3311,9 @@ static int ieee80211_set_csa_beacon(struct ieee80211_sub_if_data *sdata,
3220 return 0; 3311 return 0;
3221} 3312}
3222 3313
3223int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev, 3314static int
3224 struct cfg80211_csa_settings *params) 3315__ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev,
3316 struct cfg80211_csa_settings *params)
3225{ 3317{
3226 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 3318 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
3227 struct ieee80211_local *local = sdata->local; 3319 struct ieee80211_local *local = sdata->local;
@@ -3230,6 +3322,7 @@ int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev,
3230 int err, num_chanctx, changed = 0; 3322 int err, num_chanctx, changed = 0;
3231 3323
3232 sdata_assert_lock(sdata); 3324 sdata_assert_lock(sdata);
3325 lockdep_assert_held(&local->mtx);
3233 3326
3234 if (!list_empty(&local->roc_list) || local->scanning) 3327 if (!list_empty(&local->roc_list) || local->scanning)
3235 return -EBUSY; 3328 return -EBUSY;
@@ -3272,15 +3365,16 @@ int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev,
3272 return err; 3365 return err;
3273 3366
3274 sdata->csa_radar_required = params->radar_required; 3367 sdata->csa_radar_required = params->radar_required;
3275
3276 if (params->block_tx)
3277 ieee80211_stop_queues_by_reason(&local->hw,
3278 IEEE80211_MAX_QUEUE_MAP,
3279 IEEE80211_QUEUE_STOP_REASON_CSA);
3280
3281 sdata->csa_chandef = params->chandef; 3368 sdata->csa_chandef = params->chandef;
3369 sdata->csa_block_tx = params->block_tx;
3370 sdata->csa_current_counter = params->count;
3282 sdata->vif.csa_active = true; 3371 sdata->vif.csa_active = true;
3283 3372
3373 if (sdata->csa_block_tx)
3374 ieee80211_stop_queues_by_reason(&local->hw,
3375 IEEE80211_MAX_QUEUE_MAP,
3376 IEEE80211_QUEUE_STOP_REASON_CSA);
3377
3284 if (changed) { 3378 if (changed) {
3285 ieee80211_bss_info_change_notify(sdata, changed); 3379 ieee80211_bss_info_change_notify(sdata, changed);
3286 drv_channel_switch_beacon(sdata, &params->chandef); 3380 drv_channel_switch_beacon(sdata, &params->chandef);
@@ -3292,6 +3386,20 @@ int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev,
3292 return 0; 3386 return 0;
3293} 3387}
3294 3388
3389int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev,
3390 struct cfg80211_csa_settings *params)
3391{
3392 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
3393 struct ieee80211_local *local = sdata->local;
3394 int err;
3395
3396 mutex_lock(&local->mtx);
3397 err = __ieee80211_channel_switch(wiphy, dev, params);
3398 mutex_unlock(&local->mtx);
3399
3400 return err;
3401}
3402
3295static int ieee80211_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev, 3403static int ieee80211_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev,
3296 struct cfg80211_mgmt_tx_params *params, 3404 struct cfg80211_mgmt_tx_params *params,
3297 u64 *cookie) 3405 u64 *cookie)
@@ -3304,6 +3412,7 @@ static int ieee80211_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev,
3304 bool need_offchan = false; 3412 bool need_offchan = false;
3305 u32 flags; 3413 u32 flags;
3306 int ret; 3414 int ret;
3415 u8 *data;
3307 3416
3308 if (params->dont_wait_for_ack) 3417 if (params->dont_wait_for_ack)
3309 flags = IEEE80211_TX_CTL_NO_ACK; 3418 flags = IEEE80211_TX_CTL_NO_ACK;
@@ -3397,7 +3506,20 @@ static int ieee80211_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev,
3397 } 3506 }
3398 skb_reserve(skb, local->hw.extra_tx_headroom); 3507 skb_reserve(skb, local->hw.extra_tx_headroom);
3399 3508
3400 memcpy(skb_put(skb, params->len), params->buf, params->len); 3509 data = skb_put(skb, params->len);
3510 memcpy(data, params->buf, params->len);
3511
3512 /* Update CSA counters */
3513 if (sdata->vif.csa_active &&
3514 (sdata->vif.type == NL80211_IFTYPE_AP ||
3515 sdata->vif.type == NL80211_IFTYPE_ADHOC) &&
3516 params->n_csa_offsets) {
3517 int i;
3518 u8 c = sdata->csa_current_counter;
3519
3520 for (i = 0; i < params->n_csa_offsets; i++)
3521 data[params->csa_offsets[i]] = c;
3522 }
3401 3523
3402 IEEE80211_SKB_CB(skb)->flags = flags; 3524 IEEE80211_SKB_CB(skb)->flags = flags;
3403 3525
@@ -3506,320 +3628,6 @@ static int ieee80211_set_rekey_data(struct wiphy *wiphy,
3506 return 0; 3628 return 0;
3507} 3629}
3508 3630
3509static void ieee80211_tdls_add_ext_capab(struct sk_buff *skb)
3510{
3511 u8 *pos = (void *)skb_put(skb, 7);
3512
3513 *pos++ = WLAN_EID_EXT_CAPABILITY;
3514 *pos++ = 5; /* len */
3515 *pos++ = 0x0;
3516 *pos++ = 0x0;
3517 *pos++ = 0x0;
3518 *pos++ = 0x0;
3519 *pos++ = WLAN_EXT_CAPA5_TDLS_ENABLED;
3520}
3521
3522static u16 ieee80211_get_tdls_sta_capab(struct ieee80211_sub_if_data *sdata)
3523{
3524 struct ieee80211_local *local = sdata->local;
3525 u16 capab;
3526
3527 capab = 0;
3528 if (ieee80211_get_sdata_band(sdata) != IEEE80211_BAND_2GHZ)
3529 return capab;
3530
3531 if (!(local->hw.flags & IEEE80211_HW_2GHZ_SHORT_SLOT_INCAPABLE))
3532 capab |= WLAN_CAPABILITY_SHORT_SLOT_TIME;
3533 if (!(local->hw.flags & IEEE80211_HW_2GHZ_SHORT_PREAMBLE_INCAPABLE))
3534 capab |= WLAN_CAPABILITY_SHORT_PREAMBLE;
3535
3536 return capab;
3537}
3538
3539static void ieee80211_tdls_add_link_ie(struct sk_buff *skb, u8 *src_addr,
3540 u8 *peer, u8 *bssid)
3541{
3542 struct ieee80211_tdls_lnkie *lnkid;
3543
3544 lnkid = (void *)skb_put(skb, sizeof(struct ieee80211_tdls_lnkie));
3545
3546 lnkid->ie_type = WLAN_EID_LINK_ID;
3547 lnkid->ie_len = sizeof(struct ieee80211_tdls_lnkie) - 2;
3548
3549 memcpy(lnkid->bssid, bssid, ETH_ALEN);
3550 memcpy(lnkid->init_sta, src_addr, ETH_ALEN);
3551 memcpy(lnkid->resp_sta, peer, ETH_ALEN);
3552}
3553
3554static int
3555ieee80211_prep_tdls_encap_data(struct wiphy *wiphy, struct net_device *dev,
3556 u8 *peer, u8 action_code, u8 dialog_token,
3557 u16 status_code, struct sk_buff *skb)
3558{
3559 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
3560 enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
3561 struct ieee80211_tdls_data *tf;
3562
3563 tf = (void *)skb_put(skb, offsetof(struct ieee80211_tdls_data, u));
3564
3565 memcpy(tf->da, peer, ETH_ALEN);
3566 memcpy(tf->sa, sdata->vif.addr, ETH_ALEN);
3567 tf->ether_type = cpu_to_be16(ETH_P_TDLS);
3568 tf->payload_type = WLAN_TDLS_SNAP_RFTYPE;
3569
3570 switch (action_code) {
3571 case WLAN_TDLS_SETUP_REQUEST:
3572 tf->category = WLAN_CATEGORY_TDLS;
3573 tf->action_code = WLAN_TDLS_SETUP_REQUEST;
3574
3575 skb_put(skb, sizeof(tf->u.setup_req));
3576 tf->u.setup_req.dialog_token = dialog_token;
3577 tf->u.setup_req.capability =
3578 cpu_to_le16(ieee80211_get_tdls_sta_capab(sdata));
3579
3580 ieee80211_add_srates_ie(sdata, skb, false, band);
3581 ieee80211_add_ext_srates_ie(sdata, skb, false, band);
3582 ieee80211_tdls_add_ext_capab(skb);
3583 break;
3584 case WLAN_TDLS_SETUP_RESPONSE:
3585 tf->category = WLAN_CATEGORY_TDLS;
3586 tf->action_code = WLAN_TDLS_SETUP_RESPONSE;
3587
3588 skb_put(skb, sizeof(tf->u.setup_resp));
3589 tf->u.setup_resp.status_code = cpu_to_le16(status_code);
3590 tf->u.setup_resp.dialog_token = dialog_token;
3591 tf->u.setup_resp.capability =
3592 cpu_to_le16(ieee80211_get_tdls_sta_capab(sdata));
3593
3594 ieee80211_add_srates_ie(sdata, skb, false, band);
3595 ieee80211_add_ext_srates_ie(sdata, skb, false, band);
3596 ieee80211_tdls_add_ext_capab(skb);
3597 break;
3598 case WLAN_TDLS_SETUP_CONFIRM:
3599 tf->category = WLAN_CATEGORY_TDLS;
3600 tf->action_code = WLAN_TDLS_SETUP_CONFIRM;
3601
3602 skb_put(skb, sizeof(tf->u.setup_cfm));
3603 tf->u.setup_cfm.status_code = cpu_to_le16(status_code);
3604 tf->u.setup_cfm.dialog_token = dialog_token;
3605 break;
3606 case WLAN_TDLS_TEARDOWN:
3607 tf->category = WLAN_CATEGORY_TDLS;
3608 tf->action_code = WLAN_TDLS_TEARDOWN;
3609
3610 skb_put(skb, sizeof(tf->u.teardown));
3611 tf->u.teardown.reason_code = cpu_to_le16(status_code);
3612 break;
3613 case WLAN_TDLS_DISCOVERY_REQUEST:
3614 tf->category = WLAN_CATEGORY_TDLS;
3615 tf->action_code = WLAN_TDLS_DISCOVERY_REQUEST;
3616
3617 skb_put(skb, sizeof(tf->u.discover_req));
3618 tf->u.discover_req.dialog_token = dialog_token;
3619 break;
3620 default:
3621 return -EINVAL;
3622 }
3623
3624 return 0;
3625}
3626
3627static int
3628ieee80211_prep_tdls_direct(struct wiphy *wiphy, struct net_device *dev,
3629 u8 *peer, u8 action_code, u8 dialog_token,
3630 u16 status_code, struct sk_buff *skb)
3631{
3632 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
3633 enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
3634 struct ieee80211_mgmt *mgmt;
3635
3636 mgmt = (void *)skb_put(skb, 24);
3637 memset(mgmt, 0, 24);
3638 memcpy(mgmt->da, peer, ETH_ALEN);
3639 memcpy(mgmt->sa, sdata->vif.addr, ETH_ALEN);
3640 memcpy(mgmt->bssid, sdata->u.mgd.bssid, ETH_ALEN);
3641
3642 mgmt->frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
3643 IEEE80211_STYPE_ACTION);
3644
3645 switch (action_code) {
3646 case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
3647 skb_put(skb, 1 + sizeof(mgmt->u.action.u.tdls_discover_resp));
3648 mgmt->u.action.category = WLAN_CATEGORY_PUBLIC;
3649 mgmt->u.action.u.tdls_discover_resp.action_code =
3650 WLAN_PUB_ACTION_TDLS_DISCOVER_RES;
3651 mgmt->u.action.u.tdls_discover_resp.dialog_token =
3652 dialog_token;
3653 mgmt->u.action.u.tdls_discover_resp.capability =
3654 cpu_to_le16(ieee80211_get_tdls_sta_capab(sdata));
3655
3656 ieee80211_add_srates_ie(sdata, skb, false, band);
3657 ieee80211_add_ext_srates_ie(sdata, skb, false, band);
3658 ieee80211_tdls_add_ext_capab(skb);
3659 break;
3660 default:
3661 return -EINVAL;
3662 }
3663
3664 return 0;
3665}
3666
3667static int ieee80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev,
3668 u8 *peer, u8 action_code, u8 dialog_token,
3669 u16 status_code, u32 peer_capability,
3670 const u8 *extra_ies, size_t extra_ies_len)
3671{
3672 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
3673 struct ieee80211_local *local = sdata->local;
3674 struct sk_buff *skb = NULL;
3675 bool send_direct;
3676 int ret;
3677
3678 if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS))
3679 return -ENOTSUPP;
3680
3681 /* make sure we are in managed mode, and associated */
3682 if (sdata->vif.type != NL80211_IFTYPE_STATION ||
3683 !sdata->u.mgd.associated)
3684 return -EINVAL;
3685
3686 tdls_dbg(sdata, "TDLS mgmt action %d peer %pM\n",
3687 action_code, peer);
3688
3689 skb = dev_alloc_skb(local->hw.extra_tx_headroom +
3690 max(sizeof(struct ieee80211_mgmt),
3691 sizeof(struct ieee80211_tdls_data)) +
3692 50 + /* supported rates */
3693 7 + /* ext capab */
3694 extra_ies_len +
3695 sizeof(struct ieee80211_tdls_lnkie));
3696 if (!skb)
3697 return -ENOMEM;
3698
3699 skb_reserve(skb, local->hw.extra_tx_headroom);
3700
3701 switch (action_code) {
3702 case WLAN_TDLS_SETUP_REQUEST:
3703 case WLAN_TDLS_SETUP_RESPONSE:
3704 case WLAN_TDLS_SETUP_CONFIRM:
3705 case WLAN_TDLS_TEARDOWN:
3706 case WLAN_TDLS_DISCOVERY_REQUEST:
3707 ret = ieee80211_prep_tdls_encap_data(wiphy, dev, peer,
3708 action_code, dialog_token,
3709 status_code, skb);
3710 send_direct = false;
3711 break;
3712 case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
3713 ret = ieee80211_prep_tdls_direct(wiphy, dev, peer, action_code,
3714 dialog_token, status_code,
3715 skb);
3716 send_direct = true;
3717 break;
3718 default:
3719 ret = -ENOTSUPP;
3720 break;
3721 }
3722
3723 if (ret < 0)
3724 goto fail;
3725
3726 if (extra_ies_len)
3727 memcpy(skb_put(skb, extra_ies_len), extra_ies, extra_ies_len);
3728
3729 /* the TDLS link IE is always added last */
3730 switch (action_code) {
3731 case WLAN_TDLS_SETUP_REQUEST:
3732 case WLAN_TDLS_SETUP_CONFIRM:
3733 case WLAN_TDLS_TEARDOWN:
3734 case WLAN_TDLS_DISCOVERY_REQUEST:
3735 /* we are the initiator */
3736 ieee80211_tdls_add_link_ie(skb, sdata->vif.addr, peer,
3737 sdata->u.mgd.bssid);
3738 break;
3739 case WLAN_TDLS_SETUP_RESPONSE:
3740 case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
3741 /* we are the responder */
3742 ieee80211_tdls_add_link_ie(skb, peer, sdata->vif.addr,
3743 sdata->u.mgd.bssid);
3744 break;
3745 default:
3746 ret = -ENOTSUPP;
3747 goto fail;
3748 }
3749
3750 if (send_direct) {
3751 ieee80211_tx_skb(sdata, skb);
3752 return 0;
3753 }
3754
3755 /*
3756 * According to 802.11z: Setup req/resp are sent in AC_BK, otherwise
3757 * we should default to AC_VI.
3758 */
3759 switch (action_code) {
3760 case WLAN_TDLS_SETUP_REQUEST:
3761 case WLAN_TDLS_SETUP_RESPONSE:
3762 skb_set_queue_mapping(skb, IEEE80211_AC_BK);
3763 skb->priority = 2;
3764 break;
3765 default:
3766 skb_set_queue_mapping(skb, IEEE80211_AC_VI);
3767 skb->priority = 5;
3768 break;
3769 }
3770
3771 /* disable bottom halves when entering the Tx path */
3772 local_bh_disable();
3773 ret = ieee80211_subif_start_xmit(skb, dev);
3774 local_bh_enable();
3775
3776 return ret;
3777
3778fail:
3779 dev_kfree_skb(skb);
3780 return ret;
3781}
3782
3783static int ieee80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev,
3784 u8 *peer, enum nl80211_tdls_operation oper)
3785{
3786 struct sta_info *sta;
3787 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
3788
3789 if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS))
3790 return -ENOTSUPP;
3791
3792 if (sdata->vif.type != NL80211_IFTYPE_STATION)
3793 return -EINVAL;
3794
3795 tdls_dbg(sdata, "TDLS oper %d peer %pM\n", oper, peer);
3796
3797 switch (oper) {
3798 case NL80211_TDLS_ENABLE_LINK:
3799 rcu_read_lock();
3800 sta = sta_info_get(sdata, peer);
3801 if (!sta) {
3802 rcu_read_unlock();
3803 return -ENOLINK;
3804 }
3805
3806 set_sta_flag(sta, WLAN_STA_TDLS_PEER_AUTH);
3807 rcu_read_unlock();
3808 break;
3809 case NL80211_TDLS_DISABLE_LINK:
3810 return sta_info_destroy_addr(sdata, peer);
3811 case NL80211_TDLS_TEARDOWN:
3812 case NL80211_TDLS_SETUP:
3813 case NL80211_TDLS_DISCOVERY_REQ:
3814 /* We don't support in-driver setup/teardown/discovery */
3815 return -ENOTSUPP;
3816 default:
3817 return -ENOTSUPP;
3818 }
3819
3820 return 0;
3821}
3822
3823static int ieee80211_probe_client(struct wiphy *wiphy, struct net_device *dev, 3631static int ieee80211_probe_client(struct wiphy *wiphy, struct net_device *dev,
3824 const u8 *peer, u64 *cookie) 3632 const u8 *peer, u64 *cookie)
3825{ 3633{
diff --git a/net/mac80211/chan.c b/net/mac80211/chan.c
index 48e6d6f010cd..a310e33972de 100644
--- a/net/mac80211/chan.c
+++ b/net/mac80211/chan.c
@@ -855,7 +855,7 @@ static void
855__ieee80211_vif_copy_chanctx_to_vlans(struct ieee80211_sub_if_data *sdata, 855__ieee80211_vif_copy_chanctx_to_vlans(struct ieee80211_sub_if_data *sdata,
856 bool clear) 856 bool clear)
857{ 857{
858 struct ieee80211_local *local = sdata->local; 858 struct ieee80211_local *local __maybe_unused = sdata->local;
859 struct ieee80211_sub_if_data *vlan; 859 struct ieee80211_sub_if_data *vlan;
860 struct ieee80211_chanctx_conf *conf; 860 struct ieee80211_chanctx_conf *conf;
861 861
@@ -871,7 +871,7 @@ __ieee80211_vif_copy_chanctx_to_vlans(struct ieee80211_sub_if_data *sdata,
871 * to a channel context that has already been freed. 871 * to a channel context that has already been freed.
872 */ 872 */
873 conf = rcu_dereference_protected(sdata->vif.chanctx_conf, 873 conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
874 lockdep_is_held(&local->chanctx_mtx)); 874 lockdep_is_held(&local->chanctx_mtx));
875 WARN_ON(!conf); 875 WARN_ON(!conf);
876 876
877 if (clear) 877 if (clear)
diff --git a/net/mac80211/driver-ops.h b/net/mac80211/driver-ops.h
index 5331582a2c81..696ef78b1fb7 100644
--- a/net/mac80211/driver-ops.h
+++ b/net/mac80211/driver-ops.h
@@ -5,11 +5,11 @@
5#include "ieee80211_i.h" 5#include "ieee80211_i.h"
6#include "trace.h" 6#include "trace.h"
7 7
8static inline void check_sdata_in_driver(struct ieee80211_sub_if_data *sdata) 8static inline bool check_sdata_in_driver(struct ieee80211_sub_if_data *sdata)
9{ 9{
10 WARN(!(sdata->flags & IEEE80211_SDATA_IN_DRIVER), 10 return !WARN(!(sdata->flags & IEEE80211_SDATA_IN_DRIVER),
11 "%s: Failed check-sdata-in-driver check, flags: 0x%x\n", 11 "%s: Failed check-sdata-in-driver check, flags: 0x%x\n",
12 sdata->dev ? sdata->dev->name : sdata->name, sdata->flags); 12 sdata->dev ? sdata->dev->name : sdata->name, sdata->flags);
13} 13}
14 14
15static inline struct ieee80211_sub_if_data * 15static inline struct ieee80211_sub_if_data *
@@ -168,7 +168,8 @@ static inline int drv_change_interface(struct ieee80211_local *local,
168 168
169 might_sleep(); 169 might_sleep();
170 170
171 check_sdata_in_driver(sdata); 171 if (!check_sdata_in_driver(sdata))
172 return -EIO;
172 173
173 trace_drv_change_interface(local, sdata, type, p2p); 174 trace_drv_change_interface(local, sdata, type, p2p);
174 ret = local->ops->change_interface(&local->hw, &sdata->vif, type, p2p); 175 ret = local->ops->change_interface(&local->hw, &sdata->vif, type, p2p);
@@ -181,7 +182,8 @@ static inline void drv_remove_interface(struct ieee80211_local *local,
181{ 182{
182 might_sleep(); 183 might_sleep();
183 184
184 check_sdata_in_driver(sdata); 185 if (!check_sdata_in_driver(sdata))
186 return;
185 187
186 trace_drv_remove_interface(local, sdata); 188 trace_drv_remove_interface(local, sdata);
187 local->ops->remove_interface(&local->hw, &sdata->vif); 189 local->ops->remove_interface(&local->hw, &sdata->vif);
@@ -219,7 +221,8 @@ static inline void drv_bss_info_changed(struct ieee80211_local *local,
219 sdata->vif.type == NL80211_IFTYPE_MONITOR)) 221 sdata->vif.type == NL80211_IFTYPE_MONITOR))
220 return; 222 return;
221 223
222 check_sdata_in_driver(sdata); 224 if (!check_sdata_in_driver(sdata))
225 return;
223 226
224 trace_drv_bss_info_changed(local, sdata, info, changed); 227 trace_drv_bss_info_changed(local, sdata, info, changed);
225 if (local->ops->bss_info_changed) 228 if (local->ops->bss_info_changed)
@@ -278,7 +281,8 @@ static inline int drv_set_key(struct ieee80211_local *local,
278 might_sleep(); 281 might_sleep();
279 282
280 sdata = get_bss_sdata(sdata); 283 sdata = get_bss_sdata(sdata);
281 check_sdata_in_driver(sdata); 284 if (!check_sdata_in_driver(sdata))
285 return -EIO;
282 286
283 trace_drv_set_key(local, cmd, sdata, sta, key); 287 trace_drv_set_key(local, cmd, sdata, sta, key);
284 ret = local->ops->set_key(&local->hw, cmd, &sdata->vif, sta, key); 288 ret = local->ops->set_key(&local->hw, cmd, &sdata->vif, sta, key);
@@ -298,7 +302,8 @@ static inline void drv_update_tkip_key(struct ieee80211_local *local,
298 ista = &sta->sta; 302 ista = &sta->sta;
299 303
300 sdata = get_bss_sdata(sdata); 304 sdata = get_bss_sdata(sdata);
301 check_sdata_in_driver(sdata); 305 if (!check_sdata_in_driver(sdata))
306 return;
302 307
303 trace_drv_update_tkip_key(local, sdata, conf, ista, iv32); 308 trace_drv_update_tkip_key(local, sdata, conf, ista, iv32);
304 if (local->ops->update_tkip_key) 309 if (local->ops->update_tkip_key)
@@ -315,7 +320,8 @@ static inline int drv_hw_scan(struct ieee80211_local *local,
315 320
316 might_sleep(); 321 might_sleep();
317 322
318 check_sdata_in_driver(sdata); 323 if (!check_sdata_in_driver(sdata))
324 return -EIO;
319 325
320 trace_drv_hw_scan(local, sdata); 326 trace_drv_hw_scan(local, sdata);
321 ret = local->ops->hw_scan(&local->hw, &sdata->vif, req); 327 ret = local->ops->hw_scan(&local->hw, &sdata->vif, req);
@@ -328,7 +334,8 @@ static inline void drv_cancel_hw_scan(struct ieee80211_local *local,
328{ 334{
329 might_sleep(); 335 might_sleep();
330 336
331 check_sdata_in_driver(sdata); 337 if (!check_sdata_in_driver(sdata))
338 return;
332 339
333 trace_drv_cancel_hw_scan(local, sdata); 340 trace_drv_cancel_hw_scan(local, sdata);
334 local->ops->cancel_hw_scan(&local->hw, &sdata->vif); 341 local->ops->cancel_hw_scan(&local->hw, &sdata->vif);
@@ -345,7 +352,8 @@ drv_sched_scan_start(struct ieee80211_local *local,
345 352
346 might_sleep(); 353 might_sleep();
347 354
348 check_sdata_in_driver(sdata); 355 if (!check_sdata_in_driver(sdata))
356 return -EIO;
349 357
350 trace_drv_sched_scan_start(local, sdata); 358 trace_drv_sched_scan_start(local, sdata);
351 ret = local->ops->sched_scan_start(&local->hw, &sdata->vif, 359 ret = local->ops->sched_scan_start(&local->hw, &sdata->vif,
@@ -361,7 +369,8 @@ static inline int drv_sched_scan_stop(struct ieee80211_local *local,
361 369
362 might_sleep(); 370 might_sleep();
363 371
364 check_sdata_in_driver(sdata); 372 if (!check_sdata_in_driver(sdata))
373 return -EIO;
365 374
366 trace_drv_sched_scan_stop(local, sdata); 375 trace_drv_sched_scan_stop(local, sdata);
367 ret = local->ops->sched_scan_stop(&local->hw, &sdata->vif); 376 ret = local->ops->sched_scan_stop(&local->hw, &sdata->vif);
@@ -462,7 +471,8 @@ static inline void drv_sta_notify(struct ieee80211_local *local,
462 struct ieee80211_sta *sta) 471 struct ieee80211_sta *sta)
463{ 472{
464 sdata = get_bss_sdata(sdata); 473 sdata = get_bss_sdata(sdata);
465 check_sdata_in_driver(sdata); 474 if (!check_sdata_in_driver(sdata))
475 return;
466 476
467 trace_drv_sta_notify(local, sdata, cmd, sta); 477 trace_drv_sta_notify(local, sdata, cmd, sta);
468 if (local->ops->sta_notify) 478 if (local->ops->sta_notify)
@@ -479,7 +489,8 @@ static inline int drv_sta_add(struct ieee80211_local *local,
479 might_sleep(); 489 might_sleep();
480 490
481 sdata = get_bss_sdata(sdata); 491 sdata = get_bss_sdata(sdata);
482 check_sdata_in_driver(sdata); 492 if (!check_sdata_in_driver(sdata))
493 return -EIO;
483 494
484 trace_drv_sta_add(local, sdata, sta); 495 trace_drv_sta_add(local, sdata, sta);
485 if (local->ops->sta_add) 496 if (local->ops->sta_add)
@@ -497,7 +508,8 @@ static inline void drv_sta_remove(struct ieee80211_local *local,
497 might_sleep(); 508 might_sleep();
498 509
499 sdata = get_bss_sdata(sdata); 510 sdata = get_bss_sdata(sdata);
500 check_sdata_in_driver(sdata); 511 if (!check_sdata_in_driver(sdata))
512 return;
501 513
502 trace_drv_sta_remove(local, sdata, sta); 514 trace_drv_sta_remove(local, sdata, sta);
503 if (local->ops->sta_remove) 515 if (local->ops->sta_remove)
@@ -515,7 +527,8 @@ static inline void drv_sta_add_debugfs(struct ieee80211_local *local,
515 might_sleep(); 527 might_sleep();
516 528
517 sdata = get_bss_sdata(sdata); 529 sdata = get_bss_sdata(sdata);
518 check_sdata_in_driver(sdata); 530 if (!check_sdata_in_driver(sdata))
531 return;
519 532
520 if (local->ops->sta_add_debugfs) 533 if (local->ops->sta_add_debugfs)
521 local->ops->sta_add_debugfs(&local->hw, &sdata->vif, 534 local->ops->sta_add_debugfs(&local->hw, &sdata->vif,
@@ -545,7 +558,8 @@ static inline void drv_sta_pre_rcu_remove(struct ieee80211_local *local,
545 might_sleep(); 558 might_sleep();
546 559
547 sdata = get_bss_sdata(sdata); 560 sdata = get_bss_sdata(sdata);
548 check_sdata_in_driver(sdata); 561 if (!check_sdata_in_driver(sdata))
562 return;
549 563
550 trace_drv_sta_pre_rcu_remove(local, sdata, &sta->sta); 564 trace_drv_sta_pre_rcu_remove(local, sdata, &sta->sta);
551 if (local->ops->sta_pre_rcu_remove) 565 if (local->ops->sta_pre_rcu_remove)
@@ -566,7 +580,8 @@ int drv_sta_state(struct ieee80211_local *local,
566 might_sleep(); 580 might_sleep();
567 581
568 sdata = get_bss_sdata(sdata); 582 sdata = get_bss_sdata(sdata);
569 check_sdata_in_driver(sdata); 583 if (!check_sdata_in_driver(sdata))
584 return -EIO;
570 585
571 trace_drv_sta_state(local, sdata, &sta->sta, old_state, new_state); 586 trace_drv_sta_state(local, sdata, &sta->sta, old_state, new_state);
572 if (local->ops->sta_state) { 587 if (local->ops->sta_state) {
@@ -590,7 +605,8 @@ static inline void drv_sta_rc_update(struct ieee80211_local *local,
590 struct ieee80211_sta *sta, u32 changed) 605 struct ieee80211_sta *sta, u32 changed)
591{ 606{
592 sdata = get_bss_sdata(sdata); 607 sdata = get_bss_sdata(sdata);
593 check_sdata_in_driver(sdata); 608 if (!check_sdata_in_driver(sdata))
609 return;
594 610
595 WARN_ON(changed & IEEE80211_RC_SUPP_RATES_CHANGED && 611 WARN_ON(changed & IEEE80211_RC_SUPP_RATES_CHANGED &&
596 (sdata->vif.type != NL80211_IFTYPE_ADHOC && 612 (sdata->vif.type != NL80211_IFTYPE_ADHOC &&
@@ -612,7 +628,8 @@ static inline int drv_conf_tx(struct ieee80211_local *local,
612 628
613 might_sleep(); 629 might_sleep();
614 630
615 check_sdata_in_driver(sdata); 631 if (!check_sdata_in_driver(sdata))
632 return -EIO;
616 633
617 trace_drv_conf_tx(local, sdata, ac, params); 634 trace_drv_conf_tx(local, sdata, ac, params);
618 if (local->ops->conf_tx) 635 if (local->ops->conf_tx)
@@ -629,7 +646,8 @@ static inline u64 drv_get_tsf(struct ieee80211_local *local,
629 646
630 might_sleep(); 647 might_sleep();
631 648
632 check_sdata_in_driver(sdata); 649 if (!check_sdata_in_driver(sdata))
650 return ret;
633 651
634 trace_drv_get_tsf(local, sdata); 652 trace_drv_get_tsf(local, sdata);
635 if (local->ops->get_tsf) 653 if (local->ops->get_tsf)
@@ -644,7 +662,8 @@ static inline void drv_set_tsf(struct ieee80211_local *local,
644{ 662{
645 might_sleep(); 663 might_sleep();
646 664
647 check_sdata_in_driver(sdata); 665 if (!check_sdata_in_driver(sdata))
666 return;
648 667
649 trace_drv_set_tsf(local, sdata, tsf); 668 trace_drv_set_tsf(local, sdata, tsf);
650 if (local->ops->set_tsf) 669 if (local->ops->set_tsf)
@@ -657,7 +676,8 @@ static inline void drv_reset_tsf(struct ieee80211_local *local,
657{ 676{
658 might_sleep(); 677 might_sleep();
659 678
660 check_sdata_in_driver(sdata); 679 if (!check_sdata_in_driver(sdata))
680 return;
661 681
662 trace_drv_reset_tsf(local, sdata); 682 trace_drv_reset_tsf(local, sdata);
663 if (local->ops->reset_tsf) 683 if (local->ops->reset_tsf)
@@ -689,7 +709,8 @@ static inline int drv_ampdu_action(struct ieee80211_local *local,
689 might_sleep(); 709 might_sleep();
690 710
691 sdata = get_bss_sdata(sdata); 711 sdata = get_bss_sdata(sdata);
692 check_sdata_in_driver(sdata); 712 if (!check_sdata_in_driver(sdata))
713 return -EIO;
693 714
694 trace_drv_ampdu_action(local, sdata, action, sta, tid, ssn, buf_size); 715 trace_drv_ampdu_action(local, sdata, action, sta, tid, ssn, buf_size);
695 716
@@ -733,8 +754,8 @@ static inline void drv_flush(struct ieee80211_local *local,
733 754
734 might_sleep(); 755 might_sleep();
735 756
736 if (sdata) 757 if (sdata && !check_sdata_in_driver(sdata))
737 check_sdata_in_driver(sdata); 758 return;
738 759
739 trace_drv_flush(local, queues, drop); 760 trace_drv_flush(local, queues, drop);
740 if (local->ops->flush) 761 if (local->ops->flush)
@@ -854,7 +875,8 @@ static inline int drv_set_bitrate_mask(struct ieee80211_local *local,
854 875
855 might_sleep(); 876 might_sleep();
856 877
857 check_sdata_in_driver(sdata); 878 if (!check_sdata_in_driver(sdata))
879 return -EIO;
858 880
859 trace_drv_set_bitrate_mask(local, sdata, mask); 881 trace_drv_set_bitrate_mask(local, sdata, mask);
860 if (local->ops->set_bitrate_mask) 882 if (local->ops->set_bitrate_mask)
@@ -869,7 +891,8 @@ static inline void drv_set_rekey_data(struct ieee80211_local *local,
869 struct ieee80211_sub_if_data *sdata, 891 struct ieee80211_sub_if_data *sdata,
870 struct cfg80211_gtk_rekey_data *data) 892 struct cfg80211_gtk_rekey_data *data)
871{ 893{
872 check_sdata_in_driver(sdata); 894 if (!check_sdata_in_driver(sdata))
895 return;
873 896
874 trace_drv_set_rekey_data(local, sdata, data); 897 trace_drv_set_rekey_data(local, sdata, data);
875 if (local->ops->set_rekey_data) 898 if (local->ops->set_rekey_data)
@@ -937,7 +960,8 @@ static inline void drv_mgd_prepare_tx(struct ieee80211_local *local,
937{ 960{
938 might_sleep(); 961 might_sleep();
939 962
940 check_sdata_in_driver(sdata); 963 if (!check_sdata_in_driver(sdata))
964 return;
941 WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION); 965 WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION);
942 966
943 trace_drv_mgd_prepare_tx(local, sdata); 967 trace_drv_mgd_prepare_tx(local, sdata);
@@ -964,6 +988,9 @@ static inline int drv_add_chanctx(struct ieee80211_local *local,
964static inline void drv_remove_chanctx(struct ieee80211_local *local, 988static inline void drv_remove_chanctx(struct ieee80211_local *local,
965 struct ieee80211_chanctx *ctx) 989 struct ieee80211_chanctx *ctx)
966{ 990{
991 if (WARN_ON(!ctx->driver_present))
992 return;
993
967 trace_drv_remove_chanctx(local, ctx); 994 trace_drv_remove_chanctx(local, ctx);
968 if (local->ops->remove_chanctx) 995 if (local->ops->remove_chanctx)
969 local->ops->remove_chanctx(&local->hw, &ctx->conf); 996 local->ops->remove_chanctx(&local->hw, &ctx->conf);
@@ -989,7 +1016,8 @@ static inline int drv_assign_vif_chanctx(struct ieee80211_local *local,
989{ 1016{
990 int ret = 0; 1017 int ret = 0;
991 1018
992 check_sdata_in_driver(sdata); 1019 if (!check_sdata_in_driver(sdata))
1020 return -EIO;
993 1021
994 trace_drv_assign_vif_chanctx(local, sdata, ctx); 1022 trace_drv_assign_vif_chanctx(local, sdata, ctx);
995 if (local->ops->assign_vif_chanctx) { 1023 if (local->ops->assign_vif_chanctx) {
@@ -1007,7 +1035,8 @@ static inline void drv_unassign_vif_chanctx(struct ieee80211_local *local,
1007 struct ieee80211_sub_if_data *sdata, 1035 struct ieee80211_sub_if_data *sdata,
1008 struct ieee80211_chanctx *ctx) 1036 struct ieee80211_chanctx *ctx)
1009{ 1037{
1010 check_sdata_in_driver(sdata); 1038 if (!check_sdata_in_driver(sdata))
1039 return;
1011 1040
1012 trace_drv_unassign_vif_chanctx(local, sdata, ctx); 1041 trace_drv_unassign_vif_chanctx(local, sdata, ctx);
1013 if (local->ops->unassign_vif_chanctx) { 1042 if (local->ops->unassign_vif_chanctx) {
@@ -1024,7 +1053,8 @@ static inline int drv_start_ap(struct ieee80211_local *local,
1024{ 1053{
1025 int ret = 0; 1054 int ret = 0;
1026 1055
1027 check_sdata_in_driver(sdata); 1056 if (!check_sdata_in_driver(sdata))
1057 return -EIO;
1028 1058
1029 trace_drv_start_ap(local, sdata, &sdata->vif.bss_conf); 1059 trace_drv_start_ap(local, sdata, &sdata->vif.bss_conf);
1030 if (local->ops->start_ap) 1060 if (local->ops->start_ap)
@@ -1036,7 +1066,8 @@ static inline int drv_start_ap(struct ieee80211_local *local,
1036static inline void drv_stop_ap(struct ieee80211_local *local, 1066static inline void drv_stop_ap(struct ieee80211_local *local,
1037 struct ieee80211_sub_if_data *sdata) 1067 struct ieee80211_sub_if_data *sdata)
1038{ 1068{
1039 check_sdata_in_driver(sdata); 1069 if (!check_sdata_in_driver(sdata))
1070 return;
1040 1071
1041 trace_drv_stop_ap(local, sdata); 1072 trace_drv_stop_ap(local, sdata);
1042 if (local->ops->stop_ap) 1073 if (local->ops->stop_ap)
@@ -1059,7 +1090,8 @@ drv_set_default_unicast_key(struct ieee80211_local *local,
1059 struct ieee80211_sub_if_data *sdata, 1090 struct ieee80211_sub_if_data *sdata,
1060 int key_idx) 1091 int key_idx)
1061{ 1092{
1062 check_sdata_in_driver(sdata); 1093 if (!check_sdata_in_driver(sdata))
1094 return;
1063 1095
1064 WARN_ON_ONCE(key_idx < -1 || key_idx > 3); 1096 WARN_ON_ONCE(key_idx < -1 || key_idx > 3);
1065 1097
@@ -1101,7 +1133,8 @@ static inline int drv_join_ibss(struct ieee80211_local *local,
1101 int ret = 0; 1133 int ret = 0;
1102 1134
1103 might_sleep(); 1135 might_sleep();
1104 check_sdata_in_driver(sdata); 1136 if (!check_sdata_in_driver(sdata))
1137 return -EIO;
1105 1138
1106 trace_drv_join_ibss(local, sdata, &sdata->vif.bss_conf); 1139 trace_drv_join_ibss(local, sdata, &sdata->vif.bss_conf);
1107 if (local->ops->join_ibss) 1140 if (local->ops->join_ibss)
@@ -1114,7 +1147,8 @@ static inline void drv_leave_ibss(struct ieee80211_local *local,
1114 struct ieee80211_sub_if_data *sdata) 1147 struct ieee80211_sub_if_data *sdata)
1115{ 1148{
1116 might_sleep(); 1149 might_sleep();
1117 check_sdata_in_driver(sdata); 1150 if (!check_sdata_in_driver(sdata))
1151 return;
1118 1152
1119 trace_drv_leave_ibss(local, sdata); 1153 trace_drv_leave_ibss(local, sdata);
1120 if (local->ops->leave_ibss) 1154 if (local->ops->leave_ibss)
@@ -1122,4 +1156,17 @@ static inline void drv_leave_ibss(struct ieee80211_local *local,
1122 trace_drv_return_void(local); 1156 trace_drv_return_void(local);
1123} 1157}
1124 1158
1159static inline u32 drv_get_expected_throughput(struct ieee80211_local *local,
1160 struct ieee80211_sta *sta)
1161{
1162 u32 ret = 0;
1163
1164 trace_drv_get_expected_throughput(sta);
1165 if (local->ops->get_expected_throughput)
1166 ret = local->ops->get_expected_throughput(sta);
1167 trace_drv_return_u32(local, ret);
1168
1169 return ret;
1170}
1171
1125#endif /* __MAC80211_DRIVER_OPS */ 1172#endif /* __MAC80211_DRIVER_OPS */
diff --git a/net/mac80211/ibss.c b/net/mac80211/ibss.c
index ff4d4155a84d..1bbac94da58d 100644
--- a/net/mac80211/ibss.c
+++ b/net/mac80211/ibss.c
@@ -143,7 +143,7 @@ ieee80211_ibss_build_presp(struct ieee80211_sub_if_data *sdata,
143 *pos++ = csa_settings->block_tx ? 1 : 0; 143 *pos++ = csa_settings->block_tx ? 1 : 0;
144 *pos++ = ieee80211_frequency_to_channel( 144 *pos++ = ieee80211_frequency_to_channel(
145 csa_settings->chandef.chan->center_freq); 145 csa_settings->chandef.chan->center_freq);
146 sdata->csa_counter_offset_beacon = (pos - presp->head); 146 sdata->csa_counter_offset_beacon[0] = (pos - presp->head);
147 *pos++ = csa_settings->count; 147 *pos++ = csa_settings->count;
148 } 148 }
149 149
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
index 487c2ef0982a..ac9836e0aab3 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -754,9 +754,10 @@ struct ieee80211_sub_if_data {
754 struct mac80211_qos_map __rcu *qos_map; 754 struct mac80211_qos_map __rcu *qos_map;
755 755
756 struct work_struct csa_finalize_work; 756 struct work_struct csa_finalize_work;
757 int csa_counter_offset_beacon; 757 u16 csa_counter_offset_beacon[IEEE80211_MAX_CSA_COUNTERS_NUM];
758 int csa_counter_offset_presp; 758 u16 csa_counter_offset_presp[IEEE80211_MAX_CSA_COUNTERS_NUM];
759 bool csa_radar_required; 759 bool csa_radar_required;
760 bool csa_block_tx; /* write-protected by sdata_lock and local->mtx */
760 struct cfg80211_chan_def csa_chandef; 761 struct cfg80211_chan_def csa_chandef;
761 762
762 struct list_head assigned_chanctx_list; /* protected by chanctx_mtx */ 763 struct list_head assigned_chanctx_list; /* protected by chanctx_mtx */
@@ -766,6 +767,7 @@ struct ieee80211_sub_if_data {
766 struct ieee80211_chanctx *reserved_chanctx; 767 struct ieee80211_chanctx *reserved_chanctx;
767 struct cfg80211_chan_def reserved_chandef; 768 struct cfg80211_chan_def reserved_chandef;
768 bool reserved_radar_required; 769 bool reserved_radar_required;
770 u8 csa_current_counter;
769 771
770 /* used to reconfigure hardware SM PS */ 772 /* used to reconfigure hardware SM PS */
771 struct work_struct recalc_smps; 773 struct work_struct recalc_smps;
@@ -1459,6 +1461,7 @@ __ieee80211_request_sched_scan_start(struct ieee80211_sub_if_data *sdata,
1459int ieee80211_request_sched_scan_start(struct ieee80211_sub_if_data *sdata, 1461int ieee80211_request_sched_scan_start(struct ieee80211_sub_if_data *sdata,
1460 struct cfg80211_sched_scan_request *req); 1462 struct cfg80211_sched_scan_request *req);
1461int ieee80211_request_sched_scan_stop(struct ieee80211_sub_if_data *sdata); 1463int ieee80211_request_sched_scan_stop(struct ieee80211_sub_if_data *sdata);
1464void ieee80211_sched_scan_end(struct ieee80211_local *local);
1462void ieee80211_sched_scan_stopped_work(struct work_struct *work); 1465void ieee80211_sched_scan_stopped_work(struct work_struct *work);
1463 1466
1464/* off-channel helpers */ 1467/* off-channel helpers */
@@ -1473,6 +1476,7 @@ void ieee80211_sw_roc_work(struct work_struct *work);
1473void ieee80211_handle_roc_started(struct ieee80211_roc_work *roc); 1476void ieee80211_handle_roc_started(struct ieee80211_roc_work *roc);
1474 1477
1475/* channel switch handling */ 1478/* channel switch handling */
1479bool ieee80211_csa_needs_block_tx(struct ieee80211_local *local);
1476void ieee80211_csa_finalize_work(struct work_struct *work); 1480void ieee80211_csa_finalize_work(struct work_struct *work);
1477int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev, 1481int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev,
1478 struct cfg80211_csa_settings *params); 1482 struct cfg80211_csa_settings *params);
@@ -1834,6 +1838,15 @@ int ieee80211_check_combinations(struct ieee80211_sub_if_data *sdata,
1834 u8 radar_detect); 1838 u8 radar_detect);
1835int ieee80211_max_num_channels(struct ieee80211_local *local); 1839int ieee80211_max_num_channels(struct ieee80211_local *local);
1836 1840
1841/* TDLS */
1842int ieee80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev,
1843 const u8 *peer, u8 action_code, u8 dialog_token,
1844 u16 status_code, u32 peer_capability,
1845 const u8 *extra_ies, size_t extra_ies_len);
1846int ieee80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev,
1847 const u8 *peer, enum nl80211_tdls_operation oper);
1848
1849
1837#ifdef CONFIG_MAC80211_NOINLINE 1850#ifdef CONFIG_MAC80211_NOINLINE
1838#define debug_noinline noinline 1851#define debug_noinline noinline
1839#else 1852#else
diff --git a/net/mac80211/iface.c b/net/mac80211/iface.c
index 7fff3dcaac43..79fc98815da8 100644
--- a/net/mac80211/iface.c
+++ b/net/mac80211/iface.c
@@ -838,8 +838,15 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata,
838 838
839 cancel_work_sync(&sdata->recalc_smps); 839 cancel_work_sync(&sdata->recalc_smps);
840 sdata_lock(sdata); 840 sdata_lock(sdata);
841 mutex_lock(&local->mtx);
841 sdata->vif.csa_active = false; 842 sdata->vif.csa_active = false;
843 if (!ieee80211_csa_needs_block_tx(local))
844 ieee80211_wake_queues_by_reason(&local->hw,
845 IEEE80211_MAX_QUEUE_MAP,
846 IEEE80211_QUEUE_STOP_REASON_CSA);
847 mutex_unlock(&local->mtx);
842 sdata_unlock(sdata); 848 sdata_unlock(sdata);
849
843 cancel_work_sync(&sdata->csa_finalize_work); 850 cancel_work_sync(&sdata->csa_finalize_work);
844 851
845 cancel_delayed_work_sync(&sdata->dfs_cac_timer_work); 852 cancel_delayed_work_sync(&sdata->dfs_cac_timer_work);
diff --git a/net/mac80211/key.c b/net/mac80211/key.c
index 6ff65a1ebaa9..16d97f044a20 100644
--- a/net/mac80211/key.c
+++ b/net/mac80211/key.c
@@ -325,7 +325,8 @@ ieee80211_key_alloc(u32 cipher, int idx, size_t key_len,
325 struct ieee80211_key *key; 325 struct ieee80211_key *key;
326 int i, j, err; 326 int i, j, err;
327 327
328 BUG_ON(idx < 0 || idx >= NUM_DEFAULT_KEYS + NUM_DEFAULT_MGMT_KEYS); 328 if (WARN_ON(idx < 0 || idx >= NUM_DEFAULT_KEYS + NUM_DEFAULT_MGMT_KEYS))
329 return ERR_PTR(-EINVAL);
329 330
330 key = kzalloc(sizeof(struct ieee80211_key) + key_len, GFP_KERNEL); 331 key = kzalloc(sizeof(struct ieee80211_key) + key_len, GFP_KERNEL);
331 if (!key) 332 if (!key)
@@ -481,8 +482,8 @@ int ieee80211_key_link(struct ieee80211_key *key,
481 int idx, ret; 482 int idx, ret;
482 bool pairwise; 483 bool pairwise;
483 484
484 BUG_ON(!sdata); 485 if (WARN_ON(!sdata || !key))
485 BUG_ON(!key); 486 return -EINVAL;
486 487
487 pairwise = key->conf.flags & IEEE80211_KEY_FLAG_PAIRWISE; 488 pairwise = key->conf.flags & IEEE80211_KEY_FLAG_PAIRWISE;
488 idx = key->conf.keyidx; 489 idx = key->conf.keyidx;
diff --git a/net/mac80211/main.c b/net/mac80211/main.c
index 27b9364cdf17..d17c26d6e369 100644
--- a/net/mac80211/main.c
+++ b/net/mac80211/main.c
@@ -956,6 +956,8 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
956 if (local->hw.wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS) 956 if (local->hw.wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS)
957 local->hw.wiphy->flags |= WIPHY_FLAG_TDLS_EXTERNAL_SETUP; 957 local->hw.wiphy->flags |= WIPHY_FLAG_TDLS_EXTERNAL_SETUP;
958 958
959 local->hw.wiphy->max_num_csa_counters = IEEE80211_MAX_CSA_COUNTERS_NUM;
960
959 result = wiphy_register(local->hw.wiphy); 961 result = wiphy_register(local->hw.wiphy);
960 if (result < 0) 962 if (result < 0)
961 goto fail_wiphy_register; 963 goto fail_wiphy_register;
diff --git a/net/mac80211/mesh.c b/net/mac80211/mesh.c
index b06ddc9519ce..6495a3f0428d 100644
--- a/net/mac80211/mesh.c
+++ b/net/mac80211/mesh.c
@@ -679,7 +679,7 @@ ieee80211_mesh_build_beacon(struct ieee80211_if_mesh *ifmsh)
679 *pos++ = 0x0; 679 *pos++ = 0x0;
680 *pos++ = ieee80211_frequency_to_channel( 680 *pos++ = ieee80211_frequency_to_channel(
681 csa->settings.chandef.chan->center_freq); 681 csa->settings.chandef.chan->center_freq);
682 sdata->csa_counter_offset_beacon = hdr_len + 6; 682 sdata->csa_counter_offset_beacon[0] = hdr_len + 6;
683 *pos++ = csa->settings.count; 683 *pos++ = csa->settings.count;
684 *pos++ = WLAN_EID_CHAN_SWITCH_PARAM; 684 *pos++ = WLAN_EID_CHAN_SWITCH_PARAM;
685 *pos++ = 6; 685 *pos++ = 6;
diff --git a/net/mac80211/mesh_pathtbl.c b/net/mac80211/mesh_pathtbl.c
index 7d050ed6fe5a..cf032a8db9d7 100644
--- a/net/mac80211/mesh_pathtbl.c
+++ b/net/mac80211/mesh_pathtbl.c
@@ -287,8 +287,10 @@ static void mesh_path_move_to_queue(struct mesh_path *gate_mpath,
287 struct sk_buff_head failq; 287 struct sk_buff_head failq;
288 unsigned long flags; 288 unsigned long flags;
289 289
290 BUG_ON(gate_mpath == from_mpath); 290 if (WARN_ON(gate_mpath == from_mpath))
291 BUG_ON(!gate_mpath->next_hop); 291 return;
292 if (WARN_ON(!gate_mpath->next_hop))
293 return;
292 294
293 __skb_queue_head_init(&failq); 295 __skb_queue_head_init(&failq);
294 296
diff --git a/net/mac80211/mesh_sync.c b/net/mac80211/mesh_sync.c
index 2bc5dc25d5ad..09625d6205c3 100644
--- a/net/mac80211/mesh_sync.c
+++ b/net/mac80211/mesh_sync.c
@@ -171,7 +171,7 @@ static void mesh_sync_offset_adjust_tbtt(struct ieee80211_sub_if_data *sdata,
171 u8 cap; 171 u8 cap;
172 172
173 WARN_ON(ifmsh->mesh_sp_id != IEEE80211_SYNC_METHOD_NEIGHBOR_OFFSET); 173 WARN_ON(ifmsh->mesh_sp_id != IEEE80211_SYNC_METHOD_NEIGHBOR_OFFSET);
174 BUG_ON(!rcu_read_lock_held()); 174 WARN_ON(!rcu_read_lock_held());
175 cap = beacon->meshconf->meshconf_cap; 175 cap = beacon->meshconf->meshconf_cap;
176 176
177 spin_lock_bh(&ifmsh->sync_offset_lock); 177 spin_lock_bh(&ifmsh->sync_offset_lock);
diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c
index bfb5e20796b6..3345401be1b3 100644
--- a/net/mac80211/mlme.c
+++ b/net/mac80211/mlme.c
@@ -975,16 +975,23 @@ static void ieee80211_chswitch_work(struct work_struct *work)
975 /* XXX: shouldn't really modify cfg80211-owned data! */ 975 /* XXX: shouldn't really modify cfg80211-owned data! */
976 ifmgd->associated->channel = sdata->csa_chandef.chan; 976 ifmgd->associated->channel = sdata->csa_chandef.chan;
977 977
978 ieee80211_bss_info_change_notify(sdata, changed);
979
980 mutex_lock(&local->mtx);
981 sdata->vif.csa_active = false;
978 /* XXX: wait for a beacon first? */ 982 /* XXX: wait for a beacon first? */
979 ieee80211_wake_queues_by_reason(&local->hw, 983 if (!ieee80211_csa_needs_block_tx(local))
984 ieee80211_wake_queues_by_reason(&local->hw,
980 IEEE80211_MAX_QUEUE_MAP, 985 IEEE80211_MAX_QUEUE_MAP,
981 IEEE80211_QUEUE_STOP_REASON_CSA); 986 IEEE80211_QUEUE_STOP_REASON_CSA);
987 mutex_unlock(&local->mtx);
982 988
983 ieee80211_bss_info_change_notify(sdata, changed);
984
985 out:
986 sdata->vif.csa_active = false;
987 ifmgd->flags &= ~IEEE80211_STA_CSA_RECEIVED; 989 ifmgd->flags &= ~IEEE80211_STA_CSA_RECEIVED;
990
991 ieee80211_sta_reset_beacon_monitor(sdata);
992 ieee80211_sta_reset_conn_monitor(sdata);
993
994out:
988 sdata_unlock(sdata); 995 sdata_unlock(sdata);
989} 996}
990 997
@@ -1100,12 +1107,16 @@ ieee80211_sta_process_chanswitch(struct ieee80211_sub_if_data *sdata,
1100 mutex_unlock(&local->chanctx_mtx); 1107 mutex_unlock(&local->chanctx_mtx);
1101 1108
1102 sdata->csa_chandef = csa_ie.chandef; 1109 sdata->csa_chandef = csa_ie.chandef;
1110
1111 mutex_lock(&local->mtx);
1103 sdata->vif.csa_active = true; 1112 sdata->vif.csa_active = true;
1113 sdata->csa_block_tx = csa_ie.mode;
1104 1114
1105 if (csa_ie.mode) 1115 if (sdata->csa_block_tx)
1106 ieee80211_stop_queues_by_reason(&local->hw, 1116 ieee80211_stop_queues_by_reason(&local->hw,
1107 IEEE80211_MAX_QUEUE_MAP, 1117 IEEE80211_MAX_QUEUE_MAP,
1108 IEEE80211_QUEUE_STOP_REASON_CSA); 1118 IEEE80211_QUEUE_STOP_REASON_CSA);
1119 mutex_unlock(&local->mtx);
1109 1120
1110 if (local->ops->channel_switch) { 1121 if (local->ops->channel_switch) {
1111 /* use driver's channel switch callback */ 1122 /* use driver's channel switch callback */
@@ -1817,6 +1828,12 @@ static void ieee80211_set_disassoc(struct ieee80211_sub_if_data *sdata,
1817 ifmgd->flags = 0; 1828 ifmgd->flags = 0;
1818 mutex_lock(&local->mtx); 1829 mutex_lock(&local->mtx);
1819 ieee80211_vif_release_channel(sdata); 1830 ieee80211_vif_release_channel(sdata);
1831
1832 sdata->vif.csa_active = false;
1833 if (!ieee80211_csa_needs_block_tx(local))
1834 ieee80211_wake_queues_by_reason(&local->hw,
1835 IEEE80211_MAX_QUEUE_MAP,
1836 IEEE80211_QUEUE_STOP_REASON_CSA);
1820 mutex_unlock(&local->mtx); 1837 mutex_unlock(&local->mtx);
1821 1838
1822 sdata->encrypt_headroom = IEEE80211_ENCRYPT_HEADROOM; 1839 sdata->encrypt_headroom = IEEE80211_ENCRYPT_HEADROOM;
@@ -2045,6 +2062,7 @@ EXPORT_SYMBOL(ieee80211_ap_probereq_get);
2045 2062
2046static void __ieee80211_disconnect(struct ieee80211_sub_if_data *sdata) 2063static void __ieee80211_disconnect(struct ieee80211_sub_if_data *sdata)
2047{ 2064{
2065 struct ieee80211_local *local = sdata->local;
2048 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 2066 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
2049 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; 2067 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN];
2050 2068
@@ -2058,10 +2076,14 @@ static void __ieee80211_disconnect(struct ieee80211_sub_if_data *sdata)
2058 WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY, 2076 WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY,
2059 true, frame_buf); 2077 true, frame_buf);
2060 ifmgd->flags &= ~IEEE80211_STA_CSA_RECEIVED; 2078 ifmgd->flags &= ~IEEE80211_STA_CSA_RECEIVED;
2079
2080 mutex_lock(&local->mtx);
2061 sdata->vif.csa_active = false; 2081 sdata->vif.csa_active = false;
2062 ieee80211_wake_queues_by_reason(&sdata->local->hw, 2082 if (!ieee80211_csa_needs_block_tx(local))
2083 ieee80211_wake_queues_by_reason(&local->hw,
2063 IEEE80211_MAX_QUEUE_MAP, 2084 IEEE80211_MAX_QUEUE_MAP,
2064 IEEE80211_QUEUE_STOP_REASON_CSA); 2085 IEEE80211_QUEUE_STOP_REASON_CSA);
2086 mutex_unlock(&local->mtx);
2065 2087
2066 cfg80211_tx_mlme_mgmt(sdata->dev, frame_buf, 2088 cfg80211_tx_mlme_mgmt(sdata->dev, frame_buf,
2067 IEEE80211_DEAUTH_FRAME_LEN); 2089 IEEE80211_DEAUTH_FRAME_LEN);
@@ -3546,6 +3568,9 @@ static void ieee80211_sta_bcn_mon_timer(unsigned long data)
3546 if (local->quiescing) 3568 if (local->quiescing)
3547 return; 3569 return;
3548 3570
3571 if (sdata->vif.csa_active)
3572 return;
3573
3549 sdata->u.mgd.connection_loss = false; 3574 sdata->u.mgd.connection_loss = false;
3550 ieee80211_queue_work(&sdata->local->hw, 3575 ieee80211_queue_work(&sdata->local->hw,
3551 &sdata->u.mgd.beacon_connection_loss_work); 3576 &sdata->u.mgd.beacon_connection_loss_work);
@@ -3561,6 +3586,9 @@ static void ieee80211_sta_conn_mon_timer(unsigned long data)
3561 if (local->quiescing) 3586 if (local->quiescing)
3562 return; 3587 return;
3563 3588
3589 if (sdata->vif.csa_active)
3590 return;
3591
3564 ieee80211_queue_work(&local->hw, &ifmgd->monitor_work); 3592 ieee80211_queue_work(&local->hw, &ifmgd->monitor_work);
3565} 3593}
3566 3594
diff --git a/net/mac80211/rc80211_minstrel.c b/net/mac80211/rc80211_minstrel.c
index 26fd94fa0aed..1c1469c36dca 100644
--- a/net/mac80211/rc80211_minstrel.c
+++ b/net/mac80211/rc80211_minstrel.c
@@ -657,6 +657,17 @@ minstrel_free(void *priv)
657 kfree(priv); 657 kfree(priv);
658} 658}
659 659
660static u32 minstrel_get_expected_throughput(void *priv_sta)
661{
662 struct minstrel_sta_info *mi = priv_sta;
663 int idx = mi->max_tp_rate[0];
664
665 /* convert pkt per sec in kbps (1200 is the average pkt size used for
666 * computing cur_tp
667 */
668 return MINSTREL_TRUNC(mi->r[idx].cur_tp) * 1200 * 8 / 1024;
669}
670
660const struct rate_control_ops mac80211_minstrel = { 671const struct rate_control_ops mac80211_minstrel = {
661 .name = "minstrel", 672 .name = "minstrel",
662 .tx_status = minstrel_tx_status, 673 .tx_status = minstrel_tx_status,
@@ -670,6 +681,7 @@ const struct rate_control_ops mac80211_minstrel = {
670 .add_sta_debugfs = minstrel_add_sta_debugfs, 681 .add_sta_debugfs = minstrel_add_sta_debugfs,
671 .remove_sta_debugfs = minstrel_remove_sta_debugfs, 682 .remove_sta_debugfs = minstrel_remove_sta_debugfs,
672#endif 683#endif
684 .get_expected_throughput = minstrel_get_expected_throughput,
673}; 685};
674 686
675int __init 687int __init
diff --git a/net/mac80211/rc80211_minstrel_ht.c b/net/mac80211/rc80211_minstrel_ht.c
index bccaf854a309..85c1e74b7714 100644
--- a/net/mac80211/rc80211_minstrel_ht.c
+++ b/net/mac80211/rc80211_minstrel_ht.c
@@ -22,7 +22,7 @@
22#define MCS_NBITS (AVG_PKT_SIZE << 3) 22#define MCS_NBITS (AVG_PKT_SIZE << 3)
23 23
24/* Number of symbols for a packet with (bps) bits per symbol */ 24/* Number of symbols for a packet with (bps) bits per symbol */
25#define MCS_NSYMS(bps) ((MCS_NBITS + (bps) - 1) / (bps)) 25#define MCS_NSYMS(bps) DIV_ROUND_UP(MCS_NBITS, (bps))
26 26
27/* Transmission time (nanoseconds) for a packet containing (syms) symbols */ 27/* Transmission time (nanoseconds) for a packet containing (syms) symbols */
28#define MCS_SYMBOL_TIME(sgi, syms) \ 28#define MCS_SYMBOL_TIME(sgi, syms) \
@@ -226,8 +226,9 @@ minstrel_ht_calc_tp(struct minstrel_ht_sta *mi, int group, int rate)
226 nsecs = 1000 * mi->overhead / MINSTREL_TRUNC(mi->avg_ampdu_len); 226 nsecs = 1000 * mi->overhead / MINSTREL_TRUNC(mi->avg_ampdu_len);
227 227
228 nsecs += minstrel_mcs_groups[group].duration[rate]; 228 nsecs += minstrel_mcs_groups[group].duration[rate];
229 tp = 1000000 * ((prob * 1000) / nsecs);
230 229
230 /* prob is scaled - see MINSTREL_FRAC above */
231 tp = 1000000 * ((prob * 1000) / nsecs);
231 mr->cur_tp = MINSTREL_TRUNC(tp); 232 mr->cur_tp = MINSTREL_TRUNC(tp);
232} 233}
233 234
@@ -1031,6 +1032,22 @@ minstrel_ht_free(void *priv)
1031 mac80211_minstrel.free(priv); 1032 mac80211_minstrel.free(priv);
1032} 1033}
1033 1034
1035static u32 minstrel_ht_get_expected_throughput(void *priv_sta)
1036{
1037 struct minstrel_ht_sta_priv *msp = priv_sta;
1038 struct minstrel_ht_sta *mi = &msp->ht;
1039 int i, j;
1040
1041 if (!msp->is_ht)
1042 return mac80211_minstrel.get_expected_throughput(priv_sta);
1043
1044 i = mi->max_tp_rate / MCS_GROUP_RATES;
1045 j = mi->max_tp_rate % MCS_GROUP_RATES;
1046
1047 /* convert cur_tp from pkt per second in kbps */
1048 return mi->groups[i].rates[j].cur_tp * AVG_PKT_SIZE * 8 / 1024;
1049}
1050
1034static const struct rate_control_ops mac80211_minstrel_ht = { 1051static const struct rate_control_ops mac80211_minstrel_ht = {
1035 .name = "minstrel_ht", 1052 .name = "minstrel_ht",
1036 .tx_status = minstrel_ht_tx_status, 1053 .tx_status = minstrel_ht_tx_status,
@@ -1045,6 +1062,7 @@ static const struct rate_control_ops mac80211_minstrel_ht = {
1045 .add_sta_debugfs = minstrel_ht_add_sta_debugfs, 1062 .add_sta_debugfs = minstrel_ht_add_sta_debugfs,
1046 .remove_sta_debugfs = minstrel_ht_remove_sta_debugfs, 1063 .remove_sta_debugfs = minstrel_ht_remove_sta_debugfs,
1047#endif 1064#endif
1065 .get_expected_throughput = minstrel_ht_get_expected_throughput,
1048}; 1066};
1049 1067
1050 1068
diff --git a/net/mac80211/scan.c b/net/mac80211/scan.c
index 28185c8dc19a..f40661eb75b5 100644
--- a/net/mac80211/scan.c
+++ b/net/mac80211/scan.c
@@ -1076,12 +1076,8 @@ void ieee80211_sched_scan_results(struct ieee80211_hw *hw)
1076} 1076}
1077EXPORT_SYMBOL(ieee80211_sched_scan_results); 1077EXPORT_SYMBOL(ieee80211_sched_scan_results);
1078 1078
1079void ieee80211_sched_scan_stopped_work(struct work_struct *work) 1079void ieee80211_sched_scan_end(struct ieee80211_local *local)
1080{ 1080{
1081 struct ieee80211_local *local =
1082 container_of(work, struct ieee80211_local,
1083 sched_scan_stopped_work);
1084
1085 mutex_lock(&local->mtx); 1081 mutex_lock(&local->mtx);
1086 1082
1087 if (!rcu_access_pointer(local->sched_scan_sdata)) { 1083 if (!rcu_access_pointer(local->sched_scan_sdata)) {
@@ -1099,6 +1095,15 @@ void ieee80211_sched_scan_stopped_work(struct work_struct *work)
1099 cfg80211_sched_scan_stopped(local->hw.wiphy); 1095 cfg80211_sched_scan_stopped(local->hw.wiphy);
1100} 1096}
1101 1097
1098void ieee80211_sched_scan_stopped_work(struct work_struct *work)
1099{
1100 struct ieee80211_local *local =
1101 container_of(work, struct ieee80211_local,
1102 sched_scan_stopped_work);
1103
1104 ieee80211_sched_scan_end(local);
1105}
1106
1102void ieee80211_sched_scan_stopped(struct ieee80211_hw *hw) 1107void ieee80211_sched_scan_stopped(struct ieee80211_hw *hw)
1103{ 1108{
1104 struct ieee80211_local *local = hw_to_local(hw); 1109 struct ieee80211_local *local = hw_to_local(hw);
diff --git a/net/mac80211/tdls.c b/net/mac80211/tdls.c
new file mode 100644
index 000000000000..652813b2d3df
--- /dev/null
+++ b/net/mac80211/tdls.c
@@ -0,0 +1,325 @@
1/*
2 * mac80211 TDLS handling code
3 *
4 * Copyright 2006-2010 Johannes Berg <johannes@sipsolutions.net>
5 * Copyright 2014, Intel Corporation
6 *
7 * This file is GPLv2 as found in COPYING.
8 */
9
10#include <linux/ieee80211.h>
11#include "ieee80211_i.h"
12
13static void ieee80211_tdls_add_ext_capab(struct sk_buff *skb)
14{
15 u8 *pos = (void *)skb_put(skb, 7);
16
17 *pos++ = WLAN_EID_EXT_CAPABILITY;
18 *pos++ = 5; /* len */
19 *pos++ = 0x0;
20 *pos++ = 0x0;
21 *pos++ = 0x0;
22 *pos++ = 0x0;
23 *pos++ = WLAN_EXT_CAPA5_TDLS_ENABLED;
24}
25
26static u16 ieee80211_get_tdls_sta_capab(struct ieee80211_sub_if_data *sdata)
27{
28 struct ieee80211_local *local = sdata->local;
29 u16 capab;
30
31 capab = 0;
32 if (ieee80211_get_sdata_band(sdata) != IEEE80211_BAND_2GHZ)
33 return capab;
34
35 if (!(local->hw.flags & IEEE80211_HW_2GHZ_SHORT_SLOT_INCAPABLE))
36 capab |= WLAN_CAPABILITY_SHORT_SLOT_TIME;
37 if (!(local->hw.flags & IEEE80211_HW_2GHZ_SHORT_PREAMBLE_INCAPABLE))
38 capab |= WLAN_CAPABILITY_SHORT_PREAMBLE;
39
40 return capab;
41}
42
43static void ieee80211_tdls_add_link_ie(struct sk_buff *skb, const u8 *src_addr,
44 const u8 *peer, const u8 *bssid)
45{
46 struct ieee80211_tdls_lnkie *lnkid;
47
48 lnkid = (void *)skb_put(skb, sizeof(struct ieee80211_tdls_lnkie));
49
50 lnkid->ie_type = WLAN_EID_LINK_ID;
51 lnkid->ie_len = sizeof(struct ieee80211_tdls_lnkie) - 2;
52
53 memcpy(lnkid->bssid, bssid, ETH_ALEN);
54 memcpy(lnkid->init_sta, src_addr, ETH_ALEN);
55 memcpy(lnkid->resp_sta, peer, ETH_ALEN);
56}
57
58static int
59ieee80211_prep_tdls_encap_data(struct wiphy *wiphy, struct net_device *dev,
60 const u8 *peer, u8 action_code, u8 dialog_token,
61 u16 status_code, struct sk_buff *skb)
62{
63 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
64 enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
65 struct ieee80211_tdls_data *tf;
66
67 tf = (void *)skb_put(skb, offsetof(struct ieee80211_tdls_data, u));
68
69 memcpy(tf->da, peer, ETH_ALEN);
70 memcpy(tf->sa, sdata->vif.addr, ETH_ALEN);
71 tf->ether_type = cpu_to_be16(ETH_P_TDLS);
72 tf->payload_type = WLAN_TDLS_SNAP_RFTYPE;
73
74 switch (action_code) {
75 case WLAN_TDLS_SETUP_REQUEST:
76 tf->category = WLAN_CATEGORY_TDLS;
77 tf->action_code = WLAN_TDLS_SETUP_REQUEST;
78
79 skb_put(skb, sizeof(tf->u.setup_req));
80 tf->u.setup_req.dialog_token = dialog_token;
81 tf->u.setup_req.capability =
82 cpu_to_le16(ieee80211_get_tdls_sta_capab(sdata));
83
84 ieee80211_add_srates_ie(sdata, skb, false, band);
85 ieee80211_add_ext_srates_ie(sdata, skb, false, band);
86 ieee80211_tdls_add_ext_capab(skb);
87 break;
88 case WLAN_TDLS_SETUP_RESPONSE:
89 tf->category = WLAN_CATEGORY_TDLS;
90 tf->action_code = WLAN_TDLS_SETUP_RESPONSE;
91
92 skb_put(skb, sizeof(tf->u.setup_resp));
93 tf->u.setup_resp.status_code = cpu_to_le16(status_code);
94 tf->u.setup_resp.dialog_token = dialog_token;
95 tf->u.setup_resp.capability =
96 cpu_to_le16(ieee80211_get_tdls_sta_capab(sdata));
97
98 ieee80211_add_srates_ie(sdata, skb, false, band);
99 ieee80211_add_ext_srates_ie(sdata, skb, false, band);
100 ieee80211_tdls_add_ext_capab(skb);
101 break;
102 case WLAN_TDLS_SETUP_CONFIRM:
103 tf->category = WLAN_CATEGORY_TDLS;
104 tf->action_code = WLAN_TDLS_SETUP_CONFIRM;
105
106 skb_put(skb, sizeof(tf->u.setup_cfm));
107 tf->u.setup_cfm.status_code = cpu_to_le16(status_code);
108 tf->u.setup_cfm.dialog_token = dialog_token;
109 break;
110 case WLAN_TDLS_TEARDOWN:
111 tf->category = WLAN_CATEGORY_TDLS;
112 tf->action_code = WLAN_TDLS_TEARDOWN;
113
114 skb_put(skb, sizeof(tf->u.teardown));
115 tf->u.teardown.reason_code = cpu_to_le16(status_code);
116 break;
117 case WLAN_TDLS_DISCOVERY_REQUEST:
118 tf->category = WLAN_CATEGORY_TDLS;
119 tf->action_code = WLAN_TDLS_DISCOVERY_REQUEST;
120
121 skb_put(skb, sizeof(tf->u.discover_req));
122 tf->u.discover_req.dialog_token = dialog_token;
123 break;
124 default:
125 return -EINVAL;
126 }
127
128 return 0;
129}
130
131static int
132ieee80211_prep_tdls_direct(struct wiphy *wiphy, struct net_device *dev,
133 const u8 *peer, u8 action_code, u8 dialog_token,
134 u16 status_code, struct sk_buff *skb)
135{
136 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
137 enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
138 struct ieee80211_mgmt *mgmt;
139
140 mgmt = (void *)skb_put(skb, 24);
141 memset(mgmt, 0, 24);
142 memcpy(mgmt->da, peer, ETH_ALEN);
143 memcpy(mgmt->sa, sdata->vif.addr, ETH_ALEN);
144 memcpy(mgmt->bssid, sdata->u.mgd.bssid, ETH_ALEN);
145
146 mgmt->frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
147 IEEE80211_STYPE_ACTION);
148
149 switch (action_code) {
150 case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
151 skb_put(skb, 1 + sizeof(mgmt->u.action.u.tdls_discover_resp));
152 mgmt->u.action.category = WLAN_CATEGORY_PUBLIC;
153 mgmt->u.action.u.tdls_discover_resp.action_code =
154 WLAN_PUB_ACTION_TDLS_DISCOVER_RES;
155 mgmt->u.action.u.tdls_discover_resp.dialog_token =
156 dialog_token;
157 mgmt->u.action.u.tdls_discover_resp.capability =
158 cpu_to_le16(ieee80211_get_tdls_sta_capab(sdata));
159
160 ieee80211_add_srates_ie(sdata, skb, false, band);
161 ieee80211_add_ext_srates_ie(sdata, skb, false, band);
162 ieee80211_tdls_add_ext_capab(skb);
163 break;
164 default:
165 return -EINVAL;
166 }
167
168 return 0;
169}
170
171int ieee80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev,
172 const u8 *peer, u8 action_code, u8 dialog_token,
173 u16 status_code, u32 peer_capability,
174 const u8 *extra_ies, size_t extra_ies_len)
175{
176 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
177 struct ieee80211_local *local = sdata->local;
178 struct sk_buff *skb = NULL;
179 bool send_direct;
180 int ret;
181
182 if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS))
183 return -ENOTSUPP;
184
185 /* make sure we are in managed mode, and associated */
186 if (sdata->vif.type != NL80211_IFTYPE_STATION ||
187 !sdata->u.mgd.associated)
188 return -EINVAL;
189
190 tdls_dbg(sdata, "TDLS mgmt action %d peer %pM\n",
191 action_code, peer);
192
193 skb = dev_alloc_skb(local->hw.extra_tx_headroom +
194 max(sizeof(struct ieee80211_mgmt),
195 sizeof(struct ieee80211_tdls_data)) +
196 50 + /* supported rates */
197 7 + /* ext capab */
198 extra_ies_len +
199 sizeof(struct ieee80211_tdls_lnkie));
200 if (!skb)
201 return -ENOMEM;
202
203 skb_reserve(skb, local->hw.extra_tx_headroom);
204
205 switch (action_code) {
206 case WLAN_TDLS_SETUP_REQUEST:
207 case WLAN_TDLS_SETUP_RESPONSE:
208 case WLAN_TDLS_SETUP_CONFIRM:
209 case WLAN_TDLS_TEARDOWN:
210 case WLAN_TDLS_DISCOVERY_REQUEST:
211 ret = ieee80211_prep_tdls_encap_data(wiphy, dev, peer,
212 action_code, dialog_token,
213 status_code, skb);
214 send_direct = false;
215 break;
216 case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
217 ret = ieee80211_prep_tdls_direct(wiphy, dev, peer, action_code,
218 dialog_token, status_code,
219 skb);
220 send_direct = true;
221 break;
222 default:
223 ret = -ENOTSUPP;
224 break;
225 }
226
227 if (ret < 0)
228 goto fail;
229
230 if (extra_ies_len)
231 memcpy(skb_put(skb, extra_ies_len), extra_ies, extra_ies_len);
232
233 /* the TDLS link IE is always added last */
234 switch (action_code) {
235 case WLAN_TDLS_SETUP_REQUEST:
236 case WLAN_TDLS_SETUP_CONFIRM:
237 case WLAN_TDLS_TEARDOWN:
238 case WLAN_TDLS_DISCOVERY_REQUEST:
239 /* we are the initiator */
240 ieee80211_tdls_add_link_ie(skb, sdata->vif.addr, peer,
241 sdata->u.mgd.bssid);
242 break;
243 case WLAN_TDLS_SETUP_RESPONSE:
244 case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
245 /* we are the responder */
246 ieee80211_tdls_add_link_ie(skb, peer, sdata->vif.addr,
247 sdata->u.mgd.bssid);
248 break;
249 default:
250 ret = -ENOTSUPP;
251 goto fail;
252 }
253
254 if (send_direct) {
255 ieee80211_tx_skb(sdata, skb);
256 return 0;
257 }
258
259 /*
260 * According to 802.11z: Setup req/resp are sent in AC_BK, otherwise
261 * we should default to AC_VI.
262 */
263 switch (action_code) {
264 case WLAN_TDLS_SETUP_REQUEST:
265 case WLAN_TDLS_SETUP_RESPONSE:
266 skb_set_queue_mapping(skb, IEEE80211_AC_BK);
267 skb->priority = 2;
268 break;
269 default:
270 skb_set_queue_mapping(skb, IEEE80211_AC_VI);
271 skb->priority = 5;
272 break;
273 }
274
275 /* disable bottom halves when entering the Tx path */
276 local_bh_disable();
277 ret = ieee80211_subif_start_xmit(skb, dev);
278 local_bh_enable();
279
280 return ret;
281
282fail:
283 dev_kfree_skb(skb);
284 return ret;
285}
286
287int ieee80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev,
288 const u8 *peer, enum nl80211_tdls_operation oper)
289{
290 struct sta_info *sta;
291 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
292
293 if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS))
294 return -ENOTSUPP;
295
296 if (sdata->vif.type != NL80211_IFTYPE_STATION)
297 return -EINVAL;
298
299 tdls_dbg(sdata, "TDLS oper %d peer %pM\n", oper, peer);
300
301 switch (oper) {
302 case NL80211_TDLS_ENABLE_LINK:
303 rcu_read_lock();
304 sta = sta_info_get(sdata, peer);
305 if (!sta) {
306 rcu_read_unlock();
307 return -ENOLINK;
308 }
309
310 set_sta_flag(sta, WLAN_STA_TDLS_PEER_AUTH);
311 rcu_read_unlock();
312 break;
313 case NL80211_TDLS_DISABLE_LINK:
314 return sta_info_destroy_addr(sdata, peer);
315 case NL80211_TDLS_TEARDOWN:
316 case NL80211_TDLS_SETUP:
317 case NL80211_TDLS_DISCOVERY_REQ:
318 /* We don't support in-driver setup/teardown/discovery */
319 return -ENOTSUPP;
320 default:
321 return -ENOTSUPP;
322 }
323
324 return 0;
325}
diff --git a/net/mac80211/trace.h b/net/mac80211/trace.h
index cec5b60487a4..762e4cd16386 100644
--- a/net/mac80211/trace.h
+++ b/net/mac80211/trace.h
@@ -184,6 +184,20 @@ TRACE_EVENT(drv_return_bool,
184 "true" : "false") 184 "true" : "false")
185); 185);
186 186
187TRACE_EVENT(drv_return_u32,
188 TP_PROTO(struct ieee80211_local *local, u32 ret),
189 TP_ARGS(local, ret),
190 TP_STRUCT__entry(
191 LOCAL_ENTRY
192 __field(u32, ret)
193 ),
194 TP_fast_assign(
195 LOCAL_ASSIGN;
196 __entry->ret = ret;
197 ),
198 TP_printk(LOCAL_PR_FMT " - %u", LOCAL_PR_ARG, __entry->ret)
199);
200
187TRACE_EVENT(drv_return_u64, 201TRACE_EVENT(drv_return_u64,
188 TP_PROTO(struct ieee80211_local *local, u64 ret), 202 TP_PROTO(struct ieee80211_local *local, u64 ret),
189 TP_ARGS(local, ret), 203 TP_ARGS(local, ret),
@@ -1499,6 +1513,24 @@ DEFINE_EVENT(local_sdata_evt, drv_leave_ibss,
1499 TP_ARGS(local, sdata) 1513 TP_ARGS(local, sdata)
1500); 1514);
1501 1515
1516TRACE_EVENT(drv_get_expected_throughput,
1517 TP_PROTO(struct ieee80211_sta *sta),
1518
1519 TP_ARGS(sta),
1520
1521 TP_STRUCT__entry(
1522 STA_ENTRY
1523 ),
1524
1525 TP_fast_assign(
1526 STA_ASSIGN;
1527 ),
1528
1529 TP_printk(
1530 STA_PR_FMT, STA_PR_ARG
1531 )
1532);
1533
1502/* 1534/*
1503 * Tracing for API calls that drivers call. 1535 * Tracing for API calls that drivers call.
1504 */ 1536 */
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index 19d36d4117e0..5214686d9fd1 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -2328,7 +2328,8 @@ void ieee80211_tx_pending(unsigned long data)
2328/* functions for drivers to get certain frames */ 2328/* functions for drivers to get certain frames */
2329 2329
2330static void __ieee80211_beacon_add_tim(struct ieee80211_sub_if_data *sdata, 2330static void __ieee80211_beacon_add_tim(struct ieee80211_sub_if_data *sdata,
2331 struct ps_data *ps, struct sk_buff *skb) 2331 struct ps_data *ps, struct sk_buff *skb,
2332 bool is_template)
2332{ 2333{
2333 u8 *pos, *tim; 2334 u8 *pos, *tim;
2334 int aid0 = 0; 2335 int aid0 = 0;
@@ -2341,11 +2342,12 @@ static void __ieee80211_beacon_add_tim(struct ieee80211_sub_if_data *sdata,
2341 * checking byte-for-byte */ 2342 * checking byte-for-byte */
2342 have_bits = !bitmap_empty((unsigned long *)ps->tim, 2343 have_bits = !bitmap_empty((unsigned long *)ps->tim,
2343 IEEE80211_MAX_AID+1); 2344 IEEE80211_MAX_AID+1);
2344 2345 if (!is_template) {
2345 if (ps->dtim_count == 0) 2346 if (ps->dtim_count == 0)
2346 ps->dtim_count = sdata->vif.bss_conf.dtim_period - 1; 2347 ps->dtim_count = sdata->vif.bss_conf.dtim_period - 1;
2347 else 2348 else
2348 ps->dtim_count--; 2349 ps->dtim_count--;
2350 }
2349 2351
2350 tim = pos = (u8 *) skb_put(skb, 6); 2352 tim = pos = (u8 *) skb_put(skb, 6);
2351 *pos++ = WLAN_EID_TIM; 2353 *pos++ = WLAN_EID_TIM;
@@ -2391,7 +2393,8 @@ static void __ieee80211_beacon_add_tim(struct ieee80211_sub_if_data *sdata,
2391} 2393}
2392 2394
2393static int ieee80211_beacon_add_tim(struct ieee80211_sub_if_data *sdata, 2395static int ieee80211_beacon_add_tim(struct ieee80211_sub_if_data *sdata,
2394 struct ps_data *ps, struct sk_buff *skb) 2396 struct ps_data *ps, struct sk_buff *skb,
2397 bool is_template)
2395{ 2398{
2396 struct ieee80211_local *local = sdata->local; 2399 struct ieee80211_local *local = sdata->local;
2397 2400
@@ -2403,24 +2406,24 @@ static int ieee80211_beacon_add_tim(struct ieee80211_sub_if_data *sdata,
2403 * of the tim bitmap in mac80211 and the driver. 2406 * of the tim bitmap in mac80211 and the driver.
2404 */ 2407 */
2405 if (local->tim_in_locked_section) { 2408 if (local->tim_in_locked_section) {
2406 __ieee80211_beacon_add_tim(sdata, ps, skb); 2409 __ieee80211_beacon_add_tim(sdata, ps, skb, is_template);
2407 } else { 2410 } else {
2408 spin_lock_bh(&local->tim_lock); 2411 spin_lock_bh(&local->tim_lock);
2409 __ieee80211_beacon_add_tim(sdata, ps, skb); 2412 __ieee80211_beacon_add_tim(sdata, ps, skb, is_template);
2410 spin_unlock_bh(&local->tim_lock); 2413 spin_unlock_bh(&local->tim_lock);
2411 } 2414 }
2412 2415
2413 return 0; 2416 return 0;
2414} 2417}
2415 2418
2416static void ieee80211_update_csa(struct ieee80211_sub_if_data *sdata, 2419static void ieee80211_set_csa(struct ieee80211_sub_if_data *sdata,
2417 struct beacon_data *beacon) 2420 struct beacon_data *beacon)
2418{ 2421{
2419 struct probe_resp *resp; 2422 struct probe_resp *resp;
2420 int counter_offset_beacon = sdata->csa_counter_offset_beacon;
2421 int counter_offset_presp = sdata->csa_counter_offset_presp;
2422 u8 *beacon_data; 2423 u8 *beacon_data;
2423 size_t beacon_data_len; 2424 size_t beacon_data_len;
2425 int i;
2426 u8 count = sdata->csa_current_counter;
2424 2427
2425 switch (sdata->vif.type) { 2428 switch (sdata->vif.type) {
2426 case NL80211_IFTYPE_AP: 2429 case NL80211_IFTYPE_AP:
@@ -2438,40 +2441,57 @@ static void ieee80211_update_csa(struct ieee80211_sub_if_data *sdata,
2438 default: 2441 default:
2439 return; 2442 return;
2440 } 2443 }
2441 if (WARN_ON(counter_offset_beacon >= beacon_data_len))
2442 return;
2443 2444
2444 /* Warn if the driver did not check for/react to csa 2445 for (i = 0; i < IEEE80211_MAX_CSA_COUNTERS_NUM; ++i) {
2445 * completeness. A beacon with CSA counter set to 0 should 2446 u16 counter_offset_beacon =
2446 * never occur, because a counter of 1 means switch just 2447 sdata->csa_counter_offset_beacon[i];
2447 * before the next beacon. 2448 u16 counter_offset_presp = sdata->csa_counter_offset_presp[i];
2448 */
2449 if (WARN_ON(beacon_data[counter_offset_beacon] == 1))
2450 return;
2451 2449
2452 beacon_data[counter_offset_beacon]--; 2450 if (counter_offset_beacon) {
2451 if (WARN_ON(counter_offset_beacon >= beacon_data_len))
2452 return;
2453 2453
2454 if (sdata->vif.type == NL80211_IFTYPE_AP && counter_offset_presp) { 2454 beacon_data[counter_offset_beacon] = count;
2455 rcu_read_lock(); 2455 }
2456 resp = rcu_dereference(sdata->u.ap.probe_resp); 2456
2457 if (sdata->vif.type == NL80211_IFTYPE_AP &&
2458 counter_offset_presp) {
2459 rcu_read_lock();
2460 resp = rcu_dereference(sdata->u.ap.probe_resp);
2457 2461
2458 /* if nl80211 accepted the offset, this should not happen. */ 2462 /* If nl80211 accepted the offset, this should
2459 if (WARN_ON(!resp)) { 2463 * not happen.
2464 */
2465 if (WARN_ON(!resp)) {
2466 rcu_read_unlock();
2467 return;
2468 }
2469 resp->data[counter_offset_presp] = count;
2460 rcu_read_unlock(); 2470 rcu_read_unlock();
2461 return;
2462 } 2471 }
2463 resp->data[counter_offset_presp]--;
2464 rcu_read_unlock();
2465 } 2472 }
2466} 2473}
2467 2474
2475u8 ieee80211_csa_update_counter(struct ieee80211_vif *vif)
2476{
2477 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
2478
2479 sdata->csa_current_counter--;
2480
2481 /* the counter should never reach 0 */
2482 WARN_ON(!sdata->csa_current_counter);
2483
2484 return sdata->csa_current_counter;
2485}
2486EXPORT_SYMBOL(ieee80211_csa_update_counter);
2487
2468bool ieee80211_csa_is_complete(struct ieee80211_vif *vif) 2488bool ieee80211_csa_is_complete(struct ieee80211_vif *vif)
2469{ 2489{
2470 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif); 2490 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
2471 struct beacon_data *beacon = NULL; 2491 struct beacon_data *beacon = NULL;
2472 u8 *beacon_data; 2492 u8 *beacon_data;
2473 size_t beacon_data_len; 2493 size_t beacon_data_len;
2474 int counter_beacon = sdata->csa_counter_offset_beacon; 2494 int counter_beacon = sdata->csa_counter_offset_beacon[0];
2475 int ret = false; 2495 int ret = false;
2476 2496
2477 if (!ieee80211_sdata_running(sdata)) 2497 if (!ieee80211_sdata_running(sdata))
@@ -2521,9 +2541,11 @@ bool ieee80211_csa_is_complete(struct ieee80211_vif *vif)
2521} 2541}
2522EXPORT_SYMBOL(ieee80211_csa_is_complete); 2542EXPORT_SYMBOL(ieee80211_csa_is_complete);
2523 2543
2524struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw, 2544static struct sk_buff *
2525 struct ieee80211_vif *vif, 2545__ieee80211_beacon_get(struct ieee80211_hw *hw,
2526 u16 *tim_offset, u16 *tim_length) 2546 struct ieee80211_vif *vif,
2547 struct ieee80211_mutable_offsets *offs,
2548 bool is_template)
2527{ 2549{
2528 struct ieee80211_local *local = hw_to_local(hw); 2550 struct ieee80211_local *local = hw_to_local(hw);
2529 struct sk_buff *skb = NULL; 2551 struct sk_buff *skb = NULL;
@@ -2532,6 +2554,7 @@ struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2532 enum ieee80211_band band; 2554 enum ieee80211_band band;
2533 struct ieee80211_tx_rate_control txrc; 2555 struct ieee80211_tx_rate_control txrc;
2534 struct ieee80211_chanctx_conf *chanctx_conf; 2556 struct ieee80211_chanctx_conf *chanctx_conf;
2557 int csa_off_base = 0;
2535 2558
2536 rcu_read_lock(); 2559 rcu_read_lock();
2537 2560
@@ -2541,18 +2564,20 @@ struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2541 if (!ieee80211_sdata_running(sdata) || !chanctx_conf) 2564 if (!ieee80211_sdata_running(sdata) || !chanctx_conf)
2542 goto out; 2565 goto out;
2543 2566
2544 if (tim_offset) 2567 if (offs)
2545 *tim_offset = 0; 2568 memset(offs, 0, sizeof(*offs));
2546 if (tim_length)
2547 *tim_length = 0;
2548 2569
2549 if (sdata->vif.type == NL80211_IFTYPE_AP) { 2570 if (sdata->vif.type == NL80211_IFTYPE_AP) {
2550 struct ieee80211_if_ap *ap = &sdata->u.ap; 2571 struct ieee80211_if_ap *ap = &sdata->u.ap;
2551 struct beacon_data *beacon = rcu_dereference(ap->beacon); 2572 struct beacon_data *beacon = rcu_dereference(ap->beacon);
2552 2573
2553 if (beacon) { 2574 if (beacon) {
2554 if (sdata->vif.csa_active) 2575 if (sdata->vif.csa_active) {
2555 ieee80211_update_csa(sdata, beacon); 2576 if (!is_template)
2577 ieee80211_csa_update_counter(vif);
2578
2579 ieee80211_set_csa(sdata, beacon);
2580 }
2556 2581
2557 /* 2582 /*
2558 * headroom, head length, 2583 * headroom, head length,
@@ -2569,12 +2594,16 @@ struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2569 memcpy(skb_put(skb, beacon->head_len), beacon->head, 2594 memcpy(skb_put(skb, beacon->head_len), beacon->head,
2570 beacon->head_len); 2595 beacon->head_len);
2571 2596
2572 ieee80211_beacon_add_tim(sdata, &ap->ps, skb); 2597 ieee80211_beacon_add_tim(sdata, &ap->ps, skb,
2598 is_template);
2573 2599
2574 if (tim_offset) 2600 if (offs) {
2575 *tim_offset = beacon->head_len; 2601 offs->tim_offset = beacon->head_len;
2576 if (tim_length) 2602 offs->tim_length = skb->len - beacon->head_len;
2577 *tim_length = skb->len - beacon->head_len; 2603
2604 /* for AP the csa offsets are from tail */
2605 csa_off_base = skb->len;
2606 }
2578 2607
2579 if (beacon->tail) 2608 if (beacon->tail)
2580 memcpy(skb_put(skb, beacon->tail_len), 2609 memcpy(skb_put(skb, beacon->tail_len),
@@ -2589,9 +2618,12 @@ struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2589 if (!presp) 2618 if (!presp)
2590 goto out; 2619 goto out;
2591 2620
2592 if (sdata->vif.csa_active) 2621 if (sdata->vif.csa_active) {
2593 ieee80211_update_csa(sdata, presp); 2622 if (!is_template)
2623 ieee80211_csa_update_counter(vif);
2594 2624
2625 ieee80211_set_csa(sdata, presp);
2626 }
2595 2627
2596 skb = dev_alloc_skb(local->tx_headroom + presp->head_len + 2628 skb = dev_alloc_skb(local->tx_headroom + presp->head_len +
2597 local->hw.extra_beacon_tailroom); 2629 local->hw.extra_beacon_tailroom);
@@ -2611,8 +2643,17 @@ struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2611 if (!bcn) 2643 if (!bcn)
2612 goto out; 2644 goto out;
2613 2645
2614 if (sdata->vif.csa_active) 2646 if (sdata->vif.csa_active) {
2615 ieee80211_update_csa(sdata, bcn); 2647 if (!is_template)
2648 /* TODO: For mesh csa_counter is in TU, so
2649 * decrementing it by one isn't correct, but
2650 * for now we leave it consistent with overall
2651 * mac80211's behavior.
2652 */
2653 ieee80211_csa_update_counter(vif);
2654
2655 ieee80211_set_csa(sdata, bcn);
2656 }
2616 2657
2617 if (ifmsh->sync_ops) 2658 if (ifmsh->sync_ops)
2618 ifmsh->sync_ops->adjust_tbtt(sdata, bcn); 2659 ifmsh->sync_ops->adjust_tbtt(sdata, bcn);
@@ -2626,13 +2667,33 @@ struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2626 goto out; 2667 goto out;
2627 skb_reserve(skb, local->tx_headroom); 2668 skb_reserve(skb, local->tx_headroom);
2628 memcpy(skb_put(skb, bcn->head_len), bcn->head, bcn->head_len); 2669 memcpy(skb_put(skb, bcn->head_len), bcn->head, bcn->head_len);
2629 ieee80211_beacon_add_tim(sdata, &ifmsh->ps, skb); 2670 ieee80211_beacon_add_tim(sdata, &ifmsh->ps, skb, is_template);
2671
2672 if (offs) {
2673 offs->tim_offset = bcn->head_len;
2674 offs->tim_length = skb->len - bcn->head_len;
2675 }
2676
2630 memcpy(skb_put(skb, bcn->tail_len), bcn->tail, bcn->tail_len); 2677 memcpy(skb_put(skb, bcn->tail_len), bcn->tail, bcn->tail_len);
2631 } else { 2678 } else {
2632 WARN_ON(1); 2679 WARN_ON(1);
2633 goto out; 2680 goto out;
2634 } 2681 }
2635 2682
2683 /* CSA offsets */
2684 if (offs) {
2685 int i;
2686
2687 for (i = 0; i < IEEE80211_MAX_CSA_COUNTERS_NUM; i++) {
2688 u16 csa_off = sdata->csa_counter_offset_beacon[i];
2689
2690 if (!csa_off)
2691 continue;
2692
2693 offs->csa_counter_offs[i] = csa_off_base + csa_off;
2694 }
2695 }
2696
2636 band = chanctx_conf->def.chan->band; 2697 band = chanctx_conf->def.chan->band;
2637 2698
2638 info = IEEE80211_SKB_CB(skb); 2699 info = IEEE80211_SKB_CB(skb);
@@ -2663,6 +2724,32 @@ struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2663 out: 2724 out:
2664 rcu_read_unlock(); 2725 rcu_read_unlock();
2665 return skb; 2726 return skb;
2727
2728}
2729
2730struct sk_buff *
2731ieee80211_beacon_get_template(struct ieee80211_hw *hw,
2732 struct ieee80211_vif *vif,
2733 struct ieee80211_mutable_offsets *offs)
2734{
2735 return __ieee80211_beacon_get(hw, vif, offs, true);
2736}
2737EXPORT_SYMBOL(ieee80211_beacon_get_template);
2738
2739struct sk_buff *ieee80211_beacon_get_tim(struct ieee80211_hw *hw,
2740 struct ieee80211_vif *vif,
2741 u16 *tim_offset, u16 *tim_length)
2742{
2743 struct ieee80211_mutable_offsets offs = {};
2744 struct sk_buff *bcn = __ieee80211_beacon_get(hw, vif, &offs, false);
2745
2746 if (tim_offset)
2747 *tim_offset = offs.tim_offset;
2748
2749 if (tim_length)
2750 *tim_length = offs.tim_length;
2751
2752 return bcn;
2666} 2753}
2667EXPORT_SYMBOL(ieee80211_beacon_get_tim); 2754EXPORT_SYMBOL(ieee80211_beacon_get_tim);
2668 2755
diff --git a/net/mac80211/util.c b/net/mac80211/util.c
index c08bd4aca6bb..6886601afe1c 100644
--- a/net/mac80211/util.c
+++ b/net/mac80211/util.c
@@ -1457,6 +1457,44 @@ void ieee80211_stop_device(struct ieee80211_local *local)
1457 drv_stop(local); 1457 drv_stop(local);
1458} 1458}
1459 1459
1460static void ieee80211_handle_reconfig_failure(struct ieee80211_local *local)
1461{
1462 struct ieee80211_sub_if_data *sdata;
1463 struct ieee80211_chanctx *ctx;
1464
1465 /*
1466 * We get here if during resume the device can't be restarted properly.
1467 * We might also get here if this happens during HW reset, which is a
1468 * slightly different situation and we need to drop all connections in
1469 * the latter case.
1470 *
1471 * Ask cfg80211 to turn off all interfaces, this will result in more
1472 * warnings but at least we'll then get into a clean stopped state.
1473 */
1474
1475 local->resuming = false;
1476 local->suspended = false;
1477 local->started = false;
1478
1479 /* scheduled scan clearly can't be running any more, but tell
1480 * cfg80211 and clear local state
1481 */
1482 ieee80211_sched_scan_end(local);
1483
1484 list_for_each_entry(sdata, &local->interfaces, list)
1485 sdata->flags &= ~IEEE80211_SDATA_IN_DRIVER;
1486
1487 /* Mark channel contexts as not being in the driver any more to avoid
1488 * removing them from the driver during the shutdown process...
1489 */
1490 mutex_lock(&local->chanctx_mtx);
1491 list_for_each_entry(ctx, &local->chanctx_list, list)
1492 ctx->driver_present = false;
1493 mutex_unlock(&local->chanctx_mtx);
1494
1495 cfg80211_shutdown_all_interfaces(local->hw.wiphy);
1496}
1497
1460static void ieee80211_assign_chanctx(struct ieee80211_local *local, 1498static void ieee80211_assign_chanctx(struct ieee80211_local *local,
1461 struct ieee80211_sub_if_data *sdata) 1499 struct ieee80211_sub_if_data *sdata)
1462{ 1500{
@@ -1520,9 +1558,11 @@ int ieee80211_reconfig(struct ieee80211_local *local)
1520 */ 1558 */
1521 res = drv_start(local); 1559 res = drv_start(local);
1522 if (res) { 1560 if (res) {
1523 WARN(local->suspended, "Hardware became unavailable " 1561 if (local->suspended)
1524 "upon resume. This could be a software issue " 1562 WARN(1, "Hardware became unavailable upon resume. This could be a software issue prior to suspend or a hardware issue.\n");
1525 "prior to suspend or a hardware issue.\n"); 1563 else
1564 WARN(1, "Hardware became unavailable during restart.\n");
1565 ieee80211_handle_reconfig_failure(local);
1526 return res; 1566 return res;
1527 } 1567 }
1528 1568
diff --git a/net/nfc/digital.h b/net/nfc/digital.h
index 3759add68b1b..71ad7eefddd4 100644
--- a/net/nfc/digital.h
+++ b/net/nfc/digital.h
@@ -71,6 +71,7 @@ static inline int digital_in_send_cmd(struct nfc_digital_dev *ddev,
71void digital_poll_next_tech(struct nfc_digital_dev *ddev); 71void digital_poll_next_tech(struct nfc_digital_dev *ddev);
72 72
73int digital_in_send_sens_req(struct nfc_digital_dev *ddev, u8 rf_tech); 73int digital_in_send_sens_req(struct nfc_digital_dev *ddev, u8 rf_tech);
74int digital_in_send_sensb_req(struct nfc_digital_dev *ddev, u8 rf_tech);
74int digital_in_send_sensf_req(struct nfc_digital_dev *ddev, u8 rf_tech); 75int digital_in_send_sensf_req(struct nfc_digital_dev *ddev, u8 rf_tech);
75int digital_in_send_iso15693_inv_req(struct nfc_digital_dev *ddev, u8 rf_tech); 76int digital_in_send_iso15693_inv_req(struct nfc_digital_dev *ddev, u8 rf_tech);
76 77
diff --git a/net/nfc/digital_core.c b/net/nfc/digital_core.c
index e01e15dbf1ab..b105cfb00e76 100644
--- a/net/nfc/digital_core.c
+++ b/net/nfc/digital_core.c
@@ -22,6 +22,8 @@
22#define DIGITAL_PROTO_NFCA_RF_TECH \ 22#define DIGITAL_PROTO_NFCA_RF_TECH \
23 (NFC_PROTO_JEWEL_MASK | NFC_PROTO_MIFARE_MASK | NFC_PROTO_NFC_DEP_MASK) 23 (NFC_PROTO_JEWEL_MASK | NFC_PROTO_MIFARE_MASK | NFC_PROTO_NFC_DEP_MASK)
24 24
25#define DIGITAL_PROTO_NFCB_RF_TECH NFC_PROTO_ISO14443_B_MASK
26
25#define DIGITAL_PROTO_NFCF_RF_TECH \ 27#define DIGITAL_PROTO_NFCF_RF_TECH \
26 (NFC_PROTO_FELICA_MASK | NFC_PROTO_NFC_DEP_MASK) 28 (NFC_PROTO_FELICA_MASK | NFC_PROTO_NFC_DEP_MASK)
27 29
@@ -345,6 +347,12 @@ int digital_target_found(struct nfc_digital_dev *ddev,
345 add_crc = digital_skb_add_crc_a; 347 add_crc = digital_skb_add_crc_a;
346 break; 348 break;
347 349
350 case NFC_PROTO_ISO14443_B:
351 framing = NFC_DIGITAL_FRAMING_NFCB_T4T;
352 check_crc = digital_skb_check_crc_b;
353 add_crc = digital_skb_add_crc_b;
354 break;
355
348 default: 356 default:
349 pr_err("Invalid protocol %d\n", protocol); 357 pr_err("Invalid protocol %d\n", protocol);
350 return -EINVAL; 358 return -EINVAL;
@@ -475,6 +483,10 @@ static int digital_start_poll(struct nfc_dev *nfc_dev, __u32 im_protocols,
475 digital_add_poll_tech(ddev, NFC_DIGITAL_RF_TECH_106A, 483 digital_add_poll_tech(ddev, NFC_DIGITAL_RF_TECH_106A,
476 digital_in_send_sens_req); 484 digital_in_send_sens_req);
477 485
486 if (matching_im_protocols & DIGITAL_PROTO_NFCB_RF_TECH)
487 digital_add_poll_tech(ddev, NFC_DIGITAL_RF_TECH_106B,
488 digital_in_send_sensb_req);
489
478 if (matching_im_protocols & DIGITAL_PROTO_NFCF_RF_TECH) { 490 if (matching_im_protocols & DIGITAL_PROTO_NFCF_RF_TECH) {
479 digital_add_poll_tech(ddev, NFC_DIGITAL_RF_TECH_212F, 491 digital_add_poll_tech(ddev, NFC_DIGITAL_RF_TECH_212F,
480 digital_in_send_sensf_req); 492 digital_in_send_sensf_req);
@@ -635,7 +647,8 @@ static void digital_in_send_complete(struct nfc_digital_dev *ddev, void *arg,
635 goto done; 647 goto done;
636 } 648 }
637 649
638 if (ddev->curr_protocol == NFC_PROTO_ISO14443) { 650 if ((ddev->curr_protocol == NFC_PROTO_ISO14443) ||
651 (ddev->curr_protocol == NFC_PROTO_ISO14443_B)) {
639 rc = digital_in_iso_dep_pull_sod(ddev, resp); 652 rc = digital_in_iso_dep_pull_sod(ddev, resp);
640 if (rc) 653 if (rc)
641 goto done; 654 goto done;
@@ -676,7 +689,8 @@ static int digital_in_send(struct nfc_dev *nfc_dev, struct nfc_target *target,
676 goto exit; 689 goto exit;
677 } 690 }
678 691
679 if (ddev->curr_protocol == NFC_PROTO_ISO14443) { 692 if ((ddev->curr_protocol == NFC_PROTO_ISO14443) ||
693 (ddev->curr_protocol == NFC_PROTO_ISO14443_B)) {
680 rc = digital_in_iso_dep_push_sod(ddev, skb); 694 rc = digital_in_iso_dep_push_sod(ddev, skb);
681 if (rc) 695 if (rc)
682 goto exit; 696 goto exit;
@@ -747,6 +761,8 @@ struct nfc_digital_dev *nfc_digital_allocate_device(struct nfc_digital_ops *ops,
747 ddev->protocols |= NFC_PROTO_ISO15693_MASK; 761 ddev->protocols |= NFC_PROTO_ISO15693_MASK;
748 if (supported_protocols & NFC_PROTO_ISO14443_MASK) 762 if (supported_protocols & NFC_PROTO_ISO14443_MASK)
749 ddev->protocols |= NFC_PROTO_ISO14443_MASK; 763 ddev->protocols |= NFC_PROTO_ISO14443_MASK;
764 if (supported_protocols & NFC_PROTO_ISO14443_B_MASK)
765 ddev->protocols |= NFC_PROTO_ISO14443_B_MASK;
750 766
751 ddev->tx_headroom = tx_headroom + DIGITAL_MAX_HEADER_LEN; 767 ddev->tx_headroom = tx_headroom + DIGITAL_MAX_HEADER_LEN;
752 ddev->tx_tailroom = tx_tailroom + DIGITAL_CRC_LEN; 768 ddev->tx_tailroom = tx_tailroom + DIGITAL_CRC_LEN;
diff --git a/net/nfc/digital_technology.c b/net/nfc/digital_technology.c
index 278c3fed27e0..12a233e9ece5 100644
--- a/net/nfc/digital_technology.c
+++ b/net/nfc/digital_technology.c
@@ -41,6 +41,24 @@
41#define DIGITAL_MIFARE_READ_RES_LEN 16 41#define DIGITAL_MIFARE_READ_RES_LEN 16
42#define DIGITAL_MIFARE_ACK_RES 0x0A 42#define DIGITAL_MIFARE_ACK_RES 0x0A
43 43
44#define DIGITAL_CMD_SENSB_REQ 0x05
45#define DIGITAL_SENSB_ADVANCED BIT(5)
46#define DIGITAL_SENSB_EXTENDED BIT(4)
47#define DIGITAL_SENSB_ALLB_REQ BIT(3)
48#define DIGITAL_SENSB_N(n) ((n) & 0x7)
49
50#define DIGITAL_CMD_SENSB_RES 0x50
51
52#define DIGITAL_CMD_ATTRIB_REQ 0x1D
53#define DIGITAL_ATTRIB_P1_TR0_DEFAULT (0x0 << 6)
54#define DIGITAL_ATTRIB_P1_TR1_DEFAULT (0x0 << 4)
55#define DIGITAL_ATTRIB_P1_SUPRESS_EOS BIT(3)
56#define DIGITAL_ATTRIB_P1_SUPRESS_SOS BIT(2)
57#define DIGITAL_ATTRIB_P2_LISTEN_POLL_1 (0x0 << 6)
58#define DIGITAL_ATTRIB_P2_POLL_LISTEN_1 (0x0 << 4)
59#define DIGITAL_ATTRIB_P2_MAX_FRAME_256 0x8
60#define DIGITAL_ATTRIB_P4_DID(n) ((n) & 0xf)
61
44#define DIGITAL_CMD_SENSF_REQ 0x00 62#define DIGITAL_CMD_SENSF_REQ 0x00
45#define DIGITAL_CMD_SENSF_RES 0x01 63#define DIGITAL_CMD_SENSF_RES 0x01
46 64
@@ -75,6 +93,7 @@ static const u8 digital_ats_fsc[] = {
75}; 93};
76 94
77#define DIGITAL_ATS_FSCI(t0) ((t0) & 0x0F) 95#define DIGITAL_ATS_FSCI(t0) ((t0) & 0x0F)
96#define DIGITAL_SENSB_FSCI(pi2) (((pi2) & 0xF0) >> 4)
78#define DIGITAL_ATS_MAX_FSC 256 97#define DIGITAL_ATS_MAX_FSC 256
79 98
80#define DIGITAL_RATS_BYTE1 0xE0 99#define DIGITAL_RATS_BYTE1 0xE0
@@ -92,6 +111,32 @@ struct digital_sel_req {
92 u8 bcc; 111 u8 bcc;
93} __packed; 112} __packed;
94 113
114struct digital_sensb_req {
115 u8 cmd;
116 u8 afi;
117 u8 param;
118} __packed;
119
120struct digital_sensb_res {
121 u8 cmd;
122 u8 nfcid0[4];
123 u8 app_data[4];
124 u8 proto_info[3];
125} __packed;
126
127struct digital_attrib_req {
128 u8 cmd;
129 u8 nfcid0[4];
130 u8 param1;
131 u8 param2;
132 u8 param3;
133 u8 param4;
134} __packed;
135
136struct digital_attrib_res {
137 u8 mbli_did;
138} __packed;
139
95struct digital_sensf_req { 140struct digital_sensf_req {
96 u8 cmd; 141 u8 cmd;
97 u8 sc1; 142 u8 sc1;
@@ -531,6 +576,175 @@ int digital_in_recv_mifare_res(struct sk_buff *resp)
531 return -EIO; 576 return -EIO;
532} 577}
533 578
579static void digital_in_recv_attrib_res(struct nfc_digital_dev *ddev, void *arg,
580 struct sk_buff *resp)
581{
582 struct nfc_target *target = arg;
583 struct digital_attrib_res *attrib_res;
584 int rc;
585
586 if (IS_ERR(resp)) {
587 rc = PTR_ERR(resp);
588 resp = NULL;
589 goto exit;
590 }
591
592 if (resp->len < sizeof(*attrib_res)) {
593 PROTOCOL_ERR("12.6.2");
594 rc = -EIO;
595 goto exit;
596 }
597
598 attrib_res = (struct digital_attrib_res *)resp->data;
599
600 if (attrib_res->mbli_did & 0x0f) {
601 PROTOCOL_ERR("12.6.2.1");
602 rc = -EIO;
603 goto exit;
604 }
605
606 rc = digital_target_found(ddev, target, NFC_PROTO_ISO14443_B);
607
608exit:
609 dev_kfree_skb(resp);
610 kfree(target);
611
612 if (rc)
613 digital_poll_next_tech(ddev);
614}
615
616int digital_in_send_attrib_req(struct nfc_digital_dev *ddev,
617 struct nfc_target *target,
618 struct digital_sensb_res *sensb_res)
619{
620 struct digital_attrib_req *attrib_req;
621 struct sk_buff *skb;
622 int rc;
623
624 skb = digital_skb_alloc(ddev, sizeof(*attrib_req));
625 if (!skb)
626 return -ENOMEM;
627
628 attrib_req = (struct digital_attrib_req *)skb_put(skb,
629 sizeof(*attrib_req));
630
631 attrib_req->cmd = DIGITAL_CMD_ATTRIB_REQ;
632 memcpy(attrib_req->nfcid0, sensb_res->nfcid0,
633 sizeof(attrib_req->nfcid0));
634 attrib_req->param1 = DIGITAL_ATTRIB_P1_TR0_DEFAULT |
635 DIGITAL_ATTRIB_P1_TR1_DEFAULT;
636 attrib_req->param2 = DIGITAL_ATTRIB_P2_LISTEN_POLL_1 |
637 DIGITAL_ATTRIB_P2_POLL_LISTEN_1 |
638 DIGITAL_ATTRIB_P2_MAX_FRAME_256;
639 attrib_req->param3 = sensb_res->proto_info[1] & 0x07;
640 attrib_req->param4 = DIGITAL_ATTRIB_P4_DID(0);
641
642 rc = digital_in_send_cmd(ddev, skb, 30, digital_in_recv_attrib_res,
643 target);
644 if (rc)
645 kfree_skb(skb);
646
647 return rc;
648}
649
650static void digital_in_recv_sensb_res(struct nfc_digital_dev *ddev, void *arg,
651 struct sk_buff *resp)
652{
653 struct nfc_target *target = NULL;
654 struct digital_sensb_res *sensb_res;
655 u8 fsci;
656 int rc;
657
658 if (IS_ERR(resp)) {
659 rc = PTR_ERR(resp);
660 resp = NULL;
661 goto exit;
662 }
663
664 if (resp->len != sizeof(*sensb_res)) {
665 PROTOCOL_ERR("5.6.2.1");
666 rc = -EIO;
667 goto exit;
668 }
669
670 sensb_res = (struct digital_sensb_res *)resp->data;
671
672 if (sensb_res->cmd != DIGITAL_CMD_SENSB_RES) {
673 PROTOCOL_ERR("5.6.2");
674 rc = -EIO;
675 goto exit;
676 }
677
678 if (!(sensb_res->proto_info[1] & BIT(0))) {
679 PROTOCOL_ERR("5.6.2.12");
680 rc = -EIO;
681 goto exit;
682 }
683
684 if (sensb_res->proto_info[1] & BIT(3)) {
685 PROTOCOL_ERR("5.6.2.16");
686 rc = -EIO;
687 goto exit;
688 }
689
690 fsci = DIGITAL_SENSB_FSCI(sensb_res->proto_info[1]);
691 if (fsci >= 8)
692 ddev->target_fsc = DIGITAL_ATS_MAX_FSC;
693 else
694 ddev->target_fsc = digital_ats_fsc[fsci];
695
696 target = kzalloc(sizeof(struct nfc_target), GFP_KERNEL);
697 if (!target) {
698 rc = -ENOMEM;
699 goto exit;
700 }
701
702 rc = digital_in_send_attrib_req(ddev, target, sensb_res);
703
704exit:
705 dev_kfree_skb(resp);
706
707 if (rc) {
708 kfree(target);
709 digital_poll_next_tech(ddev);
710 }
711}
712
713int digital_in_send_sensb_req(struct nfc_digital_dev *ddev, u8 rf_tech)
714{
715 struct digital_sensb_req *sensb_req;
716 struct sk_buff *skb;
717 int rc;
718
719 rc = digital_in_configure_hw(ddev, NFC_DIGITAL_CONFIG_RF_TECH,
720 NFC_DIGITAL_RF_TECH_106B);
721 if (rc)
722 return rc;
723
724 rc = digital_in_configure_hw(ddev, NFC_DIGITAL_CONFIG_FRAMING,
725 NFC_DIGITAL_FRAMING_NFCB);
726 if (rc)
727 return rc;
728
729 skb = digital_skb_alloc(ddev, sizeof(*sensb_req));
730 if (!skb)
731 return -ENOMEM;
732
733 sensb_req = (struct digital_sensb_req *)skb_put(skb,
734 sizeof(*sensb_req));
735
736 sensb_req->cmd = DIGITAL_CMD_SENSB_REQ;
737 sensb_req->afi = 0x00; /* All families and sub-families */
738 sensb_req->param = DIGITAL_SENSB_N(0);
739
740 rc = digital_in_send_cmd(ddev, skb, 30, digital_in_recv_sensb_res,
741 NULL);
742 if (rc)
743 kfree_skb(skb);
744
745 return rc;
746}
747
534static void digital_in_recv_sensf_res(struct nfc_digital_dev *ddev, void *arg, 748static void digital_in_recv_sensf_res(struct nfc_digital_dev *ddev, void *arg,
535 struct sk_buff *resp) 749 struct sk_buff *resp)
536{ 750{
@@ -877,6 +1091,18 @@ exit:
877 dev_kfree_skb(resp); 1091 dev_kfree_skb(resp);
878} 1092}
879 1093
1094static void digital_tg_recv_atr_or_sensf_req(struct nfc_digital_dev *ddev,
1095 void *arg, struct sk_buff *resp)
1096{
1097 if (!IS_ERR(resp) && (resp->len >= 2) &&
1098 (resp->data[1] == DIGITAL_CMD_SENSF_REQ))
1099 digital_tg_recv_sensf_req(ddev, arg, resp);
1100 else
1101 digital_tg_recv_atr_req(ddev, arg, resp);
1102
1103 return;
1104}
1105
880static int digital_tg_send_sensf_res(struct nfc_digital_dev *ddev, 1106static int digital_tg_send_sensf_res(struct nfc_digital_dev *ddev,
881 struct digital_sensf_req *sensf_req) 1107 struct digital_sensf_req *sensf_req)
882{ 1108{
@@ -887,7 +1113,7 @@ static int digital_tg_send_sensf_res(struct nfc_digital_dev *ddev,
887 1113
888 size = sizeof(struct digital_sensf_res); 1114 size = sizeof(struct digital_sensf_res);
889 1115
890 if (sensf_req->rc != DIGITAL_SENSF_REQ_RC_NONE) 1116 if (sensf_req->rc == DIGITAL_SENSF_REQ_RC_NONE)
891 size -= sizeof(sensf_res->rd); 1117 size -= sizeof(sensf_res->rd);
892 1118
893 skb = digital_skb_alloc(ddev, size); 1119 skb = digital_skb_alloc(ddev, size);
@@ -922,7 +1148,7 @@ static int digital_tg_send_sensf_res(struct nfc_digital_dev *ddev,
922 digital_skb_add_crc_f(skb); 1148 digital_skb_add_crc_f(skb);
923 1149
924 rc = digital_tg_send_cmd(ddev, skb, 300, 1150 rc = digital_tg_send_cmd(ddev, skb, 300,
925 digital_tg_recv_atr_req, NULL); 1151 digital_tg_recv_atr_or_sensf_req, NULL);
926 if (rc) 1152 if (rc)
927 kfree_skb(skb); 1153 kfree_skb(skb);
928 1154
diff --git a/net/nfc/hci/command.c b/net/nfc/hci/command.c
index a9f4d2e62d8d..677d24bb70f8 100644
--- a/net/nfc/hci/command.c
+++ b/net/nfc/hci/command.c
@@ -26,6 +26,8 @@
26 26
27#include "hci.h" 27#include "hci.h"
28 28
29#define MAX_FWI 4949
30
29static int nfc_hci_execute_cmd_async(struct nfc_hci_dev *hdev, u8 pipe, u8 cmd, 31static int nfc_hci_execute_cmd_async(struct nfc_hci_dev *hdev, u8 pipe, u8 cmd,
30 const u8 *param, size_t param_len, 32 const u8 *param, size_t param_len,
31 data_exchange_cb_t cb, void *cb_context) 33 data_exchange_cb_t cb, void *cb_context)
@@ -37,7 +39,7 @@ static int nfc_hci_execute_cmd_async(struct nfc_hci_dev *hdev, u8 pipe, u8 cmd,
37 * for all commands? 39 * for all commands?
38 */ 40 */
39 return nfc_hci_hcp_message_tx(hdev, pipe, NFC_HCI_HCP_COMMAND, cmd, 41 return nfc_hci_hcp_message_tx(hdev, pipe, NFC_HCI_HCP_COMMAND, cmd,
40 param, param_len, cb, cb_context, 3000); 42 param, param_len, cb, cb_context, MAX_FWI);
41} 43}
42 44
43/* 45/*
@@ -82,7 +84,7 @@ static int nfc_hci_execute_cmd(struct nfc_hci_dev *hdev, u8 pipe, u8 cmd,
82 NFC_HCI_HCP_COMMAND, cmd, 84 NFC_HCI_HCP_COMMAND, cmd,
83 param, param_len, 85 param, param_len,
84 nfc_hci_execute_cb, &hcp_ew, 86 nfc_hci_execute_cb, &hcp_ew,
85 3000); 87 MAX_FWI);
86 if (hcp_ew.exec_result < 0) 88 if (hcp_ew.exec_result < 0)
87 return hcp_ew.exec_result; 89 return hcp_ew.exec_result;
88 90
diff --git a/net/nfc/hci/core.c b/net/nfc/hci/core.c
index d45b638e77c7..47403705197e 100644
--- a/net/nfc/hci/core.c
+++ b/net/nfc/hci/core.c
@@ -225,7 +225,7 @@ int nfc_hci_target_discovered(struct nfc_hci_dev *hdev, u8 gate)
225 goto exit; 225 goto exit;
226 } 226 }
227 227
228 targets->sens_res = be16_to_cpu(*(u16 *)atqa_skb->data); 228 targets->sens_res = be16_to_cpu(*(__be16 *)atqa_skb->data);
229 targets->sel_res = sak_skb->data[0]; 229 targets->sel_res = sak_skb->data[0];
230 230
231 r = nfc_hci_get_param(hdev, NFC_HCI_RF_READER_A_GATE, 231 r = nfc_hci_get_param(hdev, NFC_HCI_RF_READER_A_GATE,
@@ -380,34 +380,31 @@ static int hci_dev_session_init(struct nfc_hci_dev *hdev)
380 if (r < 0) 380 if (r < 0)
381 goto disconnect_all; 381 goto disconnect_all;
382 382
383 if (skb->len && skb->len == strlen(hdev->init_data.session_id)) 383 if (skb->len && skb->len == strlen(hdev->init_data.session_id) &&
384 if (memcmp(hdev->init_data.session_id, skb->data, 384 (memcmp(hdev->init_data.session_id, skb->data,
385 skb->len) == 0) { 385 skb->len) == 0) && hdev->ops->load_session) {
386 /* TODO ELa: restore gate<->pipe table from 386 /* Restore gate<->pipe table from some proprietary location. */
387 * some TBD location.
388 * note: it doesn't seem possible to get the chip
389 * currently open gate/pipe table.
390 * It is only possible to obtain the supported
391 * gate list.
392 */
393 387
394 /* goto exit 388 r = hdev->ops->load_session(hdev);
395 * For now, always do a full initialization */
396 }
397 389
398 r = nfc_hci_disconnect_all_gates(hdev); 390 if (r < 0)
399 if (r < 0) 391 goto disconnect_all;
400 goto exit; 392 } else {
401 393
402 r = hci_dev_connect_gates(hdev, hdev->init_data.gate_count, 394 r = nfc_hci_disconnect_all_gates(hdev);
403 hdev->init_data.gates); 395 if (r < 0)
404 if (r < 0) 396 goto exit;
405 goto disconnect_all;
406 397
407 r = nfc_hci_set_param(hdev, NFC_HCI_ADMIN_GATE, 398 r = hci_dev_connect_gates(hdev, hdev->init_data.gate_count,
408 NFC_HCI_ADMIN_SESSION_IDENTITY, 399 hdev->init_data.gates);
409 hdev->init_data.session_id, 400 if (r < 0)
410 strlen(hdev->init_data.session_id)); 401 goto disconnect_all;
402
403 r = nfc_hci_set_param(hdev, NFC_HCI_ADMIN_GATE,
404 NFC_HCI_ADMIN_SESSION_IDENTITY,
405 hdev->init_data.session_id,
406 strlen(hdev->init_data.session_id));
407 }
411 if (r == 0) 408 if (r == 0)
412 goto exit; 409 goto exit;
413 410
diff --git a/net/nfc/llcp_commands.c b/net/nfc/llcp_commands.c
index bec6ed15f503..a3ad69a4c648 100644
--- a/net/nfc/llcp_commands.c
+++ b/net/nfc/llcp_commands.c
@@ -387,7 +387,7 @@ int nfc_llcp_send_symm(struct nfc_dev *dev)
387 387
388 __net_timestamp(skb); 388 __net_timestamp(skb);
389 389
390 nfc_llcp_send_to_raw_sock(local, skb, NFC_LLCP_DIRECTION_TX); 390 nfc_llcp_send_to_raw_sock(local, skb, NFC_DIRECTION_TX);
391 391
392 return nfc_data_exchange(dev, local->target_idx, skb, 392 return nfc_data_exchange(dev, local->target_idx, skb,
393 nfc_llcp_recv, local); 393 nfc_llcp_recv, local);
diff --git a/net/nfc/llcp_core.c b/net/nfc/llcp_core.c
index b4671958fcf9..f6278da68763 100644
--- a/net/nfc/llcp_core.c
+++ b/net/nfc/llcp_core.c
@@ -680,16 +680,17 @@ void nfc_llcp_send_to_raw_sock(struct nfc_llcp_local *local,
680 continue; 680 continue;
681 681
682 if (skb_copy == NULL) { 682 if (skb_copy == NULL) {
683 skb_copy = __pskb_copy(skb, NFC_LLCP_RAW_HEADER_SIZE, 683 skb_copy = __pskb_copy(skb, NFC_RAW_HEADER_SIZE,
684 GFP_ATOMIC); 684 GFP_ATOMIC);
685 685
686 if (skb_copy == NULL) 686 if (skb_copy == NULL)
687 continue; 687 continue;
688 688
689 data = skb_push(skb_copy, NFC_LLCP_RAW_HEADER_SIZE); 689 data = skb_push(skb_copy, NFC_RAW_HEADER_SIZE);
690 690
691 data[0] = local->dev ? local->dev->idx : 0xFF; 691 data[0] = local->dev ? local->dev->idx : 0xFF;
692 data[1] = direction; 692 data[1] = direction & 0x01;
693 data[1] |= (RAW_PAYLOAD_LLCP << 1);
693 } 694 }
694 695
695 nskb = skb_clone(skb_copy, GFP_ATOMIC); 696 nskb = skb_clone(skb_copy, GFP_ATOMIC);
@@ -747,7 +748,7 @@ static void nfc_llcp_tx_work(struct work_struct *work)
747 __net_timestamp(skb); 748 __net_timestamp(skb);
748 749
749 nfc_llcp_send_to_raw_sock(local, skb, 750 nfc_llcp_send_to_raw_sock(local, skb,
750 NFC_LLCP_DIRECTION_TX); 751 NFC_DIRECTION_TX);
751 752
752 ret = nfc_data_exchange(local->dev, local->target_idx, 753 ret = nfc_data_exchange(local->dev, local->target_idx,
753 skb, nfc_llcp_recv, local); 754 skb, nfc_llcp_recv, local);
@@ -1476,7 +1477,7 @@ static void nfc_llcp_rx_work(struct work_struct *work)
1476 1477
1477 __net_timestamp(skb); 1478 __net_timestamp(skb);
1478 1479
1479 nfc_llcp_send_to_raw_sock(local, skb, NFC_LLCP_DIRECTION_RX); 1480 nfc_llcp_send_to_raw_sock(local, skb, NFC_DIRECTION_RX);
1480 1481
1481 nfc_llcp_rx_skb(local, skb); 1482 nfc_llcp_rx_skb(local, skb);
1482 1483
diff --git a/net/nfc/nci/core.c b/net/nfc/nci/core.c
index 6c34ac978501..2b400e1a8695 100644
--- a/net/nfc/nci/core.c
+++ b/net/nfc/nci/core.c
@@ -861,6 +861,10 @@ static int nci_send_frame(struct nci_dev *ndev, struct sk_buff *skb)
861 /* Get rid of skb owner, prior to sending to the driver. */ 861 /* Get rid of skb owner, prior to sending to the driver. */
862 skb_orphan(skb); 862 skb_orphan(skb);
863 863
864 /* Send copy to sniffer */
865 nfc_send_to_raw_sock(ndev->nfc_dev, skb,
866 RAW_PAYLOAD_NCI, NFC_DIRECTION_TX);
867
864 return ndev->ops->send(ndev, skb); 868 return ndev->ops->send(ndev, skb);
865} 869}
866 870
@@ -935,6 +939,11 @@ static void nci_rx_work(struct work_struct *work)
935 struct sk_buff *skb; 939 struct sk_buff *skb;
936 940
937 while ((skb = skb_dequeue(&ndev->rx_q))) { 941 while ((skb = skb_dequeue(&ndev->rx_q))) {
942
943 /* Send copy to sniffer */
944 nfc_send_to_raw_sock(ndev->nfc_dev, skb,
945 RAW_PAYLOAD_NCI, NFC_DIRECTION_RX);
946
938 /* Process frame */ 947 /* Process frame */
939 switch (nci_mt(skb->data)) { 948 switch (nci_mt(skb->data)) {
940 case NCI_MT_RSP_PKT: 949 case NCI_MT_RSP_PKT:
diff --git a/net/nfc/nci/ntf.c b/net/nfc/nci/ntf.c
index 1e905097456b..f8f6af231381 100644
--- a/net/nfc/nci/ntf.c
+++ b/net/nfc/nci/ntf.c
@@ -366,7 +366,6 @@ static int nci_extract_activation_params_nfc_dep(struct nci_dev *ndev,
366 struct nci_rf_intf_activated_ntf *ntf, __u8 *data) 366 struct nci_rf_intf_activated_ntf *ntf, __u8 *data)
367{ 367{
368 struct activation_params_poll_nfc_dep *poll; 368 struct activation_params_poll_nfc_dep *poll;
369 int i;
370 369
371 switch (ntf->activation_rf_tech_and_mode) { 370 switch (ntf->activation_rf_tech_and_mode) {
372 case NCI_NFC_A_PASSIVE_POLL_MODE: 371 case NCI_NFC_A_PASSIVE_POLL_MODE:
@@ -374,10 +373,8 @@ static int nci_extract_activation_params_nfc_dep(struct nci_dev *ndev,
374 poll = &ntf->activation_params.poll_nfc_dep; 373 poll = &ntf->activation_params.poll_nfc_dep;
375 poll->atr_res_len = min_t(__u8, *data++, 63); 374 poll->atr_res_len = min_t(__u8, *data++, 63);
376 pr_debug("atr_res_len %d\n", poll->atr_res_len); 375 pr_debug("atr_res_len %d\n", poll->atr_res_len);
377 if (poll->atr_res_len > 0) { 376 if (poll->atr_res_len > 0)
378 for (i = 0; i < poll->atr_res_len; i++) 377 memcpy(poll->atr_res, data, poll->atr_res_len);
379 poll->atr_res[poll->atr_res_len-1-i] = data[i];
380 }
381 break; 378 break;
382 379
383 default: 380 default:
diff --git a/net/nfc/nfc.h b/net/nfc/nfc.h
index 9d6e74f7e6b3..88d60064890e 100644
--- a/net/nfc/nfc.h
+++ b/net/nfc/nfc.h
@@ -40,6 +40,12 @@ struct nfc_rawsock {
40 struct work_struct tx_work; 40 struct work_struct tx_work;
41 bool tx_work_scheduled; 41 bool tx_work_scheduled;
42}; 42};
43
44struct nfc_sock_list {
45 struct hlist_head head;
46 rwlock_t lock;
47};
48
43#define nfc_rawsock(sk) ((struct nfc_rawsock *) sk) 49#define nfc_rawsock(sk) ((struct nfc_rawsock *) sk)
44#define to_rawsock_sk(_tx_work) \ 50#define to_rawsock_sk(_tx_work) \
45 ((struct sock *) container_of(_tx_work, struct nfc_rawsock, tx_work)) 51 ((struct sock *) container_of(_tx_work, struct nfc_rawsock, tx_work))
diff --git a/net/nfc/rawsock.c b/net/nfc/rawsock.c
index c27a6e86cae4..8627c75063e2 100644
--- a/net/nfc/rawsock.c
+++ b/net/nfc/rawsock.c
@@ -27,6 +27,24 @@
27 27
28#include "nfc.h" 28#include "nfc.h"
29 29
30static struct nfc_sock_list raw_sk_list = {
31 .lock = __RW_LOCK_UNLOCKED(raw_sk_list.lock)
32};
33
34void nfc_sock_link(struct nfc_sock_list *l, struct sock *sk)
35{
36 write_lock(&l->lock);
37 sk_add_node(sk, &l->head);
38 write_unlock(&l->lock);
39}
40
41void nfc_sock_unlink(struct nfc_sock_list *l, struct sock *sk)
42{
43 write_lock(&l->lock);
44 sk_del_node_init(sk);
45 write_unlock(&l->lock);
46}
47
30static void rawsock_write_queue_purge(struct sock *sk) 48static void rawsock_write_queue_purge(struct sock *sk)
31{ 49{
32 pr_debug("sk=%p\n", sk); 50 pr_debug("sk=%p\n", sk);
@@ -57,6 +75,9 @@ static int rawsock_release(struct socket *sock)
57 if (!sk) 75 if (!sk)
58 return 0; 76 return 0;
59 77
78 if (sock->type == SOCK_RAW)
79 nfc_sock_unlink(&raw_sk_list, sk);
80
60 sock_orphan(sk); 81 sock_orphan(sk);
61 sock_put(sk); 82 sock_put(sk);
62 83
@@ -275,6 +296,26 @@ static const struct proto_ops rawsock_ops = {
275 .mmap = sock_no_mmap, 296 .mmap = sock_no_mmap,
276}; 297};
277 298
299static const struct proto_ops rawsock_raw_ops = {
300 .family = PF_NFC,
301 .owner = THIS_MODULE,
302 .release = rawsock_release,
303 .bind = sock_no_bind,
304 .connect = sock_no_connect,
305 .socketpair = sock_no_socketpair,
306 .accept = sock_no_accept,
307 .getname = sock_no_getname,
308 .poll = datagram_poll,
309 .ioctl = sock_no_ioctl,
310 .listen = sock_no_listen,
311 .shutdown = sock_no_shutdown,
312 .setsockopt = sock_no_setsockopt,
313 .getsockopt = sock_no_getsockopt,
314 .sendmsg = sock_no_sendmsg,
315 .recvmsg = rawsock_recvmsg,
316 .mmap = sock_no_mmap,
317};
318
278static void rawsock_destruct(struct sock *sk) 319static void rawsock_destruct(struct sock *sk)
279{ 320{
280 pr_debug("sk=%p\n", sk); 321 pr_debug("sk=%p\n", sk);
@@ -300,10 +341,13 @@ static int rawsock_create(struct net *net, struct socket *sock,
300 341
301 pr_debug("sock=%p\n", sock); 342 pr_debug("sock=%p\n", sock);
302 343
303 if (sock->type != SOCK_SEQPACKET) 344 if ((sock->type != SOCK_SEQPACKET) && (sock->type != SOCK_RAW))
304 return -ESOCKTNOSUPPORT; 345 return -ESOCKTNOSUPPORT;
305 346
306 sock->ops = &rawsock_ops; 347 if (sock->type == SOCK_RAW)
348 sock->ops = &rawsock_raw_ops;
349 else
350 sock->ops = &rawsock_ops;
307 351
308 sk = sk_alloc(net, PF_NFC, GFP_ATOMIC, nfc_proto->proto); 352 sk = sk_alloc(net, PF_NFC, GFP_ATOMIC, nfc_proto->proto);
309 if (!sk) 353 if (!sk)
@@ -313,13 +357,53 @@ static int rawsock_create(struct net *net, struct socket *sock,
313 sk->sk_protocol = nfc_proto->id; 357 sk->sk_protocol = nfc_proto->id;
314 sk->sk_destruct = rawsock_destruct; 358 sk->sk_destruct = rawsock_destruct;
315 sock->state = SS_UNCONNECTED; 359 sock->state = SS_UNCONNECTED;
316 360 if (sock->type == SOCK_RAW)
317 INIT_WORK(&nfc_rawsock(sk)->tx_work, rawsock_tx_work); 361 nfc_sock_link(&raw_sk_list, sk);
318 nfc_rawsock(sk)->tx_work_scheduled = false; 362 else {
363 INIT_WORK(&nfc_rawsock(sk)->tx_work, rawsock_tx_work);
364 nfc_rawsock(sk)->tx_work_scheduled = false;
365 }
319 366
320 return 0; 367 return 0;
321} 368}
322 369
370void nfc_send_to_raw_sock(struct nfc_dev *dev, struct sk_buff *skb,
371 u8 payload_type, u8 direction)
372{
373 struct sk_buff *skb_copy = NULL, *nskb;
374 struct sock *sk;
375 u8 *data;
376
377 read_lock(&raw_sk_list.lock);
378
379 sk_for_each(sk, &raw_sk_list.head) {
380 if (!skb_copy) {
381 skb_copy = __pskb_copy(skb, NFC_RAW_HEADER_SIZE,
382 GFP_ATOMIC);
383 if (!skb_copy)
384 continue;
385
386 data = skb_push(skb_copy, NFC_RAW_HEADER_SIZE);
387
388 data[0] = dev ? dev->idx : 0xFF;
389 data[1] = direction & 0x01;
390 data[1] |= (payload_type << 1);
391 }
392
393 nskb = skb_clone(skb_copy, GFP_ATOMIC);
394 if (!nskb)
395 continue;
396
397 if (sock_queue_rcv_skb(sk, nskb))
398 kfree_skb(nskb);
399 }
400
401 read_unlock(&raw_sk_list.lock);
402
403 kfree_skb(skb_copy);
404}
405EXPORT_SYMBOL(nfc_send_to_raw_sock);
406
323static struct proto rawsock_proto = { 407static struct proto rawsock_proto = {
324 .name = "NFC_RAW", 408 .name = "NFC_RAW",
325 .owner = THIS_MODULE, 409 .owner = THIS_MODULE,
diff --git a/net/rfkill/rfkill-gpio.c b/net/rfkill/rfkill-gpio.c
index bd2a5b90400c..14c98e48f261 100644
--- a/net/rfkill/rfkill-gpio.c
+++ b/net/rfkill/rfkill-gpio.c
@@ -36,8 +36,6 @@ struct rfkill_gpio_data {
36 struct gpio_desc *shutdown_gpio; 36 struct gpio_desc *shutdown_gpio;
37 37
38 struct rfkill *rfkill_dev; 38 struct rfkill *rfkill_dev;
39 char *reset_name;
40 char *shutdown_name;
41 struct clk *clk; 39 struct clk *clk;
42 40
43 bool clk_enabled; 41 bool clk_enabled;
@@ -47,17 +45,14 @@ static int rfkill_gpio_set_power(void *data, bool blocked)
47{ 45{
48 struct rfkill_gpio_data *rfkill = data; 46 struct rfkill_gpio_data *rfkill = data;
49 47
50 if (blocked) { 48 if (!blocked && !IS_ERR(rfkill->clk) && !rfkill->clk_enabled)
51 gpiod_set_value(rfkill->shutdown_gpio, 0); 49 clk_enable(rfkill->clk);
52 gpiod_set_value(rfkill->reset_gpio, 0); 50
53 if (!IS_ERR(rfkill->clk) && rfkill->clk_enabled) 51 gpiod_set_value_cansleep(rfkill->shutdown_gpio, !blocked);
54 clk_disable(rfkill->clk); 52 gpiod_set_value_cansleep(rfkill->reset_gpio, !blocked);
55 } else { 53
56 if (!IS_ERR(rfkill->clk) && !rfkill->clk_enabled) 54 if (blocked && !IS_ERR(rfkill->clk) && rfkill->clk_enabled)
57 clk_enable(rfkill->clk); 55 clk_disable(rfkill->clk);
58 gpiod_set_value(rfkill->reset_gpio, 1);
59 gpiod_set_value(rfkill->shutdown_gpio, 1);
60 }
61 56
62 rfkill->clk_enabled = blocked; 57 rfkill->clk_enabled = blocked;
63 58
@@ -87,10 +82,8 @@ static int rfkill_gpio_probe(struct platform_device *pdev)
87{ 82{
88 struct rfkill_gpio_platform_data *pdata = pdev->dev.platform_data; 83 struct rfkill_gpio_platform_data *pdata = pdev->dev.platform_data;
89 struct rfkill_gpio_data *rfkill; 84 struct rfkill_gpio_data *rfkill;
90 const char *clk_name = NULL;
91 struct gpio_desc *gpio; 85 struct gpio_desc *gpio;
92 int ret; 86 int ret;
93 int len;
94 87
95 rfkill = devm_kzalloc(&pdev->dev, sizeof(*rfkill), GFP_KERNEL); 88 rfkill = devm_kzalloc(&pdev->dev, sizeof(*rfkill), GFP_KERNEL);
96 if (!rfkill) 89 if (!rfkill)
@@ -101,28 +94,15 @@ static int rfkill_gpio_probe(struct platform_device *pdev)
101 if (ret) 94 if (ret)
102 return ret; 95 return ret;
103 } else if (pdata) { 96 } else if (pdata) {
104 clk_name = pdata->power_clk_name;
105 rfkill->name = pdata->name; 97 rfkill->name = pdata->name;
106 rfkill->type = pdata->type; 98 rfkill->type = pdata->type;
107 } else { 99 } else {
108 return -ENODEV; 100 return -ENODEV;
109 } 101 }
110 102
111 len = strlen(rfkill->name); 103 rfkill->clk = devm_clk_get(&pdev->dev, NULL);
112 rfkill->reset_name = devm_kzalloc(&pdev->dev, len + 7, GFP_KERNEL);
113 if (!rfkill->reset_name)
114 return -ENOMEM;
115
116 rfkill->shutdown_name = devm_kzalloc(&pdev->dev, len + 10, GFP_KERNEL);
117 if (!rfkill->shutdown_name)
118 return -ENOMEM;
119 104
120 snprintf(rfkill->reset_name, len + 6 , "%s_reset", rfkill->name); 105 gpio = devm_gpiod_get_index(&pdev->dev, "reset", 0);
121 snprintf(rfkill->shutdown_name, len + 9, "%s_shutdown", rfkill->name);
122
123 rfkill->clk = devm_clk_get(&pdev->dev, clk_name);
124
125 gpio = devm_gpiod_get_index(&pdev->dev, rfkill->reset_name, 0);
126 if (!IS_ERR(gpio)) { 106 if (!IS_ERR(gpio)) {
127 ret = gpiod_direction_output(gpio, 0); 107 ret = gpiod_direction_output(gpio, 0);
128 if (ret) 108 if (ret)
@@ -130,7 +110,7 @@ static int rfkill_gpio_probe(struct platform_device *pdev)
130 rfkill->reset_gpio = gpio; 110 rfkill->reset_gpio = gpio;
131 } 111 }
132 112
133 gpio = devm_gpiod_get_index(&pdev->dev, rfkill->shutdown_name, 1); 113 gpio = devm_gpiod_get_index(&pdev->dev, "shutdown", 1);
134 if (!IS_ERR(gpio)) { 114 if (!IS_ERR(gpio)) {
135 ret = gpiod_direction_output(gpio, 0); 115 ret = gpiod_direction_output(gpio, 0);
136 if (ret) 116 if (ret)
@@ -146,14 +126,6 @@ static int rfkill_gpio_probe(struct platform_device *pdev)
146 return -EINVAL; 126 return -EINVAL;
147 } 127 }
148 128
149 if (pdata && pdata->gpio_runtime_setup) {
150 ret = pdata->gpio_runtime_setup(pdev);
151 if (ret) {
152 dev_err(&pdev->dev, "can't set up gpio\n");
153 return ret;
154 }
155 }
156
157 rfkill->rfkill_dev = rfkill_alloc(rfkill->name, &pdev->dev, 129 rfkill->rfkill_dev = rfkill_alloc(rfkill->name, &pdev->dev,
158 rfkill->type, &rfkill_gpio_ops, 130 rfkill->type, &rfkill_gpio_ops,
159 rfkill); 131 rfkill);
@@ -174,20 +146,23 @@ static int rfkill_gpio_probe(struct platform_device *pdev)
174static int rfkill_gpio_remove(struct platform_device *pdev) 146static int rfkill_gpio_remove(struct platform_device *pdev)
175{ 147{
176 struct rfkill_gpio_data *rfkill = platform_get_drvdata(pdev); 148 struct rfkill_gpio_data *rfkill = platform_get_drvdata(pdev);
177 struct rfkill_gpio_platform_data *pdata = pdev->dev.platform_data;
178 149
179 if (pdata && pdata->gpio_runtime_close)
180 pdata->gpio_runtime_close(pdev);
181 rfkill_unregister(rfkill->rfkill_dev); 150 rfkill_unregister(rfkill->rfkill_dev);
182 rfkill_destroy(rfkill->rfkill_dev); 151 rfkill_destroy(rfkill->rfkill_dev);
183 152
184 return 0; 153 return 0;
185} 154}
186 155
156#ifdef CONFIG_ACPI
187static const struct acpi_device_id rfkill_acpi_match[] = { 157static const struct acpi_device_id rfkill_acpi_match[] = {
158 { "BCM2E1A", RFKILL_TYPE_BLUETOOTH },
159 { "BCM2E39", RFKILL_TYPE_BLUETOOTH },
160 { "BCM2E3D", RFKILL_TYPE_BLUETOOTH },
188 { "BCM4752", RFKILL_TYPE_GPS }, 161 { "BCM4752", RFKILL_TYPE_GPS },
162 { "LNV4752", RFKILL_TYPE_GPS },
189 { }, 163 { },
190}; 164};
165#endif
191 166
192static struct platform_driver rfkill_gpio_driver = { 167static struct platform_driver rfkill_gpio_driver = {
193 .probe = rfkill_gpio_probe, 168 .probe = rfkill_gpio_probe,
diff --git a/net/wireless/ap.c b/net/wireless/ap.c
index 3e02ade508d8..bdad1f951561 100644
--- a/net/wireless/ap.c
+++ b/net/wireless/ap.c
@@ -6,8 +6,8 @@
6#include "rdev-ops.h" 6#include "rdev-ops.h"
7 7
8 8
9static int __cfg80211_stop_ap(struct cfg80211_registered_device *rdev, 9int __cfg80211_stop_ap(struct cfg80211_registered_device *rdev,
10 struct net_device *dev, bool notify) 10 struct net_device *dev, bool notify)
11{ 11{
12 struct wireless_dev *wdev = dev->ieee80211_ptr; 12 struct wireless_dev *wdev = dev->ieee80211_ptr;
13 int err; 13 int err;
diff --git a/net/wireless/chan.c b/net/wireless/chan.c
index 84d686e2dbd0..992b34070bcb 100644
--- a/net/wireless/chan.c
+++ b/net/wireless/chan.c
@@ -370,8 +370,8 @@ int cfg80211_chandef_dfs_required(struct wiphy *wiphy,
370 case NL80211_IFTYPE_AP_VLAN: 370 case NL80211_IFTYPE_AP_VLAN:
371 case NL80211_IFTYPE_WDS: 371 case NL80211_IFTYPE_WDS:
372 case NL80211_IFTYPE_P2P_DEVICE: 372 case NL80211_IFTYPE_P2P_DEVICE:
373 case NL80211_IFTYPE_UNSPECIFIED:
374 break; 373 break;
374 case NL80211_IFTYPE_UNSPECIFIED:
375 case NUM_NL80211_IFTYPES: 375 case NUM_NL80211_IFTYPES:
376 WARN_ON(1); 376 WARN_ON(1);
377 } 377 }
@@ -796,8 +796,7 @@ bool cfg80211_reg_can_beacon(struct wiphy *wiphy,
796 !cfg80211_go_permissive_chan(rdev, chandef->chan)) 796 !cfg80211_go_permissive_chan(rdev, chandef->chan))
797 prohibited_flags |= IEEE80211_CHAN_NO_IR; 797 prohibited_flags |= IEEE80211_CHAN_NO_IR;
798 798
799 if (cfg80211_chandef_dfs_required(wiphy, chandef, 799 if (cfg80211_chandef_dfs_required(wiphy, chandef, iftype) > 0 &&
800 NL80211_IFTYPE_UNSPECIFIED) > 0 &&
801 cfg80211_chandef_dfs_available(wiphy, chandef)) { 800 cfg80211_chandef_dfs_available(wiphy, chandef)) {
802 /* We can skip IEEE80211_CHAN_NO_IR if chandef dfs available */ 801 /* We can skip IEEE80211_CHAN_NO_IR if chandef dfs available */
803 prohibited_flags = IEEE80211_CHAN_DISABLED; 802 prohibited_flags = IEEE80211_CHAN_DISABLED;
diff --git a/net/wireless/core.c b/net/wireless/core.c
index b3ff3697239a..d03d8bdb29ca 100644
--- a/net/wireless/core.c
+++ b/net/wireless/core.c
@@ -210,15 +210,12 @@ void cfg80211_stop_p2p_device(struct cfg80211_registered_device *rdev,
210 } 210 }
211} 211}
212 212
213static int cfg80211_rfkill_set_block(void *data, bool blocked) 213void cfg80211_shutdown_all_interfaces(struct wiphy *wiphy)
214{ 214{
215 struct cfg80211_registered_device *rdev = data; 215 struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy);
216 struct wireless_dev *wdev; 216 struct wireless_dev *wdev;
217 217
218 if (!blocked) 218 ASSERT_RTNL();
219 return 0;
220
221 rtnl_lock();
222 219
223 list_for_each_entry(wdev, &rdev->wdev_list, list) { 220 list_for_each_entry(wdev, &rdev->wdev_list, list) {
224 if (wdev->netdev) { 221 if (wdev->netdev) {
@@ -234,7 +231,18 @@ static int cfg80211_rfkill_set_block(void *data, bool blocked)
234 break; 231 break;
235 } 232 }
236 } 233 }
234}
235EXPORT_SYMBOL_GPL(cfg80211_shutdown_all_interfaces);
237 236
237static int cfg80211_rfkill_set_block(void *data, bool blocked)
238{
239 struct cfg80211_registered_device *rdev = data;
240
241 if (!blocked)
242 return 0;
243
244 rtnl_lock();
245 cfg80211_shutdown_all_interfaces(&rdev->wiphy);
238 rtnl_unlock(); 246 rtnl_unlock();
239 247
240 return 0; 248 return 0;
@@ -394,6 +402,8 @@ struct wiphy *wiphy_new(const struct cfg80211_ops *ops, int sizeof_priv)
394 rdev->wiphy.rts_threshold = (u32) -1; 402 rdev->wiphy.rts_threshold = (u32) -1;
395 rdev->wiphy.coverage_class = 0; 403 rdev->wiphy.coverage_class = 0;
396 404
405 rdev->wiphy.max_num_csa_counters = 1;
406
397 return &rdev->wiphy; 407 return &rdev->wiphy;
398} 408}
399EXPORT_SYMBOL(wiphy_new); 409EXPORT_SYMBOL(wiphy_new);
@@ -690,7 +700,7 @@ void wiphy_unregister(struct wiphy *wiphy)
690 rtnl_lock(); 700 rtnl_lock();
691 rdev->wiphy.registered = false; 701 rdev->wiphy.registered = false;
692 702
693 BUG_ON(!list_empty(&rdev->wdev_list)); 703 WARN_ON(!list_empty(&rdev->wdev_list));
694 704
695 /* 705 /*
696 * First remove the hardware from everywhere, this makes 706 * First remove the hardware from everywhere, this makes
@@ -792,23 +802,23 @@ void cfg80211_update_iface_num(struct cfg80211_registered_device *rdev,
792 rdev->num_running_monitor_ifaces += num; 802 rdev->num_running_monitor_ifaces += num;
793} 803}
794 804
795void cfg80211_leave(struct cfg80211_registered_device *rdev, 805void __cfg80211_leave(struct cfg80211_registered_device *rdev,
796 struct wireless_dev *wdev) 806 struct wireless_dev *wdev)
797{ 807{
798 struct net_device *dev = wdev->netdev; 808 struct net_device *dev = wdev->netdev;
799 809
800 ASSERT_RTNL(); 810 ASSERT_RTNL();
811 ASSERT_WDEV_LOCK(wdev);
801 812
802 switch (wdev->iftype) { 813 switch (wdev->iftype) {
803 case NL80211_IFTYPE_ADHOC: 814 case NL80211_IFTYPE_ADHOC:
804 cfg80211_leave_ibss(rdev, dev, true); 815 __cfg80211_leave_ibss(rdev, dev, true);
805 break; 816 break;
806 case NL80211_IFTYPE_P2P_CLIENT: 817 case NL80211_IFTYPE_P2P_CLIENT:
807 case NL80211_IFTYPE_STATION: 818 case NL80211_IFTYPE_STATION:
808 if (rdev->sched_scan_req && dev == rdev->sched_scan_req->dev) 819 if (rdev->sched_scan_req && dev == rdev->sched_scan_req->dev)
809 __cfg80211_stop_sched_scan(rdev, false); 820 __cfg80211_stop_sched_scan(rdev, false);
810 821
811 wdev_lock(wdev);
812#ifdef CONFIG_CFG80211_WEXT 822#ifdef CONFIG_CFG80211_WEXT
813 kfree(wdev->wext.ie); 823 kfree(wdev->wext.ie);
814 wdev->wext.ie = NULL; 824 wdev->wext.ie = NULL;
@@ -817,20 +827,49 @@ void cfg80211_leave(struct cfg80211_registered_device *rdev,
817#endif 827#endif
818 cfg80211_disconnect(rdev, dev, 828 cfg80211_disconnect(rdev, dev,
819 WLAN_REASON_DEAUTH_LEAVING, true); 829 WLAN_REASON_DEAUTH_LEAVING, true);
820 wdev_unlock(wdev);
821 break; 830 break;
822 case NL80211_IFTYPE_MESH_POINT: 831 case NL80211_IFTYPE_MESH_POINT:
823 cfg80211_leave_mesh(rdev, dev); 832 __cfg80211_leave_mesh(rdev, dev);
824 break; 833 break;
825 case NL80211_IFTYPE_AP: 834 case NL80211_IFTYPE_AP:
826 case NL80211_IFTYPE_P2P_GO: 835 case NL80211_IFTYPE_P2P_GO:
827 cfg80211_stop_ap(rdev, dev, true); 836 __cfg80211_stop_ap(rdev, dev, true);
828 break; 837 break;
829 default: 838 default:
830 break; 839 break;
831 } 840 }
832} 841}
833 842
843void cfg80211_leave(struct cfg80211_registered_device *rdev,
844 struct wireless_dev *wdev)
845{
846 wdev_lock(wdev);
847 __cfg80211_leave(rdev, wdev);
848 wdev_unlock(wdev);
849}
850
851void cfg80211_stop_iface(struct wiphy *wiphy, struct wireless_dev *wdev,
852 gfp_t gfp)
853{
854 struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy);
855 struct cfg80211_event *ev;
856 unsigned long flags;
857
858 trace_cfg80211_stop_iface(wiphy, wdev);
859
860 ev = kzalloc(sizeof(*ev), gfp);
861 if (!ev)
862 return;
863
864 ev->type = EVENT_STOPPED;
865
866 spin_lock_irqsave(&wdev->event_lock, flags);
867 list_add_tail(&ev->list, &wdev->event_list);
868 spin_unlock_irqrestore(&wdev->event_lock, flags);
869 queue_work(cfg80211_wq, &rdev->event_work);
870}
871EXPORT_SYMBOL(cfg80211_stop_iface);
872
834static int cfg80211_netdev_notifier_call(struct notifier_block *nb, 873static int cfg80211_netdev_notifier_call(struct notifier_block *nb,
835 unsigned long state, void *ptr) 874 unsigned long state, void *ptr)
836{ 875{
diff --git a/net/wireless/core.h b/net/wireless/core.h
index 681b8fa4355b..e9afbf10e756 100644
--- a/net/wireless/core.h
+++ b/net/wireless/core.h
@@ -185,6 +185,7 @@ enum cfg80211_event_type {
185 EVENT_ROAMED, 185 EVENT_ROAMED,
186 EVENT_DISCONNECTED, 186 EVENT_DISCONNECTED,
187 EVENT_IBSS_JOINED, 187 EVENT_IBSS_JOINED,
188 EVENT_STOPPED,
188}; 189};
189 190
190struct cfg80211_event { 191struct cfg80211_event {
@@ -281,6 +282,8 @@ int cfg80211_join_mesh(struct cfg80211_registered_device *rdev,
281 struct net_device *dev, 282 struct net_device *dev,
282 struct mesh_setup *setup, 283 struct mesh_setup *setup,
283 const struct mesh_config *conf); 284 const struct mesh_config *conf);
285int __cfg80211_leave_mesh(struct cfg80211_registered_device *rdev,
286 struct net_device *dev);
284int cfg80211_leave_mesh(struct cfg80211_registered_device *rdev, 287int cfg80211_leave_mesh(struct cfg80211_registered_device *rdev,
285 struct net_device *dev); 288 struct net_device *dev);
286int cfg80211_set_mesh_channel(struct cfg80211_registered_device *rdev, 289int cfg80211_set_mesh_channel(struct cfg80211_registered_device *rdev,
@@ -288,6 +291,8 @@ int cfg80211_set_mesh_channel(struct cfg80211_registered_device *rdev,
288 struct cfg80211_chan_def *chandef); 291 struct cfg80211_chan_def *chandef);
289 292
290/* AP */ 293/* AP */
294int __cfg80211_stop_ap(struct cfg80211_registered_device *rdev,
295 struct net_device *dev, bool notify);
291int cfg80211_stop_ap(struct cfg80211_registered_device *rdev, 296int cfg80211_stop_ap(struct cfg80211_registered_device *rdev,
292 struct net_device *dev, bool notify); 297 struct net_device *dev, bool notify);
293 298
@@ -441,6 +446,8 @@ int cfg80211_validate_beacon_int(struct cfg80211_registered_device *rdev,
441void cfg80211_update_iface_num(struct cfg80211_registered_device *rdev, 446void cfg80211_update_iface_num(struct cfg80211_registered_device *rdev,
442 enum nl80211_iftype iftype, int num); 447 enum nl80211_iftype iftype, int num);
443 448
449void __cfg80211_leave(struct cfg80211_registered_device *rdev,
450 struct wireless_dev *wdev);
444void cfg80211_leave(struct cfg80211_registered_device *rdev, 451void cfg80211_leave(struct cfg80211_registered_device *rdev,
445 struct wireless_dev *wdev); 452 struct wireless_dev *wdev);
446 453
diff --git a/net/wireless/ibss.c b/net/wireless/ibss.c
index 6b50588b709f..8f345da3ea5f 100644
--- a/net/wireless/ibss.c
+++ b/net/wireless/ibss.c
@@ -420,8 +420,8 @@ int cfg80211_ibss_wext_siwessid(struct net_device *dev,
420 if (len > 0 && ssid[len - 1] == '\0') 420 if (len > 0 && ssid[len - 1] == '\0')
421 len--; 421 len--;
422 422
423 memcpy(wdev->ssid, ssid, len);
423 wdev->wext.ibss.ssid = wdev->ssid; 424 wdev->wext.ibss.ssid = wdev->ssid;
424 memcpy(wdev->wext.ibss.ssid, ssid, len);
425 wdev->wext.ibss.ssid_len = len; 425 wdev->wext.ibss.ssid_len = len;
426 426
427 wdev_lock(wdev); 427 wdev_lock(wdev);
diff --git a/net/wireless/mesh.c b/net/wireless/mesh.c
index 3ddfb7cd335e..092300b30c37 100644
--- a/net/wireless/mesh.c
+++ b/net/wireless/mesh.c
@@ -238,8 +238,8 @@ int cfg80211_set_mesh_channel(struct cfg80211_registered_device *rdev,
238 return 0; 238 return 0;
239} 239}
240 240
241static int __cfg80211_leave_mesh(struct cfg80211_registered_device *rdev, 241int __cfg80211_leave_mesh(struct cfg80211_registered_device *rdev,
242 struct net_device *dev) 242 struct net_device *dev)
243{ 243{
244 struct wireless_dev *wdev = dev->ieee80211_ptr; 244 struct wireless_dev *wdev = dev->ieee80211_ptr;
245 int err; 245 int err;
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
index 0f1b18f209d6..62bdb1adaa4d 100644
--- a/net/wireless/nl80211.c
+++ b/net/wireless/nl80211.c
@@ -371,8 +371,8 @@ static const struct nla_policy nl80211_policy[NL80211_ATTR_MAX+1] = {
371 [NL80211_ATTR_CH_SWITCH_COUNT] = { .type = NLA_U32 }, 371 [NL80211_ATTR_CH_SWITCH_COUNT] = { .type = NLA_U32 },
372 [NL80211_ATTR_CH_SWITCH_BLOCK_TX] = { .type = NLA_FLAG }, 372 [NL80211_ATTR_CH_SWITCH_BLOCK_TX] = { .type = NLA_FLAG },
373 [NL80211_ATTR_CSA_IES] = { .type = NLA_NESTED }, 373 [NL80211_ATTR_CSA_IES] = { .type = NLA_NESTED },
374 [NL80211_ATTR_CSA_C_OFF_BEACON] = { .type = NLA_U16 }, 374 [NL80211_ATTR_CSA_C_OFF_BEACON] = { .type = NLA_BINARY },
375 [NL80211_ATTR_CSA_C_OFF_PRESP] = { .type = NLA_U16 }, 375 [NL80211_ATTR_CSA_C_OFF_PRESP] = { .type = NLA_BINARY },
376 [NL80211_ATTR_STA_SUPPORTED_CHANNELS] = { .type = NLA_BINARY }, 376 [NL80211_ATTR_STA_SUPPORTED_CHANNELS] = { .type = NLA_BINARY },
377 [NL80211_ATTR_STA_SUPPORTED_OPER_CLASSES] = { .type = NLA_BINARY }, 377 [NL80211_ATTR_STA_SUPPORTED_OPER_CLASSES] = { .type = NLA_BINARY },
378 [NL80211_ATTR_HANDLE_DFS] = { .type = NLA_FLAG }, 378 [NL80211_ATTR_HANDLE_DFS] = { .type = NLA_FLAG },
@@ -386,6 +386,7 @@ static const struct nla_policy nl80211_policy[NL80211_ATTR_MAX+1] = {
386 [NL80211_ATTR_WIPHY_FREQ_HINT] = { .type = NLA_U32 }, 386 [NL80211_ATTR_WIPHY_FREQ_HINT] = { .type = NLA_U32 },
387 [NL80211_ATTR_TDLS_PEER_CAPABILITY] = { .type = NLA_U32 }, 387 [NL80211_ATTR_TDLS_PEER_CAPABILITY] = { .type = NLA_U32 },
388 [NL80211_ATTR_IFACE_SOCKET_OWNER] = { .type = NLA_FLAG }, 388 [NL80211_ATTR_IFACE_SOCKET_OWNER] = { .type = NLA_FLAG },
389 [NL80211_ATTR_CSA_C_OFFSETS_TX] = { .type = NLA_BINARY },
389}; 390};
390 391
391/* policy for the key attributes */ 392/* policy for the key attributes */
@@ -970,8 +971,10 @@ static int nl80211_put_iface_combinations(struct wiphy *wiphy,
970 c->max_interfaces)) 971 c->max_interfaces))
971 goto nla_put_failure; 972 goto nla_put_failure;
972 if (large && 973 if (large &&
973 nla_put_u32(msg, NL80211_IFACE_COMB_RADAR_DETECT_WIDTHS, 974 (nla_put_u32(msg, NL80211_IFACE_COMB_RADAR_DETECT_WIDTHS,
974 c->radar_detect_widths)) 975 c->radar_detect_widths) ||
976 nla_put_u32(msg, NL80211_IFACE_COMB_RADAR_DETECT_REGIONS,
977 c->radar_detect_regions)))
975 goto nla_put_failure; 978 goto nla_put_failure;
976 979
977 nla_nest_end(msg, nl_combi); 980 nla_nest_end(msg, nl_combi);
@@ -1667,6 +1670,13 @@ static int nl80211_send_wiphy(struct cfg80211_registered_device *rdev,
1667 } 1670 }
1668 nla_nest_end(msg, nested); 1671 nla_nest_end(msg, nested);
1669 } 1672 }
1673 state->split_start++;
1674 break;
1675 case 12:
1676 if (rdev->wiphy.flags & WIPHY_FLAG_HAS_CHANNEL_SWITCH &&
1677 nla_put_u8(msg, NL80211_ATTR_MAX_CSA_COUNTERS,
1678 rdev->wiphy.max_num_csa_counters))
1679 goto nla_put_failure;
1670 1680
1671 /* done */ 1681 /* done */
1672 state->split_start = 0; 1682 state->split_start = 0;
@@ -3640,6 +3650,10 @@ static int nl80211_send_station(struct sk_buff *msg, u32 portid, u32 seq,
3640 nla_put_u32(msg, NL80211_STA_INFO_TX_FAILED, 3650 nla_put_u32(msg, NL80211_STA_INFO_TX_FAILED,
3641 sinfo->tx_failed)) 3651 sinfo->tx_failed))
3642 goto nla_put_failure; 3652 goto nla_put_failure;
3653 if ((sinfo->filled & STATION_INFO_EXPECTED_THROUGHPUT) &&
3654 nla_put_u32(msg, NL80211_STA_INFO_EXPECTED_THROUGHPUT,
3655 sinfo->expected_throughput))
3656 goto nla_put_failure;
3643 if ((sinfo->filled & STATION_INFO_BEACON_LOSS_COUNT) && 3657 if ((sinfo->filled & STATION_INFO_BEACON_LOSS_COUNT) &&
3644 nla_put_u32(msg, NL80211_STA_INFO_BEACON_LOSS, 3658 nla_put_u32(msg, NL80211_STA_INFO_BEACON_LOSS,
3645 sinfo->beacon_loss_count)) 3659 sinfo->beacon_loss_count))
@@ -5820,7 +5834,7 @@ static int nl80211_start_radar_detection(struct sk_buff *skb,
5820 return -EBUSY; 5834 return -EBUSY;
5821 5835
5822 err = cfg80211_chandef_dfs_required(wdev->wiphy, &chandef, 5836 err = cfg80211_chandef_dfs_required(wdev->wiphy, &chandef,
5823 NL80211_IFTYPE_UNSPECIFIED); 5837 wdev->iftype);
5824 if (err < 0) 5838 if (err < 0)
5825 return err; 5839 return err;
5826 5840
@@ -5861,6 +5875,7 @@ static int nl80211_channel_switch(struct sk_buff *skb, struct genl_info *info)
5861 u8 radar_detect_width = 0; 5875 u8 radar_detect_width = 0;
5862 int err; 5876 int err;
5863 bool need_new_beacon = false; 5877 bool need_new_beacon = false;
5878 int len, i;
5864 5879
5865 if (!rdev->ops->channel_switch || 5880 if (!rdev->ops->channel_switch ||
5866 !(rdev->wiphy.flags & WIPHY_FLAG_HAS_CHANNEL_SWITCH)) 5881 !(rdev->wiphy.flags & WIPHY_FLAG_HAS_CHANNEL_SWITCH))
@@ -5919,26 +5934,55 @@ static int nl80211_channel_switch(struct sk_buff *skb, struct genl_info *info)
5919 if (!csa_attrs[NL80211_ATTR_CSA_C_OFF_BEACON]) 5934 if (!csa_attrs[NL80211_ATTR_CSA_C_OFF_BEACON])
5920 return -EINVAL; 5935 return -EINVAL;
5921 5936
5922 params.counter_offset_beacon = 5937 len = nla_len(csa_attrs[NL80211_ATTR_CSA_C_OFF_BEACON]);
5923 nla_get_u16(csa_attrs[NL80211_ATTR_CSA_C_OFF_BEACON]); 5938 if (!len || (len % sizeof(u16)))
5924 if (params.counter_offset_beacon >= params.beacon_csa.tail_len)
5925 return -EINVAL; 5939 return -EINVAL;
5926 5940
5927 /* sanity check - counters should be the same */ 5941 params.n_counter_offsets_beacon = len / sizeof(u16);
5928 if (params.beacon_csa.tail[params.counter_offset_beacon] != 5942 if (rdev->wiphy.max_num_csa_counters &&
5929 params.count) 5943 (params.n_counter_offsets_beacon >
5944 rdev->wiphy.max_num_csa_counters))
5930 return -EINVAL; 5945 return -EINVAL;
5931 5946
5947 params.counter_offsets_beacon =
5948 nla_data(csa_attrs[NL80211_ATTR_CSA_C_OFF_BEACON]);
5949
5950 /* sanity checks - counters should fit and be the same */
5951 for (i = 0; i < params.n_counter_offsets_beacon; i++) {
5952 u16 offset = params.counter_offsets_beacon[i];
5953
5954 if (offset >= params.beacon_csa.tail_len)
5955 return -EINVAL;
5956
5957 if (params.beacon_csa.tail[offset] != params.count)
5958 return -EINVAL;
5959 }
5960
5932 if (csa_attrs[NL80211_ATTR_CSA_C_OFF_PRESP]) { 5961 if (csa_attrs[NL80211_ATTR_CSA_C_OFF_PRESP]) {
5933 params.counter_offset_presp = 5962 len = nla_len(csa_attrs[NL80211_ATTR_CSA_C_OFF_PRESP]);
5934 nla_get_u16(csa_attrs[NL80211_ATTR_CSA_C_OFF_PRESP]); 5963 if (!len || (len % sizeof(u16)))
5935 if (params.counter_offset_presp >=
5936 params.beacon_csa.probe_resp_len)
5937 return -EINVAL; 5964 return -EINVAL;
5938 5965
5939 if (params.beacon_csa.probe_resp[params.counter_offset_presp] != 5966 params.n_counter_offsets_presp = len / sizeof(u16);
5940 params.count) 5967 if (rdev->wiphy.max_num_csa_counters &&
5968 (params.n_counter_offsets_beacon >
5969 rdev->wiphy.max_num_csa_counters))
5941 return -EINVAL; 5970 return -EINVAL;
5971
5972 params.counter_offsets_presp =
5973 nla_data(csa_attrs[NL80211_ATTR_CSA_C_OFF_PRESP]);
5974
5975 /* sanity checks - counters should fit and be the same */
5976 for (i = 0; i < params.n_counter_offsets_presp; i++) {
5977 u16 offset = params.counter_offsets_presp[i];
5978
5979 if (offset >= params.beacon_csa.probe_resp_len)
5980 return -EINVAL;
5981
5982 if (params.beacon_csa.probe_resp[offset] !=
5983 params.count)
5984 return -EINVAL;
5985 }
5942 } 5986 }
5943 5987
5944skip_beacons: 5988skip_beacons:
@@ -7784,6 +7828,27 @@ static int nl80211_tx_mgmt(struct sk_buff *skb, struct genl_info *info)
7784 if (!chandef.chan && params.offchan) 7828 if (!chandef.chan && params.offchan)
7785 return -EINVAL; 7829 return -EINVAL;
7786 7830
7831 params.buf = nla_data(info->attrs[NL80211_ATTR_FRAME]);
7832 params.len = nla_len(info->attrs[NL80211_ATTR_FRAME]);
7833
7834 if (info->attrs[NL80211_ATTR_CSA_C_OFFSETS_TX]) {
7835 int len = nla_len(info->attrs[NL80211_ATTR_CSA_C_OFFSETS_TX]);
7836 int i;
7837
7838 if (len % sizeof(u16))
7839 return -EINVAL;
7840
7841 params.n_csa_offsets = len / sizeof(u16);
7842 params.csa_offsets =
7843 nla_data(info->attrs[NL80211_ATTR_CSA_C_OFFSETS_TX]);
7844
7845 /* check that all the offsets fit the frame */
7846 for (i = 0; i < params.n_csa_offsets; i++) {
7847 if (params.csa_offsets[i] >= params.len)
7848 return -EINVAL;
7849 }
7850 }
7851
7787 if (!params.dont_wait_for_ack) { 7852 if (!params.dont_wait_for_ack) {
7788 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 7853 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7789 if (!msg) 7854 if (!msg)
@@ -7797,8 +7862,6 @@ static int nl80211_tx_mgmt(struct sk_buff *skb, struct genl_info *info)
7797 } 7862 }
7798 } 7863 }
7799 7864
7800 params.buf = nla_data(info->attrs[NL80211_ATTR_FRAME]);
7801 params.len = nla_len(info->attrs[NL80211_ATTR_FRAME]);
7802 params.chan = chandef.chan; 7865 params.chan = chandef.chan;
7803 err = cfg80211_mlme_mgmt_tx(rdev, wdev, &params, &cookie); 7866 err = cfg80211_mlme_mgmt_tx(rdev, wdev, &params, &cookie);
7804 if (err) 7867 if (err)
@@ -8495,6 +8558,8 @@ static int nl80211_set_wowlan(struct sk_buff *skb, struct genl_info *info)
8495 8558
8496 nla_for_each_nested(pat, tb[NL80211_WOWLAN_TRIG_PKT_PATTERN], 8559 nla_for_each_nested(pat, tb[NL80211_WOWLAN_TRIG_PKT_PATTERN],
8497 rem) { 8560 rem) {
8561 u8 *mask_pat;
8562
8498 nla_parse(pat_tb, MAX_NL80211_PKTPAT, nla_data(pat), 8563 nla_parse(pat_tb, MAX_NL80211_PKTPAT, nla_data(pat),
8499 nla_len(pat), NULL); 8564 nla_len(pat), NULL);
8500 err = -EINVAL; 8565 err = -EINVAL;
@@ -8518,19 +8583,18 @@ static int nl80211_set_wowlan(struct sk_buff *skb, struct genl_info *info)
8518 goto error; 8583 goto error;
8519 new_triggers.patterns[i].pkt_offset = pkt_offset; 8584 new_triggers.patterns[i].pkt_offset = pkt_offset;
8520 8585
8521 new_triggers.patterns[i].mask = 8586 mask_pat = kmalloc(mask_len + pat_len, GFP_KERNEL);
8522 kmalloc(mask_len + pat_len, GFP_KERNEL); 8587 if (!mask_pat) {
8523 if (!new_triggers.patterns[i].mask) {
8524 err = -ENOMEM; 8588 err = -ENOMEM;
8525 goto error; 8589 goto error;
8526 } 8590 }
8527 new_triggers.patterns[i].pattern = 8591 new_triggers.patterns[i].mask = mask_pat;
8528 new_triggers.patterns[i].mask + mask_len; 8592 memcpy(mask_pat, nla_data(pat_tb[NL80211_PKTPAT_MASK]),
8529 memcpy(new_triggers.patterns[i].mask,
8530 nla_data(pat_tb[NL80211_PKTPAT_MASK]),
8531 mask_len); 8593 mask_len);
8594 mask_pat += mask_len;
8595 new_triggers.patterns[i].pattern = mask_pat;
8532 new_triggers.patterns[i].pattern_len = pat_len; 8596 new_triggers.patterns[i].pattern_len = pat_len;
8533 memcpy(new_triggers.patterns[i].pattern, 8597 memcpy(mask_pat,
8534 nla_data(pat_tb[NL80211_PKTPAT_PATTERN]), 8598 nla_data(pat_tb[NL80211_PKTPAT_PATTERN]),
8535 pat_len); 8599 pat_len);
8536 i++; 8600 i++;
@@ -8722,6 +8786,8 @@ static int nl80211_parse_coalesce_rule(struct cfg80211_registered_device *rdev,
8722 8786
8723 nla_for_each_nested(pat, tb[NL80211_ATTR_COALESCE_RULE_PKT_PATTERN], 8787 nla_for_each_nested(pat, tb[NL80211_ATTR_COALESCE_RULE_PKT_PATTERN],
8724 rem) { 8788 rem) {
8789 u8 *mask_pat;
8790
8725 nla_parse(pat_tb, MAX_NL80211_PKTPAT, nla_data(pat), 8791 nla_parse(pat_tb, MAX_NL80211_PKTPAT, nla_data(pat),
8726 nla_len(pat), NULL); 8792 nla_len(pat), NULL);
8727 if (!pat_tb[NL80211_PKTPAT_MASK] || 8793 if (!pat_tb[NL80211_PKTPAT_MASK] ||
@@ -8743,17 +8809,19 @@ static int nl80211_parse_coalesce_rule(struct cfg80211_registered_device *rdev,
8743 return -EINVAL; 8809 return -EINVAL;
8744 new_rule->patterns[i].pkt_offset = pkt_offset; 8810 new_rule->patterns[i].pkt_offset = pkt_offset;
8745 8811
8746 new_rule->patterns[i].mask = 8812 mask_pat = kmalloc(mask_len + pat_len, GFP_KERNEL);
8747 kmalloc(mask_len + pat_len, GFP_KERNEL); 8813 if (!mask_pat)
8748 if (!new_rule->patterns[i].mask)
8749 return -ENOMEM; 8814 return -ENOMEM;
8750 new_rule->patterns[i].pattern = 8815
8751 new_rule->patterns[i].mask + mask_len; 8816 new_rule->patterns[i].mask = mask_pat;
8752 memcpy(new_rule->patterns[i].mask, 8817 memcpy(mask_pat, nla_data(pat_tb[NL80211_PKTPAT_MASK]),
8753 nla_data(pat_tb[NL80211_PKTPAT_MASK]), mask_len); 8818 mask_len);
8819
8820 mask_pat += mask_len;
8821 new_rule->patterns[i].pattern = mask_pat;
8754 new_rule->patterns[i].pattern_len = pat_len; 8822 new_rule->patterns[i].pattern_len = pat_len;
8755 memcpy(new_rule->patterns[i].pattern, 8823 memcpy(mask_pat, nla_data(pat_tb[NL80211_PKTPAT_PATTERN]),
8756 nla_data(pat_tb[NL80211_PKTPAT_PATTERN]), pat_len); 8824 pat_len);
8757 i++; 8825 i++;
8758 } 8826 }
8759 8827
diff --git a/net/wireless/rdev-ops.h b/net/wireless/rdev-ops.h
index 00cdf73ba6c4..d95bbe348138 100644
--- a/net/wireless/rdev-ops.h
+++ b/net/wireless/rdev-ops.h
@@ -199,7 +199,7 @@ static inline int rdev_change_station(struct cfg80211_registered_device *rdev,
199} 199}
200 200
201static inline int rdev_get_station(struct cfg80211_registered_device *rdev, 201static inline int rdev_get_station(struct cfg80211_registered_device *rdev,
202 struct net_device *dev, u8 *mac, 202 struct net_device *dev, const u8 *mac,
203 struct station_info *sinfo) 203 struct station_info *sinfo)
204{ 204{
205 int ret; 205 int ret;
diff --git a/net/wireless/reg.c b/net/wireless/reg.c
index e78f532aaa5b..558b0e3a02d8 100644
--- a/net/wireless/reg.c
+++ b/net/wireless/reg.c
@@ -1876,7 +1876,8 @@ static void reg_process_hint(struct regulatory_request *reg_request)
1876 case NL80211_REGDOM_SET_BY_USER: 1876 case NL80211_REGDOM_SET_BY_USER:
1877 treatment = reg_process_hint_user(reg_request); 1877 treatment = reg_process_hint_user(reg_request);
1878 if (treatment == REG_REQ_IGNORE || 1878 if (treatment == REG_REQ_IGNORE ||
1879 treatment == REG_REQ_ALREADY_SET) 1879 treatment == REG_REQ_ALREADY_SET ||
1880 treatment == REG_REQ_USER_HINT_HANDLED)
1880 return; 1881 return;
1881 queue_delayed_work(system_power_efficient_wq, 1882 queue_delayed_work(system_power_efficient_wq,
1882 &reg_timeout, msecs_to_jiffies(3142)); 1883 &reg_timeout, msecs_to_jiffies(3142));
diff --git a/net/wireless/scan.c b/net/wireless/scan.c
index e7329bb6a323..0798c62e6085 100644
--- a/net/wireless/scan.c
+++ b/net/wireless/scan.c
@@ -891,6 +891,7 @@ cfg80211_inform_bss_width(struct wiphy *wiphy,
891 struct cfg80211_bss_ies *ies; 891 struct cfg80211_bss_ies *ies;
892 struct ieee80211_channel *channel; 892 struct ieee80211_channel *channel;
893 struct cfg80211_internal_bss tmp = {}, *res; 893 struct cfg80211_internal_bss tmp = {}, *res;
894 bool signal_valid;
894 895
895 if (WARN_ON(!wiphy)) 896 if (WARN_ON(!wiphy))
896 return NULL; 897 return NULL;
@@ -927,8 +928,9 @@ cfg80211_inform_bss_width(struct wiphy *wiphy,
927 rcu_assign_pointer(tmp.pub.beacon_ies, ies); 928 rcu_assign_pointer(tmp.pub.beacon_ies, ies);
928 rcu_assign_pointer(tmp.pub.ies, ies); 929 rcu_assign_pointer(tmp.pub.ies, ies);
929 930
930 res = cfg80211_bss_update(wiphy_to_rdev(wiphy), &tmp, 931 signal_valid = abs(rx_channel->center_freq - channel->center_freq) <=
931 rx_channel == channel); 932 wiphy->max_adj_channel_rssi_comp;
933 res = cfg80211_bss_update(wiphy_to_rdev(wiphy), &tmp, signal_valid);
932 if (!res) 934 if (!res)
933 return NULL; 935 return NULL;
934 936
@@ -952,6 +954,7 @@ cfg80211_inform_bss_width_frame(struct wiphy *wiphy,
952 struct cfg80211_internal_bss tmp = {}, *res; 954 struct cfg80211_internal_bss tmp = {}, *res;
953 struct cfg80211_bss_ies *ies; 955 struct cfg80211_bss_ies *ies;
954 struct ieee80211_channel *channel; 956 struct ieee80211_channel *channel;
957 bool signal_valid;
955 size_t ielen = len - offsetof(struct ieee80211_mgmt, 958 size_t ielen = len - offsetof(struct ieee80211_mgmt,
956 u.probe_resp.variable); 959 u.probe_resp.variable);
957 960
@@ -999,8 +1002,9 @@ cfg80211_inform_bss_width_frame(struct wiphy *wiphy,
999 tmp.pub.beacon_interval = le16_to_cpu(mgmt->u.probe_resp.beacon_int); 1002 tmp.pub.beacon_interval = le16_to_cpu(mgmt->u.probe_resp.beacon_int);
1000 tmp.pub.capability = le16_to_cpu(mgmt->u.probe_resp.capab_info); 1003 tmp.pub.capability = le16_to_cpu(mgmt->u.probe_resp.capab_info);
1001 1004
1002 res = cfg80211_bss_update(wiphy_to_rdev(wiphy), &tmp, 1005 signal_valid = abs(rx_channel->center_freq - channel->center_freq) <=
1003 rx_channel == channel); 1006 wiphy->max_adj_channel_rssi_comp;
1007 res = cfg80211_bss_update(wiphy_to_rdev(wiphy), &tmp, signal_valid);
1004 if (!res) 1008 if (!res)
1005 return NULL; 1009 return NULL;
1006 1010
diff --git a/net/wireless/sme.c b/net/wireless/sme.c
index 0c0844b585d1..8bbeeb302216 100644
--- a/net/wireless/sme.c
+++ b/net/wireless/sme.c
@@ -149,7 +149,8 @@ static int cfg80211_conn_do_work(struct wireless_dev *wdev)
149 case CFG80211_CONN_SCAN_AGAIN: 149 case CFG80211_CONN_SCAN_AGAIN:
150 return cfg80211_conn_scan(wdev); 150 return cfg80211_conn_scan(wdev);
151 case CFG80211_CONN_AUTHENTICATE_NEXT: 151 case CFG80211_CONN_AUTHENTICATE_NEXT:
152 BUG_ON(!rdev->ops->auth); 152 if (WARN_ON(!rdev->ops->auth))
153 return -EOPNOTSUPP;
153 wdev->conn->state = CFG80211_CONN_AUTHENTICATING; 154 wdev->conn->state = CFG80211_CONN_AUTHENTICATING;
154 return cfg80211_mlme_auth(rdev, wdev->netdev, 155 return cfg80211_mlme_auth(rdev, wdev->netdev,
155 params->channel, params->auth_type, 156 params->channel, params->auth_type,
@@ -161,7 +162,8 @@ static int cfg80211_conn_do_work(struct wireless_dev *wdev)
161 case CFG80211_CONN_AUTH_FAILED: 162 case CFG80211_CONN_AUTH_FAILED:
162 return -ENOTCONN; 163 return -ENOTCONN;
163 case CFG80211_CONN_ASSOCIATE_NEXT: 164 case CFG80211_CONN_ASSOCIATE_NEXT:
164 BUG_ON(!rdev->ops->assoc); 165 if (WARN_ON(!rdev->ops->assoc))
166 return -EOPNOTSUPP;
165 wdev->conn->state = CFG80211_CONN_ASSOCIATING; 167 wdev->conn->state = CFG80211_CONN_ASSOCIATING;
166 if (wdev->conn->prev_bssid_valid) 168 if (wdev->conn->prev_bssid_valid)
167 req.prev_bssid = wdev->conn->prev_bssid; 169 req.prev_bssid = wdev->conn->prev_bssid;
@@ -877,7 +879,7 @@ void __cfg80211_disconnected(struct net_device *dev, const u8 *ie,
877} 879}
878 880
879void cfg80211_disconnected(struct net_device *dev, u16 reason, 881void cfg80211_disconnected(struct net_device *dev, u16 reason,
880 u8 *ie, size_t ie_len, gfp_t gfp) 882 const u8 *ie, size_t ie_len, gfp_t gfp)
881{ 883{
882 struct wireless_dev *wdev = dev->ieee80211_ptr; 884 struct wireless_dev *wdev = dev->ieee80211_ptr;
883 struct cfg80211_registered_device *rdev = wiphy_to_rdev(wdev->wiphy); 885 struct cfg80211_registered_device *rdev = wiphy_to_rdev(wdev->wiphy);
diff --git a/net/wireless/trace.h b/net/wireless/trace.h
index f3c13ff4d04c..560ed77084e9 100644
--- a/net/wireless/trace.h
+++ b/net/wireless/trace.h
@@ -1876,29 +1876,33 @@ TRACE_EVENT(rdev_channel_switch,
1876 WIPHY_ENTRY 1876 WIPHY_ENTRY
1877 NETDEV_ENTRY 1877 NETDEV_ENTRY
1878 CHAN_DEF_ENTRY 1878 CHAN_DEF_ENTRY
1879 __field(u16, counter_offset_beacon)
1880 __field(u16, counter_offset_presp)
1881 __field(bool, radar_required) 1879 __field(bool, radar_required)
1882 __field(bool, block_tx) 1880 __field(bool, block_tx)
1883 __field(u8, count) 1881 __field(u8, count)
1882 __dynamic_array(u16, bcn_ofs, params->n_counter_offsets_beacon)
1883 __dynamic_array(u16, pres_ofs, params->n_counter_offsets_presp)
1884 ), 1884 ),
1885 TP_fast_assign( 1885 TP_fast_assign(
1886 WIPHY_ASSIGN; 1886 WIPHY_ASSIGN;
1887 NETDEV_ASSIGN; 1887 NETDEV_ASSIGN;
1888 CHAN_DEF_ASSIGN(&params->chandef); 1888 CHAN_DEF_ASSIGN(&params->chandef);
1889 __entry->counter_offset_beacon = params->counter_offset_beacon;
1890 __entry->counter_offset_presp = params->counter_offset_presp;
1891 __entry->radar_required = params->radar_required; 1889 __entry->radar_required = params->radar_required;
1892 __entry->block_tx = params->block_tx; 1890 __entry->block_tx = params->block_tx;
1893 __entry->count = params->count; 1891 __entry->count = params->count;
1892 memcpy(__get_dynamic_array(bcn_ofs),
1893 params->counter_offsets_beacon,
1894 params->n_counter_offsets_beacon * sizeof(u16));
1895
1896 /* probe response offsets are optional */
1897 if (params->n_counter_offsets_presp)
1898 memcpy(__get_dynamic_array(pres_ofs),
1899 params->counter_offsets_presp,
1900 params->n_counter_offsets_presp * sizeof(u16));
1894 ), 1901 ),
1895 TP_printk(WIPHY_PR_FMT ", " NETDEV_PR_FMT ", " CHAN_DEF_PR_FMT 1902 TP_printk(WIPHY_PR_FMT ", " NETDEV_PR_FMT ", " CHAN_DEF_PR_FMT
1896 ", block_tx: %d, count: %u, radar_required: %d" 1903 ", block_tx: %d, count: %u, radar_required: %d",
1897 ", counter offsets (beacon/presp): %u/%u",
1898 WIPHY_PR_ARG, NETDEV_PR_ARG, CHAN_DEF_PR_ARG, 1904 WIPHY_PR_ARG, NETDEV_PR_ARG, CHAN_DEF_PR_ARG,
1899 __entry->block_tx, __entry->count, __entry->radar_required, 1905 __entry->block_tx, __entry->count, __entry->radar_required)
1900 __entry->counter_offset_beacon,
1901 __entry->counter_offset_presp)
1902); 1906);
1903 1907
1904TRACE_EVENT(rdev_set_qos_map, 1908TRACE_EVENT(rdev_set_qos_map,
@@ -2636,6 +2640,21 @@ TRACE_EVENT(cfg80211_ft_event,
2636 WIPHY_PR_ARG, NETDEV_PR_ARG, MAC_PR_ARG(target_ap)) 2640 WIPHY_PR_ARG, NETDEV_PR_ARG, MAC_PR_ARG(target_ap))
2637); 2641);
2638 2642
2643TRACE_EVENT(cfg80211_stop_iface,
2644 TP_PROTO(struct wiphy *wiphy, struct wireless_dev *wdev),
2645 TP_ARGS(wiphy, wdev),
2646 TP_STRUCT__entry(
2647 WIPHY_ENTRY
2648 WDEV_ENTRY
2649 ),
2650 TP_fast_assign(
2651 WIPHY_ASSIGN;
2652 WDEV_ASSIGN;
2653 ),
2654 TP_printk(WIPHY_PR_FMT ", " WDEV_PR_FMT,
2655 WIPHY_PR_ARG, WDEV_PR_ARG)
2656);
2657
2639#endif /* !__RDEV_OPS_TRACE || TRACE_HEADER_MULTI_READ */ 2658#endif /* !__RDEV_OPS_TRACE || TRACE_HEADER_MULTI_READ */
2640 2659
2641#undef TRACE_INCLUDE_PATH 2660#undef TRACE_INCLUDE_PATH
diff --git a/net/wireless/util.c b/net/wireless/util.c
index 7c47fa07b276..728f1c0dc70d 100644
--- a/net/wireless/util.c
+++ b/net/wireless/util.c
@@ -476,7 +476,8 @@ int ieee80211_data_to_8023(struct sk_buff *skb, const u8 *addr,
476EXPORT_SYMBOL(ieee80211_data_to_8023); 476EXPORT_SYMBOL(ieee80211_data_to_8023);
477 477
478int ieee80211_data_from_8023(struct sk_buff *skb, const u8 *addr, 478int ieee80211_data_from_8023(struct sk_buff *skb, const u8 *addr,
479 enum nl80211_iftype iftype, u8 *bssid, bool qos) 479 enum nl80211_iftype iftype,
480 const u8 *bssid, bool qos)
480{ 481{
481 struct ieee80211_hdr hdr; 482 struct ieee80211_hdr hdr;
482 u16 hdrlen, ethertype; 483 u16 hdrlen, ethertype;
@@ -839,6 +840,9 @@ void cfg80211_process_wdev_events(struct wireless_dev *wdev)
839 __cfg80211_ibss_joined(wdev->netdev, ev->ij.bssid, 840 __cfg80211_ibss_joined(wdev->netdev, ev->ij.bssid,
840 ev->ij.channel); 841 ev->ij.channel);
841 break; 842 break;
843 case EVENT_STOPPED:
844 __cfg80211_leave(wiphy_to_rdev(wdev->wiphy), wdev);
845 break;
842 } 846 }
843 wdev_unlock(wdev); 847 wdev_unlock(wdev);
844 848
@@ -1271,10 +1275,20 @@ int cfg80211_iter_combinations(struct wiphy *wiphy,
1271 void *data), 1275 void *data),
1272 void *data) 1276 void *data)
1273{ 1277{
1278 const struct ieee80211_regdomain *regdom;
1279 enum nl80211_dfs_regions region = 0;
1274 int i, j, iftype; 1280 int i, j, iftype;
1275 int num_interfaces = 0; 1281 int num_interfaces = 0;
1276 u32 used_iftypes = 0; 1282 u32 used_iftypes = 0;
1277 1283
1284 if (radar_detect) {
1285 rcu_read_lock();
1286 regdom = rcu_dereference(cfg80211_regdomain);
1287 if (regdom)
1288 region = regdom->dfs_region;
1289 rcu_read_unlock();
1290 }
1291
1278 for (iftype = 0; iftype < NUM_NL80211_IFTYPES; iftype++) { 1292 for (iftype = 0; iftype < NUM_NL80211_IFTYPES; iftype++) {
1279 num_interfaces += iftype_num[iftype]; 1293 num_interfaces += iftype_num[iftype];
1280 if (iftype_num[iftype] > 0 && 1294 if (iftype_num[iftype] > 0 &&
@@ -1315,6 +1329,10 @@ int cfg80211_iter_combinations(struct wiphy *wiphy,
1315 if (radar_detect != (c->radar_detect_widths & radar_detect)) 1329 if (radar_detect != (c->radar_detect_widths & radar_detect))
1316 goto cont; 1330 goto cont;
1317 1331
1332 if (radar_detect && c->radar_detect_regions &&
1333 !(c->radar_detect_regions & BIT(region)))
1334 goto cont;
1335
1318 /* Finally check that all iftypes that we're currently 1336 /* Finally check that all iftypes that we're currently
1319 * using are actually part of this combination. If they 1337 * using are actually part of this combination. If they
1320 * aren't then we can't use this combination and have 1338 * aren't then we can't use this combination and have
@@ -1528,6 +1546,24 @@ unsigned int ieee80211_get_num_supported_channels(struct wiphy *wiphy)
1528} 1546}
1529EXPORT_SYMBOL(ieee80211_get_num_supported_channels); 1547EXPORT_SYMBOL(ieee80211_get_num_supported_channels);
1530 1548
1549int cfg80211_get_station(struct net_device *dev, const u8 *mac_addr,
1550 struct station_info *sinfo)
1551{
1552 struct cfg80211_registered_device *rdev;
1553 struct wireless_dev *wdev;
1554
1555 wdev = dev->ieee80211_ptr;
1556 if (!wdev)
1557 return -EOPNOTSUPP;
1558
1559 rdev = wiphy_to_rdev(wdev->wiphy);
1560 if (!rdev->ops->get_station)
1561 return -EOPNOTSUPP;
1562
1563 return rdev_get_station(rdev, dev, mac_addr, sinfo);
1564}
1565EXPORT_SYMBOL(cfg80211_get_station);
1566
1531/* See IEEE 802.1H for LLC/SNAP encapsulation/decapsulation */ 1567/* See IEEE 802.1H for LLC/SNAP encapsulation/decapsulation */
1532/* Ethernet-II snap header (RFC1042 for most EtherTypes) */ 1568/* Ethernet-II snap header (RFC1042 for most EtherTypes) */
1533const unsigned char rfc1042_header[] __aligned(2) = 1569const unsigned char rfc1042_header[] __aligned(2) =