firmware in a bad state (module mwifiex)
I'm running kernel 4.2.0-rc3 with the following patches to the mwifiex driver, thanks to your advice. > Do you have following USB chipset specific fixes included? > http://www.spinics.net/lists/linux-wireless/msg129129.html > http://www.spinics.net/lists/netdev/msg334367.html I've recently noticed that the connection is lost (and the driver too only rebooting makes the card usable again) when I connect to certain websites (github for instance) I've set debugging up with the following command, and attached the output from dmesg. > "echo 0x > /sys/kernel/debug/mwifiex/mlan0/debug_mask" Thanks for your help. Regards, Julien. <6>[0.00] Initializing cgroup subsys cpuset <6>[0.00] Initializing cgroup subsys cpu <6>[0.00] Initializing cgroup subsys cpuacct <5>[0.00] Linux version 4.2.0-rc3 (root@touco) (gcc version 4.9.2 (Ubuntu 4.9.2-10ubuntu13) ) #3 SMP Mon Jul 27 15:27:49 CEST 2015 <6>[0.00] Command line: BOOT_IMAGE=/boot/vmlinuz-4.2.0-rc3 root=UUID=919f00b8-5010-46e1-b2f9-c129e17d5312 ro quiet splash vt.handoff=7 <6>[0.00] KERNEL supported cpus: <6>[0.00] Intel GenuineIntel <6>[0.00] AMD AuthenticAMD <6>[0.00] Centaur CentaurHauls <6>[0.00] x86/fpu: xstate_offset[2]: 0240, xstate_sizes[2]: 0100 <6>[0.00] x86/fpu: Supporting XSAVE feature 0x01: 'x87 floating point registers' <6>[0.00] x86/fpu: Supporting XSAVE feature 0x02: 'SSE registers' <6>[0.00] x86/fpu: Supporting XSAVE feature 0x04: 'AVX registers' <6>[0.00] x86/fpu: Enabled xstate features 0x7, context size is 0x340 bytes, using 'standard' format. <6>[0.00] x86/fpu: Using 'eager' FPU context switches. <6>[0.00] e820: BIOS-provided physical RAM map: <6>[0.00] BIOS-e820: [mem 0x-0x0009dfff] usable <6>[0.00] BIOS-e820: [mem 0x0009e000-0x0009] reserved <6>[0.00] BIOS-e820: [mem 0x0010-0x1fff] usable <6>[0.00] BIOS-e820: [mem 0x2000-0x201f] reserved <6>[0.00] BIOS-e820: [mem 0x2020-0x40003fff] usable <6>[0.00] BIOS-e820: [mem 0x40004000-0x40004fff] reserved <6>[0.00] BIOS-e820: [mem 0x40005000-0xd9202fff] usable <6>[0.00] BIOS-e820: [mem 0xd9203000-0xd9671fff] reserved <6>[0.00] BIOS-e820: [mem 0xd9672000-0xd9681fff] ACPI data <6>[0.00] BIOS-e820: [mem 0xd9682000-0xda24] ACPI NVS <6>[0.00] BIOS-e820: [mem 0xda25-0xda66cfff] reserved <6>[0.00] BIOS-e820: [mem 0xda66d000-0xda6fefff] type 20 <6>[0.00] BIOS-e820: [mem 0xda6ff000-0xda6f] usable <6>[0.00] BIOS-e820: [mem 0xda70-0xda742fff] ACPI NVS <6>[0.00] BIOS-e820: [mem 0xda743000-0xdad54fff] usable <6>[0.00] BIOS-e820: [mem 0xdad55000-0xdaff1fff] reserved <6>[0.00] BIOS-e820: [mem 0xdaff2000-0xdaff] usable <6>[0.00] BIOS-e820: [mem 0xdb80-0xdf9f] reserved <6>[0.00] BIOS-e820: [mem 0xf800-0xfbff] reserved <6>[0.00] BIOS-e820: [mem 0xfec0-0xfec00fff] reserved <6>[0.00] BIOS-e820: [mem 0xfed0-0xfed03fff] reserved <6>[0.00] BIOS-e820: [mem 0xfed1c000-0xfed1] reserved <6>[0.00] BIOS-e820: [mem 0xfee0-0xfee00fff] reserved <6>[0.00] BIOS-e820: [mem 0xff00-0x] reserved <6>[0.00] BIOS-e820: [mem 0x0001-0x00011f5f] usable <6>[0.00] NX (Execute Disable) protection: active <6>[0.00] efi: EFI v2.31 by American Megatrends <6>[0.00] efi: ESRT=0xda5f1618 ACPI=0xd9677000 ACPI 2.0=0xd9677000 SMBIOS=0xda66b198 <6>[0.00] esrt: Reserving ESRT space from 0xda5f1618 to 0xda5f16c8. <6>[0.00] SMBIOS 2.7 present. <7>[0.00] DMI: Microsoft Corporation Surface with Windows 8 Pro/Surface with Windows 8 Pro, BIOS 1.00.0250 01/08/2013 <7>[0.00] e820: update [mem 0x-0x0fff] usable ==> reserved <7>[0.00] e820: remove [mem 0x000a-0x000f] usable <6>[0.00] e820: last_pfn = 0x11f600 max_arch_pfn = 0x4 <7>[0.00] MTRR default type: uncachable <7>[0.00] MTRR fixed ranges enabled: <7>[0.00] 0-9 write-back <7>[0.00] A-F uncachable <7>[0.00] MTRR variable ranges enabled: <7>[0.00] 0 base 0 mask F write-back <7>[0.00] 1 base 1 mask FE000 write-back <7>[0.00] 2 base 0E000 mask FE000 uncachable <7>[0.00] 3 base 0DC00 mask FFC00 uncachable
[PATCH] ath10k: initialize fw_features var
If firmware did not have any feature flags set the var would be left with values found on the stack (i.e. garbage) yielding print string like this: (...) features \xffa6m:^R\xfffbԂ\xffc4^E Fixes: b27bc5a40f91 ("ath10k: dump fw features during probing") Signed-off-by: Michal Kazior --- drivers/net/wireless/ath/ath10k/debug.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/ath10k/debug.c b/drivers/net/wireless/ath/ath10k/debug.c index 1a33bf04b7b7..f7aa1c73b481 100644 --- a/drivers/net/wireless/ath/ath10k/debug.c +++ b/drivers/net/wireless/ath/ath10k/debug.c @@ -124,7 +124,7 @@ EXPORT_SYMBOL(ath10k_info); void ath10k_print_driver_info(struct ath10k *ar) { - char fw_features[128]; + char fw_features[128] = {}; ath10k_core_get_fw_features_str(ar, fw_features, sizeof(fw_features)); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[RFC v1] firmware: add an extensible system data helpers
From: "Luis R. Rodriguez" The firmware API has evolved over the years slowly, as it grows we extend it by adding new routines or at times we extend existing routines with more or less arguments. This doesn't scale well, when new arguments are added to existing routines it means we need to traverse the kernel with a slew of collateral evolutions to adjust old driver users. The firmware API is also now being used for things outside of the scope of what typically would be considered "firmware", an example here is the p54 driver enables users to provide a custom EEPROM through this interface. Another example is optional CPU microcode updates. There are other subsystems which would like to make use of the APIs for similar things but have different requirements and criteria which they'd like to be met for the requested file. If different requirements are needed it would again mean adding more arguments and making a slew of collateral evolutions, or adding yet-another-new-API-call. Instead of extending the existing firmware API even more this provides an new extensible API which can be used to supercede the old firmware API without causing a series of collateral evolutions as requirements grow. This leaves the old firmware API as-is, ignores all consideration for usermode-helpers, labels the new API to reflect its broad use outside of the scope of firmware: system data helpers, and builds on top of the original firmware core code. The new extensible "system data" set of helpers accepts that there really are only two types of requests for accessing system data: a) synchronous requests b) asynchronous requests Both of these requests may have a different set of requirements which must be met. These requirements can simply be passed as a descriptors to each type of request. The descriptor can be extended over time to support different requirements as the kernel evolves. Using the new system data helpers is only necessary if you have requirements outside of what the existing old firmware API accepts. We encourage developers to leave the old API as-is and extend the new descriptors and system data code to provide support for new features. A few simple features added as part of the new set of system data request APIs, other than making the new API easily extensible for the future: - By default the kernel will free the system data file for you after your callbacks are called, you however are allowed to request to that you wish to keep the system data file on the descriptor. This is dealt with by requiring a consumer callback for the system data file. - Allow both asynchronous and synchronous request to specify that system data files are optional. With the old APIs we had added one full API call, request_firmware_direct() just for this purpose -- although it should be noted another of its goal was to also skip the usermode helper. The system data request APIs allow for you to annotate that a system data file is optional for both synchronous or asynchronous requests through the same two basic set of APIs. - Usermode helpers are completely ignored, always - The system data request APIs currently match the old synchronous firmware API calls to refcounted firmware_class module, but it should be easy to add support now to enable also refcounting the caller's module should it be be needed. Likewise the system data request APIs match the old asynchronous firmware API call and refcounts the caller's module. In order to try to help phase out user mode helpers this makes no use of the old user mode helper code *at all*, and if we wish to can easily phase this code out with time then. Signed-off-by: Luis R. Rodriguez --- Although the design and goals behind firmware signing are still being discussed, one thing is clear: we need an extensible firmware API. This patch set then just address the extensibility of the firmware_class and leave firmware signing to be addressed later. In my previous firmware signing patch set I had added firmware signing *first* and later introduced this set of APIs *after* with the idea to let callers be able to override system defaults and provide custom signature requirements. For instance I had considered the possibility of having cfg80211 customize its signing requirements under its own Kconfig option outside of the scope of firmware signing in order to replace CRDA with in-kernel functionality. To support this we'd have to enable callers to customize their firmware signing requirements somehow. Recently its been discussed that perhaps we may want to let all callers from the start to provide a specific a sha256sum of a key which we could then use to vet a signature for. In order to support that we'd need to be able to let callers specify more arguments into the firmware_class API *prior* to adding firmware signing code. Having an extensible firmware API in place first would enable the flexibility to let us decide what requirements we want to put
Re: [PATCH v5] Add new mac80211 driver mwlwifi.
On Tuesday 04 Aug 2015 à 18:11:29 (+), Chor Teck Law wrote: Hi Chor, > mwl8k was a driver for chips few generations older sponsored by > Marvell. We did leverage part of driver framework that is still > applicable. However, for the current development, the firmware API > specs, chip capabilities and bandwidth requirements have changed in > order to handle newer technologies and features. this is a fullmac driver, what differs between them is: - how you boot the device / load firmware - how you send commands to it - datapath from a quick glance at your new driver 1) firmware loading works the same way 2) "hostcmd" are used to communicate with the firmware, of course new commands are needed for newer standards, but a common API could be used for common basic operations 3) rx datapath looks the same (look at struct mwl_rx_desc vs mwl8k_rxd_ap) 4) AMPDU code is copied/pasted from mwl8k driver, even the original comments have not been updated: + /* Defer calling mwl8k_start_stream so that the current > No, we are not treating the submission as dumping! We would not have > responded with effort to meet the requests/feedback if so. We > appreciate and have taken the feedbacks seriously to complete to > patch6. In fact the submission was requested by some community > members who has seen the benefit of its evolvement on openwrt > github, and they would like to see the new driver consolidated into > the wireless mainline. judging from the mwl8k experience (hello, unhappy customer here), mainline is indeed the goal, but after that, nothing. driver & firmware left at version 1, unless customer (me in that case) made an explicit bug report or feature request. > Due to hardware, firmware, specs and requirements change over time, > it is not feasible for us to revisit generations old products or > making sure new changes are backward compatible with it. (If > desired, we welcome the community to take any new useful changes > that are independent of chip rev to other similar branches.) no hardware specs, no firmware source or docs, community can only make blind guesses. also see my answer beyond. > Lastly, I do not think we are creating a precedence with different > generation of drivers supporting different families of chips. these are firmware based chipsets, not hard-wired. having a common driver for two completely different set of chipsets is indeed stupid, and makes it unreadable. but from my POV, your pattern is: build new chipset, obsolete previous chipset, fork current firmware, make uncompatible changes to both firmware & host driver to accomodate new chipset peculiarities. and eventually, if a customer requests a mainline linux driver, then write one... this is what I'd call "dumping" -- Maxime -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v5] Add new mac80211 driver mwlwifi.
On Tuesday 04 Aug 2015 à 20:02:23 (+0300), Kalle Valo wrote: > I haven't looked at the driver myself yet. Do you have any estimates how > much duplication there is? ok the thing is I happen to know a bit about the chipset internals and so it's easy for me to know that having a common driver is do-able. so I may be biased, and I guess someone else should have a quick glance at both driver code. -- Maxime -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 02/37] iwlwifi: mvm: handle RX MPDUs separately
From: Johannes Berg There's no need to forward RX MPDUs to notification wait tests, nor do we need to check them for firmware dump triggers, nor could they be asynchronous. It's thus more efficient to handle them separately, before going into the regular RX handlers. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/ops.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/ops.c b/drivers/net/wireless/iwlwifi/mvm/ops.c index e4fa500..8f896cd 100644 --- a/drivers/net/wireless/iwlwifi/mvm/ops.c +++ b/drivers/net/wireless/iwlwifi/mvm/ops.c @@ -221,7 +221,6 @@ struct iwl_rx_handlers { * called from a worker with mvm->mutex held. */ static const struct iwl_rx_handlers iwl_mvm_rx_handlers[] = { - RX_HANDLER(REPLY_RX_MPDU_CMD, iwl_mvm_rx_rx_mpdu, false), RX_HANDLER(REPLY_RX_PHY_CMD, iwl_mvm_rx_rx_phy_cmd, false), RX_HANDLER(TX_CMD, iwl_mvm_rx_tx_cmd, false), RX_HANDLER(BA_NOTIF, iwl_mvm_rx_ba_notif, false), @@ -716,6 +715,9 @@ static int iwl_mvm_rx_dispatch(struct iwl_op_mode *op_mode, struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode); u8 i; + if (likely(pkt->hdr.cmd == REPLY_RX_MPDU_CMD)) + return iwl_mvm_rx_rx_mpdu(mvm, rxb, cmd); + iwl_mvm_rx_check_trigger(mvm, pkt); /* -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 12/37] iwlwifi: remove command and return value from opmode RX
From: Johannes Berg With the previous patch series, no opmode continues using the command or handler_status (i.e. the return value from the RX) so it can be removed now. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/agn.h | 5 ++--- drivers/net/wireless/iwlwifi/dvm/rx.c| 5 + drivers/net/wireless/iwlwifi/iwl-op-mode.h | 10 -- drivers/net/wireless/iwlwifi/iwl-trans.h | 3 --- drivers/net/wireless/iwlwifi/mvm/ops.c | 13 + drivers/net/wireless/iwlwifi/pcie/internal.h | 2 +- drivers/net/wireless/iwlwifi/pcie/rx.c | 12 +++- drivers/net/wireless/iwlwifi/pcie/tx.c | 5 + 8 files changed, 17 insertions(+), 38 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/dvm/agn.h b/drivers/net/wireless/iwlwifi/dvm/agn.h index f549dc3..101ef31 100644 --- a/drivers/net/wireless/iwlwifi/dvm/agn.h +++ b/drivers/net/wireless/iwlwifi/dvm/agn.h @@ -122,9 +122,8 @@ static inline void iwl_set_calib_hdr(struct iwl_calib_hdr *hdr, u8 cmd) void iwl_down(struct iwl_priv *priv); void iwl_cancel_deferred_work(struct iwl_priv *priv); void iwlagn_prepare_restart(struct iwl_priv *priv); -int __must_check iwl_rx_dispatch(struct iwl_op_mode *op_mode, -struct iwl_rx_cmd_buffer *rxb, -struct iwl_device_cmd *cmd); +void iwl_rx_dispatch(struct iwl_op_mode *op_mode, +struct iwl_rx_cmd_buffer *rxb); bool iwl_check_for_ct_kill(struct iwl_priv *priv); diff --git a/drivers/net/wireless/iwlwifi/dvm/rx.c b/drivers/net/wireless/iwlwifi/dvm/rx.c index ca270a6..c91374f 100644 --- a/drivers/net/wireless/iwlwifi/dvm/rx.c +++ b/drivers/net/wireless/iwlwifi/dvm/rx.c @@ -1073,8 +1073,7 @@ void iwl_setup_rx_handlers(struct iwl_priv *priv) iwlagn_bt_rx_handler_setup(priv); } -int iwl_rx_dispatch(struct iwl_op_mode *op_mode, struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd) +void iwl_rx_dispatch(struct iwl_op_mode *op_mode, struct iwl_rx_cmd_buffer *rxb) { struct iwl_rx_packet *pkt = rxb_addr(rxb); struct iwl_priv *priv = IWL_OP_MODE_GET_DVM(op_mode); @@ -1098,6 +1097,4 @@ int iwl_rx_dispatch(struct iwl_op_mode *op_mode, struct iwl_rx_cmd_buffer *rxb, iwl_dvm_get_cmd_string(pkt->hdr.cmd), pkt->hdr.cmd); } - - return 0; } diff --git a/drivers/net/wireless/iwlwifi/iwl-op-mode.h b/drivers/net/wireless/iwlwifi/iwl-op-mode.h index ce1cdd7..71b450a 100644 --- a/drivers/net/wireless/iwlwifi/iwl-op-mode.h +++ b/drivers/net/wireless/iwlwifi/iwl-op-mode.h @@ -148,8 +148,7 @@ struct iwl_op_mode_ops { const struct iwl_fw *fw, struct dentry *dbgfs_dir); void (*stop)(struct iwl_op_mode *op_mode); - int (*rx)(struct iwl_op_mode *op_mode, struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd); + void (*rx)(struct iwl_op_mode *op_mode, struct iwl_rx_cmd_buffer *rxb); void (*napi_add)(struct iwl_op_mode *op_mode, struct napi_struct *napi, struct net_device *napi_dev, @@ -188,11 +187,10 @@ static inline void iwl_op_mode_stop(struct iwl_op_mode *op_mode) op_mode->ops->stop(op_mode); } -static inline int iwl_op_mode_rx(struct iwl_op_mode *op_mode, - struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd) +static inline void iwl_op_mode_rx(struct iwl_op_mode *op_mode, + struct iwl_rx_cmd_buffer *rxb) { - return op_mode->ops->rx(op_mode, rxb, cmd); + return op_mode->ops->rx(op_mode, rxb); } static inline void iwl_op_mode_queue_full(struct iwl_op_mode *op_mode, diff --git a/drivers/net/wireless/iwlwifi/iwl-trans.h b/drivers/net/wireless/iwlwifi/iwl-trans.h index 87a230a..7b6f095 100644 --- a/drivers/net/wireless/iwlwifi/iwl-trans.h +++ b/drivers/net/wireless/iwlwifi/iwl-trans.h @@ -261,8 +261,6 @@ enum iwl_hcmd_dataflag { * @resp_pkt: response packet, if %CMD_WANT_SKB was set * @_rx_page_order: (internally used to free response packet) * @_rx_page_addr: (internally used to free response packet) - * @handler_status: return value of the handler of the command - * (put in setup_rx_handlers) - valid for SYNC mode only * @flags: can be CMD_* * @len: array of the lengths of the chunks in data * @dataflags: IWL_HCMD_DFL_* @@ -273,7 +271,6 @@ struct iwl_host_cmd { struct iwl_rx_packet *resp_pkt; unsigned long _rx_page_addr; u32 _rx_page_order; - int handler_status; u32 flags; u16 len[IWL_MAX_CMD_TBS_PER_TFD]; diff --git a/drivers/net/wireless/iwlwifi/mvm/ops.c b/drivers/net/wireless/iwlwifi/mvm/ops.c index 00ca240..51c2fd0 100644 --- a/drivers/net/wireless/iw
[PATCH 04/37] iwlwifi: dvm: start HW before running FW
The new locking in PCIe transport requires to start_hw before start_fw. This uncovered a bug in dvm which failed to do so. Fix that. Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/mac80211.c | 12 1 file changed, 12 insertions(+) diff --git a/drivers/net/wireless/iwlwifi/dvm/mac80211.c b/drivers/net/wireless/iwlwifi/dvm/mac80211.c index 7acaa26..f603fb3 100644 --- a/drivers/net/wireless/iwlwifi/dvm/mac80211.c +++ b/drivers/net/wireless/iwlwifi/dvm/mac80211.c @@ -250,12 +250,24 @@ static int __iwl_up(struct iwl_priv *priv) } } + ret = iwl_trans_start_hw(priv->trans); + if (ret) { + IWL_ERR(priv, "Failed to start HW: %d\n", ret); + goto error; + } + ret = iwl_run_init_ucode(priv); if (ret) { IWL_ERR(priv, "Failed to run INIT ucode: %d\n", ret); goto error; } + ret = iwl_trans_start_hw(priv->trans); + if (ret) { + IWL_ERR(priv, "Failed to start HW: %d\n", ret); + goto error; + } + ret = iwl_load_ucode_wait_alive(priv, IWL_UCODE_REGULAR); if (ret) { IWL_ERR(priv, "Failed to start RT ucode: %d\n", ret); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 22/37] Revert "iwlwifi: mvm: move deferred d0i3 exit to resume_complete op"
From: Eliad Peller This reverts commit 088070a2f6575402d3dd82e1c5a4a8e1941805f6. When working in d0i3_on_idle mode, we explicitly go out of d0i3 on resume (so other potential commands could be sent). However, D0I3_DEFER_WAKEUP is currently cleared on resume complete (which happens only later on), causing d0i3 exit to timeout. Since mac80211 was modified to accept incoming frames once drv_resume was called, we can safely revert this patch, and handle the pending work on iwl_mvm_resume(). Signed-off-by: Eliad Peller Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/d3.c | 58 + drivers/net/wireless/iwlwifi/mvm/mac80211.c | 13 --- 2 files changed, 43 insertions(+), 28 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/d3.c b/drivers/net/wireless/iwlwifi/mvm/d3.c index 4165d10..246e60a 100644 --- a/drivers/net/wireless/iwlwifi/mvm/d3.c +++ b/drivers/net/wireless/iwlwifi/mvm/d3.c @@ -1935,28 +1935,56 @@ out: return 1; } -int iwl_mvm_resume(struct ieee80211_hw *hw) +static int iwl_mvm_resume_d3(struct iwl_mvm *mvm) { - struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); + iwl_trans_resume(mvm->trans); + + return __iwl_mvm_resume(mvm, false); +} + +static int iwl_mvm_resume_d0i3(struct iwl_mvm *mvm) +{ + bool exit_now; + + /* +* make sure to clear D0I3_DEFER_WAKEUP before +* calling iwl_trans_resume(), which might wait +* for d0i3 exit completion. +*/ + mutex_lock(&mvm->d0i3_suspend_mutex); + __clear_bit(D0I3_DEFER_WAKEUP, &mvm->d0i3_suspend_flags); + exit_now = __test_and_clear_bit(D0I3_PENDING_WAKEUP, + &mvm->d0i3_suspend_flags); + mutex_unlock(&mvm->d0i3_suspend_mutex); + if (exit_now) { + IWL_DEBUG_RPM(mvm, "Run deferred d0i3 exit\n"); + _iwl_mvm_exit_d0i3(mvm); + } iwl_trans_resume(mvm->trans); - if (mvm->hw->wiphy->wowlan_config->any) { - /* 'any' trigger means d0i3 usage */ - if (mvm->trans->d0i3_mode == IWL_D0I3_MODE_ON_SUSPEND) { - int ret = iwl_mvm_exit_d0i3(hw->priv); + if (mvm->trans->d0i3_mode == IWL_D0I3_MODE_ON_SUSPEND) { + int ret = iwl_mvm_exit_d0i3(mvm->hw->priv); - if (ret) - return ret; - /* -* d0i3 exit will be deferred until reconfig_complete. -* make sure there we are out of d0i3. -*/ - } - return 0; + if (ret) + return ret; + /* +* d0i3 exit will be deferred until reconfig_complete. +* make sure there we are out of d0i3. +*/ } + return 0; +} - return __iwl_mvm_resume(mvm, false); +int iwl_mvm_resume(struct ieee80211_hw *hw) +{ + struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); + + /* 'any' trigger means d0i3 was used */ + if (hw->wiphy->wowlan_config->any) + return iwl_mvm_resume_d0i3(mvm); + else + return iwl_mvm_resume_d3(mvm); } void iwl_mvm_set_wakeup(struct ieee80211_hw *hw, bool enabled) diff --git a/drivers/net/wireless/iwlwifi/mvm/mac80211.c b/drivers/net/wireless/iwlwifi/mvm/mac80211.c index dfdab38..45e9913 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mac80211.c +++ b/drivers/net/wireless/iwlwifi/mvm/mac80211.c @@ -1433,22 +1433,9 @@ static void iwl_mvm_restart_complete(struct iwl_mvm *mvm) static void iwl_mvm_resume_complete(struct iwl_mvm *mvm) { - bool exit_now; - if (!iwl_mvm_is_d0i3_supported(mvm)) return; - mutex_lock(&mvm->d0i3_suspend_mutex); - __clear_bit(D0I3_DEFER_WAKEUP, &mvm->d0i3_suspend_flags); - exit_now = __test_and_clear_bit(D0I3_PENDING_WAKEUP, - &mvm->d0i3_suspend_flags); - mutex_unlock(&mvm->d0i3_suspend_mutex); - - if (exit_now) { - IWL_DEBUG_RPM(mvm, "Run deferred d0i3 exit\n"); - _iwl_mvm_exit_d0i3(mvm); - } - if (mvm->trans->d0i3_mode == IWL_D0I3_MODE_ON_SUSPEND) if (!wait_event_timeout(mvm->d0i3_exit_waitq, !test_bit(IWL_MVM_STATUS_IN_D0I3, -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 21/37] iwlwifi: mvm: move existing UMAC commands to group 1
From: Johannes Berg Existing UMAC commands already use the long header, but are sent with group 0 and the long header inserted manually. Move them to the group 1 to take advantage of the header building in the low- level transport. Existing firmware ignores the group_id field (it's reserved) and the first firmware that really supports long command headers can parse all commands in both group 0 (with short header) and group 1 (with long header.) Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-trans.h | 5 + drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h | 18 --- drivers/net/wireless/iwlwifi/mvm/fw-api-tof.h | 5 - drivers/net/wireless/iwlwifi/mvm/scan.c| 22 -- drivers/net/wireless/iwlwifi/mvm/tof.c | 31 ++ drivers/net/wireless/iwlwifi/pcie/tx.c | 3 ++- 6 files changed, 28 insertions(+), 56 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/iwl-trans.h b/drivers/net/wireless/iwlwifi/iwl-trans.h index df71aa3..8f67004 100644 --- a/drivers/net/wireless/iwlwifi/iwl-trans.h +++ b/drivers/net/wireless/iwlwifi/iwl-trans.h @@ -148,6 +148,11 @@ static inline u32 iwl_cmd_id(u8 opcode, u8 groupid, u8 version) return opcode + (groupid << 8) + (version << 16); } +/* due to the conversion, this group is special; new groups + * should be defined in the appropriate fw-api header files + */ +#define IWL_ALWAYS_LONG_GROUP 1 + /** * struct iwl_cmd_header * diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h index 5e4cbdb..4787c32 100644 --- a/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h +++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h @@ -550,18 +550,6 @@ struct iwl_periodic_scan_complete { /* UMAC Scan API */ -/** - * struct iwl_mvm_umac_cmd_hdr - Command header for UMAC commands - * @size: size of the command (not including header) - * @reserved0: for future use and alignment - * @ver: API version number - */ -struct iwl_mvm_umac_cmd_hdr { - __le16 size; - u8 reserved0; - u8 ver; -} __packed; - /* The maximum of either of these cannot exceed 8, because we use an * 8-bit mask (see IWL_MVM_SCAN_MASK in mvm.h). */ @@ -621,7 +609,6 @@ enum iwl_channel_flags { /** * struct iwl_scan_config - * @hdr: umac command header * @flags: enum scan_config_flags * @tx_chains: valid_tx antenna - ANT_* definitions * @rx_chains: valid_rx antenna - ANT_* definitions @@ -639,7 +626,6 @@ enum iwl_channel_flags { * @channel_array: default supported channels */ struct iwl_scan_config { - struct iwl_mvm_umac_cmd_hdr hdr; __le32 flags; __le32 tx_chains; __le32 rx_chains; @@ -734,7 +720,6 @@ struct iwl_scan_req_umac_tail { /** * struct iwl_scan_req_umac - * @hdr: umac command header * @flags: &enum iwl_umac_scan_flags * @uid: scan id, &enum iwl_umac_scan_uid_offsets * @ooc_priority: out of channel priority - &enum iwl_scan_priority @@ -753,7 +738,6 @@ struct iwl_scan_req_umac_tail { * &struct iwl_scan_req_umac_tail */ struct iwl_scan_req_umac { - struct iwl_mvm_umac_cmd_hdr hdr; __le32 flags; __le32 uid; __le32 ooc_priority; @@ -775,12 +759,10 @@ struct iwl_scan_req_umac { /** * struct iwl_umac_scan_abort - * @hdr: umac command header * @uid: scan id, &enum iwl_umac_scan_uid_offsets * @flags: reserved */ struct iwl_umac_scan_abort { - struct iwl_mvm_umac_cmd_hdr hdr; __le32 uid; __le32 flags; } __packed; /* SCAN_ABORT_CMD_UMAC_API_S_VER_1 */ diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-tof.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-tof.h index 287c9ec..eed6271 100644 --- a/drivers/net/wireless/iwlwifi/mvm/fw-api-tof.h +++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-tof.h @@ -88,7 +88,6 @@ enum iwl_mvm_tof_sub_grp_ids { * @is_buf_required: 1 channel estimation buffer required, 0 - otherwise */ struct iwl_tof_config_cmd { - struct iwl_mvm_umac_cmd_hdr hdr; __le32 sub_grp_cmd_id; u8 tof_disabled; u8 one_sided_disabled; @@ -136,7 +135,6 @@ struct iwl_tof_config_cmd { * @bssid: Current AP BSSID */ struct iwl_tof_responder_config_cmd { - struct iwl_mvm_umac_cmd_hdr hdr; __le32 sub_grp_cmd_id; __le16 burst_period; u8 min_delta_ftm; @@ -171,7 +169,6 @@ struct iwl_tof_responder_config_cmd { * value to be sent to the AP */ struct iwl_tof_range_req_ext_cmd { - struct iwl_mvm_umac_cmd_hdr hdr; __le32 sub_grp_cmd_id; __le16 tsf_timer_offset_msec; __le16 reserved; @@ -273,7 +270,6 @@ enum iwl_tof_response_mode { * Bits set to 1 shall be randomized by the UMAC */ struct iwl_tof_range_req_cmd { - struct iwl_mvm_umac_cmd_hdr hdr; __le32
[PATCH 30/37] iwlwifi: call d3_suspend/resume in d0i3 case as well
From: Eliad Peller Some CSR registers have to be configured also in case of suspend/resume with unified image (which doesn't includes reconfiguration flow). Reuse the existing d3_suspend/d3_resume trans ops, while making sure some configurations are a bit different, according to the wowlan type. After this change, we no longer need the special wowlan_d0i3 configurations done in iwl_pci_resume, as they are already being done in the d3_resume op. Signed-off-by: Eliad Peller Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/d3.c | 6 ++ drivers/net/wireless/iwlwifi/pcie/drv.c | 13 +++ drivers/net/wireless/iwlwifi/pcie/trans.c | 36 +-- 3 files changed, 34 insertions(+), 21 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/d3.c b/drivers/net/wireless/iwlwifi/mvm/d3.c index 68d7218..a85be4e 100644 --- a/drivers/net/wireless/iwlwifi/mvm/d3.c +++ b/drivers/net/wireless/iwlwifi/mvm/d3.c @@ -1187,6 +1187,9 @@ int iwl_mvm_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wowlan) mutex_lock(&mvm->d0i3_suspend_mutex); __set_bit(D0I3_DEFER_WAKEUP, &mvm->d0i3_suspend_flags); mutex_unlock(&mvm->d0i3_suspend_mutex); + + iwl_trans_d3_suspend(mvm->trans, false); + return 0; } @@ -1949,6 +1952,9 @@ static int iwl_mvm_resume_d3(struct iwl_mvm *mvm) static int iwl_mvm_resume_d0i3(struct iwl_mvm *mvm) { bool exit_now; + enum iwl_d3_status d3_status; + + iwl_trans_d3_resume(mvm->trans, &d3_status, false); /* * make sure to clear D0I3_DEFER_WAKEUP before diff --git a/drivers/net/wireless/iwlwifi/pcie/drv.c b/drivers/net/wireless/iwlwifi/pcie/drv.c index dbd2a03..cdf3a0c 100644 --- a/drivers/net/wireless/iwlwifi/pcie/drv.c +++ b/drivers/net/wireless/iwlwifi/pcie/drv.c @@ -631,17 +631,10 @@ static int iwl_pci_resume(struct device *device) return 0; /* -* On suspend, ict is disabled, and the interrupt mask -* gets cleared. Reconfigure them both in case of d0i3 -* image. Otherwise, only enable rfkill interrupt (in -* order to keep track of the rfkill status) +* Enable rfkill interrupt (in order to keep track of +* the rfkill status) */ - if (trans->wowlan_d0i3) { - iwl_pcie_reset_ict(trans); - iwl_enable_interrupts(trans); - } else { - iwl_enable_rfkill_int(trans); - } + iwl_enable_rfkill_int(trans); hw_rfkill = iwl_is_rfkill_set(trans); diff --git a/drivers/net/wireless/iwlwifi/pcie/trans.c b/drivers/net/wireless/iwlwifi/pcie/trans.c index 46e900e..cbc29cc 100644 --- a/drivers/net/wireless/iwlwifi/pcie/trans.c +++ b/drivers/net/wireless/iwlwifi/pcie/trans.c @@ -1189,6 +1189,12 @@ static void iwl_trans_pcie_d3_suspend(struct iwl_trans *trans, bool test) { struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans); + if (trans->wowlan_d0i3) { + /* Enable persistence mode to avoid reset */ + iwl_set_bit(trans, CSR_HW_IF_CONFIG_REG, + CSR_HW_IF_CONFIG_REG_PERSIST_MODE); + } + iwl_disable_interrupts(trans); /* @@ -1207,12 +1213,14 @@ static void iwl_trans_pcie_d3_suspend(struct iwl_trans *trans, bool test) iwl_clear_bit(trans, CSR_GP_CNTRL, CSR_GP_CNTRL_REG_FLAG_INIT_DONE); - /* -* reset TX queues -- some of their registers reset during S3 -* so if we don't reset everything here the D3 image would try -* to execute some invalid memory upon resume -*/ - iwl_trans_pcie_tx_reset(trans); + if (!trans->wowlan_d0i3) { + /* +* reset TX queues -- some of their registers reset during S3 +* so if we don't reset everything here the D3 image would try +* to execute some invalid memory upon resume +*/ + iwl_trans_pcie_tx_reset(trans); + } iwl_pcie_set_pwr(trans, true); } @@ -1254,12 +1262,18 @@ static int iwl_trans_pcie_d3_resume(struct iwl_trans *trans, iwl_pcie_set_pwr(trans, false); - iwl_trans_pcie_tx_reset(trans); + if (trans->wowlan_d0i3) { + iwl_clear_bit(trans, CSR_GP_CNTRL, + CSR_GP_CNTRL_REG_FLAG_MAC_ACCESS_REQ); + } else { + iwl_trans_pcie_tx_reset(trans); - ret = iwl_pcie_rx_init(trans); - if (ret) { - IWL_ERR(trans, "Failed to resume the device (RX reset)\n"); - return ret; + ret = iwl_pcie_rx_init(trans); + if (ret) { + IWL_ERR(trans, + "Failed to resume the device (RX reset)\n"); + return ret; + } } val = i
[PATCH 32/37] iwlwifi: mvm: move TX PN assignment for CCMP to the driver
From: Johannes Berg Move the TX PN assignment (for CCMP only) to the driver. This prepares the driver for future DSO (driver segmentation offload) where it will split an SKB into multiple MPDUs by itself. For TDLS, split out the CCMP TX command handling so that it won't get a PN assigned, the firmware assigns the PN in that case. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/mac80211.c | 5 ++-- drivers/net/wireless/iwlwifi/mvm/mvm.h | 15 --- drivers/net/wireless/iwlwifi/mvm/tdls.c | 12 ++--- drivers/net/wireless/iwlwifi/mvm/tx.c | 41 +++-- 4 files changed, 50 insertions(+), 23 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/mac80211.c b/drivers/net/wireless/iwlwifi/mvm/mac80211.c index 4264c52..5a4bf84 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mac80211.c +++ b/drivers/net/wireless/iwlwifi/mvm/mac80211.c @@ -2873,10 +2873,11 @@ static int iwl_mvm_mac_set_key(struct ieee80211_hw *hw, switch (key->cipher) { case WLAN_CIPHER_SUITE_TKIP: key->flags |= IEEE80211_KEY_FLAG_GENERATE_MMIC; - /* fall-through */ - case WLAN_CIPHER_SUITE_CCMP: key->flags |= IEEE80211_KEY_FLAG_GENERATE_IV; break; + case WLAN_CIPHER_SUITE_CCMP: + key->flags |= IEEE80211_KEY_FLAG_PUT_IV_SPACE; + break; case WLAN_CIPHER_SUITE_AES_CMAC: WARN_ON_ONCE(!ieee80211_hw_check(hw, MFP_CAPABLE)); break; diff --git a/drivers/net/wireless/iwlwifi/mvm/mvm.h b/drivers/net/wireless/iwlwifi/mvm/mvm.h index c1f84ec..95f326d 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mvm.h +++ b/drivers/net/wireless/iwlwifi/mvm/mvm.h @@ -1000,10 +1000,6 @@ int iwl_mvm_tx_skb_non_sta(struct iwl_mvm *mvm, struct sk_buff *skb); void iwl_mvm_set_tx_cmd(struct iwl_mvm *mvm, struct sk_buff *skb, struct iwl_tx_cmd *tx_cmd, struct ieee80211_tx_info *info, u8 sta_id); -void iwl_mvm_set_tx_cmd_crypto(struct iwl_mvm *mvm, - struct ieee80211_tx_info *info, - struct iwl_tx_cmd *tx_cmd, - struct sk_buff *skb_frag); void iwl_mvm_set_tx_cmd_rate(struct iwl_mvm *mvm, struct iwl_tx_cmd *tx_cmd, struct ieee80211_tx_info *info, struct ieee80211_sta *sta, __le16 fc); @@ -1015,6 +1011,17 @@ static inline const char *iwl_mvm_get_tx_fail_reason(u32 status) { return ""; } int iwl_mvm_flush_tx_path(struct iwl_mvm *mvm, u32 tfd_msk, bool sync); void iwl_mvm_async_handlers_purge(struct iwl_mvm *mvm); +static inline void iwl_mvm_set_tx_cmd_ccmp(struct ieee80211_tx_info *info, + struct iwl_tx_cmd *tx_cmd) +{ + struct ieee80211_key_conf *keyconf = info->control.hw_key; + + tx_cmd->sec_ctl = TX_CMD_SEC_CCM; + memcpy(tx_cmd->key, keyconf->key, keyconf->keylen); + if (info->flags & IEEE80211_TX_CTL_AMPDU) + tx_cmd->tx_flags |= cpu_to_le32(TX_CMD_FLG_CCMP_AGG); +} + static inline void iwl_mvm_wait_for_async_handlers(struct iwl_mvm *mvm) { flush_work(&mvm->async_handlers_wk); diff --git a/drivers/net/wireless/iwlwifi/mvm/tdls.c b/drivers/net/wireless/iwlwifi/mvm/tdls.c index d44d02d..fe2fa56 100644 --- a/drivers/net/wireless/iwlwifi/mvm/tdls.c +++ b/drivers/net/wireless/iwlwifi/mvm/tdls.c @@ -460,13 +460,19 @@ iwl_mvm_tdls_config_channel_switch(struct iwl_mvm *mvm, cmd.frame.switch_time_offset = cpu_to_le32(ch_sw_tm_ie + 2); info = IEEE80211_SKB_CB(skb); - if (info->control.hw_key) - iwl_mvm_set_tx_cmd_crypto(mvm, info, &cmd.frame.tx_cmd, skb); + hdr = (void *)skb->data; + if (info->control.hw_key) { + if (info->control.hw_key->cipher != WLAN_CIPHER_SUITE_CCMP) { + rcu_read_unlock(); + ret = -EINVAL; + goto out; + } + iwl_mvm_set_tx_cmd_ccmp(info, &cmd.frame.tx_cmd); + } iwl_mvm_set_tx_cmd(mvm, skb, &cmd.frame.tx_cmd, info, mvmsta->sta_id); - hdr = (void *)skb->data; iwl_mvm_set_tx_cmd_rate(mvm, &cmd.frame.tx_cmd, info, sta, hdr->frame_control); rcu_read_unlock(); diff --git a/drivers/net/wireless/iwlwifi/mvm/tx.c b/drivers/net/wireless/iwlwifi/mvm/tx.c index fa3eaf9..eac511a 100644 --- a/drivers/net/wireless/iwlwifi/mvm/tx.c +++ b/drivers/net/wireless/iwlwifi/mvm/tx.c @@ -268,19 +268,29 @@ void iwl_mvm_set_tx_cmd_rate(struct iwl_mvm *mvm, struct iwl_tx_cmd *tx_cmd, /* * Sets the fields in the Tx cmd that are crypto related */ -void iwl_mvm_set_tx_cmd_crypto(struct iwl_mvm *mvm, - struct ieee80211_tx_info *info, - struct
[PATCH 06/37] iwlwifi: pcie: Set scheduler to work on auto mode
From: Haim Dreyfuss During NIC initialization shared HW is reset and this disables the scheduler. Some HW platforms do not activate the scheduler after it. Consequently all HCMD sent by the driver stay at the queues which cause to queue stuck. Set the scheduler to work on auto active mode so it would be activated upon change over one of the queues' write pointer. Signed-off-by: Haim Dreyfuss Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-prph.h | 1 + drivers/net/wireless/iwlwifi/pcie/tx.c | 1 + 2 files changed, 2 insertions(+) diff --git a/drivers/net/wireless/iwlwifi/iwl-prph.h b/drivers/net/wireless/iwlwifi/iwl-prph.h index 5af1c77..a846904 100644 --- a/drivers/net/wireless/iwlwifi/iwl-prph.h +++ b/drivers/net/wireless/iwlwifi/iwl-prph.h @@ -253,6 +253,7 @@ #define SCD_QUEUE_CTX_REG2_FRAME_LIMIT_POS (16) #define SCD_QUEUE_CTX_REG2_FRAME_LIMIT_MSK (0x007F) #define SCD_GP_CTRL_ENABLE_31_QUEUES BIT(0) +#define SCD_GP_CTRL_AUTO_ACTIVE_MODE BIT(18) /* Context Data */ #define SCD_CONTEXT_MEM_LOWER_BOUND(SCD_MEM_LOWER_BOUND + 0x600) diff --git a/drivers/net/wireless/iwlwifi/pcie/tx.c b/drivers/net/wireless/iwlwifi/pcie/tx.c index 2b86c21..d711f0b 100644 --- a/drivers/net/wireless/iwlwifi/pcie/tx.c +++ b/drivers/net/wireless/iwlwifi/pcie/tx.c @@ -915,6 +915,7 @@ int iwl_pcie_tx_init(struct iwl_trans *trans) } } + iwl_set_bits_prph(trans, SCD_GP_CTRL, SCD_GP_CTRL_AUTO_ACTIVE_MODE); if (trans->cfg->base_params->num_of_queues > 20) iwl_set_bits_prph(trans, SCD_GP_CTRL, SCD_GP_CTRL_ENABLE_31_QUEUES); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 15/37] iwlwifi: pcie: add missing calls to synchronize_irq()
In a few places, we were disabling interrupts but didn't make sure that the interrupt handler has finished running. Add calls to synchronize_irq() to ensure we finish handling the interrupts before we free resources or other things that could lead to a crash if the interrupt were to be handled later. Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/pcie/trans.c | 7 +++ 1 file changed, 7 insertions(+) diff --git a/drivers/net/wireless/iwlwifi/pcie/trans.c b/drivers/net/wireless/iwlwifi/pcie/trans.c index 23f2824..4cdfb2f 100644 --- a/drivers/net/wireless/iwlwifi/pcie/trans.c +++ b/drivers/net/wireless/iwlwifi/pcie/trans.c @@ -1178,6 +1178,8 @@ void iwl_trans_pcie_rf_kill(struct iwl_trans *trans, bool state) static void iwl_trans_pcie_d3_suspend(struct iwl_trans *trans, bool test) { + struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans); + iwl_disable_interrupts(trans); /* @@ -1189,6 +1191,8 @@ static void iwl_trans_pcie_d3_suspend(struct iwl_trans *trans, bool test) iwl_pcie_disable_ict(trans); + synchronize_irq(trans_pcie->pci_dev->irq); + iwl_clear_bit(trans, CSR_GP_CNTRL, CSR_GP_CNTRL_REG_FLAG_MAC_ACCESS_REQ); iwl_clear_bit(trans, CSR_GP_CNTRL, @@ -1326,7 +1330,10 @@ static void iwl_trans_pcie_op_mode_leave(struct iwl_trans *trans) spin_unlock(&trans_pcie->irq_lock); iwl_pcie_disable_ict(trans); + mutex_unlock(&trans_pcie->mutex); + + synchronize_irq(trans_pcie->pci_dev->irq); } static void iwl_trans_pcie_write8(struct iwl_trans *trans, u32 ofs, u8 val) -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 13/37] iwlwifi: mvm: Do not sample the device time for session protection
From: Ilan Peer Since the time-event is sent with the immediate flag set, there is no need to sample the device time. Signed-off-by: Ilan Peer Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/time-event.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/time-event.c b/drivers/net/wireless/iwlwifi/mvm/time-event.c index 6c05669..8fe7ecd 100644 --- a/drivers/net/wireless/iwlwifi/mvm/time-event.c +++ b/drivers/net/wireless/iwlwifi/mvm/time-event.c @@ -596,8 +596,7 @@ void iwl_mvm_protect_session(struct iwl_mvm *mvm, cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id, mvmvif->color)); time_cmd.id = cpu_to_le32(TE_BSS_STA_AGGRESSIVE_ASSOC); - time_cmd.apply_time = - cpu_to_le32(iwl_read_prph(mvm->trans, DEVICE_SYSTEM_TIME_REG)); + time_cmd.apply_time = cpu_to_le32(0); time_cmd.max_frags = TE_V2_FRAG_NONE; time_cmd.max_delay = cpu_to_le32(max_delay); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 07/37] iwlwifi: mvm: LRU-assign key offsets
From: Johannes Berg The current key offset assignment algorithm always uses the lowest unused key offset, which will potentially lead to issues when the firmware will change to take the key material for TX from the key table rather than from the TX command. In order to avoid those issues (and avoid forgetting about them) change the key offset allocation algorithm now to avoid reusing key offsets quickly. The new algorithm always picks as the next offset the least recently freed offset, i.e. the offset that has been unused for the longest amount of time. This is implemented by having a generation counter for each key offset that is incremented every time a key is deleted, except for the one that's deleted, which is reset to zero. Thus the highest counter is the key that's been unused longest. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/mvm.h | 1 + drivers/net/wireless/iwlwifi/mvm/sta.c | 32 ++-- 2 files changed, 27 insertions(+), 6 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/mvm.h b/drivers/net/wireless/iwlwifi/mvm/mvm.h index 2d4bad5..40d1bd7 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mvm.h +++ b/drivers/net/wireless/iwlwifi/mvm/mvm.h @@ -686,6 +686,7 @@ struct iwl_mvm { * can hold 16 keys at most. Reflect this fact. */ unsigned long fw_key_table[BITS_TO_LONGS(STA_KEY_MAX_NUM)]; + u8 fw_key_deleted[STA_KEY_MAX_NUM]; /* references taken by the driver and spinlock protecting them */ spinlock_t refs_lock; diff --git a/drivers/net/wireless/iwlwifi/mvm/sta.c b/drivers/net/wireless/iwlwifi/mvm/sta.c index d68dc69..806b2c2 100644 --- a/drivers/net/wireless/iwlwifi/mvm/sta.c +++ b/drivers/net/wireless/iwlwifi/mvm/sta.c @@ -1148,18 +1148,31 @@ int iwl_mvm_sta_tx_agg_flush(struct iwl_mvm *mvm, struct ieee80211_vif *vif, static int iwl_mvm_set_fw_key_idx(struct iwl_mvm *mvm) { - int i; + int i, max = -1, max_offs = -1; lockdep_assert_held(&mvm->mutex); - i = find_first_zero_bit(mvm->fw_key_table, STA_KEY_MAX_NUM); + /* Pick the unused key offset with the highest 'deleted' +* counter. Every time a key is deleted, all the counters +* are incremented and the one that was just deleted is +* reset to zero. Thus, the highest counter is the one +* that was deleted longest ago. Pick that one. +*/ + for (i = 0; i < STA_KEY_MAX_NUM; i++) { + if (test_bit(i, mvm->fw_key_table)) + continue; + if (mvm->fw_key_deleted[i] > max) { + max = mvm->fw_key_deleted[i]; + max_offs = i; + } + } - if (i == STA_KEY_MAX_NUM) + if (max_offs < 0) return STA_KEY_IDX_INVALID; - __set_bit(i, mvm->fw_key_table); + __set_bit(max_offs, mvm->fw_key_table); - return i; + return max_offs; } static u8 iwl_mvm_get_key_sta_id(struct ieee80211_vif *vif, @@ -1478,7 +1491,7 @@ int iwl_mvm_remove_sta_key(struct iwl_mvm *mvm, { bool mcast = !(keyconf->flags & IEEE80211_KEY_FLAG_PAIRWISE); u8 sta_id; - int ret; + int ret, i; lockdep_assert_held(&mvm->mutex); @@ -1497,6 +1510,13 @@ int iwl_mvm_remove_sta_key(struct iwl_mvm *mvm, return -ENOENT; } + /* track which key was deleted last */ + for (i = 0; i < STA_KEY_MAX_NUM; i++) { + if (mvm->fw_key_deleted[i] < U8_MAX) + mvm->fw_key_deleted[i]++; + } + mvm->fw_key_deleted[keyconf->hw_key_idx] = 0; + if (sta_id == IWL_MVM_STATION_COUNT) { IWL_DEBUG_WEP(mvm, "station non-existent, early return.\n"); return 0; -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 35/37] iwlwifi: mvm: add wide firmware command infrastructure for RX
From: Avraham Stern Add support for extended firmware event header that contains a group id as well as the command id. Signed-off-by: Avraham Stern Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/ops.c | 7 +-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/ops.c b/drivers/net/wireless/iwlwifi/mvm/ops.c index c9b9c98..a424d95 100644 --- a/drivers/net/wireless/iwlwifi/mvm/ops.c +++ b/drivers/net/wireless/iwlwifi/mvm/ops.c @@ -201,13 +201,15 @@ static void iwl_mvm_nic_config(struct iwl_op_mode *op_mode) } struct iwl_rx_handlers { - u8 cmd_id; + u16 cmd_id; bool async; void (*fn)(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb); }; #define RX_HANDLER(_cmd_id, _fn, _async) \ { .cmd_id = _cmd_id , .fn = _fn , .async = _async } +#define RX_HANDLER_GRP(_grp, _cmd, _fn, _async)\ + { .cmd_id = WIDE_ID(_grp, _cmd), .fn = _fn, .async = _async } /* * Handlers for fw notifications @@ -263,6 +265,7 @@ static const struct iwl_rx_handlers iwl_mvm_rx_handlers[] = { }; #undef RX_HANDLER +#undef RX_HANDLER_GRP #define CMD(x) [x] = #x static const char *const iwl_mvm_cmd_strings[REPLY_MAX] = { @@ -735,7 +738,7 @@ static void iwl_mvm_rx_dispatch(struct iwl_op_mode *op_mode, const struct iwl_rx_handlers *rx_h = &iwl_mvm_rx_handlers[i]; struct iwl_async_handler_entry *entry; - if (rx_h->cmd_id != pkt->hdr.cmd) + if (rx_h->cmd_id != WIDE_ID(pkt->hdr.group_id, pkt->hdr.cmd)) continue; if (!rx_h->async) { -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 25/37] iwlwifi: mvm: Use the AP station for non_sta transmit
From: Ilan Peer In iwl_mvm_tx_skb_non_sta(), in case of managed interface, use the AP station for multicast frames instead of the auxiliary station as otherwise the frames can be sent to an absent P2P GO as the FW does not block transmissions for the auxiliary station since it is not associated with the station MAC context. Note that this is not possible for unicast frames, as a TDLS discovery response is sent without a station entry, and in this case the P2P GO NoA should not block transmission to the peer. Signed-off-by: Ilan Peer Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/tx.c | 27 +++ 1 file changed, 19 insertions(+), 8 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/tx.c b/drivers/net/wireless/iwlwifi/mvm/tx.c index abde484..fa3eaf9 100644 --- a/drivers/net/wireless/iwlwifi/mvm/tx.c +++ b/drivers/net/wireless/iwlwifi/mvm/tx.c @@ -366,18 +366,29 @@ int iwl_mvm_tx_skb_non_sta(struct iwl_mvm *mvm, struct sk_buff *skb) IEEE80211_SKB_CB(skb)->hw_queue = mvm->aux_queue; /* -* If the interface on which frame is sent is the P2P_DEVICE +* If the interface on which the frame is sent is the P2P_DEVICE * or an AP/GO interface use the broadcast station associated -* with it; otherwise use the AUX station. +* with it; otherwise if the interface is a managed interface +* use the AP station associated with it for multicast traffic +* (this is not possible for unicast packets as a TLDS discovery +* response are sent without a station entry); otherwise use the +* AUX station. */ - if (info->control.vif && - (info->control.vif->type == NL80211_IFTYPE_P2P_DEVICE || -info->control.vif->type == NL80211_IFTYPE_AP)) { + sta_id = mvm->aux_sta.sta_id; + if (info->control.vif) { struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(info->control.vif); - sta_id = mvmvif->bcast_sta.sta_id; - } else { - sta_id = mvm->aux_sta.sta_id; + + if (info->control.vif->type == NL80211_IFTYPE_P2P_DEVICE || + info->control.vif->type == NL80211_IFTYPE_AP) + sta_id = mvmvif->bcast_sta.sta_id; + else if (info->control.vif->type == NL80211_IFTYPE_STATION && +is_multicast_ether_addr(hdr->addr1)) { + u8 ap_sta_id = ACCESS_ONCE(mvmvif->ap_sta_id); + + if (ap_sta_id != IWL_MVM_STATION_COUNT) + sta_id = ap_sta_id; + } } IWL_DEBUG_TX(mvm, "station Id %d, queue=%d\n", sta_id, info->hw_queue); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 23/37] iwlwifi: return error if d0i3 was aborted
From: Eliad Peller Allow the transport layer to return an error upon suspend. Signed-off-by: Eliad Peller Reviewed-by: Luciano Coelho Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-trans.h | 10 ++ drivers/net/wireless/iwlwifi/mvm/d3.c| 8 ++-- 2 files changed, 12 insertions(+), 6 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/iwl-trans.h b/drivers/net/wireless/iwlwifi/iwl-trans.h index 8f67004..e698ed5 100644 --- a/drivers/net/wireless/iwlwifi/iwl-trans.h +++ b/drivers/net/wireless/iwlwifi/iwl-trans.h @@ -598,7 +598,7 @@ struct iwl_trans_ops { u32 value); void (*ref)(struct iwl_trans *trans); void (*unref)(struct iwl_trans *trans); - void (*suspend)(struct iwl_trans *trans); + int (*suspend)(struct iwl_trans *trans); void (*resume)(struct iwl_trans *trans); struct iwl_trans_dump_data *(*dump_data)(struct iwl_trans *trans); @@ -807,10 +807,12 @@ static inline void iwl_trans_unref(struct iwl_trans *trans) trans->ops->unref(trans); } -static inline void iwl_trans_suspend(struct iwl_trans *trans) +static inline int iwl_trans_suspend(struct iwl_trans *trans) { - if (trans->ops->suspend) - trans->ops->suspend(trans); + if (!trans->ops->suspend) + return 0; + + return trans->ops->suspend(trans); } static inline void iwl_trans_resume(struct iwl_trans *trans) diff --git a/drivers/net/wireless/iwlwifi/mvm/d3.c b/drivers/net/wireless/iwlwifi/mvm/d3.c index 246e60a..68d7218 100644 --- a/drivers/net/wireless/iwlwifi/mvm/d3.c +++ b/drivers/net/wireless/iwlwifi/mvm/d3.c @@ -1168,13 +1168,17 @@ remove_notif: int iwl_mvm_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wowlan) { struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); + int ret; + + ret = iwl_trans_suspend(mvm->trans); + if (ret) + return ret; - iwl_trans_suspend(mvm->trans); mvm->trans->wowlan_d0i3 = wowlan->any; if (mvm->trans->wowlan_d0i3) { /* 'any' trigger means d0i3 usage */ if (mvm->trans->d0i3_mode == IWL_D0I3_MODE_ON_SUSPEND) { - int ret = iwl_mvm_enter_d0i3_sync(mvm); + ret = iwl_mvm_enter_d0i3_sync(mvm); if (ret) return ret; -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 17/37] iwlwifi: remove command header flags field
From: Johannes Berg The 'flags' field really has been reserved in the firmware API for a very long time, probably since 4965. As a consequence, the field is always 0 and checking for a IWL_CMD_FAILED_MSK flag makes no sense. Rename the field to 'reserved', get rid of IWL_CMD_FAILED_MSK and all the code for it. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/sta.c | 44 drivers/net/wireless/iwlwifi/iwl-trans.h | 6 + drivers/net/wireless/iwlwifi/mvm/fw.c| 7 - drivers/net/wireless/iwlwifi/mvm/nvm.c | 12 - drivers/net/wireless/iwlwifi/mvm/tdls.c | 9 +-- drivers/net/wireless/iwlwifi/mvm/utils.c | 5 drivers/net/wireless/iwlwifi/pcie/tx.c | 2 +- 7 files changed, 19 insertions(+), 66 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/dvm/sta.c b/drivers/net/wireless/iwlwifi/dvm/sta.c index c18aa3e..0fa67d3 100644 --- a/drivers/net/wireless/iwlwifi/dvm/sta.c +++ b/drivers/net/wireless/iwlwifi/dvm/sta.c @@ -65,12 +65,6 @@ static void iwl_process_add_sta_resp(struct iwl_priv *priv, { struct iwl_add_sta_resp *add_sta_resp = (void *)pkt->data; - if (pkt->hdr.flags & IWL_CMD_FAILED_MSK) { - IWL_ERR(priv, "Bad return from REPLY_ADD_STA (0x%08X)\n", - pkt->hdr.flags); - return; - } - IWL_DEBUG_INFO(priv, "Processing response for adding station\n"); spin_lock_bh(&priv->sta_lock); @@ -136,8 +130,7 @@ int iwl_send_add_sta(struct iwl_priv *priv, add_sta_resp = (void *)pkt->data; /* debug messages are printed in the handler */ - if (!(pkt->hdr.flags & IWL_CMD_FAILED_MSK) && - add_sta_resp->status == ADD_STA_SUCCESS_MSK) { + if (add_sta_resp->status == ADD_STA_SUCCESS_MSK) { spin_lock_bh(&priv->sta_lock); ret = iwl_sta_ucode_activate(priv, sta_id); spin_unlock_bh(&priv->sta_lock); @@ -431,6 +424,7 @@ static int iwl_send_remove_station(struct iwl_priv *priv, struct iwl_rx_packet *pkt; int ret; struct iwl_rem_sta_cmd rm_sta_cmd; + struct iwl_rem_sta_resp *rem_sta_resp; struct iwl_host_cmd cmd = { .id = REPLY_REMOVE_STA, @@ -450,29 +444,23 @@ static int iwl_send_remove_station(struct iwl_priv *priv, return ret; pkt = cmd.resp_pkt; - if (pkt->hdr.flags & IWL_CMD_FAILED_MSK) { - IWL_ERR(priv, "Bad return from REPLY_REMOVE_STA (0x%08X)\n", - pkt->hdr.flags); - ret = -EIO; - } + rem_sta_resp = (void *)pkt->data; - if (!ret) { - struct iwl_rem_sta_resp *rem_sta_resp = (void *)pkt->data; - switch (rem_sta_resp->status) { - case REM_STA_SUCCESS_MSK: - if (!temporary) { - spin_lock_bh(&priv->sta_lock); - iwl_sta_ucode_deactivate(priv, sta_id); - spin_unlock_bh(&priv->sta_lock); - } - IWL_DEBUG_ASSOC(priv, "REPLY_REMOVE_STA PASSED\n"); - break; - default: - ret = -EIO; - IWL_ERR(priv, "REPLY_REMOVE_STA failed\n"); - break; + switch (rem_sta_resp->status) { + case REM_STA_SUCCESS_MSK: + if (!temporary) { + spin_lock_bh(&priv->sta_lock); + iwl_sta_ucode_deactivate(priv, sta_id); + spin_unlock_bh(&priv->sta_lock); } + IWL_DEBUG_ASSOC(priv, "REPLY_REMOVE_STA PASSED\n"); + break; + default: + ret = -EIO; + IWL_ERR(priv, "REPLY_REMOVE_STA failed\n"); + break; } + iwl_free_resp(&cmd); return ret; diff --git a/drivers/net/wireless/iwlwifi/iwl-trans.h b/drivers/net/wireless/iwlwifi/iwl-trans.h index 7b6f095..64769e4 100644 --- a/drivers/net/wireless/iwlwifi/iwl-trans.h +++ b/drivers/net/wireless/iwlwifi/iwl-trans.h @@ -130,7 +130,7 @@ */ struct iwl_cmd_header { u8 cmd; /* Command ID: REPLY_RXON, etc. */ - u8 flags; /* 0:5 reserved, 6 abort, 7 internal */ + u8 reserved; /* * The driver sets up the sequence number to values of its choosing. * uCode does not use this value, but passes it back to the driver @@ -154,10 +154,6 @@ struct iwl_cmd_header { __le16 sequence; } __packed; -/* iwl_cmd_header flags value */ -#define IWL_CMD_FAILED_MSK 0x40 - - #define FH_RSCSR_FRAME_SIZE_MSK0x3FFF /* bits 0-13 */ #define FH_RSCSR_FRAME_INVALID 0x #define FH_RSCSR_FRAME_ALIGN 0x40 diff --git a/drivers/net/wireless/iwlwifi/mvm/fw.c b/drivers/net/wireless/iwlwifi/
[PATCH 37/37] iwlwifi: mvm: clean up fw-api-scan.h
From: David Spinadel Remove outdated and unused definitions Signed-off-by: David Spinadel Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h | 129 - 1 file changed, 129 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h index 4787c32..be9b665 100644 --- a/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h +++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h @@ -87,41 +87,6 @@ struct iwl_ssid_ie { u8 ssid[IEEE80211_MAX_SSID_LEN]; } __packed; /* SCAN_DIRECT_SSID_IE_API_S_VER_1 */ -/* How many statistics are gathered for each channel */ -#define SCAN_RESULTS_STATISTICS 1 - -/** - * enum iwl_scan_complete_status - status codes for scan complete notifications - * @SCAN_COMP_STATUS_OK: scan completed successfully - * @SCAN_COMP_STATUS_ABORT: scan was aborted by user - * @SCAN_COMP_STATUS_ERR_SLEEP: sending null sleep packet failed - * @SCAN_COMP_STATUS_ERR_CHAN_TIMEOUT: timeout before channel is ready - * @SCAN_COMP_STATUS_ERR_PROBE: sending probe request failed - * @SCAN_COMP_STATUS_ERR_WAKEUP: sending null wakeup packet failed - * @SCAN_COMP_STATUS_ERR_ANTENNAS: invalid antennas chosen at scan command - * @SCAN_COMP_STATUS_ERR_INTERNAL: internal error caused scan abort - * @SCAN_COMP_STATUS_ERR_COEX: medium was lost ot WiMax - * @SCAN_COMP_STATUS_P2P_ACTION_OK: P2P public action frame TX was successful - * (not an error!) - * @SCAN_COMP_STATUS_ITERATION_END: indicates end of one repetition the driver - * asked for - * @SCAN_COMP_STATUS_ERR_ALLOC_TE: scan could not allocate time events -*/ -enum iwl_scan_complete_status { - SCAN_COMP_STATUS_OK = 0x1, - SCAN_COMP_STATUS_ABORT = 0x2, - SCAN_COMP_STATUS_ERR_SLEEP = 0x3, - SCAN_COMP_STATUS_ERR_CHAN_TIMEOUT = 0x4, - SCAN_COMP_STATUS_ERR_PROBE = 0x5, - SCAN_COMP_STATUS_ERR_WAKEUP = 0x6, - SCAN_COMP_STATUS_ERR_ANTENNAS = 0x7, - SCAN_COMP_STATUS_ERR_INTERNAL = 0x8, - SCAN_COMP_STATUS_ERR_COEX = 0x9, - SCAN_COMP_STATUS_P2P_ACTION_OK = 0xA, - SCAN_COMP_STATUS_ITERATION_END = 0x0B, - SCAN_COMP_STATUS_ERR_ALLOC_TE = 0x0C, -}; - /* scan offload */ #define IWL_SCAN_MAX_BLACKLIST_LEN 64 #define IWL_SCAN_SHORT_BLACKLIST_LEN 16 @@ -144,71 +109,6 @@ enum scan_framework_client { }; /** - * struct iwl_scan_offload_cmd - SCAN_REQUEST_FIXED_PART_API_S_VER_6 - * @scan_flags:see enum iwl_scan_flags - * @channel_count: channels in channel list - * @quiet_time:dwell time, in milliseconds, on quiet channel - * @quiet_plcp_th: quiet channel num of packets threshold - * @good_CRC_th: passive to active promotion threshold - * @rx_chain: RXON rx chain. - * @max_out_time: max TUs to be out of associated channel - * @suspend_time: pause scan this TUs when returning to service channel - * @flags: RXON flags - * @filter_flags: RXONfilter - * @tx_cmd:tx command for active scan; for 2GHz and for 5GHz. - * @direct_scan: list of SSIDs for directed active scan - * @scan_type: see enum iwl_scan_type. - * @rep_count: repetition count for each scheduled scan iteration. - */ -struct iwl_scan_offload_cmd { - __le16 len; - u8 scan_flags; - u8 channel_count; - __le16 quiet_time; - __le16 quiet_plcp_th; - __le16 good_CRC_th; - __le16 rx_chain; - __le32 max_out_time; - __le32 suspend_time; - /* RX_ON_FLAGS_API_S_VER_1 */ - __le32 flags; - __le32 filter_flags; - struct iwl_tx_cmd tx_cmd[2]; - /* SCAN_DIRECT_SSID_IE_API_S_VER_1 */ - struct iwl_ssid_ie direct_scan[PROBE_OPTION_MAX]; - __le32 scan_type; - __le32 rep_count; -} __packed; - -enum iwl_scan_offload_channel_flags { - IWL_SCAN_OFFLOAD_CHANNEL_ACTIVE = BIT(0), - IWL_SCAN_OFFLOAD_CHANNEL_NARROW = BIT(22), - IWL_SCAN_OFFLOAD_CHANNEL_FULL = BIT(24), - IWL_SCAN_OFFLOAD_CHANNEL_PARTIAL= BIT(25), -}; - -/* channel configuration for struct iwl_scan_offload_cfg. Each channels needs: - * __le32 type:bitmap; bits 1-20 are for directed scan to i'th ssid and - * see enum iwl_scan_offload_channel_flags. - * __le16 channel_number: channel number 1-13 etc. - * __le16 iter_count: repetition count for the channel. - * __le32 iter_interval: interval between two iterations on one channel. - * u8 active_dwell. - * u8 passive_dwell. - */ -#define IWL_SCAN_CHAN_SIZE 14 - -/** - * iwl_scan_offload_cfg - SCAN_OFFLOAD_CONFIG_API_S - * @scan_cmd: scan command fixed part - * @data: scan channel configuration and probe request frames - */ -struct iwl_scan_offload_cfg { - struct iwl_scan_offload_cmd scan_cmd; - u8 data[0]; -} __packed; - -/** * iwl_scan_offload_blacklist - SCAN_OFFLOAD_BLACKLIST_S * @ssid: MAC addres
[PATCH 33/37] iwlwifi: make various functions void in the file rs.c
From: Nicholas Krause This makes various functions in the file rs.c void due to these functions never returning a error code to signal to their callers if and how they have failed to complete their intended work. Signed-off-by: Nicholas Krause Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/rs.c | 51 +++ 1 file changed, 21 insertions(+), 30 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/dvm/rs.c b/drivers/net/wireless/iwlwifi/dvm/rs.c index 3bd7c86..cef921c 100644 --- a/drivers/net/wireless/iwlwifi/dvm/rs.c +++ b/drivers/net/wireless/iwlwifi/dvm/rs.c @@ -1416,11 +1416,11 @@ static int rs_switch_to_siso(struct iwl_priv *priv, /* * Try to switch to new modulation mode from legacy */ -static int rs_move_legacy_other(struct iwl_priv *priv, - struct iwl_lq_sta *lq_sta, - struct ieee80211_conf *conf, - struct ieee80211_sta *sta, - int index) +static void rs_move_legacy_other(struct iwl_priv *priv, +struct iwl_lq_sta *lq_sta, +struct ieee80211_conf *conf, +struct ieee80211_sta *sta, +int index) { struct iwl_scale_tbl_info *tbl = &(lq_sta->lq_info[lq_sta->active_tbl]); struct iwl_scale_tbl_info *search_tbl = @@ -1575,7 +1575,7 @@ static int rs_move_legacy_other(struct iwl_priv *priv, } search_tbl->lq_type = LQ_NONE; - return 0; + return; out: lq_sta->search_better_tbl = 1; @@ -1584,17 +1584,15 @@ out: tbl->action = IWL_LEGACY_SWITCH_ANTENNA1; if (update_search_tbl_counter) search_tbl->action = tbl->action; - return 0; - } /* * Try to switch to new modulation mode from SISO */ -static int rs_move_siso_to_other(struct iwl_priv *priv, -struct iwl_lq_sta *lq_sta, -struct ieee80211_conf *conf, -struct ieee80211_sta *sta, int index) +static void rs_move_siso_to_other(struct iwl_priv *priv, + struct iwl_lq_sta *lq_sta, + struct ieee80211_conf *conf, + struct ieee80211_sta *sta, int index) { u8 is_green = lq_sta->is_green; struct iwl_scale_tbl_info *tbl = &(lq_sta->lq_info[lq_sta->active_tbl]); @@ -1747,7 +1745,7 @@ static int rs_move_siso_to_other(struct iwl_priv *priv, break; } search_tbl->lq_type = LQ_NONE; - return 0; + return; out: lq_sta->search_better_tbl = 1; @@ -1756,17 +1754,15 @@ static int rs_move_siso_to_other(struct iwl_priv *priv, tbl->action = IWL_SISO_SWITCH_ANTENNA1; if (update_search_tbl_counter) search_tbl->action = tbl->action; - - return 0; } /* * Try to switch to new modulation mode from MIMO2 */ -static int rs_move_mimo2_to_other(struct iwl_priv *priv, -struct iwl_lq_sta *lq_sta, -struct ieee80211_conf *conf, -struct ieee80211_sta *sta, int index) +static void rs_move_mimo2_to_other(struct iwl_priv *priv, + struct iwl_lq_sta *lq_sta, + struct ieee80211_conf *conf, + struct ieee80211_sta *sta, int index) { s8 is_green = lq_sta->is_green; struct iwl_scale_tbl_info *tbl = &(lq_sta->lq_info[lq_sta->active_tbl]); @@ -1917,7 +1913,7 @@ static int rs_move_mimo2_to_other(struct iwl_priv *priv, break; } search_tbl->lq_type = LQ_NONE; - return 0; + return; out: lq_sta->search_better_tbl = 1; tbl->action++; @@ -1926,17 +1922,15 @@ static int rs_move_mimo2_to_other(struct iwl_priv *priv, if (update_search_tbl_counter) search_tbl->action = tbl->action; - return 0; - } /* * Try to switch to new modulation mode from MIMO3 */ -static int rs_move_mimo3_to_other(struct iwl_priv *priv, -struct iwl_lq_sta *lq_sta, -struct ieee80211_conf *conf, -struct ieee80211_sta *sta, int index) +static void rs_move_mimo3_to_other(struct iwl_priv *priv, + struct iwl_lq_sta *lq_sta, + struct ieee80211_conf *conf, + struct ieee80211_sta *sta, int index) { s8 is_green = lq_sta->is_green; struct iwl_scale_tbl_info *tbl = &(lq_sta->lq_info[lq_sta->active_tbl]); @@ -2093,7 +2087,7 @@ static int rs_move_mimo3_to_other(struct iwl_priv *priv, br
[PATCH 34/37] iwlwifi: add wide firmware command support for notifications
From: Sara Sharon Add support for extended command id in notification system. Extended command id header contains group id in addition to command id. Signed-off-by: Sara Sharon Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/mac80211.c | 2 +- drivers/net/wireless/iwlwifi/dvm/rxon.c | 3 ++- drivers/net/wireless/iwlwifi/dvm/ucode.c | 5 +++-- drivers/net/wireless/iwlwifi/iwl-notif-wait.c | 8 +--- drivers/net/wireless/iwlwifi/iwl-notif-wait.h | 5 +++-- drivers/net/wireless/iwlwifi/iwl-trans.h | 3 +++ drivers/net/wireless/iwlwifi/mvm/d3.c | 2 +- drivers/net/wireless/iwlwifi/mvm/fw.c | 4 ++-- drivers/net/wireless/iwlwifi/mvm/mac80211.c | 2 +- drivers/net/wireless/iwlwifi/mvm/scan.c | 2 +- drivers/net/wireless/iwlwifi/mvm/time-event.c | 4 ++-- drivers/net/wireless/iwlwifi/mvm/tt.c | 3 ++- 12 files changed, 26 insertions(+), 17 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/dvm/mac80211.c b/drivers/net/wireless/iwlwifi/dvm/mac80211.c index f603fb3..453f7c3 100644 --- a/drivers/net/wireless/iwlwifi/dvm/mac80211.c +++ b/drivers/net/wireless/iwlwifi/dvm/mac80211.c @@ -444,7 +444,7 @@ static int iwlagn_mac_resume(struct ieee80211_hw *hw) u32 error_id; } err_info; struct iwl_notification_wait status_wait; - static const u8 status_cmd[] = { + static const u16 status_cmd[] = { REPLY_WOWLAN_GET_STATUS, }; struct iwlagn_wowlan_status status_data = {}; diff --git a/drivers/net/wireless/iwlwifi/dvm/rxon.c b/drivers/net/wireless/iwlwifi/dvm/rxon.c index ed50de6..85ceceb 100644 --- a/drivers/net/wireless/iwlwifi/dvm/rxon.c +++ b/drivers/net/wireless/iwlwifi/dvm/rxon.c @@ -1,6 +1,7 @@ /** * * Copyright(c) 2003 - 2014 Intel Corporation. All rights reserved. + * Copyright(c) 2015 Intel Deutschland GmbH * * This program is free software; you can redistribute it and/or modify it * under the terms of version 2 of the GNU General Public License as @@ -123,7 +124,7 @@ static int iwlagn_disable_pan(struct iwl_priv *priv, __le32 old_filter = send->filter_flags; u8 old_dev_type = send->dev_type; int ret; - static const u8 deactivate_cmd[] = { + static const u16 deactivate_cmd[] = { REPLY_WIPAN_DEACTIVATION_COMPLETE }; diff --git a/drivers/net/wireless/iwlwifi/dvm/ucode.c b/drivers/net/wireless/iwlwifi/dvm/ucode.c index 5244e43..931a8e4 100644 --- a/drivers/net/wireless/iwlwifi/dvm/ucode.c +++ b/drivers/net/wireless/iwlwifi/dvm/ucode.c @@ -3,6 +3,7 @@ * GPL LICENSE SUMMARY * * Copyright(c) 2008 - 2014 Intel Corporation. All rights reserved. + * Copyright(c) 2015 Intel Deutschland GmbH * * This program is free software; you can redistribute it and/or modify * it under the terms of version 2 of the GNU General Public License as @@ -327,7 +328,7 @@ int iwl_load_ucode_wait_alive(struct iwl_priv *priv, const struct fw_img *fw; int ret; enum iwl_ucode_type old_type; - static const u8 alive_cmd[] = { REPLY_ALIVE }; + static const u16 alive_cmd[] = { REPLY_ALIVE }; fw = iwl_get_ucode_image(priv, ucode_type); if (WARN_ON(!fw)) @@ -406,7 +407,7 @@ static bool iwlagn_wait_calib(struct iwl_notif_wait_data *notif_wait, int iwl_run_init_ucode(struct iwl_priv *priv) { struct iwl_notification_wait calib_wait; - static const u8 calib_complete[] = { + static const u16 calib_complete[] = { CALIBRATION_RES_NOTIFICATION, CALIBRATION_COMPLETE_NOTIFICATION }; diff --git a/drivers/net/wireless/iwlwifi/iwl-notif-wait.c b/drivers/net/wireless/iwlwifi/iwl-notif-wait.c index b5bc959..6caf2af 100644 --- a/drivers/net/wireless/iwlwifi/iwl-notif-wait.c +++ b/drivers/net/wireless/iwlwifi/iwl-notif-wait.c @@ -6,6 +6,7 @@ * GPL LICENSE SUMMARY * * Copyright(c) 2007 - 2014 Intel Corporation. All rights reserved. + * Copyright(c) 2015 Intel Deutschland GmbH * * This program is free software; you can redistribute it and/or modify * it under the terms of version 2 of the GNU General Public License as @@ -98,7 +99,8 @@ void iwl_notification_wait_notify(struct iwl_notif_wait_data *notif_wait, continue; for (i = 0; i < w->n_cmds; i++) { - if (w->cmds[i] == pkt->hdr.cmd) { + if (w->cmds[i] == + WIDE_ID(pkt->hdr.group_id, pkt->hdr.cmd)) { found = true; break; } @@ -136,7 +138,7 @@ IWL_EXPORT_SYMBOL(iwl_abort_notification_waits); void iwl_init_notification_wait(struct iwl_notif_wait_data *notif_wait, struct iwl_notification_wait
[PATCH 09/37] iwlwifi: dvm: remove ADD_STA prints relying on station ID
From: Johannes Berg This makes the logging a little less useful, but as they're mostly synchronous commands it won't matter much. It gets rid of the dependency on the input command, which this is the only user of. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/sta.c | 34 ++ 1 file changed, 6 insertions(+), 28 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/dvm/sta.c b/drivers/net/wireless/iwlwifi/dvm/sta.c index 346077f..6e1e23e 100644 --- a/drivers/net/wireless/iwlwifi/dvm/sta.c +++ b/drivers/net/wireless/iwlwifi/dvm/sta.c @@ -61,11 +61,9 @@ static int iwl_sta_ucode_activate(struct iwl_priv *priv, u8 sta_id) } static int iwl_process_add_sta_resp(struct iwl_priv *priv, - struct iwl_addsta_cmd *addsta, struct iwl_rx_packet *pkt) { struct iwl_add_sta_resp *add_sta_resp = (void *)pkt->data; - u8 sta_id = addsta->sta.sta_id; if (pkt->hdr.flags & IWL_CMD_FAILED_MSK) { IWL_ERR(priv, "Bad return from REPLY_ADD_STA (0x%08X)\n", @@ -73,8 +71,7 @@ static int iwl_process_add_sta_resp(struct iwl_priv *priv, return 0; } - IWL_DEBUG_INFO(priv, "Processing response for adding station %u\n", - sta_id); + IWL_DEBUG_INFO(priv, "Processing response for adding station\n"); spin_lock_bh(&priv->sta_lock); @@ -83,16 +80,14 @@ static int iwl_process_add_sta_resp(struct iwl_priv *priv, IWL_DEBUG_INFO(priv, "REPLY_ADD_STA PASSED\n"); break; case ADD_STA_NO_ROOM_IN_TABLE: - IWL_ERR(priv, "Adding station %d failed, no room in table.\n", - sta_id); + IWL_ERR(priv, "Adding station failed, no room in table.\n"); break; case ADD_STA_NO_BLOCK_ACK_RESOURCE: - IWL_ERR(priv, "Adding station %d failed, no block ack " - "resource.\n", sta_id); + IWL_ERR(priv, + "Adding station failed, no block ack resource.\n"); break; case ADD_STA_MODIFY_NON_EXIST_STA: - IWL_ERR(priv, "Attempting to modify non-existing station %d\n", - sta_id); + IWL_ERR(priv, "Attempting to modify non-existing station\n"); break; default: IWL_DEBUG_ASSOC(priv, "Received REPLY_ADD_STA:(0x%08X)\n", @@ -100,23 +95,6 @@ static int iwl_process_add_sta_resp(struct iwl_priv *priv, break; } - IWL_DEBUG_INFO(priv, "%s station id %u addr %pM\n", - priv->stations[sta_id].sta.mode == - STA_CONTROL_MODIFY_MSK ? "Modified" : "Added", - sta_id, priv->stations[sta_id].sta.sta.addr); - - /* -* XXX: The MAC address in the command buffer is often changed from -* the original sent to the device. That is, the MAC address -* written to the command buffer often is not the same MAC address -* read from the command buffer when the command returns. This -* issue has not yet been resolved and this debugging is left to -* observe the problem. -*/ - IWL_DEBUG_INFO(priv, "%s station according to cmd buffer %pM\n", - priv->stations[sta_id].sta.mode == - STA_CONTROL_MODIFY_MSK ? "Modified" : "Added", - addsta->sta.addr); spin_unlock_bh(&priv->sta_lock); return 0; @@ -130,7 +108,7 @@ int iwl_add_sta_callback(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb, if (!cmd) return 0; - return iwl_process_add_sta_resp(priv, (void *)cmd->payload, pkt); + return iwl_process_add_sta_resp(priv, pkt); } int iwl_send_add_sta(struct iwl_priv *priv, -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 36/37] iwlwifi: mvm: add wide firmware command support for debug triggers
From: Sara Sharon Add support for extended command id in triggers handling. Extended command id header contains group id in addition to command id. Signed-off-by: Sara Sharon Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/ops.c | 7 --- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/ops.c b/drivers/net/wireless/iwlwifi/mvm/ops.c index a424d95..6957d02 100644 --- a/drivers/net/wireless/iwlwifi/mvm/ops.c +++ b/drivers/net/wireless/iwlwifi/mvm/ops.c @@ -703,12 +703,13 @@ static inline void iwl_mvm_rx_check_trigger(struct iwl_mvm *mvm, if (!cmds_trig->cmds[i].cmd_id) break; - if (cmds_trig->cmds[i].cmd_id != pkt->hdr.cmd) + if (cmds_trig->cmds[i].cmd_id != pkt->hdr.cmd || + cmds_trig->cmds[i].group_id != pkt->hdr.group_id) continue; iwl_mvm_fw_dbg_collect_trig(mvm, trig, - "CMD 0x%02x received", - pkt->hdr.cmd); + "CMD 0x%02x.%02x received", + pkt->hdr.group_id, pkt->hdr.cmd); break; } } -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 31/37] iwlwifi: pcie: reset write pointer on ict reset
From: Eliad Peller Since the CSR_DRAM_INIT_TBL_WRITE_POINTER bit wasn't set on ict reset, in some flows (like disable ict followed by immediate reset ict) the driver and hardware went out of sync (the driver cleared the ict_index, while the hw kept it intact). Fix it by setting the flag when resetting ict. Signed-off-by: Eliad Peller Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-csr.h | 1 + drivers/net/wireless/iwlwifi/pcie/rx.c | 5 +++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/iwl-csr.h b/drivers/net/wireless/iwlwifi/iwl-csr.h index faa17f2..fa71661 100644 --- a/drivers/net/wireless/iwlwifi/iwl-csr.h +++ b/drivers/net/wireless/iwlwifi/iwl-csr.h @@ -422,6 +422,7 @@ enum { /* DRAM INT TABLE */ #define CSR_DRAM_INT_TBL_ENABLE(1 << 31) +#define CSR_DRAM_INIT_TBL_WRITE_POINTER(1 << 28) #define CSR_DRAM_INIT_TBL_WRAP_CHECK (1 << 27) /* diff --git a/drivers/net/wireless/iwlwifi/pcie/rx.c b/drivers/net/wireless/iwlwifi/pcie/rx.c index 5561dee..454ef1d 100644 --- a/drivers/net/wireless/iwlwifi/pcie/rx.c +++ b/drivers/net/wireless/iwlwifi/pcie/rx.c @@ -1443,8 +1443,9 @@ void iwl_pcie_reset_ict(struct iwl_trans *trans) val = trans_pcie->ict_tbl_dma >> ICT_SHIFT; - val |= CSR_DRAM_INT_TBL_ENABLE; - val |= CSR_DRAM_INIT_TBL_WRAP_CHECK; + val |= CSR_DRAM_INT_TBL_ENABLE | + CSR_DRAM_INIT_TBL_WRAP_CHECK | + CSR_DRAM_INIT_TBL_WRITE_POINTER; IWL_DEBUG_ISR(trans, "CSR_DRAM_INT_TBL_REG =0x%x\n", val); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 24/37] iwlwifi: mvm: update comment of power_scheme module parameter
From: Avri Altman Signed-off-by: Avri Altman Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/mvm.h | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/mvm.h b/drivers/net/wireless/iwlwifi/mvm/mvm.h index d78af9f..767880b 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mvm.h +++ b/drivers/net/wireless/iwlwifi/mvm/mvm.h @@ -123,8 +123,7 @@ extern const struct ieee80211_ops iwl_mvm_hw_ops; * be up'ed after the INIT fw asserted. This is useful to be able to use * proprietary tools over testmode to debug the INIT fw. * @tfd_q_hang_detect: enabled the detection of hung transmit queues - * @power_scheme: CAM(Continuous Active Mode)-1, BPS(Balanced Power - * Save)-2(default), LP(Low Power)-3 + * @power_scheme: one of enum iwl_power_scheme */ struct iwl_mvm_mod_params { bool init_dbg; -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 29/37] iwlwifi: mvm: ignore CQM when setting beacon filtering in D0i3 enter flow
From: Gregory Greenman CQM overwrites a few thresholds in the bf command. On the other hand, when entering D0i3 the thresholds are set to higher values on purpose, so ignore CQM in this case. Signed-off-by: Gregory Greenman Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/power.c | 7 --- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/power.c b/drivers/net/wireless/iwlwifi/mvm/power.c index 8e2490a..506294f 100644 --- a/drivers/net/wireless/iwlwifi/mvm/power.c +++ b/drivers/net/wireless/iwlwifi/mvm/power.c @@ -112,11 +112,12 @@ int iwl_mvm_beacon_filter_send_cmd(struct iwl_mvm *mvm, static void iwl_mvm_beacon_filter_set_cqm_params(struct iwl_mvm *mvm, struct ieee80211_vif *vif, - struct iwl_beacon_filter_cmd *cmd) + struct iwl_beacon_filter_cmd *cmd, + bool d0i3) { struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); - if (vif->bss_conf.cqm_rssi_thold) { + if (vif->bss_conf.cqm_rssi_thold && !d0i3) { cmd->bf_energy_delta = cpu_to_le32(vif->bss_conf.cqm_rssi_hyst); /* fw uses an absolute value for this */ @@ -807,7 +808,7 @@ static int _iwl_mvm_enable_beacon_filter(struct iwl_mvm *mvm, vif->type != NL80211_IFTYPE_STATION || vif->p2p) return 0; - iwl_mvm_beacon_filter_set_cqm_params(mvm, vif, cmd); + iwl_mvm_beacon_filter_set_cqm_params(mvm, vif, cmd, d0i3); if (!d0i3) iwl_mvm_beacon_filter_debugfs_parameters(vif, cmd); ret = iwl_mvm_beacon_filter_send_cmd(mvm, cmd, cmd_flags); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 08/37] iwlwifi: dvm: move ADD_STA response handling to sync command
From: Johannes Berg This driver currently has some very confusing ADD_STA response handling that runs asynchronously in the background for all of the commands, but is only really necessary for synchronous ones (the really asynchronous ones can only be done for already existing stations), and for the sync ones it actually waits for the RX handler to return a status code. Rework this to keep the debug printing in the handler, but do the code that's supposed to have an effect only for sync commands in the command sending function. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/sta.c | 29 ++--- 1 file changed, 18 insertions(+), 11 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/dvm/sta.c b/drivers/net/wireless/iwlwifi/dvm/sta.c index 6ec86ad..346077f 100644 --- a/drivers/net/wireless/iwlwifi/dvm/sta.c +++ b/drivers/net/wireless/iwlwifi/dvm/sta.c @@ -66,12 +66,11 @@ static int iwl_process_add_sta_resp(struct iwl_priv *priv, { struct iwl_add_sta_resp *add_sta_resp = (void *)pkt->data; u8 sta_id = addsta->sta.sta_id; - int ret = -EIO; if (pkt->hdr.flags & IWL_CMD_FAILED_MSK) { IWL_ERR(priv, "Bad return from REPLY_ADD_STA (0x%08X)\n", pkt->hdr.flags); - return ret; + return 0; } IWL_DEBUG_INFO(priv, "Processing response for adding station %u\n", @@ -82,7 +81,6 @@ static int iwl_process_add_sta_resp(struct iwl_priv *priv, switch (add_sta_resp->status) { case ADD_STA_SUCCESS_MSK: IWL_DEBUG_INFO(priv, "REPLY_ADD_STA PASSED\n"); - ret = iwl_sta_ucode_activate(priv, sta_id); break; case ADD_STA_NO_ROOM_IN_TABLE: IWL_ERR(priv, "Adding station %d failed, no room in table.\n", @@ -121,7 +119,7 @@ static int iwl_process_add_sta_resp(struct iwl_priv *priv, addsta->sta.addr); spin_unlock_bh(&priv->sta_lock); - return ret; + return 0; } int iwl_add_sta_callback(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb, @@ -146,6 +144,8 @@ int iwl_send_add_sta(struct iwl_priv *priv, .len = { sizeof(*sta), }, }; u8 sta_id __maybe_unused = sta->sta.sta_id; + struct iwl_rx_packet *pkt; + struct iwl_add_sta_resp *add_sta_resp; IWL_DEBUG_INFO(priv, "Adding sta %u (%pM) %ssynchronously\n", sta_id, sta->sta.addr, flags & CMD_ASYNC ? "a" : ""); @@ -159,16 +159,23 @@ int iwl_send_add_sta(struct iwl_priv *priv, if (ret || (flags & CMD_ASYNC)) return ret; - /*else the command was successfully sent in SYNC mode, need to free -* the reply page */ - iwl_free_resp(&cmd); + pkt = cmd.resp_pkt; + add_sta_resp = (void *)pkt->data; - if (cmd.handler_status) - IWL_ERR(priv, "%s - error in the CMD response %d\n", __func__, - cmd.handler_status); + /* debug messages are printed in the handler */ + if (!(pkt->hdr.flags & IWL_CMD_FAILED_MSK) && + add_sta_resp->status == ADD_STA_SUCCESS_MSK) { + spin_lock_bh(&priv->sta_lock); + ret = iwl_sta_ucode_activate(priv, sta_id); + spin_unlock_bh(&priv->sta_lock); + } else { + ret = -EIO; + } + + iwl_free_resp(&cmd); - return cmd.handler_status; + return ret; } bool iwl_is_ht40_tx_allowed(struct iwl_priv *priv, -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 18/37] iwlwifi: mvm: remove IWL_UCODE_TLV_API_BASIC_DWELL
From: Sara Sharon All the supported firmwares support this API. This includes removing dwell per band, as band is no longer a factor in calculating the dwell. Only basic dwell is used and FW will calculate the actual dwell time. Signed-off-by: Sara Sharon Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-fw-file.h | 4 -- drivers/net/wireless/iwlwifi/mvm/scan.c| 86 +++--- 2 files changed, 20 insertions(+), 70 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/iwl-fw-file.h b/drivers/net/wireless/iwlwifi/iwl-fw-file.h index a9b5ae4..1c6f7b9 100644 --- a/drivers/net/wireless/iwlwifi/iwl-fw-file.h +++ b/drivers/net/wireless/iwlwifi/iwl-fw-file.h @@ -247,9 +247,6 @@ typedef unsigned int __bitwise__ iwl_ucode_tlv_api_t; * @IWL_UCODE_TLV_API_WIFI_MCC_UPDATE: ucode supports MCC updates with source. * IWL_UCODE_TLV_API_HDC_PHASE_0: ucode supports finer configuration of LTR * @IWL_UCODE_TLV_API_TX_POWER_DEV: new API for tx power. - * @IWL_UCODE_TLV_API_BASIC_DWELL: use only basic dwell time in scan command, - * regardless of the band or the number of the probes. FW will calculate - * the actual dwell time. * @IWL_UCODE_TLV_API_SCD_CFG: This firmware can configure the scheduler * through the dedicated host command. * @IWL_UCODE_TLV_API_SINGLE_SCAN_EBS: EBS is supported for single scans too. @@ -266,7 +263,6 @@ enum iwl_ucode_tlv_api { IWL_UCODE_TLV_API_WIFI_MCC_UPDATE = (__force iwl_ucode_tlv_api_t)9, IWL_UCODE_TLV_API_HDC_PHASE_0 = (__force iwl_ucode_tlv_api_t)10, IWL_UCODE_TLV_API_TX_POWER_DEV = (__force iwl_ucode_tlv_api_t)11, - IWL_UCODE_TLV_API_BASIC_DWELL = (__force iwl_ucode_tlv_api_t)13, IWL_UCODE_TLV_API_SCD_CFG = (__force iwl_ucode_tlv_api_t)15, IWL_UCODE_TLV_API_SINGLE_SCAN_EBS = (__force iwl_ucode_tlv_api_t)16, IWL_UCODE_TLV_API_ASYNC_DTM = (__force iwl_ucode_tlv_api_t)17, diff --git a/drivers/net/wireless/iwlwifi/mvm/scan.c b/drivers/net/wireless/iwlwifi/mvm/scan.c index 9c70118..b891fa5 100644 --- a/drivers/net/wireless/iwlwifi/mvm/scan.c +++ b/drivers/net/wireless/iwlwifi/mvm/scan.c @@ -90,11 +90,9 @@ struct iwl_mvm_scan_params { int n_match_sets; struct iwl_scan_probe_req preq; struct cfg80211_match_set *match_sets; - struct _dwell { - u16 passive; - u16 active; - u16 fragmented; - } dwell[IEEE80211_NUM_BANDS]; + u16 passive_dwell; + u16 active_dwell; + u16 fragmented_dwell; struct { u8 iterations; u8 full_scan_mul; /* not used for UMAC */ @@ -147,34 +145,6 @@ iwl_mvm_scan_rate_n_flags(struct iwl_mvm *mvm, enum ieee80211_band band, return cpu_to_le32(IWL_RATE_6M_PLCP | tx_ant); } -/* - * If req->n_ssids > 0, it means we should do an active scan. - * In case of active scan w/o directed scan, we receive a zero-length SSID - * just to notify that this scan is active and not passive. - * In order to notify the FW of the number of SSIDs we wish to scan (including - * the zero-length one), we need to set the corresponding bits in chan->type, - * one for each SSID, and set the active bit (first). If the first SSID is - * already included in the probe template, so we need to set only - * req->n_ssids - 1 bits in addition to the first bit. - */ -static u16 iwl_mvm_get_active_dwell(struct iwl_mvm *mvm, - enum ieee80211_band band, int n_ssids) -{ - if (fw_has_api(&mvm->fw->ucode_capa, IWL_UCODE_TLV_API_BASIC_DWELL)) - return 10; - if (band == IEEE80211_BAND_2GHZ) - return 20 + 3 * (n_ssids + 1); - return 10 + 2 * (n_ssids + 1); -} - -static u16 iwl_mvm_get_passive_dwell(struct iwl_mvm *mvm, -enum ieee80211_band band) -{ - if (fw_has_api(&mvm->fw->ucode_capa, IWL_UCODE_TLV_API_BASIC_DWELL)) - return 110; - return band == IEEE80211_BAND_2GHZ ? 100 + 20 : 100 + 10; -} - static void iwl_mvm_scan_condition_iterator(void *data, u8 *mac, struct ieee80211_vif *vif) { @@ -191,7 +161,6 @@ static void iwl_mvm_scan_calc_dwell(struct iwl_mvm *mvm, struct iwl_mvm_scan_params *params) { int global_cnt = 0; - enum ieee80211_band band; u8 frag_passive_dwell = 0; ieee80211_iterate_active_interfaces_atomic(mvm->hw, @@ -227,14 +196,10 @@ static void iwl_mvm_scan_calc_dwell(struct iwl_mvm *mvm, /* * P2P device scan should not be fragmented to avoid negative * impact on P2P device discovery. Configure max_out_time to be -* equal to dwell time on passive channel. Take a longest -* possible value, one that corresponds to 2GHz ba
[PATCH 28/37] iwlwifi: mvm: fix beacon filtering temperature thresholds for D0i3
From: Gregory Greenman The slow filtering threshold should be higher in D0i3 case. Signed-off-by: Gregory Greenman Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/fw-api-power.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h b/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h index b1baa33..b86b169 100644 --- a/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h +++ b/drivers/net/wireless/iwlwifi/mvm/fw-api-power.h @@ -413,7 +413,7 @@ struct iwl_beacon_filter_cmd { #define IWL_BF_TEMP_FAST_FILTER_MIN 0 #define IWL_BF_TEMP_SLOW_FILTER_DEFAULT 5 -#define IWL_BF_TEMP_SLOW_FILTER_D0I3 5 +#define IWL_BF_TEMP_SLOW_FILTER_D0I3 20 #define IWL_BF_TEMP_SLOW_FILTER_MAX 255 #define IWL_BF_TEMP_SLOW_FILTER_MIN 0 -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 14/37] iwlwifi: pcie: cancel Tx timer upon firmware crash
When the firmware crashes, we can't expect the Tx queues to progress. Cancel their timer. Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/pcie/rx.c | 4 1 file changed, 4 insertions(+) diff --git a/drivers/net/wireless/iwlwifi/pcie/rx.c b/drivers/net/wireless/iwlwifi/pcie/rx.c index 32ec95b..5561dee 100644 --- a/drivers/net/wireless/iwlwifi/pcie/rx.c +++ b/drivers/net/wireless/iwlwifi/pcie/rx.c @@ -1014,6 +1014,7 @@ restart: static void iwl_pcie_irq_handle_error(struct iwl_trans *trans) { struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans); + int i; /* W/A for WiFi/WiMAX coex and WiMAX own the RF */ if (trans->cfg->internal_wimax_coex && @@ -1037,6 +1038,9 @@ static void iwl_pcie_irq_handle_error(struct iwl_trans *trans) iwl_trans_fw_error(trans); local_bh_enable(); + for (i = 0; i < trans->cfg->base_params->num_of_queues; i++) + del_timer(&trans_pcie->txq[i].stuck_timer); + clear_bit(STATUS_SYNC_HCMD_ACTIVE, &trans->status); wake_up(&trans_pcie->wait_command_queue); } -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 26/37] iwlwifi: pcie: provide a way to stop configuration if it is forbidden
From: Haim Dreyfuss The firmware debug infrastructure allows the user to provide a firmware that will toggle a few registers to configure the debugging capabilities. On certain devices, certain operations are forbidden. Executing a forbidden operation will cause the hardware to die in a way that only driver unload / load will bring it back to life. Fortunately, there is a way to know in advance if those operations will be accepted by the device. This is where the new PRPH_BLOCKBIT operation plays its role. If the bit X from PRPH register Y is set, then we should prevent any further register configuration. When that happens, drop a line in the kernel log since this is really an error state: the user won't have his device configured as he expected. Add operations that will be used in the future: INDIRECT_ASSIGN, INDIRECT_SETBIT, and INDIRECT_CLEARBIT. Other debugging configurations (such as destination configuration for the monitor) will take place in any case. Signed-off-by: Haim Dreyfuss Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-fw-file.h | 6 ++ drivers/net/wireless/iwlwifi/pcie/trans.c | 9 + 2 files changed, 15 insertions(+) diff --git a/drivers/net/wireless/iwlwifi/iwl-fw-file.h b/drivers/net/wireless/iwlwifi/iwl-fw-file.h index f99ec4e..884825c 100644 --- a/drivers/net/wireless/iwlwifi/iwl-fw-file.h +++ b/drivers/net/wireless/iwlwifi/iwl-fw-file.h @@ -412,6 +412,12 @@ enum iwl_fw_dbg_reg_operator { PRPH_ASSIGN, PRPH_SETBIT, PRPH_CLEARBIT, + + INDIRECT_ASSIGN, + INDIRECT_SETBIT, + INDIRECT_CLEARBIT, + + PRPH_BLOCKBIT, }; /** diff --git a/drivers/net/wireless/iwlwifi/pcie/trans.c b/drivers/net/wireless/iwlwifi/pcie/trans.c index 88ab79f..46e900e 100644 --- a/drivers/net/wireless/iwlwifi/pcie/trans.c +++ b/drivers/net/wireless/iwlwifi/pcie/trans.c @@ -881,6 +881,14 @@ static void iwl_pcie_apply_destination(struct iwl_trans *trans) case PRPH_CLEARBIT: iwl_clear_bits_prph(trans, addr, BIT(val)); break; + case PRPH_BLOCKBIT: + if (iwl_read_prph(trans, addr) & BIT(val)) { + IWL_ERR(trans, + "BIT(%u) in address 0x%x is 1, stopping FW configuration\n", + val, addr); + goto monitor; + } + break; default: IWL_ERR(trans, "FW debug - unknown OP %d\n", dest->reg_ops[i].op); @@ -888,6 +896,7 @@ static void iwl_pcie_apply_destination(struct iwl_trans *trans) } } +monitor: if (dest->monitor_mode == EXTERNAL_MODE && trans_pcie->fw_mon_size) { iwl_write_prph(trans, le32_to_cpu(dest->base_reg), trans_pcie->fw_mon_phys >> dest->base_shift); -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 11/37] iwlwifi: mvm: remove command/return value from RX handlers
From: Johannes Berg In the mvm driver, neither the old command nor the return value are used, so remove them. Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/coex.c| 44 +- drivers/net/wireless/iwlwifi/mvm/coex_legacy.c | 31 +++ drivers/net/wireless/iwlwifi/mvm/fw.c | 13 +-- drivers/net/wireless/iwlwifi/mvm/mac-ctxt.c| 13 +-- drivers/net/wireless/iwlwifi/mvm/mvm.h | 107 ++--- drivers/net/wireless/iwlwifi/mvm/nvm.c | 11 +-- drivers/net/wireless/iwlwifi/mvm/ops.c | 22 ++--- drivers/net/wireless/iwlwifi/mvm/power.c | 7 +- drivers/net/wireless/iwlwifi/mvm/rx.c | 20 ++--- drivers/net/wireless/iwlwifi/mvm/scan.c| 35 +++- drivers/net/wireless/iwlwifi/mvm/sta.c | 9 +-- drivers/net/wireless/iwlwifi/mvm/sta.h | 5 +- drivers/net/wireless/iwlwifi/mvm/tdls.c| 12 +-- drivers/net/wireless/iwlwifi/mvm/time-event.c | 7 +- drivers/net/wireless/iwlwifi/mvm/time-event.h | 5 +- drivers/net/wireless/iwlwifi/mvm/tt.c | 10 +-- drivers/net/wireless/iwlwifi/mvm/tx.c | 16 ++-- drivers/net/wireless/iwlwifi/mvm/utils.c | 4 +- 18 files changed, 139 insertions(+), 232 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/coex.c b/drivers/net/wireless/iwlwifi/mvm/coex.c index b4737e2..e290ac6 100644 --- a/drivers/net/wireless/iwlwifi/mvm/coex.c +++ b/drivers/net/wireless/iwlwifi/mvm/coex.c @@ -725,15 +725,17 @@ static void iwl_mvm_bt_coex_notif_handle(struct iwl_mvm *mvm) } } -int iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm, -struct iwl_rx_cmd_buffer *rxb, -struct iwl_device_cmd *dev_cmd) +void iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb) { struct iwl_rx_packet *pkt = rxb_addr(rxb); struct iwl_bt_coex_profile_notif *notif = (void *)pkt->data; - if (!fw_has_api(&mvm->fw->ucode_capa, IWL_UCODE_TLV_API_BT_COEX_SPLIT)) - return iwl_mvm_rx_bt_coex_notif_old(mvm, rxb, dev_cmd); + if (!fw_has_api(&mvm->fw->ucode_capa, + IWL_UCODE_TLV_API_BT_COEX_SPLIT)) { + iwl_mvm_rx_bt_coex_notif_old(mvm, rxb); + return; + } IWL_DEBUG_COEX(mvm, "BT Coex Notification received\n"); IWL_DEBUG_COEX(mvm, "\tBT ci compliance %d\n", notif->bt_ci_compliance); @@ -748,12 +750,6 @@ int iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm, memcpy(&mvm->last_bt_notif, notif, sizeof(mvm->last_bt_notif)); iwl_mvm_bt_coex_notif_handle(mvm); - - /* -* This is an async handler for a notification, returning anything other -* than 0 doesn't make sense even if HCMD failed. -*/ - return 0; } void iwl_mvm_bt_rssi_event(struct iwl_mvm *mvm, struct ieee80211_vif *vif, @@ -947,9 +943,8 @@ void iwl_mvm_bt_coex_vif_change(struct iwl_mvm *mvm) iwl_mvm_bt_coex_notif_handle(mvm); } -int iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm, - struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *dev_cmd) +void iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb) { struct iwl_rx_packet *pkt = rxb_addr(rxb); u32 ant_isolation = le32_to_cpup((void *)pkt->data); @@ -957,20 +952,23 @@ int iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm, u8 __maybe_unused lower_bound, upper_bound; u8 lut; - if (!fw_has_api(&mvm->fw->ucode_capa, IWL_UCODE_TLV_API_BT_COEX_SPLIT)) - return iwl_mvm_rx_ant_coupling_notif_old(mvm, rxb, dev_cmd); + if (!fw_has_api(&mvm->fw->ucode_capa, + IWL_UCODE_TLV_API_BT_COEX_SPLIT)) { + iwl_mvm_rx_ant_coupling_notif_old(mvm, rxb); + return; + } if (!iwl_mvm_bt_is_plcr_supported(mvm)) - return 0; + return; lockdep_assert_held(&mvm->mutex); /* Ignore updates if we are in force mode */ if (unlikely(mvm->bt_force_ant_mode != BT_FORCE_ANT_DIS)) - return 0; + return; if (ant_isolation == mvm->last_ant_isol) - return 0; + return; for (lut = 0; lut < ARRAY_SIZE(antenna_coupling_ranges) - 1; lut++) if (ant_isolation < antenna_coupling_ranges[lut + 1].range) @@ -989,7 +987,7 @@ int iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm, mvm->last_ant_isol = ant_isolation; if (mvm->last_corun_lut == lut) - return 0; + return; mvm->last_corun_lut = lut; @@ -1000,6 +998,8 @@ int iwl_mvm_rx_ant_coupling_notif(struct iwl_mvm *mvm, memcpy(&cmd.corun_lut40, antenna_coupling_ranges[l
[PATCH 20/37] iwlwifi: add wide firmware command infrastructure for TX
From: Aviya Erenfeld As the firmware is slowly running out of command IDs and grouping of commands is desirable anyway, the firmware is extending the command header from 4 bytes to 8 bytes to introduce a group (in place of the former flags field, since that's always 0 on commands and thus can be easily used to distinguish between the two. In order to support this most easily in the driver widen the command command ID used in the command sending functions and encode the new values (group and version) in the ID. That way existing code doesn't have to be changed (since the higher bits are 0 automatically) and newer code can easily use the new ID generation function to create a value to use in place of just the command ID. Signed-off-by: Aviya Erenfeld Signed-off-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- .../net/wireless/iwlwifi/iwl-devtrace-iwlwifi.h| 14 +++-- drivers/net/wireless/iwlwifi/iwl-fw-file.h | 2 + drivers/net/wireless/iwlwifi/iwl-trans.h | 66 -- drivers/net/wireless/iwlwifi/mvm/mvm.h | 4 +- drivers/net/wireless/iwlwifi/mvm/ops.c | 2 + drivers/net/wireless/iwlwifi/mvm/utils.c | 4 +- drivers/net/wireless/iwlwifi/pcie/internal.h | 2 + drivers/net/wireless/iwlwifi/pcie/trans.c | 1 + drivers/net/wireless/iwlwifi/pcie/tx.c | 53 - 9 files changed, 121 insertions(+), 27 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/iwl-devtrace-iwlwifi.h b/drivers/net/wireless/iwlwifi/iwl-devtrace-iwlwifi.h index 948ce08..eb4b99a 100644 --- a/drivers/net/wireless/iwlwifi/iwl-devtrace-iwlwifi.h +++ b/drivers/net/wireless/iwlwifi/iwl-devtrace-iwlwifi.h @@ -36,7 +36,7 @@ TRACE_EVENT(iwlwifi_dev_hcmd, TP_PROTO(const struct device *dev, struct iwl_host_cmd *cmd, u16 total_size, -struct iwl_cmd_header *hdr), +struct iwl_cmd_header_wide *hdr), TP_ARGS(dev, cmd, total_size, hdr), TP_STRUCT__entry( DEV_ENTRY @@ -44,11 +44,14 @@ TRACE_EVENT(iwlwifi_dev_hcmd, __field(u32, flags) ), TP_fast_assign( - int i, offset = sizeof(*hdr); + int i, offset = sizeof(struct iwl_cmd_header); + + if (hdr->group_id) + offset = sizeof(struct iwl_cmd_header_wide); DEV_ASSIGN; __entry->flags = cmd->flags; - memcpy(__get_dynamic_array(hcmd), hdr, sizeof(*hdr)); + memcpy(__get_dynamic_array(hcmd), hdr, offset); for (i = 0; i < IWL_MAX_CMD_TBS_PER_TFD; i++) { if (!cmd->len[i]) @@ -58,8 +61,9 @@ TRACE_EVENT(iwlwifi_dev_hcmd, offset += cmd->len[i]; } ), - TP_printk("[%s] hcmd %#.2x (%ssync)", - __get_str(dev), ((u8 *)__get_dynamic_array(hcmd))[0], + TP_printk("[%s] hcmd %#.2x.%#.2x (%ssync)", + __get_str(dev), ((u8 *)__get_dynamic_array(hcmd))[1], + ((u8 *)__get_dynamic_array(hcmd))[0], __entry->flags & CMD_ASYNC ? "a" : "") ); diff --git a/drivers/net/wireless/iwlwifi/iwl-fw-file.h b/drivers/net/wireless/iwlwifi/iwl-fw-file.h index c31cf82..f99ec4e 100644 --- a/drivers/net/wireless/iwlwifi/iwl-fw-file.h +++ b/drivers/net/wireless/iwlwifi/iwl-fw-file.h @@ -247,6 +247,7 @@ typedef unsigned int __bitwise__ iwl_ucode_tlv_api_t; * @IWL_UCODE_TLV_API_WIFI_MCC_UPDATE: ucode supports MCC updates with source. * IWL_UCODE_TLV_API_HDC_PHASE_0: ucode supports finer configuration of LTR * @IWL_UCODE_TLV_API_TX_POWER_DEV: new API for tx power. + * @IWL_UCODE_TLV_API_WIDE_CMD_HDR: ucode supports wide command header * @IWL_UCODE_TLV_API_SCD_CFG: This firmware can configure the scheduler * through the dedicated host command. * @IWL_UCODE_TLV_API_SINGLE_SCAN_EBS: EBS is supported for single scans too. @@ -263,6 +264,7 @@ enum iwl_ucode_tlv_api { IWL_UCODE_TLV_API_WIFI_MCC_UPDATE = (__force iwl_ucode_tlv_api_t)9, IWL_UCODE_TLV_API_HDC_PHASE_0 = (__force iwl_ucode_tlv_api_t)10, IWL_UCODE_TLV_API_TX_POWER_DEV = (__force iwl_ucode_tlv_api_t)11, + IWL_UCODE_TLV_API_WIDE_CMD_HDR = (__force iwl_ucode_tlv_api_t)14, IWL_UCODE_TLV_API_SCD_CFG = (__force iwl_ucode_tlv_api_t)15, IWL_UCODE_TLV_API_SINGLE_SCAN_EBS = (__force iwl_ucode_tlv_api_t)16, IWL_UCODE_TLV_API_ASYNC_DTM = (__force iwl_ucode_tlv_api_t)17, diff --git a/drivers/net/wireless/iwlwifi/iwl-trans.h b/drivers/net/wireless/iwlwifi/iwl-trans.h index 64769e4..df71aa3 100644 --- a/drivers/net/wireless/iwlwifi/iwl-trans.h +++ b/drivers/net/wireless/iwlwifi/iwl-trans.h @@ -122,6 +122,32 @@ #define INDEX_TO_SEQ(i)((i) & 0xff) #define SEQ_RX_FRAME cpu_to_le16(0x8000) +/* + * those functions retrieve spe
[PATCH 16/37] iwlwifi: pcie: don't warn on long MPDUs when supported
In iwlmvm firmwares, the Byte count written in the scheduler byte count table is in DWORDs and not in bytes. We should check that this value fits in the 12 bits and the value can be either in bits of in DWORD or bytes depending on the firmware. Check the value after the translation to DWORDs is done (if needed). Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/pcie/tx.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/pcie/tx.c b/drivers/net/wireless/iwlwifi/pcie/tx.c index c6572ff..90d02d5 100644 --- a/drivers/net/wireless/iwlwifi/pcie/tx.c +++ b/drivers/net/wireless/iwlwifi/pcie/tx.c @@ -219,8 +219,6 @@ static void iwl_pcie_txq_update_byte_cnt_tbl(struct iwl_trans *trans, scd_bc_tbl = trans_pcie->scd_bc_tbls.addr; - WARN_ON(len > 0xFFF || write_ptr >= TFD_QUEUE_SIZE_MAX); - sta_id = tx_cmd->sta_id; sec_ctl = tx_cmd->sec_ctl; @@ -239,6 +237,9 @@ static void iwl_pcie_txq_update_byte_cnt_tbl(struct iwl_trans *trans, if (trans_pcie->bc_table_dword) len = DIV_ROUND_UP(len, 4); + if (WARN_ON(len > 0xFFF || write_ptr >= TFD_QUEUE_SIZE_MAX)) + return; + bc_ent = cpu_to_le16(len | (sta_id << 12)); scd_bc_tbl[txq_id].tfd_offset[write_ptr] = bc_ent; -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 05/37] iwlwifi: pcie: lock start_hw / start_fw / stop_device
This allows to ensure that we don't have races between them. A user reported that stop_device was called twice upon rfkill interrupt after suspend. When the interrupts are enabled, and right after when we directly check the rfkill state. Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/pcie/drv.c | 4 ++ drivers/net/wireless/iwlwifi/pcie/internal.h | 3 + drivers/net/wireless/iwlwifi/pcie/rx.c | 2 + drivers/net/wireless/iwlwifi/pcie/trans.c| 82 4 files changed, 81 insertions(+), 10 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/pcie/drv.c b/drivers/net/wireless/iwlwifi/pcie/drv.c index 2ed1e4d..dbd2a03 100644 --- a/drivers/net/wireless/iwlwifi/pcie/drv.c +++ b/drivers/net/wireless/iwlwifi/pcie/drv.c @@ -613,6 +613,7 @@ static int iwl_pci_resume(struct device *device) { struct pci_dev *pdev = to_pci_dev(device); struct iwl_trans *trans = pci_get_drvdata(pdev); + struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans); bool hw_rfkill; /* Before you put code here, think about WoWLAN. You cannot check here @@ -643,7 +644,10 @@ static int iwl_pci_resume(struct device *device) } hw_rfkill = iwl_is_rfkill_set(trans); + + mutex_lock(&trans_pcie->mutex); iwl_trans_pcie_rf_kill(trans, hw_rfkill); + mutex_unlock(&trans_pcie->mutex); return 0; } diff --git a/drivers/net/wireless/iwlwifi/pcie/internal.h b/drivers/net/wireless/iwlwifi/pcie/internal.h index 31f72a6..4f06407 100644 --- a/drivers/net/wireless/iwlwifi/pcie/internal.h +++ b/drivers/net/wireless/iwlwifi/pcie/internal.h @@ -301,6 +301,7 @@ iwl_pcie_get_scratchbuf_dma(struct iwl_txq *txq, int idx) * @scd_set_active: should the transport configure the SCD for HCMD queue * @rx_page_order: page order for receive buffer size * @reg_lock: protect hw register access + * @mutex: to protect stop_device / start_fw / start_hw * @cmd_in_flight: true when we have a host command in flight * @fw_mon_phys: physical address of the buffer for the firmware monitor * @fw_mon_page: points to the first page of the buffer for the firmware monitor @@ -320,9 +321,11 @@ struct iwl_trans_pcie { dma_addr_t ict_tbl_dma; int ict_index; bool use_ict; + bool is_down; struct isr_statistics isr_stats; spinlock_t irq_lock; + struct mutex mutex; u32 inta_mask; u32 scd_base_addr; struct iwl_dma_ptr scd_bc_tbls; diff --git a/drivers/net/wireless/iwlwifi/pcie/rx.c b/drivers/net/wireless/iwlwifi/pcie/rx.c index a3fbaa0..93062f2 100644 --- a/drivers/net/wireless/iwlwifi/pcie/rx.c +++ b/drivers/net/wireless/iwlwifi/pcie/rx.c @@ -1251,7 +1251,9 @@ irqreturn_t iwl_pcie_irq_handler(int irq, void *dev_id) isr_stats->rfkill++; + mutex_lock(&trans_pcie->mutex); iwl_trans_pcie_rf_kill(trans, hw_rfkill); + mutex_unlock(&trans_pcie->mutex); if (hw_rfkill) { set_bit(STATUS_RFKILL, &trans->status); if (test_and_clear_bit(STATUS_SYNC_HCMD_ACTIVE, diff --git a/drivers/net/wireless/iwlwifi/pcie/trans.c b/drivers/net/wireless/iwlwifi/pcie/trans.c index 43ae658..23f2824 100644 --- a/drivers/net/wireless/iwlwifi/pcie/trans.c +++ b/drivers/net/wireless/iwlwifi/pcie/trans.c @@ -982,13 +982,25 @@ static int iwl_pcie_load_given_ucode_8000(struct iwl_trans *trans, static int iwl_trans_pcie_start_fw(struct iwl_trans *trans, const struct fw_img *fw, bool run_in_rfkill) { - int ret; + struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans); bool hw_rfkill; + int ret; + + mutex_lock(&trans_pcie->mutex); + + /* Someone called stop_device, don't try to start_fw */ + if (trans_pcie->is_down) { + IWL_WARN(trans, +"Can't start_fw since the HW hasn't been started\n"); + ret = EIO; + goto out; + } /* This may fail if AMT took ownership of the device */ if (iwl_pcie_prepare_card_hw(trans)) { IWL_WARN(trans, "Exit HW not ready\n"); - return -EIO; + ret = -EIO; + goto out; } iwl_enable_rfkill_int(trans); @@ -1000,15 +1012,17 @@ static int iwl_trans_pcie_start_fw(struct iwl_trans *trans, else clear_bit(STATUS_RFKILL, &trans->status); iwl_trans_pcie_rf_kill(trans, hw_rfkill); - if (hw_rfkill && !run_in_rfkill) - return -ERFKILL; + if (hw_rfkill && !run_in_rfkill) { + ret = -ERFKILL; + goto out; + } iwl_write32(trans, CSR_INT, 0x); ret = iwl_pcie_nic_init(trans); if (ret) { IWL_ERR(trans, "Unable to init nic\n"); -
[PATCH 27/37] iwlwifi: mvm: Enable Rx Checksum hw
From: Avri Altman TCP software implementation on the host requires extensive computing power. Offloading even some of the TCP/IP stack to the NIC might save a significant overhead. In order to enable this feature on our hw, we need to configure it first. Once done, we mark this capability, to be advertised later to the OS via ieee80211_register_hw. The driver Rx indications for TCP Checksum is integrated within the standard Rx status. The driver responds to those indications as follows: If the frame was tested by hw and checksum ok report CHECKSUM_UNNECESSARY. Otherwise, report CHECKSUM_NONE. Signed-off-by: Avri Altman Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-8000.c | 1 + drivers/net/wireless/iwlwifi/iwl-config.h | 2 ++ drivers/net/wireless/iwlwifi/iwl-fw-file.h | 2 ++ drivers/net/wireless/iwlwifi/iwl-prph.h | 3 +++ drivers/net/wireless/iwlwifi/mvm/fw-api.h | 31 +++-- drivers/net/wireless/iwlwifi/mvm/fw.c | 4 drivers/net/wireless/iwlwifi/mvm/mac80211.c | 6 ++ drivers/net/wireless/iwlwifi/mvm/mvm.h | 10 ++ drivers/net/wireless/iwlwifi/mvm/rx.c | 17 9 files changed, 74 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/iwl-8000.c b/drivers/net/wireless/iwlwifi/iwl-8000.c index 0de5751..7caea69 100644 --- a/drivers/net/wireless/iwlwifi/iwl-8000.c +++ b/drivers/net/wireless/iwlwifi/iwl-8000.c @@ -154,6 +154,7 @@ static const struct iwl_tt_params iwl8000_tt_params = { .led_mode = IWL_LED_RF_STATE, \ .nvm_hw_section_num = NVM_HW_SECTION_NUM_FAMILY_8000, \ .d0i3 = true, \ + .features = NETIF_F_RXCSUM, \ .non_shared_ant = ANT_A,\ .dccm_offset = IWL8260_DCCM_OFFSET, \ .dccm_len = IWL8260_DCCM_LEN, \ diff --git a/drivers/net/wireless/iwlwifi/iwl-config.h b/drivers/net/wireless/iwlwifi/iwl-config.h index 08c14af..939fa22 100644 --- a/drivers/net/wireless/iwlwifi/iwl-config.h +++ b/drivers/net/wireless/iwlwifi/iwl-config.h @@ -297,6 +297,7 @@ struct iwl_pwr_tx_backoff { * mode set * @d0i3: device uses d0i3 instead of d3 * @nvm_hw_section_num: the ID of the HW NVM section + * @features: hw features, any combination of feature_whitelist * @pwr_tx_backoffs: translation table between power limits and backoffs * @max_rx_agg_size: max RX aggregation size of the ADDBA request/response * @max_tx_agg_size: max TX aggregation size of the ADDBA request/response @@ -348,6 +349,7 @@ struct iwl_cfg { bool no_power_up_nic_in_init; const char *default_nvm_file_B_step; const char *default_nvm_file_C_step; + netdev_features_t features; unsigned int max_rx_agg_size; bool disable_dummy_notification; unsigned int max_tx_agg_size; diff --git a/drivers/net/wireless/iwlwifi/iwl-fw-file.h b/drivers/net/wireless/iwlwifi/iwl-fw-file.h index 884825c..926e456 100644 --- a/drivers/net/wireless/iwlwifi/iwl-fw-file.h +++ b/drivers/net/wireless/iwlwifi/iwl-fw-file.h @@ -297,6 +297,7 @@ typedef unsigned int __bitwise__ iwl_ucode_tlv_capa_t; * @IWL_UCODE_TLV_CAPA_TDLS_CHANNEL_SWITCH: supports TDLS channel switching * @IWL_UCODE_TLV_CAPA_HOTSPOT_SUPPORT: supports Hot Spot Command * @IWL_UCODE_TLV_CAPA_DC2DC_SUPPORT: supports DC2DC Command + * @IWL_UCODE_TLV_CAPA_CSUM_SUPPORT: supports TCP Checksum Offload * @IWL_UCODE_TLV_CAPA_RADIO_BEACON_STATS: support radio and beacon statistics * @IWL_UCODE_TLV_CAPA_BT_COEX_PLCR: enabled BT Coex packet level co-running * @IWL_UCODE_TLV_CAPA_LAR_MULTI_MCC: ucode supports LAR updates with different @@ -320,6 +321,7 @@ enum iwl_ucode_tlv_capa { IWL_UCODE_TLV_CAPA_TDLS_CHANNEL_SWITCH = (__force iwl_ucode_tlv_capa_t)13, IWL_UCODE_TLV_CAPA_HOTSPOT_SUPPORT = (__force iwl_ucode_tlv_capa_t)18, IWL_UCODE_TLV_CAPA_DC2DC_CONFIG_SUPPORT = (__force iwl_ucode_tlv_capa_t)19, + IWL_UCODE_TLV_CAPA_CSUM_SUPPORT = (__force iwl_ucode_tlv_capa_t)21, IWL_UCODE_TLV_CAPA_RADIO_BEACON_STATS = (__force iwl_ucode_tlv_capa_t)22, IWL_UCODE_TLV_CAPA_BT_COEX_PLCR = (__force iwl_ucode_tlv_capa_t)28, IWL_UCODE_TLV_CAPA_LAR_MULTI_MCC= (__force iwl_ucode_tlv_capa_t)29, diff --git a/drivers/net/wireless/iwlwifi/iwl-prph.h b/drivers/net/wireless/iwlwifi/iwl-prph.h index a846904..cd98b9f 100644 --- a/drivers/net/wireless/iwlwifi/iwl-prph.h +++ b/drivers/net/wireless/iwlwifi/iwl-prph.h @@ -292,6 +292,9 @@ /*** END TX SCHEDULER */ +/* tcp checksum offload */ +#define RX_EN_CSUM (0x00a00d88) + /* Oscillator clock *
[PATCH 03/37] iwlwifi: deprecate -10.ucode for 3160 / 7260 / 7265
From: Sara Sharon This firmware is not supported anymore - stop loading this firmware. Remove code handling older versions. Signed-off-by: Sara Sharon Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-7000.c | 2 +- drivers/net/wireless/iwlwifi/iwl-8000.c | 2 +- drivers/net/wireless/iwlwifi/mvm/fw.c | 3 +-- 3 files changed, 3 insertions(+), 4 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/iwl-7000.c b/drivers/net/wireless/iwlwifi/iwl-7000.c index cc35f79..fa35da4 100644 --- a/drivers/net/wireless/iwlwifi/iwl-7000.c +++ b/drivers/net/wireless/iwlwifi/iwl-7000.c @@ -76,7 +76,7 @@ #define IWL3165_UCODE_API_OK 13 /* Lowest firmware API version supported */ -#define IWL7260_UCODE_API_MIN 10 +#define IWL7260_UCODE_API_MIN 12 #define IWL3165_UCODE_API_MIN 13 /* NVM versions */ diff --git a/drivers/net/wireless/iwlwifi/iwl-8000.c b/drivers/net/wireless/iwlwifi/iwl-8000.c index 72040cd..0de5751 100644 --- a/drivers/net/wireless/iwlwifi/iwl-8000.c +++ b/drivers/net/wireless/iwlwifi/iwl-8000.c @@ -75,7 +75,7 @@ #define IWL8000_UCODE_API_OK 12 /* Lowest firmware API version supported */ -#define IWL8000_UCODE_API_MIN 10 +#define IWL8000_UCODE_API_MIN 12 /* NVM versions */ #define IWL8000_NVM_VERSION0x0a1d diff --git a/drivers/net/wireless/iwlwifi/mvm/fw.c b/drivers/net/wireless/iwlwifi/mvm/fw.c index eb10c5e..a482ce6 100644 --- a/drivers/net/wireless/iwlwifi/mvm/fw.c +++ b/drivers/net/wireless/iwlwifi/mvm/fw.c @@ -676,8 +676,7 @@ int iwl_mvm_up(struct iwl_mvm *mvm) goto error; } - if (IWL_UCODE_API(mvm->fw->ucode_ver) >= 10) - iwl_mvm_get_shared_mem_conf(mvm); + iwl_mvm_get_shared_mem_conf(mvm); ret = iwl_mvm_sf_update(mvm, NULL, false); if (ret) -- 2.1.4 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 19/37] iwlwifi: mvm: add basic Time of Flight (802.11mc FTM) support
From: Gregory Greenman ToF is a time based method for measurement of the WiFi device location within a WiFi environment. The driver functionality provided by this patch is the interface for communication with FW and receiving location related updates from the FW. The interface provided by this patch is via debugfs. Signed-off-by: Gregory Greenman Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/iwl-fw-file.h | 2 + drivers/net/wireless/iwlwifi/mvm/Makefile | 1 + drivers/net/wireless/iwlwifi/mvm/constants.h | 1 + drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c | 751 + drivers/net/wireless/iwlwifi/mvm/fw-api-tof.h | 391 + drivers/net/wireless/iwlwifi/mvm/fw-api.h | 5 + drivers/net/wireless/iwlwifi/mvm/mvm.h | 2 + drivers/net/wireless/iwlwifi/mvm/ops.c | 5 + drivers/net/wireless/iwlwifi/mvm/tof.c | 311 ++ drivers/net/wireless/iwlwifi/mvm/tof.h | 94 10 files changed, 1563 insertions(+) create mode 100644 drivers/net/wireless/iwlwifi/mvm/fw-api-tof.h create mode 100644 drivers/net/wireless/iwlwifi/mvm/tof.c create mode 100644 drivers/net/wireless/iwlwifi/mvm/tof.h diff --git a/drivers/net/wireless/iwlwifi/iwl-fw-file.h b/drivers/net/wireless/iwlwifi/iwl-fw-file.h index 1c6f7b9..c31cf82 100644 --- a/drivers/net/wireless/iwlwifi/iwl-fw-file.h +++ b/drivers/net/wireless/iwlwifi/iwl-fw-file.h @@ -280,6 +280,7 @@ typedef unsigned int __bitwise__ iwl_ucode_tlv_capa_t; * @IWL_UCODE_TLV_CAPA_LAR_SUPPORT: supports Location Aware Regulatory * @IWL_UCODE_TLV_CAPA_UMAC_SCAN: supports UMAC scan. * @IWL_UCODE_TLV_CAPA_BEAMFORMER: supports Beamformer + * @IWL_UCODE_TLV_CAPA_TOF_SUPPORT: supports Time of Flight (802.11mc FTM) * @IWL_UCODE_TLV_CAPA_TDLS_SUPPORT: support basic TDLS functionality * @IWL_UCODE_TLV_CAPA_TXPOWER_INSERTION_SUPPORT: supports insertion of current * tx power value into TPC Report action frame and Link Measurement Report @@ -307,6 +308,7 @@ enum iwl_ucode_tlv_capa { IWL_UCODE_TLV_CAPA_LAR_SUPPORT = (__force iwl_ucode_tlv_capa_t)1, IWL_UCODE_TLV_CAPA_UMAC_SCAN= (__force iwl_ucode_tlv_capa_t)2, IWL_UCODE_TLV_CAPA_BEAMFORMER = (__force iwl_ucode_tlv_capa_t)3, + IWL_UCODE_TLV_CAPA_TOF_SUPPORT = (__force iwl_ucode_tlv_capa_t)5, IWL_UCODE_TLV_CAPA_TDLS_SUPPORT = (__force iwl_ucode_tlv_capa_t)6, IWL_UCODE_TLV_CAPA_TXPOWER_INSERTION_SUPPORT= (__force iwl_ucode_tlv_capa_t)8, IWL_UCODE_TLV_CAPA_DS_PARAM_SET_IE_SUPPORT = (__force iwl_ucode_tlv_capa_t)9, diff --git a/drivers/net/wireless/iwlwifi/mvm/Makefile b/drivers/net/wireless/iwlwifi/mvm/Makefile index 2d7c3ea..8c2c3d1 100644 --- a/drivers/net/wireless/iwlwifi/mvm/Makefile +++ b/drivers/net/wireless/iwlwifi/mvm/Makefile @@ -6,6 +6,7 @@ iwlmvm-y += power.o coex.o coex_legacy.o iwlmvm-y += tt.o offloading.o tdls.o iwlmvm-$(CONFIG_IWLWIFI_DEBUGFS) += debugfs.o debugfs-vif.o iwlmvm-$(CONFIG_IWLWIFI_LEDS) += led.o +iwlmvm-y += tof.o iwlmvm-$(CONFIG_PM_SLEEP) += d3.o ccflags-y += -D__CHECK_ENDIAN__ -I$(src)/../ diff --git a/drivers/net/wireless/iwlwifi/mvm/constants.h b/drivers/net/wireless/iwlwifi/mvm/constants.h index beba375..b8ee312 100644 --- a/drivers/net/wireless/iwlwifi/mvm/constants.h +++ b/drivers/net/wireless/iwlwifi/mvm/constants.h @@ -102,6 +102,7 @@ #define IWL_MVM_QUOTA_THRESHOLD4 #define IWL_MVM_RS_RSSI_BASED_INIT_RATE 0 #define IWL_MVM_RS_DISABLE_P2P_MIMO0 +#define IWL_MVM_TOF_IS_RESPONDER 0 #define IWL_MVM_RS_NUM_TRY_BEFORE_ANT_TOGGLE1 #define IWL_MVM_RS_HT_VHT_RETRIES_PER_RATE 2 #define IWL_MVM_RS_HT_VHT_RETRIES_PER_RATE_TW 1 diff --git a/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c b/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c index 5c8a65d..ddb1c84 100644 --- a/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c +++ b/drivers/net/wireless/iwlwifi/mvm/debugfs-vif.c @@ -63,6 +63,7 @@ * */ #include "mvm.h" +#include "fw-api-tof.h" #include "debugfs.h" static void iwl_dbgfs_update_pm(struct iwl_mvm *mvm, @@ -497,6 +498,731 @@ static ssize_t iwl_dbgfs_bf_params_read(struct file *file, return simple_read_from_buffer(user_buf, count, ppos, buf, pos); } +static inline char *iwl_dbgfs_is_match(char *name, char *buf) +{ + int len = strlen(name); + + return !strncmp(name, buf, len) ? buf + len : NULL; +} + +static ssize_t iwl_dbgfs_tof_enable_write(struct ieee80211_vif *vif, + char *buf, + size_t count, loff_t *ppos) +{ + struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); + struct iwl_mvm *mvm = mvmvif->mvm; + int value
[PATCH 10/37] iwlwifi: dvm: remove command/return value from RX handlers
From: Johannes Berg After the previous patches, the command that's passed in nor the return value are used any more, so can be removed. While at it, make some functions static. Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/dvm/agn.h | 14 ++--- drivers/net/wireless/iwlwifi/dvm/dev.h | 5 +- drivers/net/wireless/iwlwifi/dvm/lib.c | 8 +-- drivers/net/wireless/iwlwifi/dvm/rx.c | 103 drivers/net/wireless/iwlwifi/dvm/scan.c | 25 +++- drivers/net/wireless/iwlwifi/dvm/sta.c | 16 ++--- drivers/net/wireless/iwlwifi/dvm/tx.c | 18 ++ 7 files changed, 65 insertions(+), 124 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/dvm/agn.h b/drivers/net/wireless/iwlwifi/dvm/agn.h index c160dad..f549dc3 100644 --- a/drivers/net/wireless/iwlwifi/dvm/agn.h +++ b/drivers/net/wireless/iwlwifi/dvm/agn.h @@ -216,11 +216,9 @@ int iwlagn_tx_agg_stop(struct iwl_priv *priv, struct ieee80211_vif *vif, struct ieee80211_sta *sta, u16 tid); int iwlagn_tx_agg_flush(struct iwl_priv *priv, struct ieee80211_vif *vif, struct ieee80211_sta *sta, u16 tid); -int iwlagn_rx_reply_compressed_ba(struct iwl_priv *priv, - struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd); -int iwlagn_rx_reply_tx(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd); +void iwlagn_rx_reply_compressed_ba(struct iwl_priv *priv, + struct iwl_rx_cmd_buffer *rxb); +void iwlagn_rx_reply_tx(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb); static inline u32 iwl_tx_status_to_mac80211(u32 status) { @@ -277,9 +275,6 @@ int __must_check iwl_scan_initiate(struct iwl_priv *priv, /* bt coex */ void iwlagn_send_advance_bt_config(struct iwl_priv *priv); -int iwlagn_bt_coex_profile_notif(struct iwl_priv *priv, - struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd); void iwlagn_bt_rx_handler_setup(struct iwl_priv *priv); void iwlagn_bt_setup_deferred_work(struct iwl_priv *priv); void iwlagn_bt_cancel_deferred_work(struct iwl_priv *priv); @@ -332,8 +327,7 @@ u8 iwl_prep_station(struct iwl_priv *priv, struct iwl_rxon_context *ctx, int iwl_send_lq_cmd(struct iwl_priv *priv, struct iwl_rxon_context *ctx, struct iwl_link_quality_cmd *lq, u8 flags, bool init); -int iwl_add_sta_callback(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd); +void iwl_add_sta_callback(struct iwl_priv *priv, struct iwl_rx_cmd_buffer *rxb); int iwl_sta_update_ht(struct iwl_priv *priv, struct iwl_rxon_context *ctx, struct ieee80211_sta *sta); diff --git a/drivers/net/wireless/iwlwifi/dvm/dev.h b/drivers/net/wireless/iwlwifi/dvm/dev.h index 3811878..1f51757 100644 --- a/drivers/net/wireless/iwlwifi/dvm/dev.h +++ b/drivers/net/wireless/iwlwifi/dvm/dev.h @@ -678,9 +678,8 @@ struct iwl_priv { enum ieee80211_band band; u8 valid_contexts; - int (*rx_handlers[REPLY_MAX])(struct iwl_priv *priv, - struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd); + void (*rx_handlers[REPLY_MAX])(struct iwl_priv *priv, + struct iwl_rx_cmd_buffer *rxb); struct iwl_notif_wait_data notif_wait; diff --git a/drivers/net/wireless/iwlwifi/dvm/lib.c b/drivers/net/wireless/iwlwifi/dvm/lib.c index 1d2223d..ab45819 100644 --- a/drivers/net/wireless/iwlwifi/dvm/lib.c +++ b/drivers/net/wireless/iwlwifi/dvm/lib.c @@ -659,9 +659,8 @@ static bool iwlagn_fill_txpower_mode(struct iwl_priv *priv, return need_update; } -int iwlagn_bt_coex_profile_notif(struct iwl_priv *priv, - struct iwl_rx_cmd_buffer *rxb, - struct iwl_device_cmd *cmd) +static void iwlagn_bt_coex_profile_notif(struct iwl_priv *priv, +struct iwl_rx_cmd_buffer *rxb) { struct iwl_rx_packet *pkt = rxb_addr(rxb); struct iwl_bt_coex_profile_notif *coex = (void *)pkt->data; @@ -669,7 +668,7 @@ int iwlagn_bt_coex_profile_notif(struct iwl_priv *priv, if (priv->bt_enable_flag == IWLAGN_BT_FLAG_COEX_MODE_DISABLED) { /* bt coex disabled */ - return 0; + return; } IWL_DEBUG_COEX(priv, "BT Coex notification:\n"); @@ -714,7 +713,6 @@ int iwlagn_bt_coex_profile_notif(struct iwl_priv *priv, /* FIXME: based on notification, adjust the prio_boost */ priv->bt_ci_compliance = coex->bt_ci_compliance; - return 0; } void iwlagn_bt_rx_handler_setup(struct iwl_priv *priv) diff --git a/drivers/net/wireless/iwlwifi/dvm/rx.c b/drive
[PATCH 01/37] iwlwifi: mvm: rs: report last tx rate based on RSSI and caps
From: Eyal Shapira In scenarios where we haven't converged yet to a specific modulation and rate it could be better to report to userspace the last tx rate based on the STA capabilities and RSSI. This is important as sometimes userspace displays the last tx rate as the link speed. This avoids being presented with low legacy rates when rs just begins its search or after an idle period in which it resets itself. Signed-off-by: Eyal Shapira Reviewed-by: Johannes Berg Signed-off-by: Emmanuel Grumbach --- drivers/net/wireless/iwlwifi/mvm/rs.c | 157 -- drivers/net/wireless/iwlwifi/mvm/rs.h | 10 +++ 2 files changed, 160 insertions(+), 7 deletions(-) diff --git a/drivers/net/wireless/iwlwifi/mvm/rs.c b/drivers/net/wireless/iwlwifi/mvm/rs.c index daff1d0..19a7926 100644 --- a/drivers/net/wireless/iwlwifi/mvm/rs.c +++ b/drivers/net/wireless/iwlwifi/mvm/rs.c @@ -2403,7 +2403,7 @@ struct rs_init_rate_info { u8 rate_idx; }; -static const struct rs_init_rate_info rs_init_rates_24ghz[] = { +static const struct rs_init_rate_info rs_optimal_rates_24ghz_legacy[] = { { -60, IWL_RATE_54M_INDEX }, { -64, IWL_RATE_48M_INDEX }, { -68, IWL_RATE_36M_INDEX }, @@ -2416,7 +2416,7 @@ static const struct rs_init_rate_info rs_init_rates_24ghz[] = { { S8_MIN, IWL_RATE_1M_INDEX }, }; -static const struct rs_init_rate_info rs_init_rates_5ghz[] = { +static const struct rs_init_rate_info rs_optimal_rates_5ghz_legacy[] = { { -60, IWL_RATE_54M_INDEX }, { -64, IWL_RATE_48M_INDEX }, { -72, IWL_RATE_36M_INDEX }, @@ -2427,6 +2427,124 @@ static const struct rs_init_rate_info rs_init_rates_5ghz[] = { { S8_MIN, IWL_RATE_6M_INDEX }, }; +static const struct rs_init_rate_info rs_optimal_rates_ht[] = { + { -60, IWL_RATE_MCS_7_INDEX }, + { -64, IWL_RATE_MCS_6_INDEX }, + { -68, IWL_RATE_MCS_5_INDEX }, + { -72, IWL_RATE_MCS_4_INDEX }, + { -80, IWL_RATE_MCS_3_INDEX }, + { -84, IWL_RATE_MCS_2_INDEX }, + { -85, IWL_RATE_MCS_1_INDEX }, + { S8_MIN, IWL_RATE_MCS_0_INDEX}, +}; + +static const struct rs_init_rate_info rs_optimal_rates_vht_20mhz[] = { + { -60, IWL_RATE_MCS_8_INDEX }, + { -64, IWL_RATE_MCS_7_INDEX }, + { -68, IWL_RATE_MCS_6_INDEX }, + { -72, IWL_RATE_MCS_5_INDEX }, + { -80, IWL_RATE_MCS_4_INDEX }, + { -84, IWL_RATE_MCS_3_INDEX }, + { -85, IWL_RATE_MCS_2_INDEX }, + { -87, IWL_RATE_MCS_1_INDEX }, + { S8_MIN, IWL_RATE_MCS_0_INDEX}, +}; + +static const struct rs_init_rate_info rs_optimal_rates_vht_40_80mhz[] = { + { -60, IWL_RATE_MCS_9_INDEX }, + { -64, IWL_RATE_MCS_8_INDEX }, + { -68, IWL_RATE_MCS_7_INDEX }, + { -72, IWL_RATE_MCS_6_INDEX }, + { -80, IWL_RATE_MCS_5_INDEX }, + { -84, IWL_RATE_MCS_4_INDEX }, + { -85, IWL_RATE_MCS_3_INDEX }, + { -87, IWL_RATE_MCS_2_INDEX }, + { -88, IWL_RATE_MCS_1_INDEX }, + { S8_MIN, IWL_RATE_MCS_0_INDEX }, +}; + +/* Init the optimal rate based on STA caps + * This combined with rssi is used to report the last tx rate + * to userspace when we haven't transmitted enough frames. + */ +static void rs_init_optimal_rate(struct iwl_mvm *mvm, +struct ieee80211_sta *sta, +struct iwl_lq_sta *lq_sta) +{ + struct rs_rate *rate = &lq_sta->optimal_rate; + + if (lq_sta->max_mimo2_rate_idx != IWL_RATE_INVALID) + rate->type = lq_sta->is_vht ? LQ_VHT_MIMO2 : LQ_HT_MIMO2; + else if (lq_sta->max_siso_rate_idx != IWL_RATE_INVALID) + rate->type = lq_sta->is_vht ? LQ_VHT_SISO : LQ_HT_SISO; + else if (lq_sta->band == IEEE80211_BAND_5GHZ) + rate->type = LQ_LEGACY_A; + else + rate->type = LQ_LEGACY_G; + + rate->bw = rs_bw_from_sta_bw(sta); + rate->sgi = rs_sgi_allow(mvm, sta, rate, NULL); + + /* ANT/LDPC/STBC aren't relevant for the rate reported to userspace */ + + if (is_mimo(rate)) { + lq_sta->optimal_rate_mask = lq_sta->active_mimo2_rate; + } else if (is_siso(rate)) { + lq_sta->optimal_rate_mask = lq_sta->active_siso_rate; + } else { + lq_sta->optimal_rate_mask = lq_sta->active_legacy_rate; + + if (lq_sta->band == IEEE80211_BAND_5GHZ) { + lq_sta->optimal_rates = rs_optimal_rates_5ghz_legacy; + lq_sta->optimal_nentries = + ARRAY_SIZE(rs_optimal_rates_5ghz_legacy); + } else { + lq_sta->optimal_rates = rs_optimal_rates_24ghz_legacy; + lq_sta->optimal_nentries = + ARRAY_SIZE(rs_optimal_rates_24ghz_legacy); + } + } + + if (is_vht(rate)) { + if (rate->bw == RATE_MCS_CHAN_WIDTH_20) { + lq_sta->optimal_rates =
pull request: iwlwifi-next 2015-08-04
Hi Kalle, It comes late, but this is the first pull request for 4.3. I have quite a bit for the next one that will come after this one. Please pull - thanks! emmanuel The following changes since commit e0456717e483bb8a9431b80a5bdc99a928b9b003: Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-next (2015-06-24 16:49:49 -0700) are available in the git repository at: https://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/iwlwifi-next.git tags/iwlwifi-next-for-kalle-2015-08-04 for you to fetch changes up to 75118fdb63496e4611ab50380499ddd62b9de69f: iwlwifi: mvm: clean up fw-api-scan.h (2015-08-04 21:29:37 +0300) * Deprecate -10.ucode * Clean ups towards multiple Rx queues * Add support for longer CMD IDs. This will be required by new firmwares since we are getting close to the u8 limit. * bugfixes for the D0i3 power state * Add basic support for FTM * More random that doesn't really stand out Aviya Erenfeld (1): iwlwifi: add wide firmware command infrastructure for TX Avraham Stern (1): iwlwifi: mvm: add wide firmware command infrastructure for RX Avri Altman (2): iwlwifi: mvm: update comment of power_scheme module parameter iwlwifi: mvm: Enable Rx Checksum hw David Spinadel (1): iwlwifi: mvm: clean up fw-api-scan.h Eliad Peller (4): Revert "iwlwifi: mvm: move deferred d0i3 exit to resume_complete op" iwlwifi: return error if d0i3 was aborted iwlwifi: call d3_suspend/resume in d0i3 case as well iwlwifi: pcie: reset write pointer on ict reset Emmanuel Grumbach (5): iwlwifi: dvm: start HW before running FW iwlwifi: pcie: lock start_hw / start_fw / stop_device iwlwifi: pcie: cancel Tx timer upon firmware crash iwlwifi: pcie: add missing calls to synchronize_irq() iwlwifi: pcie: don't warn on long MPDUs when supported Eyal Shapira (1): iwlwifi: mvm: rs: report last tx rate based on RSSI and caps Gregory Greenman (3): iwlwifi: mvm: add basic Time of Flight (802.11mc FTM) support iwlwifi: mvm: fix beacon filtering temperature thresholds for D0i3 iwlwifi: mvm: ignore CQM when setting beacon filtering in D0i3 enter flow Haim Dreyfuss (2): iwlwifi: pcie: Set scheduler to work on auto mode iwlwifi: pcie: provide a way to stop configuration if it is forbidden Ilan Peer (2): iwlwifi: mvm: Do not sample the device time for session protection iwlwifi: mvm: Use the AP station for non_sta transmit Johannes Berg (10): iwlwifi: mvm: handle RX MPDUs separately iwlwifi: mvm: LRU-assign key offsets iwlwifi: dvm: move ADD_STA response handling to sync command iwlwifi: dvm: remove ADD_STA prints relying on station ID iwlwifi: dvm: remove command/return value from RX handlers iwlwifi: mvm: remove command/return value from RX handlers iwlwifi: remove command and return value from opmode RX iwlwifi: remove command header flags field iwlwifi: mvm: move existing UMAC commands to group 1 iwlwifi: mvm: move TX PN assignment for CCMP to the driver Nicholas Krause (1): iwlwifi: make various functions void in the file rs.c Sara Sharon (4): iwlwifi: deprecate -10.ucode for 3160 / 7260 / 7265 iwlwifi: mvm: remove IWL_UCODE_TLV_API_BASIC_DWELL iwlwifi: add wide firmware command support for notifications iwlwifi: mvm: add wide firmware command support for debug triggers drivers/net/wireless/iwlwifi/dvm/agn.h | 19 +-- drivers/net/wireless/iwlwifi/dvm/dev.h | 5 +- drivers/net/wireless/iwlwifi/dvm/lib.c | 8 +- drivers/net/wireless/iwlwifi/dvm/mac80211.c | 14 +- drivers/net/wireless/iwlwifi/dvm/rs.c | 51 +++--- drivers/net/wireless/iwlwifi/dvm/rx.c | 104 drivers/net/wireless/iwlwifi/dvm/rxon.c | 3 +- drivers/net/wireless/iwlwifi/dvm/scan.c | 25 +-- drivers/net/wireless/iwlwifi/dvm/sta.c | 111 + drivers/net/wireless/iwlwifi/dvm/tx.c | 18 +- drivers/net/wireless/iwlwifi/dvm/ucode.c| 5 +- drivers/net/wireless/iwlwifi/iwl-7000.c | 2 +- drivers/net/wireless/iwlwifi/iwl-8000.c | 3 +- drivers/net/wireless/iwlwifi/iwl-config.h | 2 + drivers/net/wireless/iwlwifi/iwl-csr.h | 1 + drivers/net/wireless/iwlwifi/iwl-devtrace-iwlwifi.h | 14 +- drivers/net/wireless/iwlwifi/iwl-fw-file.h | 16 +- drivers/net/wireless/iwlwifi/iwl-notif-wait.c | 8 +- drivers/net/wireless/iwlwifi/iwl-notif-wait.h | 5 +- drivers/net/wireless/iwlwifi/iwl-op-mode.h | 10 +- drivers/net/wireless/iwlwifi/iwl-prph.h | 4 + drivers/net/wireless/iwlwifi/iwl-trans.h| 89 -- drivers/net/wir
[PATCH] Staging: wilc1000: Remove typedefs for struct
The Linux kernel coding style guidelines suggest not using typedefs for structure and enum types. This patch gets rid of the typedefs for Ack_session_info_t. The following Coccinelle semantic patch detects the cases for struct type: @tn@ identifier i; type td; @@ -typedef struct i { ... } -td ; @@ type tn.td; identifier tn.i; @@ -td + struct i Signed-off-by: Shraddha Barke --- drivers/staging/wilc1000/wilc_wlan.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/staging/wilc1000/wilc_wlan.c b/drivers/staging/wilc1000/wilc_wlan.c index def72fd..1eb13f9 100644 --- a/drivers/staging/wilc1000/wilc_wlan.c +++ b/drivers/staging/wilc1000/wilc_wlan.c @@ -291,13 +291,13 @@ uint32_t Statisitcs_totalAcks = 0, Statisitcs_DroppedAcks = 0; #ifdef TCP_ACK_FILTER struct Ack_session_info; -typedef struct Ack_session_info { +struct Ack_session_info { uint32_t Ack_seq_num; uint32_t Bigger_Ack_num; uint16_t src_port; uint16_t dst_port; uint16_t status; -} Ack_session_info_t; +}; typedef struct { uint32_t ack_num; @@ -318,7 +318,7 @@ struct Ack_session_info *Alloc_head; #define MAX_TCP_SESSION25 #define MAX_PENDING_ACKS 256 -Ack_session_info_t Acks_keep_track_info[2 * MAX_TCP_SESSION]; +struct Ack_session_info Acks_keep_track_info[2 * MAX_TCP_SESSION]; Pending_Acks_info_t Pending_Acks_info[MAX_PENDING_ACKS]; uint32_t PendingAcks_arrBase; -- 2.1.0 -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v2 3/3] mwifiex: fix unable to connect hidden SSID AP on DFS channel
On Tue, Aug 4, 2015 at 5:30 AM, Amitkumar Karwar wrote: > From: chunfan chen > > We will check if any hidden SSID found in passive scan channels > and do specific SSID active scan for those channels. > > Signed-off-by: chunfan chen > Signed-off-by: Amitkumar Karwar > --- > v2: Corrected hidden SSID detection logic as per Paul Stewart's comment. > --- > drivers/net/wireless/mwifiex/fw.h | 1 + > drivers/net/wireless/mwifiex/init.c | 2 +- > drivers/net/wireless/mwifiex/main.h | 2 + > drivers/net/wireless/mwifiex/scan.c | 136 > +--- > 4 files changed, 129 insertions(+), 12 deletions(-) > > diff --git a/drivers/net/wireless/mwifiex/fw.h > b/drivers/net/wireless/mwifiex/fw.h > index 9a8c1832..3ec2ac8 100644 > --- a/drivers/net/wireless/mwifiex/fw.h > +++ b/drivers/net/wireless/mwifiex/fw.h > @@ -685,6 +685,7 @@ struct mwifiex_fw_chan_stats { > enum mwifiex_chan_scan_mode_bitmasks { > MWIFIEX_PASSIVE_SCAN = BIT(0), > MWIFIEX_DISABLE_CHAN_FILT = BIT(1), > + MWIFIEX_HIDDEN_SSID_REPORT = BIT(4), > }; > > struct mwifiex_chan_scan_param_set { > diff --git a/drivers/net/wireless/mwifiex/init.c > b/drivers/net/wireless/mwifiex/init.c > index 7a970c2..5d3ae63 100644 > --- a/drivers/net/wireless/mwifiex/init.c > +++ b/drivers/net/wireless/mwifiex/init.c > @@ -301,7 +301,7 @@ static void mwifiex_init_adapter(struct mwifiex_adapter > *adapter) > adapter->iface_limit.sta_intf = MWIFIEX_MAX_STA_NUM; > adapter->iface_limit.uap_intf = MWIFIEX_MAX_UAP_NUM; > adapter->iface_limit.p2p_intf = MWIFIEX_MAX_P2P_NUM; > - > + adapter->active_scan_triggered = false; > setup_timer(&adapter->wakeup_timer, wakeup_timer_fn, > (unsigned long)adapter); > } > diff --git a/drivers/net/wireless/mwifiex/main.h > b/drivers/net/wireless/mwifiex/main.h > index face747..6b95121 100644 > --- a/drivers/net/wireless/mwifiex/main.h > +++ b/drivers/net/wireless/mwifiex/main.h > @@ -666,6 +666,7 @@ struct mwifiex_private { > struct mwifiex_11h_intf_state state_11h; > struct mwifiex_ds_mem_rw mem_rw; > struct sk_buff_head bypass_txq; > + struct mwifiex_user_scan_chan hidden_chan[MWIFIEX_USER_SCAN_CHAN_MAX]; > }; > > > @@ -986,6 +987,7 @@ struct mwifiex_adapter { > u8 coex_tx_win_size; > u8 coex_rx_win_size; > bool drcs_enabled; > + u8 active_scan_triggered; > }; > > void mwifiex_process_tx_queue(struct mwifiex_adapter *adapter); > diff --git a/drivers/net/wireless/mwifiex/scan.c > b/drivers/net/wireless/mwifiex/scan.c > index ef8da8e..47e9253 100644 > --- a/drivers/net/wireless/mwifiex/scan.c > +++ b/drivers/net/wireless/mwifiex/scan.c > @@ -527,7 +527,8 @@ mwifiex_scan_create_channel_list(struct mwifiex_private > *priv, > > if (ch->flags & IEEE80211_CHAN_NO_IR) > scan_chan_list[chan_idx].chan_scan_mode_bitmap > - |= MWIFIEX_PASSIVE_SCAN; > + |= (MWIFIEX_PASSIVE_SCAN | > + MWIFIEX_HIDDEN_SSID_REPORT); > else > scan_chan_list[chan_idx].chan_scan_mode_bitmap > &= ~MWIFIEX_PASSIVE_SCAN; > @@ -1049,7 +1050,8 @@ mwifiex_config_scan(struct mwifiex_private *priv, > if (scan_type == MWIFIEX_SCAN_TYPE_PASSIVE) > (scan_chan_list + > chan_idx)->chan_scan_mode_bitmap > - |= MWIFIEX_PASSIVE_SCAN; > + |= (MWIFIEX_PASSIVE_SCAN | > + MWIFIEX_HIDDEN_SSID_REPORT); > else > (scan_chan_list + > chan_idx)->chan_scan_mode_bitmap > @@ -1600,6 +1602,58 @@ int mwifiex_check_network_compatibility(struct > mwifiex_private *priv, > return ret; > } > > +/* This function checks if SSID string contains all zeroes or length is zero > */ > +static bool mwifiex_is_hidden_ssid(struct cfg80211_ssid *ssid) > +{ > + int idx; > + > + for (idx = 0; idx < ssid->ssid_len; idx++) { > + if (ssid->ssid[idx]) > + return false; > + } > + > + return true; > +} > + > +/* This function checks if any hidden SSID found in passive scan channels > + * and save those channels for specific SSID active scan > + */ > +static int mwifiex_save_hidden_ssid_channels(struct mwifiex_private *priv, > +struct cfg80211_bss *bss) > +{ > + struct mwifiex_bssdescriptor *bss_desc; > + int ret; > + int chid; > + > + /* Allocate and fill new bss descriptor */ > + bss_desc = kzalloc(sizeof(*bss_desc), GFP_KERNEL); > + if (!bss_d
RE: [PATCH v5] Add new mac80211 driver mwlwifi.
Hi Kalle, > -Original Message- > From: Kalle Valo [mailto:kv...@codeaurora.org] > Sent: Tuesday, August 04, 2015 10:02 AM > > Maxime Bizon writes: > > > On Fri, 2015-07-03 at 06:10 +, David Lin wrote: > > > > Hello, > > > >> The Linux driver for WRT1900AC. The work was initially developed as > >> part of openwrt effort and maintained on > >> https://github.com/kaloz/mwlwifi. > > > > I see *massive* code duplication with the mwl8k driver. > > I haven't looked at the driver myself yet. Do you have any estimates > how much duplication there is? > mwl8k was a driver for chips few generations older sponsored by Marvell. We did leverage part of driver framework that is still applicable. However, for the current development, the firmware API specs, chip capabilities and bandwidth requirements have changed in order to handle newer technologies and features. > > This is, I guess, not a surprise since the supported chipset are an > > evolution of the ones supported by mwl8k, just look at how > > close/similar the descriptor format is. > > > > The problem is that each new Marvell chipset comes with a new > firmware > > version, and there is no effort to have a common firmware API or code > > base that supports multiple chipsets. > > > > That pushes the bloat on the kernel side, do we really agree on that > ? > > That is a very good question. The kernel should not be a dumping ground > for random drivers which duplicate lots of code but this is a sort of > gray area and depends on the case. > No, we are not treating the submission as dumping! We would not have responded with effort to meet the requests/feedback if so. We appreciate and have taken the feedbacks seriously to complete to patch6. In fact the submission was requested by some community members who has seen the benefit of its evolvement on openwrt github, and they would like to see the new driver consolidated into the wireless mainline. Due to hardware, firmware, specs and requirements change over time, it is not feasible for us to revisit generations old products or making sure new changes are backward compatible with it. (If desired, we welcome the community to take any new useful changes that are independent of chip rev to other similar branches.) Lastly, I do not think we are creating a precedence with different generation of drivers supporting different families of chips. > > Did Marvell reply to this? I didn't find any comments about this. > Sorry, we have missed that email earlier... I hope the above response will suffice to get accepted. Best regards, > -- > Kalle Valo -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v5] Add new mac80211 driver mwlwifi.
Maxime Bizon writes: > On Fri, 2015-07-03 at 06:10 +, David Lin wrote: > > Hello, > >> The Linux driver for WRT1900AC. The work was initially developed as >> part of openwrt effort and maintained on >> https://github.com/kaloz/mwlwifi. > > I see *massive* code duplication with the mwl8k driver. I haven't looked at the driver myself yet. Do you have any estimates how much duplication there is? > This is, I guess, not a surprise since the supported chipset are an > evolution of the ones supported by mwl8k, just look at how close/similar > the descriptor format is. > > The problem is that each new Marvell chipset comes with a new firmware > version, and there is no effort to have a common firmware API or code > base that supports multiple chipsets. > > That pushes the bloat on the kernel side, do we really agree on that ? That is a very good question. The kernel should not be a dumping ground for random drivers which duplicate lots of code but this is a sort of gray area and depends on the case. Did Marvell reply to this? I didn't find any comments about this. -- Kalle Valo -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
pull-request: wireless-drivers 2015-08-04
Hi Dave, here are few small fixes I would like to get to 4.2. Please let me know if there are any problems. Kalle The following changes since commit df2cd4586f177acf9493dee079fc7d18268c5f54: Merge tag 'iwlwifi-for-kalle-2015-06-12' of https://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/iwlwifi-fixes (2015-07-17 11:19:08 +0300) are available in the git repository at: git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/wireless-drivers.git tags/wireless-drivers-for-davem-2015-08-04 for you to fetch changes up to 741e3b9902d11585e18bfc7f8d47e913616bb070: rtlwifi: rtl8723be: Add module parameter for MSI interrupts (2015-08-03 11:26:24 +0300) iwlwifi: * a fix for the stuck TFD queue mechanism - it was producing noisy false alarms * a fix for the NIC prepare flow that prevented the driver from being able to access the device on certain systems * a fix for the scan prority handling which allows the regular scan to run even if a scheduled scan is already running rsi: * fix firmware load DMA regression b43: * fix extpa_gain check for 2GHz rtlwifi: * fix NULL dereference when PCI driver used as an AP * add missing module parameter declaration for rtl8723be_mod_params.msi_support Avraham Stern (1): iwlwifi: mvm: Fix regular scan priority Emmanuel Grumbach (2): iwlwifi: pcie: fix prepare card flow iwlwifi: pcie: fix stuck queue detection for sleeping clients Hauke Mehrtens (1): b43: fix extpa_gain check for 2GHz Kalle Valo (1): Merge tag 'iwlwifi-for-kalle-2015-07-30' of https://git.kernel.org/.../iwlwifi/iwlwifi-fixes Larry Finger (1): rtlwifi: rtl8723be: Add module parameter for MSI interrupts Luis Felipe Dominguez Vega (1): rtlwifi: Fix NULL dereference when PCI driver used as an AP Mike Looijmans (1): rsi: Fix failure to load firmware after memory leak fix and fix the leak drivers/net/wireless/b43/tables_nphy.c |2 +- drivers/net/wireless/iwlwifi/mvm/scan.c |2 +- drivers/net/wireless/iwlwifi/pcie/trans.c | 22 +++--- drivers/net/wireless/iwlwifi/pcie/tx.c | 15 +-- drivers/net/wireless/rsi/rsi_91x_sdio_ops.c |8 +++- drivers/net/wireless/rsi/rsi_91x_usb_ops.c |4 drivers/net/wireless/rtlwifi/core.c |7 +-- drivers/net/wireless/rtlwifi/rtl8723be/sw.c |1 + 8 files changed, 51 insertions(+), 10 deletions(-) -- Kalle Valo -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v2 4/5] wireless-regdb: Update 5GHz rules for US
On Tue, Aug 04, 2015 at 09:31:58AM +0800, Chen-Yu Tsai wrote: > On Tue, Aug 4, 2015 at 2:34 AM, Seth Forshee > wrote: > > On Thu, Jul 23, 2015 at 11:32:59AM +0800, Chen-Yu Tsai wrote: > >> The FCC increased the maximum conducted transmission power for the > >> U-NII-1 (5150 ~ 5250 MHz) band to 30 dBm or 1 W for master devices > >> and 24 dBm or 250 mW for mobile/portable devices. > >> > >> Effective 6/2/2014. > >> > >> See FCC KDB 905462 D06. > >> > >> Signed-off-by: Chen-Yu Tsai > >> --- > >> db.txt | 2 +- > >> 1 file changed, 1 insertion(+), 1 deletion(-) > >> > >> diff --git a/db.txt b/db.txt > >> index cadd52c..29ba4b6 100644 > >> --- a/db.txt > >> +++ b/db.txt > >> @@ -1160,7 +1160,7 @@ country UG: DFS-FCC > >> > >> country US: DFS-FCC > >> (2402 - 2472 @ 40), (30) > >> - (5170 - 5250 @ 80), (17), AUTO-BW > >> + (5170 - 5250 @ 80), (30), AUTO-BW > > > > The 30 dB limit is for devices in master mode, for clients the limit > > seems to be 250 mW (about 24 dB). Given the TPC requirement for U-NII > > devices the most it could be bumped up to is 21 dB, unless there's some > > other reason I don't know about to keep it at 17 dB. > > I suppose we have no way to differentiate between master mode and clients? > I'll drop it down to 24 dBm and add a comment above it. We don't have any way to specify differing rules for APs and clients today. Probably the limit should be 23 dBm instead, since 250 mW comes out to just less than 24 dBm. Better to be conservative, and besides that is consistent with other ranges which have a 250 mW limit. > As for 17 dB, that was the original limit prior to the bump, as seen in > the FCC KDB attachment "905462 D05 802.11 Channel Plans Old Rules v01". Ah, okay. Thanks, Seth -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v2 1/5] wireless-regdb: Update U-NII-2c (5470 ~ 5725 MHz) rules for Taiwan (TW)
On Tue, Aug 04, 2015 at 09:55:06AM +0800, Chen-Yu Tsai wrote: > On Tue, Aug 4, 2015 at 9:26 AM, Chen-Yu Tsai wrote: > > On Tue, Aug 4, 2015 at 2:27 AM, Seth Forshee > > wrote: > >> On Thu, Jul 23, 2015 at 11:32:56AM +0800, Chen-Yu Tsai wrote: > >>> Taiwan's Ministry of Transportation and Communications revised its > >>> frequency allocation rules [1] on 2014/11/17, allowing usage of 5600 ~ > >>> 5650 MHz, previously allocated to weather radars, to U-NII applications > >>> with DFS support. > >>> > >>> Also, the technical regulations [2] show that for 5470 ~ 5725 MHz U-NII > >>> applications, the peak transmit power shall not exceed the lesser of > >>> 250 mW (slightly less than 24 dBm) or 11 dBm + 10log B, where B is the > >>> 26dB emission bandwidth in MHz. This is slightly more than 23 dBm for > >>> 20 MHz channels. > >>> > >>> This patch updates both. Also add links to the two documents into the > >>> database. > >>> > >>> [1] > >>> http://www.motc.gov.tw/websitedowndoc?file=post/201411171137330.doc&filedisplay=Table+of+radio+frequency+allocation.doc > >>> [2] > >>> http://www.ncc.gov.tw/english/show_file.aspx?table_name=news&file_sn=681 > >>> > >>> Signed-off-by: Chen-Yu Tsai > >> > >> Sorry for the slow response to these patches. > >> > >>> --- > >>> db.txt | 10 -- > >>> 1 file changed, 8 insertions(+), 2 deletions(-) > >>> > >>> diff --git a/db.txt b/db.txt > >>> index 982db34..5114557 100644 > >>> --- a/db.txt > >>> +++ b/db.txt > >>> @@ -1118,11 +1118,17 @@ country TT: DFS-FCC > >>> (5490 - 5730 @ 160), (24), DFS > >>> (5735 - 5835 @ 80), (30) > >>> > >>> +# Source: > >>> +# Table of Frequency Allocations of Republic of China (Taiwan) / Nov > >>> 2014: > >>> +# http://www.motc.gov.tw/websitedowndoc?file=post/201411171137330.doc&; > >>> \ > >>> +# filedisplay=Table+of+radio+frequency+allocation.doc > >>> +# LP0002 Low-power Radio-frequency Devices Technical Regulations / 28 > >>> Jun 2011: > >>> +# > >>> http://www.ncc.gov.tw/english/show_file.aspx?table_name=news&file_sn=681 > >>> +# (section 3.10.1, 4.7) > >>> country TW: DFS-JP > >>> (2402 - 2472 @ 40), (30) > >>> (5270 - 5330 @ 40), (17), DFS > >>> - (5490 - 5590 @ 80), (30), DFS > >>> - (5650 - 5710 @ 40), (30), DFS > >>> + (5470 - 5725 @ 160), (23), DFS > >> > >> Based on [2], it looks like this range requires TPC, in which case the > >> power limit should be dropped by 3 dB on account of our not supporting > >> TPC. > > > > Will fix. > > > > Is there any plan to support multiple rules per band? Such as different > > power limits with vs without TPC, or something like DFS vs indoor only? Not that I know of. Currently the binary database format is a constraint on doing anything like that. > BTW, this band has the exact same restrictions as the US, as specified > by the FCC. The relevant rules were added in > > f894543 wireless-regdb: Add back regulatory rules for US > > and expanded to cover the whole band in > > 3c61549 wireless-regdb: Update 5GHz rules for US > > These show the power limit at 23 dBm as well. Any comments on this? Good question. Afaict this probably originates with commit 31dc1c5e which defines the limit for 5250-5330 MHz in the US, then using the same limit for the 5490-5730 MHz rule seemed logical. The 5250-5330 MHz rule came from QCA then. Adding Jouni to the Cc to see if he can help clarify how they arrived at 23 dBm. Hmm, I see now that 15.407(h)(1) says that TPC is not required for systems with an EIRP of less than 500 mW. In that case I guess maybe we don't need to drop the power limit by 3 dB, so in light of that 23 dBm does make sense. The documents you linked to say the same, seemingly word-for-word, so in all likelihood 23 dBm is actually okay. Thanks, Seth -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v2 1/3] mwifiex: add support for 8997 chipset
From: Zhaoyang Liu This patch adds support for 8997 chipset to mwifiex with SDIO/PCIe/USB interface. The corresponding firmware image files are located in: "mrvl/sd8997_uapsta.bin" "mrvl/pcie8997_uapsta.bin" "mrvl/usb8997_uapsta.bin" Signed-off-by: Zhaoyang Liu Signed-off-by: Cathy Luo Signed-off-by: Amitkumar Karwar --- drivers/net/wireless/mwifiex/Kconfig | 12 +++ drivers/net/wireless/mwifiex/pcie.c | 12 +-- drivers/net/wireless/mwifiex/pcie.h | 45 - drivers/net/wireless/mwifiex/sdio.c | 5 +++ drivers/net/wireless/mwifiex/sdio.h | 65 drivers/net/wireless/mwifiex/usb.c | 14 drivers/net/wireless/mwifiex/usb.h | 3 ++ 7 files changed, 147 insertions(+), 9 deletions(-) diff --git a/drivers/net/wireless/mwifiex/Kconfig b/drivers/net/wireless/mwifiex/Kconfig index 48edf38..317d991 100644 --- a/drivers/net/wireless/mwifiex/Kconfig +++ b/drivers/net/wireless/mwifiex/Kconfig @@ -9,36 +9,36 @@ config MWIFIEX mwifiex. config MWIFIEX_SDIO - tristate "Marvell WiFi-Ex Driver for SD8786/SD8787/SD8797/SD8887/SD8897" + tristate "Marvell WiFi-Ex Driver for SD8786/SD8787/SD8797/SD8887/SD8897/SD8997" depends on MWIFIEX && MMC select FW_LOADER select WANT_DEV_COREDUMP ---help--- This adds support for wireless adapters based on Marvell - 8786/8787/8797/8887/8897 chipsets with SDIO interface. + 8786/8787/8797/8887/8897/8997 chipsets with SDIO interface. If you choose to build it as a module, it will be called mwifiex_sdio. config MWIFIEX_PCIE - tristate "Marvell WiFi-Ex Driver for PCIE 8766/8897" + tristate "Marvell WiFi-Ex Driver for PCIE 8766/8897/8997" depends on MWIFIEX && PCI select FW_LOADER select WANT_DEV_COREDUMP ---help--- This adds support for wireless adapters based on Marvell - 8766/8897 chipsets with PCIe interface. + 8766/8897/8997 chipsets with PCIe interface. If you choose to build it as a module, it will be called mwifiex_pcie. config MWIFIEX_USB - tristate "Marvell WiFi-Ex Driver for USB8766/8797/8897" + tristate "Marvell WiFi-Ex Driver for USB8766/8797/8897/8997" depends on MWIFIEX && USB select FW_LOADER ---help--- This adds support for wireless adapters based on Marvell - 8797/8897 chipset with USB interface. + 8797/8897/8997 chipset with USB interface. If you choose to build it as a module, it will be called mwifiex_usb. diff --git a/drivers/net/wireless/mwifiex/pcie.c b/drivers/net/wireless/mwifiex/pcie.c index 33c75d7..408b684 100644 --- a/drivers/net/wireless/mwifiex/pcie.c +++ b/drivers/net/wireless/mwifiex/pcie.c @@ -266,12 +266,17 @@ static const struct pci_device_id mwifiex_ids[] = { { PCIE_VENDOR_ID_MARVELL, PCIE_DEVICE_ID_MARVELL_88W8766P, PCI_ANY_ID, PCI_ANY_ID, 0, 0, - .driver_data = (unsigned long) &mwifiex_pcie8766, + .driver_data = (unsigned long)&mwifiex_pcie8766, }, { PCIE_VENDOR_ID_MARVELL, PCIE_DEVICE_ID_MARVELL_88W8897, PCI_ANY_ID, PCI_ANY_ID, 0, 0, - .driver_data = (unsigned long) &mwifiex_pcie8897, + .driver_data = (unsigned long)&mwifiex_pcie8897, + }, + { + PCIE_VENDOR_ID_MARVELL, PCIE_DEVICE_ID_MARVELL_88W8997, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, + .driver_data = (unsigned long)&mwifiex_pcie8997, }, {}, }; @@ -1082,6 +1087,7 @@ static int mwifiex_pcie_send_data_complete(struct mwifiex_adapter *adapter) card->txbd_rdptr++; break; case PCIE_DEVICE_ID_MARVELL_88W8897: + case PCIE_DEVICE_ID_MARVELL_88W8997: card->txbd_rdptr += reg->ring_tx_start_ptr; break; } @@ -1179,6 +1185,7 @@ mwifiex_pcie_send_data(struct mwifiex_adapter *adapter, struct sk_buff *skb, card->txbd_wrptr++; break; case PCIE_DEVICE_ID_MARVELL_88W8897: + case PCIE_DEVICE_ID_MARVELL_88W8997: card->txbd_wrptr += reg->ring_tx_start_ptr; break; } @@ -2733,3 +2740,4 @@ MODULE_VERSION(PCIE_VERSION); MODULE_LICENSE("GPL v2"); MODULE_FIRMWARE(PCIE8766_DEFAULT_FW_NAME); MODULE_FIRMWARE(PCIE8897_DEFAULT_FW_NAME); +MODULE_FIRMWARE(PCIE8997_DEFAULT_FW_NAME); diff --git a/drivers/net/wireless/mwifiex/pcie.h b/drivers/net/wireless/mwifiex/pcie.h index 0e7ee8b..48e549c 100644 --- a/drivers/net/wireless/mwifiex/pcie.h +++ b/drivers/net/wireless/mwifiex/pcie.h @@ -30,10 +30,12 @@ #define PCIE8766_DEFAULT_FW_NAME "mrvl/pcie8766_uapsta.bin" #define PCIE889
[PATCH v2 2/3] mwifiex: add firmware dump support for SD8997
From: Zhaoyang Liu This patch adds firmware dump feature for SD8997 chipset. The difference here is only one memory type is needed to save all firmware information. Device dump information will be uploaded to usersapace file. Signed-off-by: Zhaoyang Liu Signed-off-by: Cathy Luo Signed-off-by: Amitkumar Karwar --- drivers/net/wireless/mwifiex/sdio.c | 147 +--- drivers/net/wireless/mwifiex/sdio.h | 11 ++- 2 files changed, 148 insertions(+), 10 deletions(-) diff --git a/drivers/net/wireless/mwifiex/sdio.c b/drivers/net/wireless/mwifiex/sdio.c index 9904a77..7cef27e9 100644 --- a/drivers/net/wireless/mwifiex/sdio.c +++ b/drivers/net/wireless/mwifiex/sdio.c @@ -51,6 +51,10 @@ static unsigned long iface_work_flags; static struct semaphore add_remove_card_sem; +static struct memory_type_mapping generic_mem_type_map[] = { + {"DUMP", NULL, 0, 0xDD}, +}; + static struct memory_type_mapping mem_type_mapping_tbl[] = { {"ITCM", NULL, 0, 0xF0}, {"DTCM", NULL, 0, 0xF1}, @@ -108,6 +112,7 @@ mwifiex_sdio_probe(struct sdio_func *func, const struct sdio_device_id *id) card->mp_tx_agg_buf_size = data->mp_tx_agg_buf_size; card->mp_rx_agg_buf_size = data->mp_rx_agg_buf_size; card->can_dump_fw = data->can_dump_fw; + card->fw_dump_enh = data->fw_dump_enh; card->can_auto_tdls = data->can_auto_tdls; card->can_ext_scan = data->can_ext_scan; } @@ -1969,8 +1974,13 @@ static int mwifiex_register_dev(struct mwifiex_adapter *adapter) adapter->dev = &func->dev; strcpy(adapter->fw_name, card->firmware); - adapter->mem_type_mapping_tbl = mem_type_mapping_tbl; - adapter->num_mem_types = ARRAY_SIZE(mem_type_mapping_tbl); + if (card->fw_dump_enh) { + adapter->mem_type_mapping_tbl = generic_mem_type_map; + adapter->num_mem_types = 1; + } else { + adapter->mem_type_mapping_tbl = mem_type_mapping_tbl; + adapter->num_mem_types = ARRAY_SIZE(mem_type_mapping_tbl); + } return 0; } @@ -2163,8 +2173,8 @@ rdwr_status mwifiex_sdio_rdwr_firmware(struct mwifiex_adapter *adapter, int ret, tries; u8 ctrl_data = 0; - sdio_writeb(card->func, FW_DUMP_HOST_READY, card->reg->fw_dump_ctrl, - &ret); + sdio_writeb(card->func, card->reg->fw_dump_host_ready, + card->reg->fw_dump_ctrl, &ret); if (ret) { mwifiex_dbg(adapter, ERROR, "SDIO Write ERR\n"); return RDWR_STATUS_FAILURE; @@ -2180,10 +2190,10 @@ rdwr_status mwifiex_sdio_rdwr_firmware(struct mwifiex_adapter *adapter, break; if (doneflag && ctrl_data == doneflag) return RDWR_STATUS_DONE; - if (ctrl_data != FW_DUMP_HOST_READY) { + if (ctrl_data != card->reg->fw_dump_host_ready) { mwifiex_dbg(adapter, WARN, - "The ctrl reg was changed, re-try again!\n"); - sdio_writeb(card->func, FW_DUMP_HOST_READY, + "The ctrl reg was changed, re-try again\n"); + sdio_writeb(card->func, card->reg->fw_dump_host_ready, card->reg->fw_dump_ctrl, &ret); if (ret) { mwifiex_dbg(adapter, ERROR, "SDIO write err\n"); @@ -2192,7 +2202,7 @@ rdwr_status mwifiex_sdio_rdwr_firmware(struct mwifiex_adapter *adapter, } usleep_range(100, 200); } - if (ctrl_data == FW_DUMP_HOST_READY) { + if (ctrl_data == card->reg->fw_dump_host_ready) { mwifiex_dbg(adapter, ERROR, "Fail to pull ctrl_data\n"); return RDWR_STATUS_FAILURE; @@ -2325,10 +2335,129 @@ done: sdio_release_host(card->func); } +static void mwifiex_sdio_generic_fw_dump(struct mwifiex_adapter *adapter) +{ + struct sdio_mmc_card *card = adapter->card; + struct memory_type_mapping *entry = &generic_mem_type_map[0]; + unsigned int reg, reg_start, reg_end; + u8 start_flag = 0, done_flag = 0; + u8 *dbg_ptr, *end_ptr; + enum rdwr_status stat; + int ret = -1, tries; + + if (!card->fw_dump_enh) + return; + + if (entry->mem_ptr) { + vfree(entry->mem_ptr); + entry->mem_ptr = NULL; + } + entry->mem_size = 0; + + mwifiex_pm_wakeup_card(adapter); + sdio_claim_host(card->func); + + mwifiex_dbg(adapter, MSG, "== mwifiex firmware dump start ==\n"); + + stat = mwifiex_sdio_rdwr_firmware(adapter, done_flag); + if (stat == RDWR_STATUS_FAILURE) + goto done; + + reg_start = card->reg->fw_dump_start; + reg_end = card->reg->fw_dum
[PATCH v2 3/3] mwifiex: fix unable to connect hidden SSID AP on DFS channel
From: chunfan chen We will check if any hidden SSID found in passive scan channels and do specific SSID active scan for those channels. Signed-off-by: chunfan chen Signed-off-by: Amitkumar Karwar --- v2: Corrected hidden SSID detection logic as per Paul Stewart's comment. --- drivers/net/wireless/mwifiex/fw.h | 1 + drivers/net/wireless/mwifiex/init.c | 2 +- drivers/net/wireless/mwifiex/main.h | 2 + drivers/net/wireless/mwifiex/scan.c | 136 +--- 4 files changed, 129 insertions(+), 12 deletions(-) diff --git a/drivers/net/wireless/mwifiex/fw.h b/drivers/net/wireless/mwifiex/fw.h index 9a8c1832..3ec2ac8 100644 --- a/drivers/net/wireless/mwifiex/fw.h +++ b/drivers/net/wireless/mwifiex/fw.h @@ -685,6 +685,7 @@ struct mwifiex_fw_chan_stats { enum mwifiex_chan_scan_mode_bitmasks { MWIFIEX_PASSIVE_SCAN = BIT(0), MWIFIEX_DISABLE_CHAN_FILT = BIT(1), + MWIFIEX_HIDDEN_SSID_REPORT = BIT(4), }; struct mwifiex_chan_scan_param_set { diff --git a/drivers/net/wireless/mwifiex/init.c b/drivers/net/wireless/mwifiex/init.c index 7a970c2..5d3ae63 100644 --- a/drivers/net/wireless/mwifiex/init.c +++ b/drivers/net/wireless/mwifiex/init.c @@ -301,7 +301,7 @@ static void mwifiex_init_adapter(struct mwifiex_adapter *adapter) adapter->iface_limit.sta_intf = MWIFIEX_MAX_STA_NUM; adapter->iface_limit.uap_intf = MWIFIEX_MAX_UAP_NUM; adapter->iface_limit.p2p_intf = MWIFIEX_MAX_P2P_NUM; - + adapter->active_scan_triggered = false; setup_timer(&adapter->wakeup_timer, wakeup_timer_fn, (unsigned long)adapter); } diff --git a/drivers/net/wireless/mwifiex/main.h b/drivers/net/wireless/mwifiex/main.h index face747..6b95121 100644 --- a/drivers/net/wireless/mwifiex/main.h +++ b/drivers/net/wireless/mwifiex/main.h @@ -666,6 +666,7 @@ struct mwifiex_private { struct mwifiex_11h_intf_state state_11h; struct mwifiex_ds_mem_rw mem_rw; struct sk_buff_head bypass_txq; + struct mwifiex_user_scan_chan hidden_chan[MWIFIEX_USER_SCAN_CHAN_MAX]; }; @@ -986,6 +987,7 @@ struct mwifiex_adapter { u8 coex_tx_win_size; u8 coex_rx_win_size; bool drcs_enabled; + u8 active_scan_triggered; }; void mwifiex_process_tx_queue(struct mwifiex_adapter *adapter); diff --git a/drivers/net/wireless/mwifiex/scan.c b/drivers/net/wireless/mwifiex/scan.c index ef8da8e..47e9253 100644 --- a/drivers/net/wireless/mwifiex/scan.c +++ b/drivers/net/wireless/mwifiex/scan.c @@ -527,7 +527,8 @@ mwifiex_scan_create_channel_list(struct mwifiex_private *priv, if (ch->flags & IEEE80211_CHAN_NO_IR) scan_chan_list[chan_idx].chan_scan_mode_bitmap - |= MWIFIEX_PASSIVE_SCAN; + |= (MWIFIEX_PASSIVE_SCAN | + MWIFIEX_HIDDEN_SSID_REPORT); else scan_chan_list[chan_idx].chan_scan_mode_bitmap &= ~MWIFIEX_PASSIVE_SCAN; @@ -1049,7 +1050,8 @@ mwifiex_config_scan(struct mwifiex_private *priv, if (scan_type == MWIFIEX_SCAN_TYPE_PASSIVE) (scan_chan_list + chan_idx)->chan_scan_mode_bitmap - |= MWIFIEX_PASSIVE_SCAN; + |= (MWIFIEX_PASSIVE_SCAN | + MWIFIEX_HIDDEN_SSID_REPORT); else (scan_chan_list + chan_idx)->chan_scan_mode_bitmap @@ -1600,6 +1602,58 @@ int mwifiex_check_network_compatibility(struct mwifiex_private *priv, return ret; } +/* This function checks if SSID string contains all zeroes or length is zero */ +static bool mwifiex_is_hidden_ssid(struct cfg80211_ssid *ssid) +{ + int idx; + + for (idx = 0; idx < ssid->ssid_len; idx++) { + if (ssid->ssid[idx]) + return false; + } + + return true; +} + +/* This function checks if any hidden SSID found in passive scan channels + * and save those channels for specific SSID active scan + */ +static int mwifiex_save_hidden_ssid_channels(struct mwifiex_private *priv, +struct cfg80211_bss *bss) +{ + struct mwifiex_bssdescriptor *bss_desc; + int ret; + int chid; + + /* Allocate and fill new bss descriptor */ + bss_desc = kzalloc(sizeof(*bss_desc), GFP_KERNEL); + if (!bss_desc) + return -ENOMEM; + + ret = mwifiex_fill_new_bss_desc(priv, bss, bss_desc); + if (ret) + goto done; + + if (mwifiex_is_hidden_ssid(&bss_desc->ssid)) { + mwifiex_dbg(priv->adapter, INFO, "found hidden SSID\n"); + f
Re: [PATCH 1/2] iwlwifi: convert hex_dump_to_buffer() to %*ph
On Tue, Aug 4, 2015 at 2:48 PM, Emmanuel Grumbach wrote: > On Tue, Aug 4, 2015 at 1:47 PM, Andy Shevchenko > wrote: >> On Thu, 2015-07-16 at 15:42 +0300, Andy Shevchenko wrote: >>> There is no need to use hex_dump_to_buffer() in the cases like this: >>> >>> hexdump_to_buffer(buf, len, 16, 1, outbuf, outlen, false); > /* >>> len <= 16 >>> */ >>> sprintf("%s\n", outbuf); >>> >>> since it maybe easily converted to simple: >>> >>> sprintf("%*ph\n", len, buf); >>> >>> Note: it seems in one case the output is groupped by 2 bytes and >>> looks like a >>> typo. Thus, patch changes that to plain byte stream. >> >> >> Any comments on this, anyone? >> >> The idea is to minimize usage of hexdump_to_buffer(), i.e. not using it >> when it's an obvious overkill. >> > > Sorry for the delay, since the buffer is small (less than 16 bytes, it > should be fine). I applied it on our internal tree. Thank you. -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] iwlwifi: convert hex_dump_to_buffer() to %*ph
On Tue, Aug 4, 2015 at 1:47 PM, Andy Shevchenko wrote: > On Thu, 2015-07-16 at 15:42 +0300, Andy Shevchenko wrote: >> There is no need to use hex_dump_to_buffer() in the cases like this: >> >> hexdump_to_buffer(buf, len, 16, 1, outbuf, outlen, false); > /* >> len <= 16 >> */ >> sprintf("%s\n", outbuf); >> >> since it maybe easily converted to simple: >> >> sprintf("%*ph\n", len, buf); >> >> Note: it seems in one case the output is groupped by 2 bytes and >> looks like a >> typo. Thus, patch changes that to plain byte stream. > > > Any comments on this, anyone? > > The idea is to minimize usage of hexdump_to_buffer(), i.e. not using it > when it's an obvious overkill. > Sorry for the delay, since the buffer is small (less than 16 bytes, it should be fine). -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] iwlwifi: convert hex_dump_to_buffer() to %*ph
On Thu, 2015-07-16 at 15:42 +0300, Andy Shevchenko wrote: > There is no need to use hex_dump_to_buffer() in the cases like this: > > hexdump_to_buffer(buf, len, 16, 1, outbuf, outlen, false); > /* > len <= 16 > */ > sprintf("%s\n", outbuf); > > since it maybe easily converted to simple: > > sprintf("%*ph\n", len, buf); > > Note: it seems in one case the output is groupped by 2 bytes and > looks like a > typo. Thus, patch changes that to plain byte stream. Any comments on this, anyone? The idea is to minimize usage of hexdump_to_buffer(), i.e. not using it when it's an obvious overkill. > > Signed-off-by: Andy Shevchenko > --- > drivers/net/wireless/iwlwifi/dvm/debugfs.c | 8 ++-- > drivers/net/wireless/iwlwifi/mvm/debugfs.c | 7 +-- > 2 files changed, 3 insertions(+), 12 deletions(-) > > diff --git a/drivers/net/wireless/iwlwifi/dvm/debugfs.c > b/drivers/net/wireless/iwlwifi/dvm/debugfs.c > index 0ffb6ff..b15e44f 100644 > --- a/drivers/net/wireless/iwlwifi/dvm/debugfs.c > +++ b/drivers/net/wireless/iwlwifi/dvm/debugfs.c > @@ -310,12 +310,8 @@ static ssize_t iwl_dbgfs_nvm_read(struct file > *file, > pos += scnprintf(buf + pos, buf_size - pos, >"NVM version: 0x%x\n", nvm_ver); > for (ofs = 0 ; ofs < eeprom_len ; ofs += 16) { > - pos += scnprintf(buf + pos, buf_size - pos, "0x%.4x > ", ofs); > - hex_dump_to_buffer(ptr + ofs, 16 , 16, 2, buf + pos, > -buf_size - pos, 0); > - pos += strlen(buf + pos); > - if (buf_size - pos > 0) > - buf[pos++] = '\n'; > + pos += scnprintf(buf + pos, buf_size - pos, "0x%.4x > %16ph\n", > + ofs, ptr + ofs); > } > > ret = simple_read_from_buffer(user_buf, count, ppos, buf, > pos); > diff --git a/drivers/net/wireless/iwlwifi/mvm/debugfs.c > b/drivers/net/wireless/iwlwifi/mvm/debugfs.c > index ffb4b5c..98abd31 100644 > --- a/drivers/net/wireless/iwlwifi/mvm/debugfs.c > +++ b/drivers/net/wireless/iwlwifi/mvm/debugfs.c > @@ -1200,12 +1200,7 @@ static ssize_t iwl_dbgfs_d3_sram_read(struct > file *file, char __user *user_buf, > if (ptr) { > for (ofs = 0; ofs < len; ofs += 16) { > pos += scnprintf(buf + pos, bufsz - pos, > - "0x%.4x ", ofs); > - hex_dump_to_buffer(ptr + ofs, 16, 16, 1, buf > + pos, > -bufsz - pos, false); > - pos += strlen(buf + pos); > - if (bufsz - pos > 0) > - buf[pos++] = '\n'; > + "0x%.4x %16ph\n", ofs, ptr > + ofs); > } > } else { > pos += scnprintf(buf + pos, bufsz - pos, -- Andy Shevchenko Intel Finland Oy -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] staging: rtl8723au: fix up coding style warnings reported by checkpatch.pl.
Ting-Chih Hsiao writes: > remove spaces at the start of a line > align enum variable with other parameters > > Signed-off-by: Ting-Chih Hsiao Acked-by: Jes Sorensen > --- > drivers/staging/rtl8723au/hal/odm_RegConfig8723A.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/staging/rtl8723au/hal/odm_RegConfig8723A.c > b/drivers/staging/rtl8723au/hal/odm_RegConfig8723A.c > index 342dec3..a63c6cb 100644 > --- a/drivers/staging/rtl8723au/hal/odm_RegConfig8723A.c > +++ b/drivers/staging/rtl8723au/hal/odm_RegConfig8723A.c > @@ -21,7 +21,7 @@ odm_ConfigRFReg_8723A( > struct dm_odm_t *pDM_Odm, > u32 Addr, > u32 Data, > - enum RF_RADIO_PATH RF_PATH, > + enum RF_RADIO_PATH RF_PATH, > u32 RegAddr > ) > { -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch] mwifiex: usb: return an error if kmalloc fails
The current code returns success if kmalloc fails. Signed-off-by: Dan Carpenter diff --git a/drivers/net/wireless/mwifiex/usb.c b/drivers/net/wireless/mwifiex/usb.c index fbad99c..f866d5d 100644 --- a/drivers/net/wireless/mwifiex/usb.c +++ b/drivers/net/wireless/mwifiex/usb.c @@ -870,8 +870,10 @@ static int mwifiex_prog_fw_w_helper(struct mwifiex_adapter *adapter, /* Allocate memory for transmit */ fwdata = kzalloc(FW_DNLD_TX_BUF_SIZE, GFP_KERNEL); - if (!fwdata) + if (!fwdata) { + ret = -ENOMEM; goto fw_exit; + } /* Allocate memory for receive */ recv_buff = kzalloc(FW_DNLD_RX_BUF_SIZE, GFP_KERNEL); -- To unsubscribe from this list: send the line "unsubscribe linux-wireless" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html