From 17818dfa8f2e90a6f40e047a3ea9c39af1a8a87d Mon Sep 17 00:00:00 2001 From: Colin Ian King Date: Fri, 23 Apr 2021 14:41:33 +0100 Subject: [PATCH 01/91] ath10k/ath11k: fix spelling mistake "requed" -> "requeued" There are multiple occurrances of the misspelling of requeued in the drivers with symbol names and debug text. Fix these. Signed-off-by: Colin Ian King Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210423134133.339751-1-colin.king@canonical.com --- drivers/net/wireless/ath/ath10k/core.h | 2 +- drivers/net/wireless/ath/ath10k/debug.c | 4 ++-- drivers/net/wireless/ath/ath10k/htt.h | 4 ++-- drivers/net/wireless/ath/ath10k/wmi.c | 6 +++--- drivers/net/wireless/ath/ath10k/wmi.h | 8 ++++---- drivers/net/wireless/ath/ath11k/core.h | 4 ++-- drivers/net/wireless/ath/ath11k/debugfs_htt_stats.c | 2 +- drivers/net/wireless/ath/ath11k/debugfs_htt_stats.h | 2 +- drivers/net/wireless/ath/ath11k/wmi.c | 4 ++-- drivers/net/wireless/ath/ath11k/wmi.h | 4 ++-- 10 files changed, 20 insertions(+), 20 deletions(-) diff --git a/drivers/net/wireless/ath/ath10k/core.h b/drivers/net/wireless/ath/ath10k/core.h index 648ed36f845f..5aeff2d9f6cf 100644 --- a/drivers/net/wireless/ath/ath10k/core.h +++ b/drivers/net/wireless/ath/ath10k/core.h @@ -301,7 +301,7 @@ struct ath10k_fw_stats_pdev { s32 underrun; u32 hw_paused; s32 tx_abort; - s32 mpdus_requed; + s32 mpdus_requeued; u32 tx_ko; u32 data_rc; u32 self_triggers; diff --git a/drivers/net/wireless/ath/ath10k/debug.c b/drivers/net/wireless/ath/ath10k/debug.c index fd052f6ed019..39378e3f9b2b 100644 --- a/drivers/net/wireless/ath/ath10k/debug.c +++ b/drivers/net/wireless/ath/ath10k/debug.c @@ -1105,7 +1105,7 @@ static const char ath10k_gstrings_stats[][ETH_GSTRING_LEN] = { "d_tx_ppdu_reaped", "d_tx_fifo_underrun", "d_tx_ppdu_abort", - "d_tx_mpdu_requed", + "d_tx_mpdu_requeued", "d_tx_excessive_retries", "d_tx_hw_rate", "d_tx_dropped_sw_retries", @@ -1205,7 +1205,7 @@ void ath10k_debug_get_et_stats(struct ieee80211_hw *hw, data[i++] = pdev_stats->hw_reaped; data[i++] = pdev_stats->underrun; data[i++] = pdev_stats->tx_abort; - data[i++] = pdev_stats->mpdus_requed; + data[i++] = pdev_stats->mpdus_requeued; data[i++] = pdev_stats->tx_ko; data[i++] = pdev_stats->data_rc; data[i++] = pdev_stats->sw_retry_failure; diff --git a/drivers/net/wireless/ath/ath10k/htt.h b/drivers/net/wireless/ath/ath10k/htt.h index 956157946106..4e11ee775b4d 100644 --- a/drivers/net/wireless/ath/ath10k/htt.h +++ b/drivers/net/wireless/ath/ath10k/htt.h @@ -1282,8 +1282,8 @@ struct htt_dbg_stats_wal_tx_stats { /* Num PPDUs cleaned up in TX abort */ __le32 tx_abort; - /* Num MPDUs requed by SW */ - __le32 mpdus_requed; + /* Num MPDUs requeued by SW */ + __le32 mpdus_requeued; /* excessive retries */ __le32 tx_ko; diff --git a/drivers/net/wireless/ath/ath10k/wmi.c b/drivers/net/wireless/ath/ath10k/wmi.c index d48b922215eb..f42bf2c8f9e7 100644 --- a/drivers/net/wireless/ath/ath10k/wmi.c +++ b/drivers/net/wireless/ath/ath10k/wmi.c @@ -2867,7 +2867,7 @@ void ath10k_wmi_pull_pdev_stats_tx(const struct wmi_pdev_stats_tx *src, dst->hw_reaped = __le32_to_cpu(src->hw_reaped); dst->underrun = __le32_to_cpu(src->underrun); dst->tx_abort = __le32_to_cpu(src->tx_abort); - dst->mpdus_requed = __le32_to_cpu(src->mpdus_requed); + dst->mpdus_requeued = __le32_to_cpu(src->mpdus_requeued); dst->tx_ko = __le32_to_cpu(src->tx_ko); dst->data_rc = __le32_to_cpu(src->data_rc); dst->self_triggers = __le32_to_cpu(src->self_triggers); @@ -2895,7 +2895,7 @@ ath10k_wmi_10_4_pull_pdev_stats_tx(const struct wmi_10_4_pdev_stats_tx *src, dst->hw_reaped = __le32_to_cpu(src->hw_reaped); dst->underrun = __le32_to_cpu(src->underrun); dst->tx_abort = __le32_to_cpu(src->tx_abort); - dst->mpdus_requed = __le32_to_cpu(src->mpdus_requed); + dst->mpdus_requeued = __le32_to_cpu(src->mpdus_requeued); dst->tx_ko = __le32_to_cpu(src->tx_ko); dst->data_rc = __le32_to_cpu(src->data_rc); dst->self_triggers = __le32_to_cpu(src->self_triggers); @@ -8270,7 +8270,7 @@ ath10k_wmi_fw_pdev_tx_stats_fill(const struct ath10k_fw_stats_pdev *pdev, len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", "PPDUs cleaned", pdev->tx_abort); len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", - "MPDUs requed", pdev->mpdus_requed); + "MPDUs requeued", pdev->mpdus_requeued); len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", "Excessive retries", pdev->tx_ko); len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", diff --git a/drivers/net/wireless/ath/ath10k/wmi.h b/drivers/net/wireless/ath/ath10k/wmi.h index d870f7067cb7..dd980c81793e 100644 --- a/drivers/net/wireless/ath/ath10k/wmi.h +++ b/drivers/net/wireless/ath/ath10k/wmi.h @@ -4371,8 +4371,8 @@ struct wmi_pdev_stats_tx { /* Num PPDUs cleaned up in TX abort */ __le32 tx_abort; - /* Num MPDUs requed by SW */ - __le32 mpdus_requed; + /* Num MPDUs requeued by SW */ + __le32 mpdus_requeued; /* excessive retries */ __le32 tx_ko; @@ -4444,8 +4444,8 @@ struct wmi_10_4_pdev_stats_tx { /* Num PPDUs cleaned up in TX abort */ __le32 tx_abort; - /* Num MPDUs requed by SW */ - __le32 mpdus_requed; + /* Num MPDUs requeued by SW */ + __le32 mpdus_requeued; /* excessive retries */ __le32 tx_ko; diff --git a/drivers/net/wireless/ath/ath11k/core.h b/drivers/net/wireless/ath/ath11k/core.h index 55af982deca7..382df5318b61 100644 --- a/drivers/net/wireless/ath/ath11k/core.h +++ b/drivers/net/wireless/ath/ath11k/core.h @@ -795,8 +795,8 @@ struct ath11k_fw_stats_pdev { s32 underrun; /* Num PPDUs cleaned up in TX abort */ s32 tx_abort; - /* Num MPDUs requed by SW */ - s32 mpdus_requed; + /* Num MPDUs requeued by SW */ + s32 mpdus_requeued; /* excessive retries */ u32 tx_ko; /* data hw rate code */ diff --git a/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.c b/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.c index ec93f14e6d2a..9e0c90da99d3 100644 --- a/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.c +++ b/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.c @@ -89,7 +89,7 @@ static inline void htt_print_tx_pdev_stats_cmn_tlv(const void *tag_buf, len += HTT_DBG_OUT(buf + len, buf_len - len, "tx_abort = %u", htt_stats_buf->tx_abort); len += HTT_DBG_OUT(buf + len, buf_len - len, "mpdu_requeued = %u", - htt_stats_buf->mpdu_requed); + htt_stats_buf->mpdu_requeued); len += HTT_DBG_OUT(buf + len, buf_len - len, "tx_xretry = %u", htt_stats_buf->tx_xretry); len += HTT_DBG_OUT(buf + len, buf_len - len, "data_rc = %u", diff --git a/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.h b/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.h index 567a26d485a9..d428f52003a4 100644 --- a/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.h +++ b/drivers/net/wireless/ath/ath11k/debugfs_htt_stats.h @@ -147,7 +147,7 @@ struct htt_tx_pdev_stats_cmn_tlv { u32 hw_flush; u32 hw_filt; u32 tx_abort; - u32 mpdu_requed; + u32 mpdu_requeued; u32 tx_xretry; u32 data_rc; u32 mpdu_dropped_xretry; diff --git a/drivers/net/wireless/ath/ath11k/wmi.c b/drivers/net/wireless/ath/ath11k/wmi.c index 5ca2d80679b6..6c253eae9d06 100644 --- a/drivers/net/wireless/ath/ath11k/wmi.c +++ b/drivers/net/wireless/ath/ath11k/wmi.c @@ -5235,7 +5235,7 @@ ath11k_wmi_pull_pdev_stats_tx(const struct wmi_pdev_stats_tx *src, dst->hw_reaped = src->hw_reaped; dst->underrun = src->underrun; dst->tx_abort = src->tx_abort; - dst->mpdus_requed = src->mpdus_requed; + dst->mpdus_requeued = src->mpdus_requeued; dst->tx_ko = src->tx_ko; dst->data_rc = src->data_rc; dst->self_triggers = src->self_triggers; @@ -5505,7 +5505,7 @@ ath11k_wmi_fw_pdev_tx_stats_fill(const struct ath11k_fw_stats_pdev *pdev, len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", "PPDUs cleaned", pdev->tx_abort); len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", - "MPDUs requed", pdev->mpdus_requed); + "MPDUs requeued", pdev->mpdus_requeued); len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", "Excessive retries", pdev->tx_ko); len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", diff --git a/drivers/net/wireless/ath/ath11k/wmi.h b/drivers/net/wireless/ath/ath11k/wmi.h index 3ade1ddd35c9..d35c47e0b19d 100644 --- a/drivers/net/wireless/ath/ath11k/wmi.h +++ b/drivers/net/wireless/ath/ath11k/wmi.h @@ -4171,8 +4171,8 @@ struct wmi_pdev_stats_tx { /* Num PPDUs cleaned up in TX abort */ s32 tx_abort; - /* Num MPDUs requed by SW */ - s32 mpdus_requed; + /* Num MPDUs requeued by SW */ + s32 mpdus_requeued; /* excessive retries */ u32 tx_ko; From 238ebd8b487b7fc995284e9580257801f2c76aa5 Mon Sep 17 00:00:00 2001 From: Philipp Borgers Date: Mon, 24 May 2021 08:52:11 +0300 Subject: [PATCH 02/91] ath9k: ar9003_mac: read STBC indicator from rx descriptor The rx descriptor contains a STBC indicator. If the indicator is set the frame was received with STBC. Signed-off-by: Philipp Borgers Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517172426.15919-1-borgers@mi.fu-berlin.de --- drivers/net/wireless/ath/ath9k/ar9003_mac.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/net/wireless/ath/ath9k/ar9003_mac.c b/drivers/net/wireless/ath/ath9k/ar9003_mac.c index 76b538942a79..5184a0aacfe2 100644 --- a/drivers/net/wireless/ath/ath9k/ar9003_mac.c +++ b/drivers/net/wireless/ath/ath9k/ar9003_mac.c @@ -522,6 +522,8 @@ int ath9k_hw_process_rxdesc_edma(struct ath_hw *ah, struct ath_rx_status *rxs, rxs->rs_moreaggr = (rxsp->status11 & AR_RxMoreAggr) ? 1 : 0; rxs->rs_antenna = (MS(rxsp->status4, AR_RxAntenna) & 0x7); rxs->enc_flags |= (rxsp->status4 & AR_GI) ? RX_ENC_FLAG_SHORT_GI : 0; + rxs->enc_flags |= + (rxsp->status4 & AR_STBC) ? (1 << RX_ENC_FLAG_STBC_SHIFT) : 0; rxs->bw = (rxsp->status4 & AR_2040) ? RATE_INFO_BW_40 : RATE_INFO_BW_20; rxs->evm0 = rxsp->status6; From da16f5be45d0458e5240737fe90194ee33314bdf Mon Sep 17 00:00:00 2001 From: Zhen Lei Date: Tue, 11 May 2021 11:42:03 +0800 Subject: [PATCH 03/91] b43: phy_n: Delete some useless TODO code These TODO empty code are added by commit 9442e5b58edb ("b43: N-PHY: partly implement SPUR workaround"). It's been more than a decade now. I don't think anyone who wants to perfect this workaround can follow this TODO tip exactly. Instead, it limits them to new thinking. Remove it will be better. No functional change. By the way, this helps reduce some binary code size. Before: text data bss dec hex 74472 9967 0 84439 149d7 After: text data bss dec hex 74408 9919 0 84327 14967 Signed-off-by: Zhen Lei Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511034203.4122-2-thunder.leizhen@huawei.com --- drivers/net/wireless/broadcom/b43/phy_n.c | 47 ----------------------- 1 file changed, 47 deletions(-) diff --git a/drivers/net/wireless/broadcom/b43/phy_n.c b/drivers/net/wireless/broadcom/b43/phy_n.c index 665b737fbb0d..cf3ccf4ddfe7 100644 --- a/drivers/net/wireless/broadcom/b43/phy_n.c +++ b/drivers/net/wireless/broadcom/b43/phy_n.c @@ -4592,58 +4592,11 @@ static void b43_nphy_spur_workaround(struct b43_wldev *dev) { struct b43_phy_n *nphy = dev->phy.n; - u8 channel = dev->phy.channel; - int tone[2] = { 57, 58 }; - u32 noise[2] = { 0x3FF, 0x3FF }; - B43_WARN_ON(dev->phy.rev < 3); if (nphy->hang_avoid) b43_nphy_stay_in_carrier_search(dev, 1); - if (nphy->gband_spurwar_en) { - /* TODO: N PHY Adjust Analog Pfbw (7) */ - if (channel == 11 && b43_is_40mhz(dev)) { - ; /* TODO: N PHY Adjust Min Noise Var(2, tone, noise)*/ - } else { - ; /* TODO: N PHY Adjust Min Noise Var(0, NULL, NULL)*/ - } - /* TODO: N PHY Adjust CRS Min Power (0x1E) */ - } - - if (nphy->aband_spurwar_en) { - if (channel == 54) { - tone[0] = 0x20; - noise[0] = 0x25F; - } else if (channel == 38 || channel == 102 || channel == 118) { - if (0 /* FIXME */) { - tone[0] = 0x20; - noise[0] = 0x21F; - } else { - tone[0] = 0; - noise[0] = 0; - } - } else if (channel == 134) { - tone[0] = 0x20; - noise[0] = 0x21F; - } else if (channel == 151) { - tone[0] = 0x10; - noise[0] = 0x23F; - } else if (channel == 153 || channel == 161) { - tone[0] = 0x30; - noise[0] = 0x23F; - } else { - tone[0] = 0; - noise[0] = 0; - } - - if (!tone[0] && !noise[0]) { - ; /* TODO: N PHY Adjust Min Noise Var(1, tone, noise)*/ - } else { - ; /* TODO: N PHY Adjust Min Noise Var(0, NULL, NULL)*/ - } - } - if (nphy->hang_avoid) b43_nphy_stay_in_carrier_search(dev, 0); } From d1dbaa54191e0014493cb4065aadb6764b404dd1 Mon Sep 17 00:00:00 2001 From: YueHaibing Date: Sat, 29 May 2021 19:51:31 +0800 Subject: [PATCH 04/91] b43legacy: Remove unused inline function txring_to_priority() commit 5d07a3d62f63 ("b43legacy: Avoid packet losses in the dma worker code") left behind this. Signed-off-by: YueHaibing Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210529115131.6028-1-yuehaibing@huawei.com --- drivers/net/wireless/broadcom/b43legacy/dma.c | 13 ------------- 1 file changed, 13 deletions(-) diff --git a/drivers/net/wireless/broadcom/b43legacy/dma.c b/drivers/net/wireless/broadcom/b43legacy/dma.c index 7e2f70c4207c..6869f2bf1bae 100644 --- a/drivers/net/wireless/broadcom/b43legacy/dma.c +++ b/drivers/net/wireless/broadcom/b43legacy/dma.c @@ -213,19 +213,6 @@ return dev->dma.tx_ring1; return ring; } -/* Bcm4301-ring to mac80211-queue mapping */ -static inline int txring_to_priority(struct b43legacy_dmaring *ring) -{ - static const u8 idx_to_prio[] = - { 3, 2, 1, 0, 4, 5, }; - -/*FIXME: have only one queue, for now */ -return 0; - - return idx_to_prio[ring->index]; -} - - static u16 b43legacy_dmacontroller_base(enum b43legacy_dmatype type, int controller_idx) { From fef1cdbba4d12fb67555364c22cc8d7c500600aa Mon Sep 17 00:00:00 2001 From: Colin Ian King Date: Tue, 1 Jun 2021 11:28:55 +0100 Subject: [PATCH 05/91] b43legacy: Fix spelling mistake "overflew" -> "overflowed" There is a spelling mistake in a comment. Fix it. Signed-off-by: Colin Ian King Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210601102855.8884-1-colin.king@canonical.com --- drivers/net/wireless/broadcom/b43legacy/main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/broadcom/b43legacy/main.c b/drivers/net/wireless/broadcom/b43legacy/main.c index f64ebff68308..eec3af9c3745 100644 --- a/drivers/net/wireless/broadcom/b43legacy/main.c +++ b/drivers/net/wireless/broadcom/b43legacy/main.c @@ -391,7 +391,7 @@ void b43legacy_tsf_read(struct b43legacy_wldev *dev, u64 *tsf) * registers, we should take care of register overflows. * In theory, the whole tsf read process should be atomic. * We try to be atomic here, by restaring the read process, - * if any of the high registers changed (overflew). + * if any of the high registers changed (overflowed). */ if (dev->dev->id.revision >= 3) { u32 low; From 080f9c10c773df39ccebe8dc414179d9179005a9 Mon Sep 17 00:00:00 2001 From: Souptick Joarder Date: Sun, 25 Apr 2021 16:20:42 +0530 Subject: [PATCH 06/91] ipw2x00: Minor documentation update Kernel test robot throws below warning -> drivers/net/wireless/intel/ipw2x00/ipw2100.c:5359: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst Minor update in documentation. Reported-by: kernel test robot Signed-off-by: Souptick Joarder Cc: Randy Dunlap Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1619347842-6638-1-git-send-email-jrdr.linux@gmail.com --- drivers/net/wireless/intel/ipw2x00/ipw2100.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/intel/ipw2x00/ipw2100.c b/drivers/net/wireless/intel/ipw2x00/ipw2100.c index 23fbddd0c1f8..47eb89b773cf 100644 --- a/drivers/net/wireless/intel/ipw2x00/ipw2100.c +++ b/drivers/net/wireless/intel/ipw2x00/ipw2100.c @@ -5356,7 +5356,7 @@ struct ipw2100_wep_key { #define WEP_STR_128(x) x[0],x[1],x[2],x[3],x[4],x[5],x[6],x[7],x[8],x[9],x[10] /** - * Set a the wep key + * ipw2100_set_key() - Set a the wep key * * @priv: struct to work on * @idx: index of the key we want to set From fb312ac5ccb007e843f982b38d4d6886ba4b32f2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pali=20Roh=C3=A1r?= Date: Mon, 31 May 2021 17:41:27 +0300 Subject: [PATCH 07/91] ath9k: Fix kernel NULL pointer dereference during ath_reset_internal() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit I got this crash more times during debugging of PCIe controller and crash happens somehow at the time when PCIe kernel code started link retraining (as part of ASPM code) when at the same time PCIe link went down and ath9k probably executed hw reset procedure. Currently I'm not able to reproduce this issue as it looks like to be some race condition between link training, ASPM, link down and reset path. And as always, race conditions which depends on more input parameters are hard to reproduce as it depends on precise timings. But it is clear that pointers are zero in this case and should be properly filled as same code pattern is used in ath9k_stop() function. Anyway I was able to reproduce this crash by manually triggering ath reset worker prior putting card up. I created simple patch to export reset functionality via debugfs and use it to "simulate" of triggering reset. s proved that NULL-pointer dereference issue is there. Function ath9k_hw_reset() is dereferencing chan structure pointer, so it needs to be non-NULL pointer. Function ath9k_stop() already contains code which sets ah->curchan to valid non-NULL pointer prior calling ath9k_hw_reset() function. Add same code pattern also into ath_reset_internal() function to prevent kernel NULL pointer dereference in ath9k_hw_reset() function. This change fixes kernel NULL pointer dereference in ath9k_hw_reset() which is caused by calling ath9k_hw_reset() from ath_reset_internal() with NULL chan structure. [ 45.334305] Unable to handle kernel NULL pointer dereference at virtual address 0000000000000008 [ 45.344417] Mem abort info: [ 45.347301] ESR = 0x96000005 [ 45.350448] EC = 0x25: DABT (current EL), IL = 32 bits [ 45.356166] SET = 0, FnV = 0 [ 45.359350] EA = 0, S1PTW = 0 [ 45.362596] Data abort info: [ 45.365756] ISV = 0, ISS = 0x00000005 [ 45.369735] CM = 0, WnR = 0 [ 45.372814] user pgtable: 4k pages, 39-bit VAs, pgdp=000000000685d000 [ 45.379663] [0000000000000008] pgd=0000000000000000, p4d=0000000000000000, pud=0000000000000000 [ 45.388856] Internal error: Oops: 96000005 [#1] SMP [ 45.393897] Modules linked in: ath9k ath9k_common ath9k_hw [ 45.399574] CPU: 1 PID: 309 Comm: kworker/u4:2 Not tainted 5.12.0-rc2-dirty #785 [ 45.414746] Workqueue: phy0 ath_reset_work [ath9k] [ 45.419713] pstate: 40000005 (nZcv daif -PAN -UAO -TCO BTYPE=--) [ 45.425910] pc : ath9k_hw_reset+0xc4/0x1c48 [ath9k_hw] [ 45.431234] lr : ath9k_hw_reset+0xc0/0x1c48 [ath9k_hw] [ 45.436548] sp : ffffffc0118dbca0 [ 45.439961] x29: ffffffc0118dbca0 x28: 0000000000000000 [ 45.445442] x27: ffffff800dee4080 x26: 0000000000000000 [ 45.450923] x25: ffffff800df9b9d8 x24: 0000000000000000 [ 45.456404] x23: ffffffc0115f6000 x22: ffffffc008d0d408 [ 45.461885] x21: ffffff800dee5080 x20: ffffff800df9b9d8 [ 45.467366] x19: 0000000000000000 x18: 0000000000000000 [ 45.472846] x17: 0000000000000000 x16: 0000000000000000 [ 45.478326] x15: 0000000000000010 x14: ffffffffffffffff [ 45.483807] x13: ffffffc0918db94f x12: ffffffc011498720 [ 45.489289] x11: 0000000000000003 x10: ffffffc0114806e0 [ 45.494770] x9 : ffffffc01014b2ec x8 : 0000000000017fe8 [ 45.500251] x7 : c0000000ffffefff x6 : 0000000000000001 [ 45.505733] x5 : 0000000000000000 x4 : 0000000000000000 [ 45.511213] x3 : 0000000000000000 x2 : ffffff801fece870 [ 45.516693] x1 : ffffffc00eded000 x0 : 000000000000003f [ 45.522174] Call trace: [ 45.524695] ath9k_hw_reset+0xc4/0x1c48 [ath9k_hw] [ 45.529653] ath_reset_internal+0x1a8/0x2b8 [ath9k] [ 45.534696] ath_reset_work+0x2c/0x40 [ath9k] [ 45.539198] process_one_work+0x210/0x480 [ 45.543339] worker_thread+0x5c/0x510 [ 45.547115] kthread+0x12c/0x130 [ 45.550445] ret_from_fork+0x10/0x1c [ 45.554138] Code: 910922c2 9117e021 95ff0398 b4000294 (b9400a61) [ 45.560430] ---[ end trace 566410ba90b50e8b ]--- [ 45.565193] Kernel panic - not syncing: Oops: Fatal exception in interrupt [ 45.572282] SMP: stopping secondary CPUs [ 45.576331] Kernel Offset: disabled [ 45.579924] CPU features: 0x00040002,0000200c [ 45.584416] Memory Limit: none [ 45.587564] Rebooting in 3 seconds.. Signed-off-by: Pali Rohár Cc: stable@vger.kernel.org Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210402122653.24014-1-pali@kernel.org --- drivers/net/wireless/ath/ath9k/main.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/net/wireless/ath/ath9k/main.c b/drivers/net/wireless/ath/ath9k/main.c index 45f6402478b5..97c3a53f9cef 100644 --- a/drivers/net/wireless/ath/ath9k/main.c +++ b/drivers/net/wireless/ath/ath9k/main.c @@ -307,6 +307,11 @@ static int ath_reset_internal(struct ath_softc *sc, struct ath9k_channel *hchan) hchan = ah->curchan; } + if (!hchan) { + fastcc = false; + hchan = ath9k_cmn_get_channel(sc->hw, ah, &sc->cur_chan->chandef); + } + if (!ath_prepare_reset(sc)) fastcc = false; From 755b1f73173e004e8c89a17fa4e8b329481495d4 Mon Sep 17 00:00:00 2001 From: Baochen Qiang Date: Mon, 31 May 2021 17:41:27 +0300 Subject: [PATCH 08/91] ath11k: add hw reg support for WCN6855 Reg address of WCN6855 is different from other devices, so add separate reg definition for this target. Tested-on: WCN6855 hw2.0 PCI WLAN.HSP.1.1-01720.1-QCAHSPSWPL_V1_V2_SILICONZ_LITE-1 Signed-off-by: Govind Singh Signed-off-by: Baochen Qiang Signed-off-by: Jouni Malinen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511162214.29475-2-jouni@codeaurora.org --- drivers/net/wireless/ath/ath11k/hw.c | 71 ++++++++++++++++++++++++++++ drivers/net/wireless/ath/ath11k/hw.h | 1 + 2 files changed, 72 insertions(+) diff --git a/drivers/net/wireless/ath/ath11k/hw.c b/drivers/net/wireless/ath/ath11k/hw.c index 377ae8d5b58f..d9d7c4608052 100644 --- a/drivers/net/wireless/ath/ath11k/hw.c +++ b/drivers/net/wireless/ath/ath11k/hw.c @@ -1688,3 +1688,74 @@ const struct ath11k_hw_regs qcn9074_regs = { .pcie_qserdes_sysclk_en_sel = 0x01e0e0a8, .pcie_pcs_osc_dtct_config_base = 0x01e0f45c, }; + +const struct ath11k_hw_regs wcn6855_regs = { + /* SW2TCL(x) R0 ring configuration address */ + .hal_tcl1_ring_base_lsb = 0x00000690, + .hal_tcl1_ring_base_msb = 0x00000694, + .hal_tcl1_ring_id = 0x00000698, + .hal_tcl1_ring_misc = 0x000006a0, + .hal_tcl1_ring_tp_addr_lsb = 0x000006ac, + .hal_tcl1_ring_tp_addr_msb = 0x000006b0, + .hal_tcl1_ring_consumer_int_setup_ix0 = 0x000006c0, + .hal_tcl1_ring_consumer_int_setup_ix1 = 0x000006c4, + .hal_tcl1_ring_msi1_base_lsb = 0x000006d8, + .hal_tcl1_ring_msi1_base_msb = 0x000006dc, + .hal_tcl1_ring_msi1_data = 0x000006e0, + .hal_tcl2_ring_base_lsb = 0x000006e8, + .hal_tcl_ring_base_lsb = 0x00000798, + + /* TCL STATUS ring address */ + .hal_tcl_status_ring_base_lsb = 0x000008a0, + + /* REO2SW(x) R0 ring configuration address */ + .hal_reo1_ring_base_lsb = 0x00000244, + .hal_reo1_ring_base_msb = 0x00000248, + .hal_reo1_ring_id = 0x0000024c, + .hal_reo1_ring_misc = 0x00000254, + .hal_reo1_ring_hp_addr_lsb = 0x00000258, + .hal_reo1_ring_hp_addr_msb = 0x0000025c, + .hal_reo1_ring_producer_int_setup = 0x00000268, + .hal_reo1_ring_msi1_base_lsb = 0x0000028c, + .hal_reo1_ring_msi1_base_msb = 0x00000290, + .hal_reo1_ring_msi1_data = 0x00000294, + .hal_reo2_ring_base_lsb = 0x0000029c, + .hal_reo1_aging_thresh_ix_0 = 0x000005bc, + .hal_reo1_aging_thresh_ix_1 = 0x000005c0, + .hal_reo1_aging_thresh_ix_2 = 0x000005c4, + .hal_reo1_aging_thresh_ix_3 = 0x000005c8, + + /* REO2SW(x) R2 ring pointers (head/tail) address */ + .hal_reo1_ring_hp = 0x00003030, + .hal_reo1_ring_tp = 0x00003034, + .hal_reo2_ring_hp = 0x00003038, + + /* REO2TCL R0 ring configuration address */ + .hal_reo_tcl_ring_base_lsb = 0x00000454, + .hal_reo_tcl_ring_hp = 0x00003060, + + /* REO status address */ + .hal_reo_status_ring_base_lsb = 0x0000055c, + .hal_reo_status_hp = 0x00003078, + + /* WCSS relative address */ + .hal_seq_wcss_umac_ce0_src_reg = 0x1b80000, + .hal_seq_wcss_umac_ce0_dst_reg = 0x1b81000, + .hal_seq_wcss_umac_ce1_src_reg = 0x1b82000, + .hal_seq_wcss_umac_ce1_dst_reg = 0x1b83000, + + /* WBM Idle address */ + .hal_wbm_idle_link_ring_base_lsb = 0x00000870, + .hal_wbm_idle_link_ring_misc = 0x00000880, + + /* SW2WBM release address */ + .hal_wbm_release_ring_base_lsb = 0x000001e8, + + /* WBM2SW release address */ + .hal_wbm0_release_ring_base_lsb = 0x00000920, + .hal_wbm1_release_ring_base_lsb = 0x00000978, + + /* PCIe base address */ + .pcie_qserdes_sysclk_en_sel = 0x01e0c0ac, + .pcie_pcs_osc_dtct_config_base = 0x01e0c628, +}; diff --git a/drivers/net/wireless/ath/ath11k/hw.h b/drivers/net/wireless/ath/ath11k/hw.h index c81a6328361d..4e7261c0dca1 100644 --- a/drivers/net/wireless/ath/ath11k/hw.h +++ b/drivers/net/wireless/ath/ath11k/hw.h @@ -318,5 +318,6 @@ struct ath11k_hw_regs { extern const struct ath11k_hw_regs ipq8074_regs; extern const struct ath11k_hw_regs qca6390_regs; extern const struct ath11k_hw_regs qcn9074_regs; +extern const struct ath11k_hw_regs wcn6855_regs; #endif From e4073430ee1dec5402a6158755ac8b84eade83c6 Mon Sep 17 00:00:00 2001 From: Baochen Qiang Date: Mon, 31 May 2021 17:41:27 +0300 Subject: [PATCH 09/91] ath11k: add dp support for WCN6855 hal rx descriptor is different for WCN6855 and there are such a lot of handlers processing this descriptor in data path. So add separate handling for this target. Tested-on: WCN6855 hw2.0 PCI WLAN.HSP.1.1-01720.1-QCAHSPSWPL_V1_V2_SILICONZ_LITE-1 Signed-off-by: Baochen Qiang Signed-off-by: Jouni Malinen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511162214.29475-3-jouni@codeaurora.org --- drivers/net/wireless/ath/ath11k/hw.c | 201 ++++++++++++++++++++++ drivers/net/wireless/ath/ath11k/hw.h | 1 + drivers/net/wireless/ath/ath11k/rx_desc.h | 87 ++++++++++ 3 files changed, 289 insertions(+) diff --git a/drivers/net/wireless/ath/ath11k/hw.c b/drivers/net/wireless/ath/ath11k/hw.c index d9d7c4608052..023047df954c 100644 --- a/drivers/net/wireless/ath/ath11k/hw.c +++ b/drivers/net/wireless/ath/ath11k/hw.c @@ -45,6 +45,13 @@ static void ath11k_hw_qcn9074_tx_mesh_enable(struct ath11k_base *ab, true); } +static void ath11k_hw_wcn6855_tx_mesh_enable(struct ath11k_base *ab, + struct hal_tcl_data_cmd *tcl_cmd) +{ + tcl_cmd->info3 |= FIELD_PREP(HAL_QCN9074_TCL_DATA_CMD_INFO3_MESH_ENABLE, + true); +} + static void ath11k_init_wmi_config_qca6390(struct ath11k_base *ab, struct target_resource_config *config) { @@ -489,6 +496,166 @@ static u8 *ath11k_hw_qcn9074_rx_desc_get_msdu_payload(struct hal_rx_desc *desc) return &desc->u.qcn9074.msdu_payload[0]; } +static bool ath11k_hw_wcn6855_rx_desc_get_first_msdu(struct hal_rx_desc *desc) +{ + return !!FIELD_GET(RX_MSDU_END_INFO2_FIRST_MSDU_WCN6855, + __le32_to_cpu(desc->u.wcn6855.msdu_end.info2)); +} + +static bool ath11k_hw_wcn6855_rx_desc_get_last_msdu(struct hal_rx_desc *desc) +{ + return !!FIELD_GET(RX_MSDU_END_INFO2_LAST_MSDU_WCN6855, + __le32_to_cpu(desc->u.wcn6855.msdu_end.info2)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_l3_pad_bytes(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_END_INFO2_L3_HDR_PADDING, + __le32_to_cpu(desc->u.wcn6855.msdu_end.info2)); +} + +static u8 *ath11k_hw_wcn6855_rx_desc_get_hdr_status(struct hal_rx_desc *desc) +{ + return desc->u.wcn6855.hdr_status; +} + +static bool ath11k_hw_wcn6855_rx_desc_encrypt_valid(struct hal_rx_desc *desc) +{ + return __le32_to_cpu(desc->u.wcn6855.mpdu_start.info1) & + RX_MPDU_START_INFO1_ENCRYPT_INFO_VALID; +} + +static u32 ath11k_hw_wcn6855_rx_desc_get_encrypt_type(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MPDU_START_INFO2_ENC_TYPE, + __le32_to_cpu(desc->u.wcn6855.mpdu_start.info2)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_decap_type(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO2_DECAP_FORMAT, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info2)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_mesh_ctl(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO2_MESH_CTRL_PRESENT, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info2)); +} + +static bool ath11k_hw_wcn6855_rx_desc_get_mpdu_seq_ctl_vld(struct hal_rx_desc *desc) +{ + return !!FIELD_GET(RX_MPDU_START_INFO1_MPDU_SEQ_CTRL_VALID, + __le32_to_cpu(desc->u.wcn6855.mpdu_start.info1)); +} + +static bool ath11k_hw_wcn6855_rx_desc_get_mpdu_fc_valid(struct hal_rx_desc *desc) +{ + return !!FIELD_GET(RX_MPDU_START_INFO1_MPDU_FCTRL_VALID, + __le32_to_cpu(desc->u.wcn6855.mpdu_start.info1)); +} + +static u16 ath11k_hw_wcn6855_rx_desc_get_mpdu_start_seq_no(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MPDU_START_INFO1_MPDU_SEQ_NUM, + __le32_to_cpu(desc->u.wcn6855.mpdu_start.info1)); +} + +static u16 ath11k_hw_wcn6855_rx_desc_get_msdu_len(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO1_MSDU_LENGTH, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info1)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_msdu_sgi(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO3_SGI, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info3)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_msdu_rate_mcs(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO3_RATE_MCS, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info3)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_msdu_rx_bw(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO3_RECV_BW, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info3)); +} + +static u32 ath11k_hw_wcn6855_rx_desc_get_msdu_freq(struct hal_rx_desc *desc) +{ + return __le32_to_cpu(desc->u.wcn6855.msdu_start.phy_meta_data); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_msdu_pkt_type(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO3_PKT_TYPE, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info3)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_msdu_nss(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MSDU_START_INFO3_MIMO_SS_BITMAP, + __le32_to_cpu(desc->u.wcn6855.msdu_start.info3)); +} + +static u8 ath11k_hw_wcn6855_rx_desc_get_mpdu_tid(struct hal_rx_desc *desc) +{ + return FIELD_GET(RX_MPDU_START_INFO2_TID_WCN6855, + __le32_to_cpu(desc->u.wcn6855.mpdu_start.info2)); +} + +static u16 ath11k_hw_wcn6855_rx_desc_get_mpdu_peer_id(struct hal_rx_desc *desc) +{ + return __le16_to_cpu(desc->u.wcn6855.mpdu_start.sw_peer_id); +} + +static void ath11k_hw_wcn6855_rx_desc_copy_attn_end(struct hal_rx_desc *fdesc, + struct hal_rx_desc *ldesc) +{ + memcpy((u8 *)&fdesc->u.wcn6855.msdu_end, (u8 *)&ldesc->u.wcn6855.msdu_end, + sizeof(struct rx_msdu_end_wcn6855)); + memcpy((u8 *)&fdesc->u.wcn6855.attention, (u8 *)&ldesc->u.wcn6855.attention, + sizeof(struct rx_attention)); + memcpy((u8 *)&fdesc->u.wcn6855.mpdu_end, (u8 *)&ldesc->u.wcn6855.mpdu_end, + sizeof(struct rx_mpdu_end)); +} + +static u32 ath11k_hw_wcn6855_rx_desc_get_mpdu_start_tag(struct hal_rx_desc *desc) +{ + return FIELD_GET(HAL_TLV_HDR_TAG, + __le32_to_cpu(desc->u.wcn6855.mpdu_start_tag)); +} + +static u32 ath11k_hw_wcn6855_rx_desc_get_mpdu_ppdu_id(struct hal_rx_desc *desc) +{ + return __le16_to_cpu(desc->u.wcn6855.mpdu_start.phy_ppdu_id); +} + +static void ath11k_hw_wcn6855_rx_desc_set_msdu_len(struct hal_rx_desc *desc, u16 len) +{ + u32 info = __le32_to_cpu(desc->u.wcn6855.msdu_start.info1); + + info &= ~RX_MSDU_START_INFO1_MSDU_LENGTH; + info |= FIELD_PREP(RX_MSDU_START_INFO1_MSDU_LENGTH, len); + + desc->u.wcn6855.msdu_start.info1 = __cpu_to_le32(info); +} + +static +struct rx_attention *ath11k_hw_wcn6855_rx_desc_get_attention(struct hal_rx_desc *desc) +{ + return &desc->u.wcn6855.attention; +} + +static u8 *ath11k_hw_wcn6855_rx_desc_get_msdu_payload(struct hal_rx_desc *desc) +{ + return &desc->u.wcn6855.msdu_payload[0]; +} + const struct ath11k_hw_ops ipq8074_ops = { .get_hw_mac_from_pdev_id = ath11k_hw_ipq8074_mac_from_pdev_id, .wmi_init_config = ath11k_init_wmi_config_ipq8074, @@ -625,6 +792,40 @@ const struct ath11k_hw_ops qcn9074_ops = { .rx_desc_get_msdu_payload = ath11k_hw_qcn9074_rx_desc_get_msdu_payload, }; +const struct ath11k_hw_ops wcn6855_ops = { + .get_hw_mac_from_pdev_id = ath11k_hw_ipq8074_mac_from_pdev_id, + .wmi_init_config = ath11k_init_wmi_config_qca6390, + .mac_id_to_pdev_id = ath11k_hw_mac_id_to_pdev_id_qca6390, + .mac_id_to_srng_id = ath11k_hw_mac_id_to_srng_id_qca6390, + .tx_mesh_enable = ath11k_hw_wcn6855_tx_mesh_enable, + .rx_desc_get_first_msdu = ath11k_hw_wcn6855_rx_desc_get_first_msdu, + .rx_desc_get_last_msdu = ath11k_hw_wcn6855_rx_desc_get_last_msdu, + .rx_desc_get_l3_pad_bytes = ath11k_hw_wcn6855_rx_desc_get_l3_pad_bytes, + .rx_desc_get_hdr_status = ath11k_hw_wcn6855_rx_desc_get_hdr_status, + .rx_desc_encrypt_valid = ath11k_hw_wcn6855_rx_desc_encrypt_valid, + .rx_desc_get_encrypt_type = ath11k_hw_wcn6855_rx_desc_get_encrypt_type, + .rx_desc_get_decap_type = ath11k_hw_wcn6855_rx_desc_get_decap_type, + .rx_desc_get_mesh_ctl = ath11k_hw_wcn6855_rx_desc_get_mesh_ctl, + .rx_desc_get_mpdu_seq_ctl_vld = ath11k_hw_wcn6855_rx_desc_get_mpdu_seq_ctl_vld, + .rx_desc_get_mpdu_fc_valid = ath11k_hw_wcn6855_rx_desc_get_mpdu_fc_valid, + .rx_desc_get_mpdu_start_seq_no = ath11k_hw_wcn6855_rx_desc_get_mpdu_start_seq_no, + .rx_desc_get_msdu_len = ath11k_hw_wcn6855_rx_desc_get_msdu_len, + .rx_desc_get_msdu_sgi = ath11k_hw_wcn6855_rx_desc_get_msdu_sgi, + .rx_desc_get_msdu_rate_mcs = ath11k_hw_wcn6855_rx_desc_get_msdu_rate_mcs, + .rx_desc_get_msdu_rx_bw = ath11k_hw_wcn6855_rx_desc_get_msdu_rx_bw, + .rx_desc_get_msdu_freq = ath11k_hw_wcn6855_rx_desc_get_msdu_freq, + .rx_desc_get_msdu_pkt_type = ath11k_hw_wcn6855_rx_desc_get_msdu_pkt_type, + .rx_desc_get_msdu_nss = ath11k_hw_wcn6855_rx_desc_get_msdu_nss, + .rx_desc_get_mpdu_tid = ath11k_hw_wcn6855_rx_desc_get_mpdu_tid, + .rx_desc_get_mpdu_peer_id = ath11k_hw_wcn6855_rx_desc_get_mpdu_peer_id, + .rx_desc_copy_attn_end_tlv = ath11k_hw_wcn6855_rx_desc_copy_attn_end, + .rx_desc_get_mpdu_start_tag = ath11k_hw_wcn6855_rx_desc_get_mpdu_start_tag, + .rx_desc_get_mpdu_ppdu_id = ath11k_hw_wcn6855_rx_desc_get_mpdu_ppdu_id, + .rx_desc_set_msdu_len = ath11k_hw_wcn6855_rx_desc_set_msdu_len, + .rx_desc_get_attention = ath11k_hw_wcn6855_rx_desc_get_attention, + .rx_desc_get_msdu_payload = ath11k_hw_wcn6855_rx_desc_get_msdu_payload, +}; + #define ATH11K_TX_RING_MASK_0 0x1 #define ATH11K_TX_RING_MASK_1 0x2 #define ATH11K_TX_RING_MASK_2 0x4 diff --git a/drivers/net/wireless/ath/ath11k/hw.h b/drivers/net/wireless/ath/ath11k/hw.h index 4e7261c0dca1..6e924f628f22 100644 --- a/drivers/net/wireless/ath/ath11k/hw.h +++ b/drivers/net/wireless/ath/ath11k/hw.h @@ -205,6 +205,7 @@ extern const struct ath11k_hw_ops ipq8074_ops; extern const struct ath11k_hw_ops ipq6018_ops; extern const struct ath11k_hw_ops qca6390_ops; extern const struct ath11k_hw_ops qcn9074_ops; +extern const struct ath11k_hw_ops wcn6855_ops; extern const struct ath11k_hw_ring_mask ath11k_hw_ring_mask_ipq8074; extern const struct ath11k_hw_ring_mask ath11k_hw_ring_mask_qca6390; diff --git a/drivers/net/wireless/ath/ath11k/rx_desc.h b/drivers/net/wireless/ath/ath11k/rx_desc.h index 0cdb4a1f816e..79c50804d7dc 100644 --- a/drivers/net/wireless/ath/ath11k/rx_desc.h +++ b/drivers/net/wireless/ath/ath11k/rx_desc.h @@ -368,6 +368,7 @@ struct rx_attention { #define RX_MPDU_START_INFO2_BSSID_HIT BIT(9) #define RX_MPDU_START_INFO2_BSSID_NUM GENMASK(13, 10) #define RX_MPDU_START_INFO2_TID GENMASK(17, 14) +#define RX_MPDU_START_INFO2_TID_WCN6855 GENMASK(18, 15) #define RX_MPDU_START_INFO3_REO_DEST_IND GENMASK(4, 0) #define RX_MPDU_START_INFO3_FLOW_ID_TOEPLITZ BIT(7) @@ -546,6 +547,31 @@ struct rx_mpdu_start_qcn9074 { __le32 ht_ctrl; } __packed; +struct rx_mpdu_start_wcn6855 { + __le32 info3; + __le32 reo_queue_desc_lo; + __le32 info4; + __le32 pn[4]; + __le32 info2; + __le32 peer_meta_data; + __le16 info0; + __le16 phy_ppdu_id; + __le16 ast_index; + __le16 sw_peer_id; + __le32 info1; + __le32 info5; + __le32 info6; + __le16 frame_ctrl; + __le16 duration; + u8 addr1[ETH_ALEN]; + u8 addr2[ETH_ALEN]; + u8 addr3[ETH_ALEN]; + __le16 seq_ctrl; + u8 addr4[ETH_ALEN]; + __le16 qos_ctrl; + __le32 ht_ctrl; +} __packed; + /* rx_mpdu_start * * rxpcu_mpdu_filter_in_category @@ -804,6 +830,20 @@ struct rx_msdu_start_qcn9074 { __le16 vlan_stag_c1; } __packed; +struct rx_msdu_start_wcn6855 { + __le16 info0; + __le16 phy_ppdu_id; + __le32 info1; + __le32 info2; + __le32 toeplitz_hash; + __le32 flow_id_toeplitz; + __le32 info3; + __le32 ppdu_start_timestamp; + __le32 phy_meta_data; + __le16 vlan_ctag_ci; + __le16 vlan_stag_ci; +} __packed; + /* rx_msdu_start * * rxpcu_mpdu_filter_in_category @@ -988,7 +1028,9 @@ struct rx_msdu_start_qcn9074 { #define RX_MSDU_END_INFO2_REPORTED_MPDU_LEN GENMASK(13, 0) #define RX_MSDU_END_INFO2_FIRST_MSDU BIT(14) +#define RX_MSDU_END_INFO2_FIRST_MSDU_WCN6855 BIT(28) #define RX_MSDU_END_INFO2_LAST_MSDU BIT(15) +#define RX_MSDU_END_INFO2_LAST_MSDU_WCN6855 BIT(29) #define RX_MSDU_END_INFO2_SA_IDX_TIMEOUT BIT(16) #define RX_MSDU_END_INFO2_DA_IDX_TIMEOUT BIT(17) #define RX_MSDU_END_INFO2_MSDU_LIMIT_ERR BIT(18) @@ -1037,6 +1079,31 @@ struct rx_msdu_end_ipq8074 { __le16 sa_sw_peer_id; } __packed; +struct rx_msdu_end_wcn6855 { + __le16 info0; + __le16 phy_ppdu_id; + __le16 ip_hdr_cksum; + __le16 reported_mpdu_len; + __le32 info1; + __le32 ext_wapi_pn[2]; + __le32 info4; + __le32 ipv6_options_crc; + __le32 tcp_seq_num; + __le32 tcp_ack_num; + __le16 info3; + __le16 window_size; + __le32 info2; + __le16 sa_idx; + __le16 da_idx; + __le32 info5; + __le32 fse_metadata; + __le16 cce_metadata; + __le16 sa_sw_peer_id; + __le32 rule_indication[2]; + __le32 info6; + __le32 info7; +} __packed; + #define RX_MSDU_END_MPDU_LENGTH_INFO GENMASK(13, 0) #define RX_MSDU_END_INFO2_DA_OFFSET GENMASK(5, 0) @@ -1400,10 +1467,30 @@ struct hal_rx_desc_qcn9074 { u8 msdu_payload[0]; } __packed; +struct hal_rx_desc_wcn6855 { + __le32 msdu_end_tag; + struct rx_msdu_end_wcn6855 msdu_end; + __le32 rx_attn_tag; + struct rx_attention attention; + __le32 msdu_start_tag; + struct rx_msdu_start_wcn6855 msdu_start; + u8 rx_padding0[HAL_RX_DESC_PADDING0_BYTES]; + __le32 mpdu_start_tag; + struct rx_mpdu_start_wcn6855 mpdu_start; + __le32 mpdu_end_tag; + struct rx_mpdu_end mpdu_end; + u8 rx_padding1[HAL_RX_DESC_PADDING1_BYTES]; + __le32 hdr_status_tag; + __le32 phy_ppdu_id; + u8 hdr_status[HAL_RX_DESC_HDR_STATUS_LEN]; + u8 msdu_payload[0]; +} __packed; + struct hal_rx_desc { union { struct hal_rx_desc_ipq8074 ipq8074; struct hal_rx_desc_qcn9074 qcn9074; + struct hal_rx_desc_wcn6855 wcn6855; } u; } __packed; From 0d55b76fd815f4d685a62afe44e623501186ceb4 Mon Sep 17 00:00:00 2001 From: Baochen Qiang Date: Mon, 31 May 2021 17:41:27 +0300 Subject: [PATCH 10/91] ath11k: setup REO for WCN6855 WCN6855 needs a different reo configuration, so add separate handling for this target in ath11k_hw_ops. Tested-on: WCN6855 hw2.0 PCI WLAN.HSP.1.1-01720.1-QCAHSPSWPL_V1_V2_SILICONZ_LITE-1 Tested-on: QCA6390 hw2.0 PCI WLAN.HST.1.0.1-01740-QCAHSTSWPLZ_V2_TO_X86-1 Signed-off-by: Baochen Qiang Signed-off-by: Jouni Malinen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511162214.29475-4-jouni@codeaurora.org --- drivers/net/wireless/ath/ath11k/dp.c | 16 +---- drivers/net/wireless/ath/ath11k/hal.h | 3 +- drivers/net/wireless/ath/ath11k/hal_rx.c | 37 ---------- drivers/net/wireless/ath/ath11k/hw.c | 91 ++++++++++++++++++++++++ drivers/net/wireless/ath/ath11k/hw.h | 1 + 5 files changed, 96 insertions(+), 52 deletions(-) diff --git a/drivers/net/wireless/ath/ath11k/dp.c b/drivers/net/wireless/ath/ath11k/dp.c index 04f6c4e0658b..b0c8f6290099 100644 --- a/drivers/net/wireless/ath/ath11k/dp.c +++ b/drivers/net/wireless/ath/ath11k/dp.c @@ -342,7 +342,6 @@ static int ath11k_dp_srng_common_setup(struct ath11k_base *ab) struct ath11k_dp *dp = &ab->dp; struct hal_srng *srng; int i, ret; - u32 ring_hash_map; ret = ath11k_dp_srng_setup(ab, &dp->wbm_desc_rel_ring, HAL_SW2WBM_RELEASE, 0, 0, @@ -439,20 +438,9 @@ static int ath11k_dp_srng_common_setup(struct ath11k_base *ab) } /* When hash based routing of rx packet is enabled, 32 entries to map - * the hash values to the ring will be configured. Each hash entry uses - * three bits to map to a particular ring. The ring mapping will be - * 0:TCL, 1:SW1, 2:SW2, 3:SW3, 4:SW4, 5:Release, 6:FW and 7:Not used. + * the hash values to the ring will be configured. */ - ring_hash_map = HAL_HASH_ROUTING_RING_SW1 << 0 | - HAL_HASH_ROUTING_RING_SW2 << 3 | - HAL_HASH_ROUTING_RING_SW3 << 6 | - HAL_HASH_ROUTING_RING_SW4 << 9 | - HAL_HASH_ROUTING_RING_SW1 << 12 | - HAL_HASH_ROUTING_RING_SW2 << 15 | - HAL_HASH_ROUTING_RING_SW3 << 18 | - HAL_HASH_ROUTING_RING_SW4 << 21; - - ath11k_hal_reo_hw_setup(ab, ring_hash_map); + ab->hw_params.hw_ops->reo_setup(ab); return 0; diff --git a/drivers/net/wireless/ath/ath11k/hal.h b/drivers/net/wireless/ath/ath11k/hal.h index 91d1428b8b94..35ed3a14e200 100644 --- a/drivers/net/wireless/ath/ath11k/hal.h +++ b/drivers/net/wireless/ath/ath11k/hal.h @@ -120,6 +120,7 @@ struct ath11k_base; #define HAL_REO1_DEST_RING_CTRL_IX_1 0x00000008 #define HAL_REO1_DEST_RING_CTRL_IX_2 0x0000000c #define HAL_REO1_DEST_RING_CTRL_IX_3 0x00000010 +#define HAL_REO1_MISC_CTL 0x00000630 #define HAL_REO1_RING_BASE_LSB(ab) ab->hw_params.regs->hal_reo1_ring_base_lsb #define HAL_REO1_RING_BASE_MSB(ab) ab->hw_params.regs->hal_reo1_ring_base_msb #define HAL_REO1_RING_ID(ab) ab->hw_params.regs->hal_reo1_ring_id @@ -280,6 +281,7 @@ struct ath11k_base; #define HAL_REO1_GEN_ENABLE_FRAG_DST_RING GENMASK(25, 23) #define HAL_REO1_GEN_ENABLE_AGING_LIST_ENABLE BIT(2) #define HAL_REO1_GEN_ENABLE_AGING_FLUSH_ENABLE BIT(3) +#define HAL_REO1_MISC_CTL_FRAGMENT_DST_RING GENMASK(20, 17) /* CE ring bit field mask and shift */ #define HAL_CE_DST_R0_DEST_CTRL_MAX_LEN GENMASK(15, 0) @@ -906,7 +908,6 @@ void ath11k_hal_reo_qdesc_setup(void *vaddr, int tid, u32 ba_window_size, u32 start_seq, enum hal_pn_type type); void ath11k_hal_reo_init_cmd_ring(struct ath11k_base *ab, struct hal_srng *srng); -void ath11k_hal_reo_hw_setup(struct ath11k_base *ab, u32 ring_hash_map); void ath11k_hal_setup_link_idle_list(struct ath11k_base *ab, struct hal_wbm_idle_scatter_list *sbuf, u32 nsbufs, u32 tot_link_desc, diff --git a/drivers/net/wireless/ath/ath11k/hal_rx.c b/drivers/net/wireless/ath/ath11k/hal_rx.c index fac2396edf32..80999bae0958 100644 --- a/drivers/net/wireless/ath/ath11k/hal_rx.c +++ b/drivers/net/wireless/ath/ath11k/hal_rx.c @@ -801,43 +801,6 @@ void ath11k_hal_reo_init_cmd_ring(struct ath11k_base *ab, } } -void ath11k_hal_reo_hw_setup(struct ath11k_base *ab, u32 ring_hash_map) -{ - u32 reo_base = HAL_SEQ_WCSS_UMAC_REO_REG; - u32 val; - - val = ath11k_hif_read32(ab, reo_base + HAL_REO1_GEN_ENABLE); - - val &= ~HAL_REO1_GEN_ENABLE_FRAG_DST_RING; - val |= FIELD_PREP(HAL_REO1_GEN_ENABLE_FRAG_DST_RING, - HAL_SRNG_RING_ID_REO2SW1) | - FIELD_PREP(HAL_REO1_GEN_ENABLE_AGING_LIST_ENABLE, 1) | - FIELD_PREP(HAL_REO1_GEN_ENABLE_AGING_FLUSH_ENABLE, 1); - ath11k_hif_write32(ab, reo_base + HAL_REO1_GEN_ENABLE, val); - - ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_0(ab), - HAL_DEFAULT_REO_TIMEOUT_USEC); - ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_1(ab), - HAL_DEFAULT_REO_TIMEOUT_USEC); - ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_2(ab), - HAL_DEFAULT_REO_TIMEOUT_USEC); - ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_3(ab), - HAL_DEFAULT_REO_TIMEOUT_USEC); - - ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_0, - FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, - ring_hash_map)); - ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_1, - FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, - ring_hash_map)); - ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_2, - FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, - ring_hash_map)); - ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_3, - FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, - ring_hash_map)); -} - static enum hal_rx_mon_status ath11k_hal_rx_parse_mon_status_tlv(struct ath11k_base *ab, struct hal_rx_mon_ppdu_info *ppdu_info, diff --git a/drivers/net/wireless/ath/ath11k/hw.c b/drivers/net/wireless/ath/ath11k/hw.c index 023047df954c..01207b50a454 100644 --- a/drivers/net/wireless/ath/ath11k/hw.c +++ b/drivers/net/wireless/ath/ath11k/hw.c @@ -10,6 +10,7 @@ #include "hw.h" #include "core.h" #include "ce.h" +#include "hif.h" /* Map from pdev index to hw mac index */ static u8 ath11k_hw_ipq8074_mac_from_pdev_id(int pdev_idx) @@ -98,6 +99,52 @@ static void ath11k_init_wmi_config_qca6390(struct ath11k_base *ab, config->num_keep_alive_pattern = 0; } +static void ath11k_hw_ipq8074_reo_setup(struct ath11k_base *ab) +{ + u32 reo_base = HAL_SEQ_WCSS_UMAC_REO_REG; + u32 val; + /* Each hash entry uses three bits to map to a particular ring. */ + u32 ring_hash_map = HAL_HASH_ROUTING_RING_SW1 << 0 | + HAL_HASH_ROUTING_RING_SW2 << 3 | + HAL_HASH_ROUTING_RING_SW3 << 6 | + HAL_HASH_ROUTING_RING_SW4 << 9 | + HAL_HASH_ROUTING_RING_SW1 << 12 | + HAL_HASH_ROUTING_RING_SW2 << 15 | + HAL_HASH_ROUTING_RING_SW3 << 18 | + HAL_HASH_ROUTING_RING_SW4 << 21; + + val = ath11k_hif_read32(ab, reo_base + HAL_REO1_GEN_ENABLE); + + val &= ~HAL_REO1_GEN_ENABLE_FRAG_DST_RING; + val |= FIELD_PREP(HAL_REO1_GEN_ENABLE_FRAG_DST_RING, + HAL_SRNG_RING_ID_REO2SW1) | + FIELD_PREP(HAL_REO1_GEN_ENABLE_AGING_LIST_ENABLE, 1) | + FIELD_PREP(HAL_REO1_GEN_ENABLE_AGING_FLUSH_ENABLE, 1); + ath11k_hif_write32(ab, reo_base + HAL_REO1_GEN_ENABLE, val); + + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_0(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_1(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_2(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_3(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + + ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_0, + FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, + ring_hash_map)); + ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_1, + FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, + ring_hash_map)); + ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_2, + FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, + ring_hash_map)); + ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_3, + FIELD_PREP(HAL_REO_DEST_RING_CTRL_HASH_RING_MAP, + ring_hash_map)); +} + static void ath11k_init_wmi_config_ipq8074(struct ath11k_base *ab, struct target_resource_config *config) { @@ -656,6 +703,45 @@ static u8 *ath11k_hw_wcn6855_rx_desc_get_msdu_payload(struct hal_rx_desc *desc) return &desc->u.wcn6855.msdu_payload[0]; } +static void ath11k_hw_wcn6855_reo_setup(struct ath11k_base *ab) +{ + u32 reo_base = HAL_SEQ_WCSS_UMAC_REO_REG; + u32 val; + /* Each hash entry uses four bits to map to a particular ring. */ + u32 ring_hash_map = HAL_HASH_ROUTING_RING_SW1 << 0 | + HAL_HASH_ROUTING_RING_SW2 << 4 | + HAL_HASH_ROUTING_RING_SW3 << 8 | + HAL_HASH_ROUTING_RING_SW4 << 12 | + HAL_HASH_ROUTING_RING_SW1 << 16 | + HAL_HASH_ROUTING_RING_SW2 << 20 | + HAL_HASH_ROUTING_RING_SW3 << 24 | + HAL_HASH_ROUTING_RING_SW4 << 28; + + val = ath11k_hif_read32(ab, reo_base + HAL_REO1_GEN_ENABLE); + val |= FIELD_PREP(HAL_REO1_GEN_ENABLE_AGING_LIST_ENABLE, 1) | + FIELD_PREP(HAL_REO1_GEN_ENABLE_AGING_FLUSH_ENABLE, 1); + ath11k_hif_write32(ab, reo_base + HAL_REO1_GEN_ENABLE, val); + + val = ath11k_hif_read32(ab, reo_base + HAL_REO1_MISC_CTL); + val &= ~HAL_REO1_MISC_CTL_FRAGMENT_DST_RING; + val |= FIELD_PREP(HAL_REO1_MISC_CTL_FRAGMENT_DST_RING, HAL_SRNG_RING_ID_REO2SW1); + ath11k_hif_write32(ab, reo_base + HAL_REO1_MISC_CTL, val); + + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_0(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_1(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_2(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + ath11k_hif_write32(ab, reo_base + HAL_REO1_AGING_THRESH_IX_3(ab), + HAL_DEFAULT_REO_TIMEOUT_USEC); + + ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_2, + ring_hash_map); + ath11k_hif_write32(ab, reo_base + HAL_REO1_DEST_RING_CTRL_IX_3, + ring_hash_map); +} + const struct ath11k_hw_ops ipq8074_ops = { .get_hw_mac_from_pdev_id = ath11k_hw_ipq8074_mac_from_pdev_id, .wmi_init_config = ath11k_init_wmi_config_ipq8074, @@ -688,6 +774,7 @@ const struct ath11k_hw_ops ipq8074_ops = { .rx_desc_set_msdu_len = ath11k_hw_ipq8074_rx_desc_set_msdu_len, .rx_desc_get_attention = ath11k_hw_ipq8074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_ipq8074_rx_desc_get_msdu_payload, + .reo_setup = ath11k_hw_ipq8074_reo_setup, }; const struct ath11k_hw_ops ipq6018_ops = { @@ -722,6 +809,7 @@ const struct ath11k_hw_ops ipq6018_ops = { .rx_desc_set_msdu_len = ath11k_hw_ipq8074_rx_desc_set_msdu_len, .rx_desc_get_attention = ath11k_hw_ipq8074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_ipq8074_rx_desc_get_msdu_payload, + .reo_setup = ath11k_hw_ipq8074_reo_setup, }; const struct ath11k_hw_ops qca6390_ops = { @@ -756,6 +844,7 @@ const struct ath11k_hw_ops qca6390_ops = { .rx_desc_set_msdu_len = ath11k_hw_ipq8074_rx_desc_set_msdu_len, .rx_desc_get_attention = ath11k_hw_ipq8074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_ipq8074_rx_desc_get_msdu_payload, + .reo_setup = ath11k_hw_ipq8074_reo_setup, }; const struct ath11k_hw_ops qcn9074_ops = { @@ -790,6 +879,7 @@ const struct ath11k_hw_ops qcn9074_ops = { .rx_desc_set_msdu_len = ath11k_hw_qcn9074_rx_desc_set_msdu_len, .rx_desc_get_attention = ath11k_hw_qcn9074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_qcn9074_rx_desc_get_msdu_payload, + .reo_setup = ath11k_hw_ipq8074_reo_setup, }; const struct ath11k_hw_ops wcn6855_ops = { @@ -824,6 +914,7 @@ const struct ath11k_hw_ops wcn6855_ops = { .rx_desc_set_msdu_len = ath11k_hw_wcn6855_rx_desc_set_msdu_len, .rx_desc_get_attention = ath11k_hw_wcn6855_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_wcn6855_rx_desc_get_msdu_payload, + .reo_setup = ath11k_hw_wcn6855_reo_setup, }; #define ATH11K_TX_RING_MASK_0 0x1 diff --git a/drivers/net/wireless/ath/ath11k/hw.h b/drivers/net/wireless/ath/ath11k/hw.h index 6e924f628f22..afe3b3c71695 100644 --- a/drivers/net/wireless/ath/ath11k/hw.h +++ b/drivers/net/wireless/ath/ath11k/hw.h @@ -199,6 +199,7 @@ struct ath11k_hw_ops { void (*rx_desc_set_msdu_len)(struct hal_rx_desc *desc, u16 len); struct rx_attention *(*rx_desc_get_attention)(struct hal_rx_desc *desc); u8 *(*rx_desc_get_msdu_payload)(struct hal_rx_desc *desc); + void (*reo_setup)(struct ath11k_base *ab); }; extern const struct ath11k_hw_ops ipq8074_ops; From ed66849e159ba92a91ccde13ce3aebd90c644e05 Mon Sep 17 00:00:00 2001 From: Baochen Qiang Date: Mon, 31 May 2021 17:41:27 +0300 Subject: [PATCH 11/91] ath11k: setup WBM_IDLE_LINK ring once again For WCN6855, WBM idle link ring needs a reinit. Without this reinit, firmware crash might happen occasionally. This is requested by the hw team. Tested-on: WCN6855 hw2.0 PCI WLAN.HSP.1.1-01720.1-QCAHSPSWPL_V1_V2_SILICONZ_LITE-1 Tested-on: QCA6390 hw2.0 PCI WLAN.HST.1.0.1-01740-QCAHSTSWPLZ_V2_TO_X86-1 Signed-off-by: Baochen Qiang Signed-off-by: Jouni Malinen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511162214.29475-5-jouni@codeaurora.org --- drivers/net/wireless/ath/ath11k/hal.c | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/drivers/net/wireless/ath/ath11k/hal.c b/drivers/net/wireless/ath/ath11k/hal.c index 08e3c72d9237..eaa0edca5576 100644 --- a/drivers/net/wireless/ath/ath11k/hal.c +++ b/drivers/net/wireless/ath/ath11k/hal.c @@ -382,6 +382,16 @@ static void ath11k_hal_srng_src_hw_init(struct ath11k_base *ab, val = FIELD_PREP(HAL_REO1_RING_ID_ENTRY_SIZE, srng->entry_size); ath11k_hif_write32(ab, reg_base + HAL_TCL1_RING_ID_OFFSET(ab), val); + if (srng->ring_id == HAL_SRNG_RING_ID_WBM_IDLE_LINK) { + ath11k_hif_write32(ab, reg_base, (u32)srng->ring_base_paddr); + val = FIELD_PREP(HAL_TCL1_RING_BASE_MSB_RING_BASE_ADDR_MSB, + ((u64)srng->ring_base_paddr >> + HAL_ADDR_MSB_REG_SHIFT)) | + FIELD_PREP(HAL_TCL1_RING_BASE_MSB_RING_SIZE, + (srng->entry_size * srng->num_entries)); + ath11k_hif_write32(ab, reg_base + HAL_TCL1_RING_BASE_MSB_OFFSET(ab), val); + } + /* interrupt setup */ /* NOTE: IPQ8074 v2 requires the interrupt timer threshold in the * unit of 8 usecs instead of 1 usec (as required by v1). From 8845fed1ad7b2fcd4dde82737c197805255bed0f Mon Sep 17 00:00:00 2001 From: Baochen Qiang Date: Mon, 31 May 2021 17:41:27 +0300 Subject: [PATCH 12/91] ath11k: add support to get peer id for WCN6855 For WCN6855, the layout of hal rx mpdu info is different, so need to handle this target differently when getting peer id. Tested-on: WCN6855 hw2.0 PCI WLAN.HSP.1.1-01720.1-QCAHSPSWPL_V1_V2_SILICONZ_LITE-1 Tested-on: QCA6390 hw2.0 PCI WLAN.HST.1.0.1-01740-QCAHSTSWPLZ_V2_TO_X86-1 Signed-off-by: Baochen Qiang Signed-off-by: Jouni Malinen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511162214.29475-6-jouni@codeaurora.org --- drivers/net/wireless/ath/ath11k/hal_rx.c | 5 +---- drivers/net/wireless/ath/ath11k/hal_rx.h | 8 +++++++ drivers/net/wireless/ath/ath11k/hw.c | 28 ++++++++++++++++++++++++ drivers/net/wireless/ath/ath11k/hw.h | 1 + 4 files changed, 38 insertions(+), 4 deletions(-) diff --git a/drivers/net/wireless/ath/ath11k/hal_rx.c b/drivers/net/wireless/ath/ath11k/hal_rx.c index 80999bae0958..325055ca41ab 100644 --- a/drivers/net/wireless/ath/ath11k/hal_rx.c +++ b/drivers/net/wireless/ath/ath11k/hal_rx.c @@ -1091,12 +1091,9 @@ ath11k_hal_rx_parse_mon_status_tlv(struct ath11k_base *ab, break; } case HAL_RX_MPDU_START: { - struct hal_rx_mpdu_info *mpdu_info = - (struct hal_rx_mpdu_info *)tlv_data; u16 peer_id; - peer_id = FIELD_GET(HAL_RX_MPDU_INFO_INFO0_PEERID, - __le32_to_cpu(mpdu_info->info0)); + peer_id = ab->hw_params.hw_ops->mpdu_info_get_peerid(tlv_data); if (peer_id) ppdu_info->peer_id = peer_id; break; diff --git a/drivers/net/wireless/ath/ath11k/hal_rx.h b/drivers/net/wireless/ath/ath11k/hal_rx.h index d464a270c049..0f1f04b812b9 100644 --- a/drivers/net/wireless/ath/ath11k/hal_rx.h +++ b/drivers/net/wireless/ath/ath11k/hal_rx.h @@ -254,12 +254,20 @@ struct hal_rx_phyrx_rssi_legacy_info { } __packed; #define HAL_RX_MPDU_INFO_INFO0_PEERID GENMASK(31, 16) +#define HAL_RX_MPDU_INFO_INFO0_PEERID_WCN6855 GENMASK(15, 0) + struct hal_rx_mpdu_info { __le32 rsvd0; __le32 info0; __le32 rsvd1[21]; } __packed; +struct hal_rx_mpdu_info_wcn6855 { + __le32 rsvd0[8]; + __le32 info0; + __le32 rsvd1[14]; +} __packed; + #define HAL_RX_PPDU_END_DURATION GENMASK(23, 0) struct hal_rx_ppdu_end_duration { __le32 rsvd0[9]; diff --git a/drivers/net/wireless/ath/ath11k/hw.c b/drivers/net/wireless/ath/ath11k/hw.c index 01207b50a454..d9596903b0a5 100644 --- a/drivers/net/wireless/ath/ath11k/hw.c +++ b/drivers/net/wireless/ath/ath11k/hw.c @@ -742,6 +742,29 @@ static void ath11k_hw_wcn6855_reo_setup(struct ath11k_base *ab) ring_hash_map); } +static u16 ath11k_hw_ipq8074_mpdu_info_get_peerid(u8 *tlv_data) +{ + u16 peer_id = 0; + struct hal_rx_mpdu_info *mpdu_info = + (struct hal_rx_mpdu_info *)tlv_data; + + peer_id = FIELD_GET(HAL_RX_MPDU_INFO_INFO0_PEERID, + __le32_to_cpu(mpdu_info->info0)); + + return peer_id; +} + +static u16 ath11k_hw_wcn6855_mpdu_info_get_peerid(u8 *tlv_data) +{ + u16 peer_id = 0; + struct hal_rx_mpdu_info_wcn6855 *mpdu_info = + (struct hal_rx_mpdu_info_wcn6855 *)tlv_data; + + peer_id = FIELD_GET(HAL_RX_MPDU_INFO_INFO0_PEERID_WCN6855, + __le32_to_cpu(mpdu_info->info0)); + return peer_id; +} + const struct ath11k_hw_ops ipq8074_ops = { .get_hw_mac_from_pdev_id = ath11k_hw_ipq8074_mac_from_pdev_id, .wmi_init_config = ath11k_init_wmi_config_ipq8074, @@ -775,6 +798,7 @@ const struct ath11k_hw_ops ipq8074_ops = { .rx_desc_get_attention = ath11k_hw_ipq8074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_ipq8074_rx_desc_get_msdu_payload, .reo_setup = ath11k_hw_ipq8074_reo_setup, + .mpdu_info_get_peerid = ath11k_hw_ipq8074_mpdu_info_get_peerid, }; const struct ath11k_hw_ops ipq6018_ops = { @@ -810,6 +834,7 @@ const struct ath11k_hw_ops ipq6018_ops = { .rx_desc_get_attention = ath11k_hw_ipq8074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_ipq8074_rx_desc_get_msdu_payload, .reo_setup = ath11k_hw_ipq8074_reo_setup, + .mpdu_info_get_peerid = ath11k_hw_ipq8074_mpdu_info_get_peerid, }; const struct ath11k_hw_ops qca6390_ops = { @@ -845,6 +870,7 @@ const struct ath11k_hw_ops qca6390_ops = { .rx_desc_get_attention = ath11k_hw_ipq8074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_ipq8074_rx_desc_get_msdu_payload, .reo_setup = ath11k_hw_ipq8074_reo_setup, + .mpdu_info_get_peerid = ath11k_hw_ipq8074_mpdu_info_get_peerid, }; const struct ath11k_hw_ops qcn9074_ops = { @@ -880,6 +906,7 @@ const struct ath11k_hw_ops qcn9074_ops = { .rx_desc_get_attention = ath11k_hw_qcn9074_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_qcn9074_rx_desc_get_msdu_payload, .reo_setup = ath11k_hw_ipq8074_reo_setup, + .mpdu_info_get_peerid = ath11k_hw_ipq8074_mpdu_info_get_peerid, }; const struct ath11k_hw_ops wcn6855_ops = { @@ -915,6 +942,7 @@ const struct ath11k_hw_ops wcn6855_ops = { .rx_desc_get_attention = ath11k_hw_wcn6855_rx_desc_get_attention, .rx_desc_get_msdu_payload = ath11k_hw_wcn6855_rx_desc_get_msdu_payload, .reo_setup = ath11k_hw_wcn6855_reo_setup, + .mpdu_info_get_peerid = ath11k_hw_wcn6855_mpdu_info_get_peerid, }; #define ATH11K_TX_RING_MASK_0 0x1 diff --git a/drivers/net/wireless/ath/ath11k/hw.h b/drivers/net/wireless/ath/ath11k/hw.h index afe3b3c71695..be62f0c2e25e 100644 --- a/drivers/net/wireless/ath/ath11k/hw.h +++ b/drivers/net/wireless/ath/ath11k/hw.h @@ -200,6 +200,7 @@ struct ath11k_hw_ops { struct rx_attention *(*rx_desc_get_attention)(struct hal_rx_desc *desc); u8 *(*rx_desc_get_msdu_payload)(struct hal_rx_desc *desc); void (*reo_setup)(struct ath11k_base *ab); + u16 (*mpdu_info_get_peerid)(u8 *tlv_data); }; extern const struct ath11k_hw_ops ipq8074_ops; From 0fbf19570099cf1c41e86b3b14a392d46131ed0d Mon Sep 17 00:00:00 2001 From: Baochen Qiang Date: Mon, 31 May 2021 17:41:28 +0300 Subject: [PATCH 13/91] ath11k: add support for WCN6855 This patch is to add support for WCN6855. For station mode, WCN6855 is able to connect to an AP, and ping works well. For AP mode, hostapd is able to bringup an SAP interface with WCN6855, a normal station can connect to this AP and ping works well. Tested-on: WCN6855 hw2.0 PCI WLAN.HSP.1.1-01720.1-QCAHSPSWPL_V1_V2_SILICONZ_LITE-1 Tested-on: QCA6390 hw2.0 PCI WLAN.HST.1.0.1-01740-QCAHSTSWPLZ_V2_TO_X86-1 Signed-off-by: Baochen Qiang Signed-off-by: Jouni Malinen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511162214.29475-7-jouni@codeaurora.org --- drivers/net/wireless/ath/ath11k/core.c | 39 +++++++++++++++++++++++ drivers/net/wireless/ath/ath11k/core.h | 1 + drivers/net/wireless/ath/ath11k/mhi.c | 1 + drivers/net/wireless/ath/ath11k/pci.c | 44 ++++++++++++++++++++------ 4 files changed, 75 insertions(+), 10 deletions(-) diff --git a/drivers/net/wireless/ath/ath11k/core.c b/drivers/net/wireless/ath/ath11k/core.c index 77ce3347ab86..fd8941905fdb 100644 --- a/drivers/net/wireless/ath/ath11k/core.c +++ b/drivers/net/wireless/ath/ath11k/core.c @@ -187,6 +187,45 @@ static const struct ath11k_hw_params ath11k_hw_params[] = { .supports_suspend = false, .hal_desc_sz = sizeof(struct hal_rx_desc_qcn9074), }, + { + .name = "wcn6855 hw2.0", + .hw_rev = ATH11K_HW_WCN6855_HW20, + .fw = { + .dir = "WCN6855/hw2.0", + .board_size = 256 * 1024, + .cal_size = 256 * 1024, + }, + .max_radios = 3, + .bdf_addr = 0x4B0C0000, + .hw_ops = &wcn6855_ops, + .ring_mask = &ath11k_hw_ring_mask_qca6390, + .internal_sleep_clock = true, + .regs = &wcn6855_regs, + .qmi_service_ins_id = ATH11K_QMI_WLFW_SERVICE_INS_ID_V01_QCA6390, + .host_ce_config = ath11k_host_ce_config_qca6390, + .ce_count = 9, + .target_ce_config = ath11k_target_ce_config_wlan_qca6390, + .target_ce_count = 9, + .svc_to_ce_map = ath11k_target_service_to_ce_map_wlan_qca6390, + .svc_to_ce_map_len = 14, + .single_pdev_only = true, + .rxdma1_enable = false, + .num_rxmda_per_pdev = 2, + .rx_mac_buf_ring = true, + .vdev_start_delay = true, + .htt_peer_map_v2 = false, + .tcl_0_only = true, + .spectral_fft_sz = 0, + + .interface_modes = BIT(NL80211_IFTYPE_STATION) | + BIT(NL80211_IFTYPE_AP), + .supports_monitor = false, + .supports_shadow_regs = true, + .idle_ps = true, + .cold_boot_calib = false, + .supports_suspend = true, + .hal_desc_sz = sizeof(struct hal_rx_desc_wcn6855), + }, }; int ath11k_core_suspend(struct ath11k_base *ab) diff --git a/drivers/net/wireless/ath/ath11k/core.h b/drivers/net/wireless/ath/ath11k/core.h index 382df5318b61..018fb2385f2a 100644 --- a/drivers/net/wireless/ath/ath11k/core.h +++ b/drivers/net/wireless/ath/ath11k/core.h @@ -107,6 +107,7 @@ enum ath11k_hw_rev { ATH11K_HW_QCA6390_HW20, ATH11K_HW_IPQ6018_HW10, ATH11K_HW_QCN9074_HW10, + ATH11K_HW_WCN6855_HW20, }; enum ath11k_firmware_mode { diff --git a/drivers/net/wireless/ath/ath11k/mhi.c b/drivers/net/wireless/ath/ath11k/mhi.c index 27b394d115e2..75cc2d80fde8 100644 --- a/drivers/net/wireless/ath/ath11k/mhi.c +++ b/drivers/net/wireless/ath/ath11k/mhi.c @@ -354,6 +354,7 @@ int ath11k_mhi_register(struct ath11k_pci *ab_pci) ath11k_mhi_config = &ath11k_mhi_config_qcn9074; break; case ATH11K_HW_QCA6390_HW20: + case ATH11K_HW_WCN6855_HW20: ath11k_mhi_config = &ath11k_mhi_config_qca6390; break; default: diff --git a/drivers/net/wireless/ath/ath11k/pci.c b/drivers/net/wireless/ath/ath11k/pci.c index 0f31eb566fb6..a4688b6beeb1 100644 --- a/drivers/net/wireless/ath/ath11k/pci.c +++ b/drivers/net/wireless/ath/ath11k/pci.c @@ -36,9 +36,11 @@ #define QCA6390_DEVICE_ID 0x1101 #define QCN9074_DEVICE_ID 0x1104 +#define WCN6855_DEVICE_ID 0x1103 static const struct pci_device_id ath11k_pci_id_table[] = { { PCI_VDEVICE(QCOM, QCA6390_DEVICE_ID) }, + { PCI_VDEVICE(QCOM, WCN6855_DEVICE_ID) }, /* TODO: add QCN9074_DEVICE_ID) once firmware issues are resolved */ {0} }; @@ -1176,12 +1178,26 @@ static const struct ath11k_hif_ops ath11k_pci_hif_ops = { .get_ce_msi_idx = ath11k_pci_get_ce_msi_idx, }; +static void ath11k_pci_read_hw_version(struct ath11k_base *ab, u32 *major, u32 *minor) +{ + u32 soc_hw_version; + + soc_hw_version = ath11k_pci_read32(ab, TCSR_SOC_HW_VERSION); + *major = FIELD_GET(TCSR_SOC_HW_VERSION_MAJOR_MASK, + soc_hw_version); + *minor = FIELD_GET(TCSR_SOC_HW_VERSION_MINOR_MASK, + soc_hw_version); + + ath11k_dbg(ab, ATH11K_DBG_PCI, "pci tcsr_soc_hw_version major %d minor %d\n", + *major, *minor); +} + static int ath11k_pci_probe(struct pci_dev *pdev, const struct pci_device_id *pci_dev) { struct ath11k_base *ab; struct ath11k_pci *ab_pci; - u32 soc_hw_version, soc_hw_version_major, soc_hw_version_minor; + u32 soc_hw_version_major, soc_hw_version_minor; int ret; ab = ath11k_core_alloc(&pdev->dev, sizeof(*ab_pci), ATH11K_BUS_PCI, @@ -1209,15 +1225,8 @@ static int ath11k_pci_probe(struct pci_dev *pdev, switch (pci_dev->device) { case QCA6390_DEVICE_ID: - soc_hw_version = ath11k_pci_read32(ab, TCSR_SOC_HW_VERSION); - soc_hw_version_major = FIELD_GET(TCSR_SOC_HW_VERSION_MAJOR_MASK, - soc_hw_version); - soc_hw_version_minor = FIELD_GET(TCSR_SOC_HW_VERSION_MINOR_MASK, - soc_hw_version); - - ath11k_dbg(ab, ATH11K_DBG_PCI, "pci tcsr_soc_hw_version major %d minor %d\n", - soc_hw_version_major, soc_hw_version_minor); - + ath11k_pci_read_hw_version(ab, &soc_hw_version_major, + &soc_hw_version_minor); switch (soc_hw_version_major) { case 2: ab->hw_rev = ATH11K_HW_QCA6390_HW20; @@ -1235,6 +1244,21 @@ static int ath11k_pci_probe(struct pci_dev *pdev, ab->bus_params.static_window_map = true; ab->hw_rev = ATH11K_HW_QCN9074_HW10; break; + case WCN6855_DEVICE_ID: + ath11k_pci_read_hw_version(ab, &soc_hw_version_major, + &soc_hw_version_minor); + switch (soc_hw_version_major) { + case 2: + ab->hw_rev = ATH11K_HW_WCN6855_HW20; + break; + default: + dev_err(&pdev->dev, "Unsupported WCN6855 SOC hardware version: %d %d\n", + soc_hw_version_major, soc_hw_version_minor); + ret = -EOPNOTSUPP; + goto err_pci_free_region; + } + ab_pci->msi_config = &ath11k_msi_config[0]; + break; default: dev_err(&pdev->dev, "Unknown PCI device found: 0x%x\n", pci_dev->device); From 5088df0504fe7d9623bf5789950327bc9e594fed Mon Sep 17 00:00:00 2001 From: Baochen Qiang Date: Mon, 31 May 2021 17:41:28 +0300 Subject: [PATCH 14/91] ath11k: don't call ath11k_pci_set_l1ss for WCN6855 For QCA6390, one PCI related clock drifts sometimes, and it makes PCI link difficult to quit L1ss. Current implementation fixed this by configuring some related regs using ath11k_pci_fix_l1ss. WCN6855 does not have this clock drift problem, so no need to set these regs. Tested-on: WCN6855 hw2.0 PCI WLAN.HSP.1.1-01720.1-QCAHSPSWPL_V1_V2_SILICONZ_LITE-1 Tested-on: QCA6390 hw2.0 PCI WLAN.HST.1.0.1-01740-QCAHSTSWPLZ_V2_TO_X86-1 Signed-off-by: Baochen Qiang Signed-off-by: Jouni Malinen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511162214.29475-8-jouni@codeaurora.org --- drivers/net/wireless/ath/ath11k/core.c | 5 +++++ drivers/net/wireless/ath/ath11k/hw.h | 1 + drivers/net/wireless/ath/ath11k/pci.c | 3 ++- 3 files changed, 8 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/ath11k/core.c b/drivers/net/wireless/ath/ath11k/core.c index fd8941905fdb..4a1051418f33 100644 --- a/drivers/net/wireless/ath/ath11k/core.c +++ b/drivers/net/wireless/ath/ath11k/core.c @@ -70,6 +70,7 @@ static const struct ath11k_hw_params ath11k_hw_params[] = { .cold_boot_calib = true, .supports_suspend = false, .hal_desc_sz = sizeof(struct hal_rx_desc_ipq8074), + .fix_l1ss = true, }, { .hw_rev = ATH11K_HW_IPQ6018_HW10, @@ -110,6 +111,7 @@ static const struct ath11k_hw_params ath11k_hw_params[] = { .cold_boot_calib = true, .supports_suspend = false, .hal_desc_sz = sizeof(struct hal_rx_desc_ipq8074), + .fix_l1ss = true, }, { .name = "qca6390 hw2.0", @@ -149,6 +151,7 @@ static const struct ath11k_hw_params ath11k_hw_params[] = { .cold_boot_calib = false, .supports_suspend = true, .hal_desc_sz = sizeof(struct hal_rx_desc_ipq8074), + .fix_l1ss = true, }, { .name = "qcn9074 hw1.0", @@ -186,6 +189,7 @@ static const struct ath11k_hw_params ath11k_hw_params[] = { .cold_boot_calib = false, .supports_suspend = false, .hal_desc_sz = sizeof(struct hal_rx_desc_qcn9074), + .fix_l1ss = true, }, { .name = "wcn6855 hw2.0", @@ -225,6 +229,7 @@ static const struct ath11k_hw_params ath11k_hw_params[] = { .cold_boot_calib = false, .supports_suspend = true, .hal_desc_sz = sizeof(struct hal_rx_desc_wcn6855), + .fix_l1ss = false, }, }; diff --git a/drivers/net/wireless/ath/ath11k/hw.h b/drivers/net/wireless/ath/ath11k/hw.h index be62f0c2e25e..62f5978b3005 100644 --- a/drivers/net/wireless/ath/ath11k/hw.h +++ b/drivers/net/wireless/ath/ath11k/hw.h @@ -162,6 +162,7 @@ struct ath11k_hw_params { bool cold_boot_calib; bool supports_suspend; u32 hal_desc_sz; + bool fix_l1ss; }; struct ath11k_hw_ops { diff --git a/drivers/net/wireless/ath/ath11k/pci.c b/drivers/net/wireless/ath/ath11k/pci.c index a4688b6beeb1..f8f6b2090dad 100644 --- a/drivers/net/wireless/ath/ath11k/pci.c +++ b/drivers/net/wireless/ath/ath11k/pci.c @@ -434,7 +434,8 @@ static void ath11k_pci_sw_reset(struct ath11k_base *ab, bool power_on) ath11k_pci_enable_ltssm(ab); ath11k_pci_clear_all_intrs(ab); ath11k_pci_set_wlaon_pwr_ctrl(ab); - ath11k_pci_fix_l1ss(ab); + if (ab->hw_params.fix_l1ss) + ath11k_pci_fix_l1ss(ab); } ath11k_mhi_clear_vector(ab); From 9e88dd431d2345acdb7a549f3e88aaf4c2a307a1 Mon Sep 17 00:00:00 2001 From: Yang Yingliang Date: Mon, 31 May 2021 17:41:28 +0300 Subject: [PATCH 15/91] ath10k: go to path err_unsupported when chip id is not supported When chip id is not supported, it go to path err_unsupported to print the error message. Fixes: f8914a14623a ("ath10k: restore QCA9880-AR1A (v1) detection") Signed-off-by: Yang Yingliang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210522105822.1091848-2-yangyingliang@huawei.com --- drivers/net/wireless/ath/ath10k/pci.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/ath10k/pci.c b/drivers/net/wireless/ath/ath10k/pci.c index e7fde635e0ee..463cf3f8f8a5 100644 --- a/drivers/net/wireless/ath/ath10k/pci.c +++ b/drivers/net/wireless/ath/ath10k/pci.c @@ -3701,7 +3701,7 @@ static int ath10k_pci_probe(struct pci_dev *pdev, goto err_unsupported; if (!ath10k_pci_chip_is_supported(pdev->device, bus_params.chip_id)) - goto err_free_irq; + goto err_unsupported; ret = ath10k_core_register(ar, &bus_params); if (ret) { From e2783e2f39ba99178dedfc1646d5cc0979d1bab3 Mon Sep 17 00:00:00 2001 From: Yang Yingliang Date: Mon, 31 May 2021 17:41:28 +0300 Subject: [PATCH 16/91] ath10k: add missing error return code in ath10k_pci_probe() When chip_id is not supported, the resources will be freed on path err_unsupported, these resources will also be freed when calling ath10k_pci_remove(), it will cause double free, so return -ENODEV when it doesn't support the device with wrong chip_id. Fixes: c0c378f9907c ("ath10k: remove target soc ps code") Fixes: 7505f7c3ec1d ("ath10k: create a chip revision whitelist") Fixes: f8914a14623a ("ath10k: restore QCA9880-AR1A (v1) detection") Reported-by: Hulk Robot Signed-off-by: Yang Yingliang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210522105822.1091848-3-yangyingliang@huawei.com --- drivers/net/wireless/ath/ath10k/pci.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/drivers/net/wireless/ath/ath10k/pci.c b/drivers/net/wireless/ath/ath10k/pci.c index 463cf3f8f8a5..71878ab35b93 100644 --- a/drivers/net/wireless/ath/ath10k/pci.c +++ b/drivers/net/wireless/ath/ath10k/pci.c @@ -3685,8 +3685,10 @@ static int ath10k_pci_probe(struct pci_dev *pdev, ath10k_pci_soc_read32(ar, SOC_CHIP_ID_ADDRESS); if (bus_params.chip_id != 0xffffffff) { if (!ath10k_pci_chip_is_supported(pdev->device, - bus_params.chip_id)) + bus_params.chip_id)) { + ret = -ENODEV; goto err_unsupported; + } } } @@ -3697,11 +3699,15 @@ static int ath10k_pci_probe(struct pci_dev *pdev, } bus_params.chip_id = ath10k_pci_soc_read32(ar, SOC_CHIP_ID_ADDRESS); - if (bus_params.chip_id == 0xffffffff) + if (bus_params.chip_id == 0xffffffff) { + ret = -ENODEV; goto err_unsupported; + } - if (!ath10k_pci_chip_is_supported(pdev->device, bus_params.chip_id)) + if (!ath10k_pci_chip_is_supported(pdev->device, bus_params.chip_id)) { + ret = -ENODEV; goto err_unsupported; + } ret = ath10k_core_register(ar, &bus_params); if (ret) { From 272fdc0c4542fad173b44965be02a16d6db95499 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Mon, 31 May 2021 17:41:28 +0300 Subject: [PATCH 17/91] wireless: carl9170: fix LEDS build errors & warnings kernel test robot reports over 200 build errors and warnings that are due to this Kconfig problem when CARL9170=m, MAC80211=y, and LEDS_CLASS=m. WARNING: unmet direct dependencies detected for MAC80211_LEDS Depends on [n]: NET [=y] && WIRELESS [=y] && MAC80211 [=y] && (LEDS_CLASS [=m]=y || LEDS_CLASS [=m]=MAC80211 [=y]) Selected by [m]: - CARL9170_LEDS [=y] && NETDEVICES [=y] && WLAN [=y] && WLAN_VENDOR_ATH [=y] && CARL9170 [=m] CARL9170_LEDS selects MAC80211_LEDS even though its kconfig dependencies are not met. This happens because 'select' does not follow any Kconfig dependency chains. Fix this by making CARL9170_LEDS depend on MAC80211_LEDS, where the latter supplies any needed dependencies on LEDS_CLASS. Fixes: 1d7e1e6b1b8ed ("carl9170: Makefile, Kconfig files and MAINTAINERS") Signed-off-by: Randy Dunlap Reported-by: kernel test robot Cc: Kalle Valo Cc: Christian Lamparter Cc: linux-wireless@vger.kernel.org Cc: Arnd Bergmann Suggested-by: Christian Lamparter Acked-by: Arnd Bergmann Acked-by: Christian Lamparter Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210530031134.23274-1-rdunlap@infradead.org --- drivers/net/wireless/ath/carl9170/Kconfig | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/drivers/net/wireless/ath/carl9170/Kconfig b/drivers/net/wireless/ath/carl9170/Kconfig index b2d760873992..ba9bea79381c 100644 --- a/drivers/net/wireless/ath/carl9170/Kconfig +++ b/drivers/net/wireless/ath/carl9170/Kconfig @@ -16,13 +16,11 @@ config CARL9170 config CARL9170_LEDS bool "SoftLED Support" - depends on CARL9170 - select MAC80211_LEDS - select LEDS_CLASS - select NEW_LEDS default y + depends on CARL9170 + depends on MAC80211_LEDS help - This option is necessary, if you want your device' LEDs to blink + This option is necessary, if you want your device's LEDs to blink. Say Y, unless you need the LEDs for firmware debugging. From e0a6120f6816ddd366530ce7ae5cb001a5e819dd Mon Sep 17 00:00:00 2001 From: Yang Yingliang Date: Wed, 26 May 2021 22:22:19 +0800 Subject: [PATCH 18/91] ath10k: remove unused more_frags variable MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fix the following W=1 build warning: drivers/net/wireless/ath/ath10k/htt_rx.c:1790:7: warning: variable ‘more_frags’ set but not used [-Wunused-but-set-variable] 1790 | bool more_frags; | ^~~~~~~~~~ Fixes: a1166b2653db ("ath10k: add CCMP PN replay protection for fragmented frames for PCIe") Reported-by: Hulk Robot Signed-off-by: Yang Yingliang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210526142219.2542528-1-yangyingliang@huawei.com --- drivers/net/wireless/ath/ath10k/htt_rx.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/drivers/net/wireless/ath/ath10k/htt_rx.c b/drivers/net/wireless/ath/ath10k/htt_rx.c index 7ffb5d5b2a70..adbaeb67eedf 100644 --- a/drivers/net/wireless/ath/ath10k/htt_rx.c +++ b/drivers/net/wireless/ath/ath10k/htt_rx.c @@ -1787,7 +1787,6 @@ static bool ath10k_htt_rx_h_frag_pn_check(struct ath10k *ar, struct ath10k_peer *peer; union htt_rx_pn_t *last_pn, new_pn = {0}; struct ieee80211_hdr *hdr; - bool more_frags; u8 tid, frag_number; u32 seq; @@ -1805,7 +1804,6 @@ static bool ath10k_htt_rx_h_frag_pn_check(struct ath10k *ar, last_pn = &peer->frag_tids_last_pn[tid]; new_pn.pn48 = ath10k_htt_rx_h_get_pn(ar, skb, offset, enctype); - more_frags = ieee80211_has_morefrags(hdr->frame_control); frag_number = le16_to_cpu(hdr->seq_ctrl) & IEEE80211_SCTL_FRAG; seq = (__le16_to_cpu(hdr->seq_ctrl) & IEEE80211_SCTL_SEQ) >> 4; From ba4e967379f0a2c2a72fb572c69761218a2468a6 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:29 +0100 Subject: [PATCH 19/91] wcn36xx: Return result of set_power_params in suspend wcn36xx_smd_set_power_params() can return an error. For the purposes of entering into suspend we need the suspend() function to trap and report errors up the stack. First step in this process is reporting the existing result code for wcn36xx_smd_set_power_params(). Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-2-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index afb4877eaad8..b361e40697a6 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1091,12 +1091,14 @@ static int wcn36xx_sta_remove(struct ieee80211_hw *hw, static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) { struct wcn36xx *wcn = hw->priv; + int ret; wcn36xx_dbg(WCN36XX_DBG_MAC, "mac suspend\n"); flush_workqueue(wcn->hal_ind_wq); - wcn36xx_smd_set_power_params(wcn, true); - return 0; + ret = wcn36xx_smd_set_power_params(wcn, true); + + return ret; } static int wcn36xx_resume(struct ieee80211_hw *hw) From f2f49601067bd7b7f3392a50a3738335fe9d0cb8 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:30 +0100 Subject: [PATCH 20/91] wcn36xx: Run suspend for the first ieee80211_vif A subsequent set of patches will extend out suspend/resume support in this driver, we cannot set the firmware up for multiple ipv4/ipv6 addresses and as such we can't iterate through a list of ieee80211_vif. Constrain the interaction with the firmware to the first ieee80211_vif on the suspend/resume/wowlan path. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-3-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 31 ++++++++++++++++++++++--- 1 file changed, 28 insertions(+), 3 deletions(-) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index b361e40697a6..9a97a288a96f 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1088,15 +1088,34 @@ static int wcn36xx_sta_remove(struct ieee80211_hw *hw, #ifdef CONFIG_PM +static struct ieee80211_vif *wcn36xx_get_first_assoc_vif(struct wcn36xx *wcn) +{ + struct wcn36xx_vif *vif_priv = NULL; + struct ieee80211_vif *vif = NULL; + + list_for_each_entry(vif_priv, &wcn->vif_list, list) { + if (vif_priv->sta_assoc) { + vif = wcn36xx_priv_to_vif(vif_priv); + break; + } + } + return vif; +} + static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) { struct wcn36xx *wcn = hw->priv; - int ret; + struct ieee80211_vif *vif = NULL; + int ret = 0; wcn36xx_dbg(WCN36XX_DBG_MAC, "mac suspend\n"); flush_workqueue(wcn->hal_ind_wq); - ret = wcn36xx_smd_set_power_params(wcn, true); + mutex_lock(&wcn->conf_mutex); + vif = wcn36xx_get_first_assoc_vif(wcn); + if (vif) + ret = wcn36xx_smd_set_power_params(wcn, true); + mutex_unlock(&wcn->conf_mutex); return ret; } @@ -1104,11 +1123,17 @@ static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) static int wcn36xx_resume(struct ieee80211_hw *hw) { struct wcn36xx *wcn = hw->priv; + struct ieee80211_vif *vif = NULL; wcn36xx_dbg(WCN36XX_DBG_MAC, "mac resume\n"); flush_workqueue(wcn->hal_ind_wq); - wcn36xx_smd_set_power_params(wcn, false); + mutex_lock(&wcn->conf_mutex); + vif = wcn36xx_get_first_assoc_vif(wcn); + if (vif) + wcn36xx_smd_set_power_params(wcn, false); + mutex_unlock(&wcn->conf_mutex); + return 0; } From 5478c41fce5dd6b751075856666a0f9a101c3dd2 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:31 +0100 Subject: [PATCH 21/91] wcn36xx: Add ipv4 ARP offload support in suspend Add ARP offload support. Firmware is capable of responding to ARP requests for a single ipv4 address only. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-4-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/hal.h | 10 +++---- drivers/net/wireless/ath/wcn36xx/main.c | 17 +++++++---- drivers/net/wireless/ath/wcn36xx/smd.c | 38 +++++++++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/smd.h | 4 +++ 4 files changed, 59 insertions(+), 10 deletions(-) diff --git a/drivers/net/wireless/ath/wcn36xx/hal.h b/drivers/net/wireless/ath/wcn36xx/hal.h index 65ef893f2736..b56c8292fa62 100644 --- a/drivers/net/wireless/ath/wcn36xx/hal.h +++ b/drivers/net/wireless/ath/wcn36xx/hal.h @@ -3465,7 +3465,7 @@ struct wcn36xx_hal_rem_bcn_filter_req { #define WCN36XX_HAL_OFFLOAD_ENABLE 1 #define WCN36XX_HAL_OFFLOAD_BCAST_FILTER_ENABLE 0x2 #define WCN36XX_HAL_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE \ - (HAL_OFFLOAD_ENABLE|HAL_OFFLOAD_BCAST_FILTER_ENABLE) + (WCN36XX_HAL_OFFLOAD_ENABLE | WCN36XX_HAL_OFFLOAD_BCAST_FILTER_ENABLE) struct wcn36xx_hal_ns_offload_params { u8 src_ipv6_addr[WCN36XX_HAL_IPV6_ADDR_LEN]; @@ -3487,10 +3487,10 @@ struct wcn36xx_hal_ns_offload_params { /* slot index for this offload */ u32 slot_index; u8 bss_index; -}; +} __packed; struct wcn36xx_hal_host_offload_req { - u8 offload_Type; + u8 offload_type; /* enable or disable */ u8 enable; @@ -3499,13 +3499,13 @@ struct wcn36xx_hal_host_offload_req { u8 host_ipv4_addr[4]; u8 host_ipv6_addr[WCN36XX_HAL_IPV6_ADDR_LEN]; } u; -}; +} __packed; struct wcn36xx_hal_host_offload_req_msg { struct wcn36xx_hal_msg_header header; struct wcn36xx_hal_host_offload_req host_offload_params; struct wcn36xx_hal_ns_offload_params ns_offload_params; -}; +} __packed; /* Packet Types. */ #define WCN36XX_HAL_KEEP_ALIVE_NULL_PKT 1 diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index 9a97a288a96f..0da123660fa1 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1112,11 +1112,16 @@ static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) flush_workqueue(wcn->hal_ind_wq); mutex_lock(&wcn->conf_mutex); - vif = wcn36xx_get_first_assoc_vif(wcn); - if (vif) - ret = wcn36xx_smd_set_power_params(wcn, true); - mutex_unlock(&wcn->conf_mutex); + vif = wcn36xx_get_first_assoc_vif(wcn); + if (vif) { + ret = wcn36xx_smd_arp_offload(wcn, vif, true); + if (ret) + goto out; + ret = wcn36xx_smd_set_power_params(wcn, true); + } +out: + mutex_unlock(&wcn->conf_mutex); return ret; } @@ -1130,8 +1135,10 @@ static int wcn36xx_resume(struct ieee80211_hw *hw) flush_workqueue(wcn->hal_ind_wq); mutex_lock(&wcn->conf_mutex); vif = wcn36xx_get_first_assoc_vif(wcn); - if (vif) + if (vif) { wcn36xx_smd_set_power_params(wcn, false); + wcn36xx_smd_arp_offload(wcn, vif, false); + } mutex_unlock(&wcn->conf_mutex); return 0; diff --git a/drivers/net/wireless/ath/wcn36xx/smd.c b/drivers/net/wireless/ath/wcn36xx/smd.c index d0c3a1557e8d..478e363610e1 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.c +++ b/drivers/net/wireless/ath/wcn36xx/smd.c @@ -2756,6 +2756,43 @@ int wcn36xx_smd_set_mc_list(struct wcn36xx *wcn, return ret; } +int wcn36xx_smd_arp_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, + bool enable) +{ + struct wcn36xx_vif *vif_priv = wcn36xx_vif_to_priv(vif); + struct wcn36xx_hal_host_offload_req_msg msg_body; + int ret; + + mutex_lock(&wcn->hal_mutex); + + INIT_HAL_MSG(msg_body, WCN36XX_HAL_HOST_OFFLOAD_REQ); + msg_body.host_offload_params.offload_type = + WCN36XX_HAL_IPV4_ARP_REPLY_OFFLOAD; + if (enable) { + msg_body.host_offload_params.enable = + WCN36XX_HAL_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE; + memcpy(&msg_body.host_offload_params.u, + &vif->bss_conf.arp_addr_list[0], sizeof(__be32)); + } + msg_body.ns_offload_params.bss_index = vif_priv->bss_index; + + PREPARE_HAL_BUF(wcn->hal_buf, msg_body); + + ret = wcn36xx_smd_send_and_wait(wcn, msg_body.header.len); + if (ret) { + wcn36xx_err("Sending host_offload_arp failed\n"); + goto out; + } + ret = wcn36xx_smd_rsp_status_check(wcn->hal_buf, wcn->hal_rsp_len); + if (ret) { + wcn36xx_err("host_offload_arp failed err=%d\n", ret); + goto out; + } +out: + mutex_unlock(&wcn->hal_mutex); + return ret; +} + int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, void *buf, int len, void *priv, u32 addr) { @@ -2804,6 +2841,7 @@ int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, case WCN36XX_HAL_8023_MULTICAST_LIST_RSP: case WCN36XX_HAL_START_SCAN_OFFLOAD_RSP: case WCN36XX_HAL_STOP_SCAN_OFFLOAD_RSP: + case WCN36XX_HAL_HOST_OFFLOAD_RSP: memcpy(wcn->hal_buf, buf, len); wcn->hal_rsp_len = len; complete(&wcn->hal_rsp_compl); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.h b/drivers/net/wireless/ath/wcn36xx/smd.h index 462860572e1f..6492a628ea6a 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.h +++ b/drivers/net/wireless/ath/wcn36xx/smd.h @@ -146,4 +146,8 @@ int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, int wcn36xx_smd_set_mc_list(struct wcn36xx *wcn, struct ieee80211_vif *vif, struct wcn36xx_hal_rcv_flt_mc_addr_list_type *fp); + +int wcn36xx_smd_arp_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, + bool enable); + #endif /* _SMD_H_ */ From 6feb634f4d9fceb0241612ad46ad55b54fd78df5 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:32 +0100 Subject: [PATCH 22/91] wcn36xx: Do not flush indication queue on suspend/resume Testing on Android reveals that the flush on both suspend and resume of the firmware indication work-queue can stall indefinitely. Given this code path doesn't appear to have been exercised up until now, removing this flush to unblock this situation. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-5-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index 0da123660fa1..9731fcbe2e7f 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1110,7 +1110,6 @@ static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) wcn36xx_dbg(WCN36XX_DBG_MAC, "mac suspend\n"); - flush_workqueue(wcn->hal_ind_wq); mutex_lock(&wcn->conf_mutex); vif = wcn36xx_get_first_assoc_vif(wcn); @@ -1132,7 +1131,6 @@ static int wcn36xx_resume(struct ieee80211_hw *hw) wcn36xx_dbg(WCN36XX_DBG_MAC, "mac resume\n"); - flush_workqueue(wcn->hal_ind_wq); mutex_lock(&wcn->conf_mutex); vif = wcn36xx_get_first_assoc_vif(wcn); if (vif) { From c7a61af55976dbd11b176d2badda869a7537dca4 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:33 +0100 Subject: [PATCH 23/91] wcn36xx: Add ipv6 address tracking Taking code from iwlwifi this commit adds a standard callback for ipv6_addr_change(). This callback allows wcn36xx to know the set of ipv6 addresses. Something we need to know in order to get wowlan working with ipv6. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-6-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/hal.h | 1 + drivers/net/wireless/ath/wcn36xx/main.c | 32 ++++++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/wcn36xx.h | 8 ++++++ 3 files changed, 41 insertions(+) diff --git a/drivers/net/wireless/ath/wcn36xx/hal.h b/drivers/net/wireless/ath/wcn36xx/hal.h index b56c8292fa62..90333daed845 100644 --- a/drivers/net/wireless/ath/wcn36xx/hal.h +++ b/drivers/net/wireless/ath/wcn36xx/hal.h @@ -3466,6 +3466,7 @@ struct wcn36xx_hal_rem_bcn_filter_req { #define WCN36XX_HAL_OFFLOAD_BCAST_FILTER_ENABLE 0x2 #define WCN36XX_HAL_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE \ (WCN36XX_HAL_OFFLOAD_ENABLE | WCN36XX_HAL_OFFLOAD_BCAST_FILTER_ENABLE) +#define WCN36XX_HAL_IPV6_OFFLOAD_ADDR_MAX 0x02 struct wcn36xx_hal_ns_offload_params { u8 src_ipv6_addr[WCN36XX_HAL_IPV6_ADDR_LEN]; diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index 9731fcbe2e7f..240ecdd52f81 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -25,6 +25,7 @@ #include #include #include +#include #include "wcn36xx.h" #include "testmode.h" @@ -1208,6 +1209,34 @@ static int wcn36xx_ampdu_action(struct ieee80211_hw *hw, return ret; } +#if IS_ENABLED(CONFIG_IPV6) +static void wcn36xx_ipv6_addr_change(struct ieee80211_hw *hw, + struct ieee80211_vif *vif, + struct inet6_dev *idev) +{ + struct wcn36xx_vif *vif_priv = wcn36xx_vif_to_priv(vif); + struct inet6_ifaddr *ifa; + int idx = 0; + + memset(vif_priv->tentative_addrs, 0, sizeof(vif_priv->tentative_addrs)); + + read_lock_bh(&idev->lock); + list_for_each_entry(ifa, &idev->addr_list, if_list) { + vif_priv->target_ipv6_addrs[idx] = ifa->addr; + if (ifa->flags & IFA_F_TENTATIVE) + __set_bit(idx, vif_priv->tentative_addrs); + idx++; + if (idx >= WCN36XX_HAL_IPV6_OFFLOAD_ADDR_MAX) + break; + wcn36xx_dbg(WCN36XX_DBG_MAC, "%pI6 %s\n", &ifa->addr, + (ifa->flags & IFA_F_TENTATIVE) ? "tentative" : NULL); + } + read_unlock_bh(&idev->lock); + + vif_priv->num_target_ipv6_addrs = idx; +} +#endif + static const struct ieee80211_ops wcn36xx_ops = { .start = wcn36xx_start, .stop = wcn36xx_stop, @@ -1231,6 +1260,9 @@ static const struct ieee80211_ops wcn36xx_ops = { .sta_add = wcn36xx_sta_add, .sta_remove = wcn36xx_sta_remove, .ampdu_action = wcn36xx_ampdu_action, +#if IS_ENABLED(CONFIG_IPV6) + .ipv6_addr_change = wcn36xx_ipv6_addr_change, +#endif CFG80211_TESTMODE_CMD(wcn36xx_tm_cmd) }; diff --git a/drivers/net/wireless/ath/wcn36xx/wcn36xx.h b/drivers/net/wireless/ath/wcn36xx/wcn36xx.h index 71fa9992b118..5a5114660b18 100644 --- a/drivers/net/wireless/ath/wcn36xx/wcn36xx.h +++ b/drivers/net/wireless/ath/wcn36xx/wcn36xx.h @@ -18,6 +18,7 @@ #define _WCN36XX_H_ #include +#include #include #include #include @@ -136,6 +137,13 @@ struct wcn36xx_vif { u8 self_dpu_desc_index; u8 self_ucast_dpu_sign; +#if IS_ENABLED(CONFIG_IPV6) + /* IPv6 addresses for WoWLAN */ + struct in6_addr target_ipv6_addrs[WCN36XX_HAL_IPV6_OFFLOAD_ADDR_MAX]; + unsigned long tentative_addrs[BITS_TO_LONGS(WCN36XX_HAL_IPV6_OFFLOAD_ADDR_MAX)]; + int num_target_ipv6_addrs; +#endif + struct list_head sta_list; }; From 1456223c468447b1c5d2c1d8748748eea379a501 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:34 +0100 Subject: [PATCH 24/91] wcn36xx: Add ipv6 namespace offload in suspend We need to respond to ipv6 namespace lookups when in suspend. This patch adds the necessary changes to issue the appropriate firmware command on suspend and resume to enter/exit firmware offloaded ns lookup. Signed-off-by: Bryan O'Donoghue Reported-by: kernel test robot Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-7-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/hal.h | 3 ++ drivers/net/wireless/ath/wcn36xx/main.c | 4 ++ drivers/net/wireless/ath/wcn36xx/smd.c | 63 +++++++++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/smd.h | 3 ++ 4 files changed, 73 insertions(+) diff --git a/drivers/net/wireless/ath/wcn36xx/hal.h b/drivers/net/wireless/ath/wcn36xx/hal.h index 90333daed845..3b949b0b3792 100644 --- a/drivers/net/wireless/ath/wcn36xx/hal.h +++ b/drivers/net/wireless/ath/wcn36xx/hal.h @@ -3464,6 +3464,9 @@ struct wcn36xx_hal_rem_bcn_filter_req { #define WCN36XX_HAL_OFFLOAD_DISABLE 0 #define WCN36XX_HAL_OFFLOAD_ENABLE 1 #define WCN36XX_HAL_OFFLOAD_BCAST_FILTER_ENABLE 0x2 +#define WCN36XX_HAL_OFFLOAD_MCAST_FILTER_ENABLE 0x4 +#define WCN36XX_HAL_OFFLOAD_NS_AND_MCAST_FILTER_ENABLE \ + (WCN36XX_HAL_OFFLOAD_ENABLE | WCN36XX_HAL_OFFLOAD_MCAST_FILTER_ENABLE) #define WCN36XX_HAL_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE \ (WCN36XX_HAL_OFFLOAD_ENABLE | WCN36XX_HAL_OFFLOAD_BCAST_FILTER_ENABLE) #define WCN36XX_HAL_IPV6_OFFLOAD_ADDR_MAX 0x02 diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index 240ecdd52f81..09e22f829682 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1116,6 +1116,9 @@ static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) vif = wcn36xx_get_first_assoc_vif(wcn); if (vif) { ret = wcn36xx_smd_arp_offload(wcn, vif, true); + if (ret) + goto out; + ret = wcn36xx_smd_ipv6_ns_offload(wcn, vif, true); if (ret) goto out; ret = wcn36xx_smd_set_power_params(wcn, true); @@ -1136,6 +1139,7 @@ static int wcn36xx_resume(struct ieee80211_hw *hw) vif = wcn36xx_get_first_assoc_vif(wcn); if (vif) { wcn36xx_smd_set_power_params(wcn, false); + wcn36xx_smd_ipv6_ns_offload(wcn, vif, false); wcn36xx_smd_arp_offload(wcn, vif, false); } mutex_unlock(&wcn->conf_mutex); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.c b/drivers/net/wireless/ath/wcn36xx/smd.c index 478e363610e1..4a50e5f8456a 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.c +++ b/drivers/net/wireless/ath/wcn36xx/smd.c @@ -2793,6 +2793,69 @@ int wcn36xx_smd_arp_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, return ret; } +#if IS_ENABLED(CONFIG_IPV6) +int wcn36xx_smd_ipv6_ns_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, + bool enable) +{ + struct wcn36xx_vif *vif_priv = wcn36xx_vif_to_priv(vif); + struct wcn36xx_hal_host_offload_req_msg msg_body; + struct wcn36xx_hal_ns_offload_params *ns_params; + struct wcn36xx_hal_host_offload_req *ho_params; + int ret; + + mutex_lock(&wcn->hal_mutex); + + INIT_HAL_MSG(msg_body, WCN36XX_HAL_HOST_OFFLOAD_REQ); + ho_params = &msg_body.host_offload_params; + ns_params = &msg_body.ns_offload_params; + + ho_params->offload_type = WCN36XX_HAL_IPV6_NS_OFFLOAD; + if (enable) { + ho_params->enable = + WCN36XX_HAL_OFFLOAD_NS_AND_MCAST_FILTER_ENABLE; + if (vif_priv->num_target_ipv6_addrs) { + memcpy(&ho_params->u, + &vif_priv->target_ipv6_addrs[0].in6_u, + sizeof(struct in6_addr)); + memcpy(&ns_params->target_ipv6_addr1, + &vif_priv->target_ipv6_addrs[0].in6_u, + sizeof(struct in6_addr)); + ns_params->target_ipv6_addr1_valid = 1; + } + if (vif_priv->num_target_ipv6_addrs > 1) { + memcpy(&ns_params->target_ipv6_addr2, + &vif_priv->target_ipv6_addrs[1].in6_u, + sizeof(struct in6_addr)); + ns_params->target_ipv6_addr2_valid = 1; + } + } + memcpy(&ns_params->self_addr, vif->addr, ETH_ALEN); + ns_params->bss_index = vif_priv->bss_index; + + PREPARE_HAL_BUF(wcn->hal_buf, msg_body); + + ret = wcn36xx_smd_send_and_wait(wcn, msg_body.header.len); + if (ret) { + wcn36xx_err("Sending host_offload_arp failed\n"); + goto out; + } + ret = wcn36xx_smd_rsp_status_check(wcn->hal_buf, wcn->hal_rsp_len); + if (ret) { + wcn36xx_err("host_offload_arp failed err=%d\n", ret); + goto out; + } +out: + mutex_unlock(&wcn->hal_mutex); + return ret; +} +#else +int wcn36xx_smd_ipv6_ns_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, + bool enable) +{ + return 0; +} +#endif + int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, void *buf, int len, void *priv, u32 addr) { diff --git a/drivers/net/wireless/ath/wcn36xx/smd.h b/drivers/net/wireless/ath/wcn36xx/smd.h index 6492a628ea6a..e03ab7878432 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.h +++ b/drivers/net/wireless/ath/wcn36xx/smd.h @@ -150,4 +150,7 @@ int wcn36xx_smd_set_mc_list(struct wcn36xx *wcn, int wcn36xx_smd_arp_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, bool enable); +int wcn36xx_smd_ipv6_ns_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, + bool enable); + #endif /* _SMD_H_ */ From 8974e5917b31c30ab30af1e992cfb35eec839a5f Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:35 +0100 Subject: [PATCH 25/91] wcn36xx: Add set_rekey_data callback Add a callback for Group Temporal Key tracking as provided by the standard WiFi ops structure. We track the key to integrate GTK offloading into the WoWLAN suspend path later on. Code comes from the Intel iwlwifi driver with minimal name changes. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-8-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 19 +++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/wcn36xx.h | 6 ++++++ 2 files changed, 25 insertions(+) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index 09e22f829682..ec32b8b0067d 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1147,6 +1147,24 @@ static int wcn36xx_resume(struct ieee80211_hw *hw) return 0; } +static void wcn36xx_set_rekey_data(struct ieee80211_hw *hw, + struct ieee80211_vif *vif, + struct cfg80211_gtk_rekey_data *data) +{ + struct wcn36xx *wcn = hw->priv; + struct wcn36xx_vif *vif_priv = wcn36xx_vif_to_priv(vif); + + mutex_lock(&wcn->conf_mutex); + + memcpy(vif_priv->rekey_data.kek, data->kek, NL80211_KEK_LEN); + memcpy(vif_priv->rekey_data.kck, data->kck, NL80211_KCK_LEN); + vif_priv->rekey_data.replay_ctr = + cpu_to_le64(be64_to_cpup((__be64 *)data->replay_ctr)); + vif_priv->rekey_data.valid = true; + + mutex_unlock(&wcn->conf_mutex); +} + #endif static int wcn36xx_ampdu_action(struct ieee80211_hw *hw, @@ -1249,6 +1267,7 @@ static const struct ieee80211_ops wcn36xx_ops = { #ifdef CONFIG_PM .suspend = wcn36xx_suspend, .resume = wcn36xx_resume, + .set_rekey_data = wcn36xx_set_rekey_data, #endif .config = wcn36xx_config, .prepare_multicast = wcn36xx_prepare_multicast, diff --git a/drivers/net/wireless/ath/wcn36xx/wcn36xx.h b/drivers/net/wireless/ath/wcn36xx/wcn36xx.h index 5a5114660b18..6121d8a5641a 100644 --- a/drivers/net/wireless/ath/wcn36xx/wcn36xx.h +++ b/drivers/net/wireless/ath/wcn36xx/wcn36xx.h @@ -143,6 +143,12 @@ struct wcn36xx_vif { unsigned long tentative_addrs[BITS_TO_LONGS(WCN36XX_HAL_IPV6_OFFLOAD_ADDR_MAX)]; int num_target_ipv6_addrs; #endif + /* WoWLAN GTK rekey data */ + struct { + u8 kck[NL80211_KCK_LEN], kek[NL80211_KEK_LEN]; + __le64 replay_ctr; + bool valid; + } rekey_data; struct list_head sta_list; }; From 6693f7675c9b055ee3428844ee8999bfe22d3cd2 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:36 +0100 Subject: [PATCH 26/91] wcn36xx: Add GTK offload to WoWLAN path Using previously set GTK KCK and KEK material this commit adds GTK rekeying to the WoWLAN suspend/resume path. A small error in the packing of the up to now unused command structure is fixed as we go. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-9-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/hal.h | 2 +- drivers/net/wireless/ath/wcn36xx/main.c | 4 +++ drivers/net/wireless/ath/wcn36xx/smd.c | 39 +++++++++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/smd.h | 3 ++ 4 files changed, 47 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/wcn36xx/hal.h b/drivers/net/wireless/ath/wcn36xx/hal.h index 3b949b0b3792..1f3c2e840232 100644 --- a/drivers/net/wireless/ath/wcn36xx/hal.h +++ b/drivers/net/wireless/ath/wcn36xx/hal.h @@ -4905,7 +4905,7 @@ struct wcn36xx_hal_gtk_offload_req_msg { u64 key_replay_counter; u8 bss_index; -}; +} __packed; struct wcn36xx_hal_gtk_offload_rsp_msg { struct wcn36xx_hal_msg_header header; diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index ec32b8b0067d..db1528a14757 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1119,6 +1119,9 @@ static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) if (ret) goto out; ret = wcn36xx_smd_ipv6_ns_offload(wcn, vif, true); + if (ret) + goto out; + ret = wcn36xx_smd_gtk_offload(wcn, vif, true); if (ret) goto out; ret = wcn36xx_smd_set_power_params(wcn, true); @@ -1139,6 +1142,7 @@ static int wcn36xx_resume(struct ieee80211_hw *hw) vif = wcn36xx_get_first_assoc_vif(wcn); if (vif) { wcn36xx_smd_set_power_params(wcn, false); + wcn36xx_smd_gtk_offload(wcn, vif, false); wcn36xx_smd_ipv6_ns_offload(wcn, vif, false); wcn36xx_smd_arp_offload(wcn, vif, false); } diff --git a/drivers/net/wireless/ath/wcn36xx/smd.c b/drivers/net/wireless/ath/wcn36xx/smd.c index 4a50e5f8456a..4063888e3f03 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.c +++ b/drivers/net/wireless/ath/wcn36xx/smd.c @@ -2856,6 +2856,44 @@ int wcn36xx_smd_ipv6_ns_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, } #endif +int wcn36xx_smd_gtk_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, + bool enable) +{ + struct wcn36xx_vif *vif_priv = wcn36xx_vif_to_priv(vif); + struct wcn36xx_hal_gtk_offload_req_msg msg_body; + int ret; + + mutex_lock(&wcn->hal_mutex); + + INIT_HAL_MSG(msg_body, WCN36XX_HAL_GTK_OFFLOAD_REQ); + + if (enable) { + memcpy(&msg_body.kek, vif_priv->rekey_data.kek, NL80211_KEK_LEN); + memcpy(&msg_body.kck, vif_priv->rekey_data.kck, NL80211_KCK_LEN); + msg_body.key_replay_counter = + le64_to_cpu(vif_priv->rekey_data.replay_ctr); + msg_body.bss_index = vif_priv->bss_index; + } else { + msg_body.flags = WCN36XX_HAL_GTK_OFFLOAD_FLAGS_DISABLE; + } + + PREPARE_HAL_BUF(wcn->hal_buf, msg_body); + + ret = wcn36xx_smd_send_and_wait(wcn, msg_body.header.len); + if (ret) { + wcn36xx_err("Sending host_offload_arp failed\n"); + goto out; + } + ret = wcn36xx_smd_rsp_status_check(wcn->hal_buf, wcn->hal_rsp_len); + if (ret) { + wcn36xx_err("host_offload_arp failed err=%d\n", ret); + goto out; + } +out: + mutex_unlock(&wcn->hal_mutex); + return ret; +} + int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, void *buf, int len, void *priv, u32 addr) { @@ -2905,6 +2943,7 @@ int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, case WCN36XX_HAL_START_SCAN_OFFLOAD_RSP: case WCN36XX_HAL_STOP_SCAN_OFFLOAD_RSP: case WCN36XX_HAL_HOST_OFFLOAD_RSP: + case WCN36XX_HAL_GTK_OFFLOAD_RSP: memcpy(wcn->hal_buf, buf, len); wcn->hal_rsp_len = len; complete(&wcn->hal_rsp_compl); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.h b/drivers/net/wireless/ath/wcn36xx/smd.h index e03ab7878432..cdf4231efe26 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.h +++ b/drivers/net/wireless/ath/wcn36xx/smd.h @@ -153,4 +153,7 @@ int wcn36xx_smd_arp_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, int wcn36xx_smd_ipv6_ns_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, bool enable); +int wcn36xx_smd_gtk_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, + bool enable); + #endif /* _SMD_H_ */ From bedf1169bcae2f762b37d40dc9db648fe7ad1952 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:37 +0100 Subject: [PATCH 27/91] wcn36xx: Add GTK offload info to WoWLAN resume Having enabled GTK rekey in suspend, we need to extract the replay counter from the firmware on resume and perform a ieee80211_gtk_rekey_notify() so that the STA remains verified from the perspective of the AP. In order to enable the SMD command and response we need to pack the existing command/response structures. Given these structures are currently unused, there's no need to backport this as a fix. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-10-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/hal.h | 4 +- drivers/net/wireless/ath/wcn36xx/main.c | 1 + drivers/net/wireless/ath/wcn36xx/smd.c | 73 +++++++++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/smd.h | 3 + 4 files changed, 79 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/ath/wcn36xx/hal.h b/drivers/net/wireless/ath/wcn36xx/hal.h index 1f3c2e840232..455143c4164e 100644 --- a/drivers/net/wireless/ath/wcn36xx/hal.h +++ b/drivers/net/wireless/ath/wcn36xx/hal.h @@ -4919,7 +4919,7 @@ struct wcn36xx_hal_gtk_offload_rsp_msg { struct wcn36xx_hal_gtk_offload_get_info_req_msg { struct wcn36xx_hal_msg_header header; u8 bss_index; -}; +} __packed; struct wcn36xx_hal_gtk_offload_get_info_rsp_msg { struct wcn36xx_hal_msg_header header; @@ -4943,7 +4943,7 @@ struct wcn36xx_hal_gtk_offload_get_info_rsp_msg { u32 igtk_rekey_count; u8 bss_index; -}; +} __packed; struct dhcp_info { /* Indicates the device mode which indicates about the DHCP activity */ diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index db1528a14757..8e5d8326d551 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1142,6 +1142,7 @@ static int wcn36xx_resume(struct ieee80211_hw *hw) vif = wcn36xx_get_first_assoc_vif(wcn); if (vif) { wcn36xx_smd_set_power_params(wcn, false); + wcn36xx_smd_gtk_offload_get_info(wcn, vif); wcn36xx_smd_gtk_offload(wcn, vif, false); wcn36xx_smd_ipv6_ns_offload(wcn, vif, false); wcn36xx_smd_arp_offload(wcn, vif, false); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.c b/drivers/net/wireless/ath/wcn36xx/smd.c index 4063888e3f03..13200a079bd0 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.c +++ b/drivers/net/wireless/ath/wcn36xx/smd.c @@ -2894,6 +2894,78 @@ int wcn36xx_smd_gtk_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, return ret; } +static int wcn36xx_smd_gtk_offload_get_info_rsp(struct wcn36xx *wcn, + struct ieee80211_vif *vif) +{ + struct wcn36xx_vif *vif_priv = wcn36xx_vif_to_priv(vif); + struct wcn36xx_hal_gtk_offload_get_info_rsp_msg *rsp; + __be64 replay_ctr; + + if (wcn36xx_smd_rsp_status_check(wcn->hal_buf, wcn->hal_rsp_len)) + return -EIO; + + rsp = (struct wcn36xx_hal_gtk_offload_get_info_rsp_msg *)wcn->hal_buf; + + if (rsp->bss_index != vif_priv->bss_index) { + wcn36xx_err("gtk_offload_info invalid response bss index %d\n", + rsp->bss_index); + return -ENOENT; + } + + if (vif_priv->rekey_data.replay_ctr != cpu_to_le64(rsp->key_replay_counter)) { + replay_ctr = cpu_to_be64(rsp->key_replay_counter); + vif_priv->rekey_data.replay_ctr = + cpu_to_le64(rsp->key_replay_counter); + ieee80211_gtk_rekey_notify(vif, vif->bss_conf.bssid, + (void *)&replay_ctr, GFP_KERNEL); + wcn36xx_dbg(WCN36XX_DBG_HAL, + "GTK replay counter increment %llu\n", + rsp->key_replay_counter); + } + + wcn36xx_dbg(WCN36XX_DBG_HAL, + "gtk offload info status %d last_rekey_status %d " + "replay_counter %llu total_rekey_count %d gtk_rekey_count %d " + "igtk_rekey_count %d bss_index %d\n", + rsp->status, rsp->last_rekey_status, + rsp->key_replay_counter, rsp->total_rekey_count, + rsp->gtk_rekey_count, rsp->igtk_rekey_count, + rsp->bss_index); + + return 0; +} + +int wcn36xx_smd_gtk_offload_get_info(struct wcn36xx *wcn, + struct ieee80211_vif *vif) +{ + struct wcn36xx_vif *vif_priv = wcn36xx_vif_to_priv(vif); + struct wcn36xx_hal_gtk_offload_get_info_req_msg msg_body; + int ret; + + mutex_lock(&wcn->hal_mutex); + + INIT_HAL_MSG(msg_body, WCN36XX_HAL_GTK_OFFLOAD_GETINFO_REQ); + + msg_body.bss_index = vif_priv->bss_index; + + PREPARE_HAL_BUF(wcn->hal_buf, msg_body); + + ret = wcn36xx_smd_send_and_wait(wcn, msg_body.header.len); + if (ret) { + wcn36xx_err("Sending gtk_offload_get_info failed\n"); + goto out; + } + ret = wcn36xx_smd_rsp_status_check(wcn->hal_buf, wcn->hal_rsp_len); + if (ret) { + wcn36xx_err("gtk_offload_get_info failed err=%d\n", ret); + goto out; + } + ret = wcn36xx_smd_gtk_offload_get_info_rsp(wcn, vif); +out: + mutex_unlock(&wcn->hal_mutex); + return ret; +} + int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, void *buf, int len, void *priv, u32 addr) { @@ -2944,6 +3016,7 @@ int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, case WCN36XX_HAL_STOP_SCAN_OFFLOAD_RSP: case WCN36XX_HAL_HOST_OFFLOAD_RSP: case WCN36XX_HAL_GTK_OFFLOAD_RSP: + case WCN36XX_HAL_GTK_OFFLOAD_GETINFO_RSP: memcpy(wcn->hal_buf, buf, len); wcn->hal_rsp_len = len; complete(&wcn->hal_rsp_compl); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.h b/drivers/net/wireless/ath/wcn36xx/smd.h index cdf4231efe26..90c7faea0ef6 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.h +++ b/drivers/net/wireless/ath/wcn36xx/smd.h @@ -156,4 +156,7 @@ int wcn36xx_smd_ipv6_ns_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, int wcn36xx_smd_gtk_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, bool enable); +int wcn36xx_smd_gtk_offload_get_info(struct wcn36xx *wcn, + struct ieee80211_vif *vif); + #endif /* _SMD_H_ */ From 60f0078b1ebd51b5cde01f0001c8402a9ef0cec5 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:38 +0100 Subject: [PATCH 28/91] wcn36xx: Add Host suspend indication support In order to activate ipv4 ARP offload, ipv6 NS offload and firmware GTK offload we need to send a unidirectional indication from host to wcn indicating a transition to suspend. Once done, firmware will respond to ARP broadcasts, ipv6 NS lookups and perform GTK rekeys without waking the host. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-11-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 3 +++ drivers/net/wireless/ath/wcn36xx/smd.c | 19 +++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/smd.h | 2 ++ 3 files changed, 24 insertions(+) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index 8e5d8326d551..e4d5e4d597f9 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1125,6 +1125,9 @@ static int wcn36xx_suspend(struct ieee80211_hw *hw, struct cfg80211_wowlan *wow) if (ret) goto out; ret = wcn36xx_smd_set_power_params(wcn, true); + if (ret) + goto out; + ret = wcn36xx_smd_wlan_host_suspend_ind(wcn); } out: mutex_unlock(&wcn->conf_mutex); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.c b/drivers/net/wireless/ath/wcn36xx/smd.c index 13200a079bd0..3b4ba6edd17a 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.c +++ b/drivers/net/wireless/ath/wcn36xx/smd.c @@ -2966,6 +2966,25 @@ int wcn36xx_smd_gtk_offload_get_info(struct wcn36xx *wcn, return ret; } +int wcn36xx_smd_wlan_host_suspend_ind(struct wcn36xx *wcn) +{ + struct wcn36xx_hal_wlan_host_suspend_ind_msg msg_body; + int ret; + + mutex_lock(&wcn->hal_mutex); + + INIT_HAL_MSG(msg_body, WCN36XX_HAL_HOST_SUSPEND_IND); + msg_body.configured_mcst_bcst_filter_setting = 0; + msg_body.active_session_count = 1; + PREPARE_HAL_BUF(wcn->hal_buf, msg_body); + + ret = rpmsg_send(wcn->smd_channel, wcn->hal_buf, msg_body.header.len); + + mutex_unlock(&wcn->hal_mutex); + + return ret; +} + int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, void *buf, int len, void *priv, u32 addr) { diff --git a/drivers/net/wireless/ath/wcn36xx/smd.h b/drivers/net/wireless/ath/wcn36xx/smd.h index 90c7faea0ef6..2909facdb100 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.h +++ b/drivers/net/wireless/ath/wcn36xx/smd.h @@ -159,4 +159,6 @@ int wcn36xx_smd_gtk_offload(struct wcn36xx *wcn, struct ieee80211_vif *vif, int wcn36xx_smd_gtk_offload_get_info(struct wcn36xx *wcn, struct ieee80211_vif *vif); +int wcn36xx_smd_wlan_host_suspend_ind(struct wcn36xx *wcn); + #endif /* _SMD_H_ */ From ebe7c1a6635f19c61c14b78ba05a287e3022f4f8 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:39 +0100 Subject: [PATCH 29/91] wcn36xx: Add host resume request support This commit is the corresponding resume() path request to the firmware when resuming. Unlike the suspend() version which is a unidirectional indication, the resume version is a standard request/response. Once the resume() request completes ipv4 ARP, ipv6 NS and GTK rekey offload stop working and can subsequently be rolled back. Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-12-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 1 + drivers/net/wireless/ath/wcn36xx/smd.c | 35 +++++++++++++++++++++++++ drivers/net/wireless/ath/wcn36xx/smd.h | 2 ++ 3 files changed, 38 insertions(+) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index e4d5e4d597f9..c697b9f3633a 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -1144,6 +1144,7 @@ static int wcn36xx_resume(struct ieee80211_hw *hw) mutex_lock(&wcn->conf_mutex); vif = wcn36xx_get_first_assoc_vif(wcn); if (vif) { + wcn36xx_smd_host_resume(wcn); wcn36xx_smd_set_power_params(wcn, false); wcn36xx_smd_gtk_offload_get_info(wcn, vif); wcn36xx_smd_gtk_offload(wcn, vif, false); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.c b/drivers/net/wireless/ath/wcn36xx/smd.c index 3b4ba6edd17a..cf8e52cbdd9b 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.c +++ b/drivers/net/wireless/ath/wcn36xx/smd.c @@ -2985,6 +2985,40 @@ int wcn36xx_smd_wlan_host_suspend_ind(struct wcn36xx *wcn) return ret; } +int wcn36xx_smd_host_resume(struct wcn36xx *wcn) +{ + struct wcn36xx_hal_wlan_host_resume_req_msg msg_body; + struct wcn36xx_hal_host_resume_rsp_msg *rsp; + int ret; + + mutex_lock(&wcn->hal_mutex); + + INIT_HAL_MSG(msg_body, WCN36XX_HAL_HOST_RESUME_REQ); + msg_body.configured_mcst_bcst_filter_setting = 0; + + PREPARE_HAL_BUF(wcn->hal_buf, msg_body); + + ret = wcn36xx_smd_send_and_wait(wcn, msg_body.header.len); + if (ret) { + wcn36xx_err("Sending wlan_host_resume failed\n"); + goto out; + } + ret = wcn36xx_smd_rsp_status_check(wcn->hal_buf, wcn->hal_rsp_len); + if (ret) { + wcn36xx_err("wlan_host_resume err=%d\n", ret); + goto out; + } + + rsp = (struct wcn36xx_hal_host_resume_rsp_msg *)wcn->hal_buf; + if (rsp->status) + wcn36xx_warn("wlan_host_resume status=%d\n", rsp->status); + +out: + mutex_unlock(&wcn->hal_mutex); + + return ret; +} + int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, void *buf, int len, void *priv, u32 addr) { @@ -3036,6 +3070,7 @@ int wcn36xx_smd_rsp_process(struct rpmsg_device *rpdev, case WCN36XX_HAL_HOST_OFFLOAD_RSP: case WCN36XX_HAL_GTK_OFFLOAD_RSP: case WCN36XX_HAL_GTK_OFFLOAD_GETINFO_RSP: + case WCN36XX_HAL_HOST_RESUME_RSP: memcpy(wcn->hal_buf, buf, len); wcn->hal_rsp_len = len; complete(&wcn->hal_rsp_compl); diff --git a/drivers/net/wireless/ath/wcn36xx/smd.h b/drivers/net/wireless/ath/wcn36xx/smd.h index 2909facdb100..d8bded03945d 100644 --- a/drivers/net/wireless/ath/wcn36xx/smd.h +++ b/drivers/net/wireless/ath/wcn36xx/smd.h @@ -161,4 +161,6 @@ int wcn36xx_smd_gtk_offload_get_info(struct wcn36xx *wcn, int wcn36xx_smd_wlan_host_suspend_ind(struct wcn36xx *wcn); +int wcn36xx_smd_host_resume(struct wcn36xx *wcn); + #endif /* _SMD_H_ */ From 1e2e8ee957343575be7b370367b8312f7c489ac0 Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 02:11:40 +0100 Subject: [PATCH 30/91] wcn36xx: Enable WOWLAN flags Enable flags for - Magic packet - GTK rekey Previous patches implemented the necessary code to switch these two on. Standalone magic packet absent GTK rekey is pretty useless, so it makes sense to flag both at once. Once done it is possible for wcn36xx firmware to 1. Respond to ipv4 and ipv6 ARP/NS lookup requests 2. Bring the system out of suspend when a magic packet is received. Magic in our case is a simple ipv4 or ipv6 unicast. 3. GTK rekey whilst in suspend Once we wake from suspend the GTK will be updated as necessary Signed-off-by: Bryan O'Donoghue Tested-by: Benjamin Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605011140.2004643-13-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index c697b9f3633a..3a4e383b3a6c 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -173,7 +173,9 @@ static struct ieee80211_supported_band wcn_band_5ghz = { #ifdef CONFIG_PM static const struct wiphy_wowlan_support wowlan_support = { - .flags = WIPHY_WOWLAN_ANY + .flags = WIPHY_WOWLAN_ANY | + WIPHY_WOWLAN_MAGIC_PKT | + WIPHY_WOWLAN_SUPPORTS_GTK_REKEY }; #endif From 743b575af18ddfdb45bd7d1c338d3d9e730728b3 Mon Sep 17 00:00:00 2001 From: Jiapeng Chong Date: Wed, 26 May 2021 18:22:48 +0800 Subject: [PATCH 31/91] wcn36xx: Fix inconsistent indenting Eliminate the follow smatch warning: drivers/net/wireless/ath/wcn36xx/dxe.c:803 wcn36xx_dxe_tx_frame() warn: inconsistent indenting. Reported-by: Abaci Robot Signed-off-by: Jiapeng Chong Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1622024568-32130-1-git-send-email-jiapeng.chong@linux.alibaba.com --- drivers/net/wireless/ath/wcn36xx/dxe.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/wcn36xx/dxe.c b/drivers/net/wireless/ath/wcn36xx/dxe.c index 63079231e48e..8e1dbfda6538 100644 --- a/drivers/net/wireless/ath/wcn36xx/dxe.c +++ b/drivers/net/wireless/ath/wcn36xx/dxe.c @@ -800,7 +800,7 @@ int wcn36xx_dxe_tx_frame(struct wcn36xx *wcn, (char *)ctl_skb->skb->data, ctl_skb->skb->len); /* Move the head of the ring to the next empty descriptor */ - ch->head_blk_ctl = ctl_skb->next; + ch->head_blk_ctl = ctl_skb->next; /* Commit all previous writes and set descriptors to VALID */ wmb(); From ef48667557c53d4b51a1ee3090eab7699324c9de Mon Sep 17 00:00:00 2001 From: Bryan O'Donoghue Date: Sat, 5 Jun 2021 18:33:47 +0100 Subject: [PATCH 32/91] wcn36xx: Move hal_buf allocation to devm_kmalloc in probe Right now wcn->hal_buf is allocated in wcn36xx_start(). This is a problem since we should have setup all of the buffers we required by the time ieee80211_register_hw() is called. struct ieee80211_ops callbacks may run prior to mac_start() and therefore wcn->hal_buf must be initialized. This is easily remediated by moving the allocation to probe() taking the opportunity to tidy up freeing memory by using devm_kmalloc(). Fixes: 8e84c2582169 ("wcn36xx: mac80211 driver for Qualcomm WCN3660/WCN3680 hardware") Signed-off-by: Bryan O'Donoghue Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605173347.2266003-1-bryan.odonoghue@linaro.org --- drivers/net/wireless/ath/wcn36xx/main.c | 21 ++++++++------------- 1 file changed, 8 insertions(+), 13 deletions(-) diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c index 3a4e383b3a6c..d202f2128df2 100644 --- a/drivers/net/wireless/ath/wcn36xx/main.c +++ b/drivers/net/wireless/ath/wcn36xx/main.c @@ -296,23 +296,16 @@ static int wcn36xx_start(struct ieee80211_hw *hw) goto out_free_dxe_pool; } - wcn->hal_buf = kmalloc(WCN36XX_HAL_BUF_SIZE, GFP_KERNEL); - if (!wcn->hal_buf) { - wcn36xx_err("Failed to allocate smd buf\n"); - ret = -ENOMEM; - goto out_free_dxe_ctl; - } - ret = wcn36xx_smd_load_nv(wcn); if (ret) { wcn36xx_err("Failed to push NV to chip\n"); - goto out_free_smd_buf; + goto out_free_dxe_ctl; } ret = wcn36xx_smd_start(wcn); if (ret) { wcn36xx_err("Failed to start chip\n"); - goto out_free_smd_buf; + goto out_free_dxe_ctl; } if (!wcn36xx_is_fw_version(wcn, 1, 2, 2, 24)) { @@ -339,8 +332,6 @@ static int wcn36xx_start(struct ieee80211_hw *hw) out_smd_stop: wcn36xx_smd_stop(wcn); -out_free_smd_buf: - kfree(wcn->hal_buf); out_free_dxe_ctl: wcn36xx_dxe_free_ctl_blks(wcn); out_free_dxe_pool: @@ -375,8 +366,6 @@ static void wcn36xx_stop(struct ieee80211_hw *hw) wcn36xx_dxe_free_mem_pools(wcn); wcn36xx_dxe_free_ctl_blks(wcn); - - kfree(wcn->hal_buf); } static void wcn36xx_change_ps(struct wcn36xx *wcn, bool enable) @@ -1499,6 +1488,12 @@ static int wcn36xx_probe(struct platform_device *pdev) mutex_init(&wcn->hal_mutex); mutex_init(&wcn->scan_lock); + wcn->hal_buf = devm_kmalloc(wcn->dev, WCN36XX_HAL_BUF_SIZE, GFP_KERNEL); + if (!wcn->hal_buf) { + ret = -ENOMEM; + goto out_wq; + } + ret = dma_set_mask_and_coherent(wcn->dev, DMA_BIT_MASK(32)); if (ret < 0) { wcn36xx_err("failed to set DMA mask: %d\n", ret); From 86f1ea9d645edb16358e4a3e1602e1cec81e5048 Mon Sep 17 00:00:00 2001 From: YueHaibing Date: Sun, 23 May 2021 11:35:38 +0800 Subject: [PATCH 33/91] wlcore: use DEVICE_ATTR_ macro Use DEVICE_ATTR_ helper instead of plain DEVICE_ATTR, which makes the code a bit shorter and easier to read. Signed-off-by: YueHaibing Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210523033538.25568-1-yuehaibing@huawei.com --- drivers/net/wireless/ti/wlcore/sysfs.c | 24 +++++++++++------------- 1 file changed, 11 insertions(+), 13 deletions(-) diff --git a/drivers/net/wireless/ti/wlcore/sysfs.c b/drivers/net/wireless/ti/wlcore/sysfs.c index 5cf0379b88b6..35b535c125b6 100644 --- a/drivers/net/wireless/ti/wlcore/sysfs.c +++ b/drivers/net/wireless/ti/wlcore/sysfs.c @@ -12,9 +12,9 @@ #include "debug.h" #include "sysfs.h" -static ssize_t wl1271_sysfs_show_bt_coex_state(struct device *dev, - struct device_attribute *attr, - char *buf) +static ssize_t bt_coex_state_show(struct device *dev, + struct device_attribute *attr, + char *buf) { struct wl1271 *wl = dev_get_drvdata(dev); ssize_t len; @@ -30,9 +30,9 @@ static ssize_t wl1271_sysfs_show_bt_coex_state(struct device *dev, } -static ssize_t wl1271_sysfs_store_bt_coex_state(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t bt_coex_state_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct wl1271 *wl = dev_get_drvdata(dev); unsigned long res; @@ -71,13 +71,11 @@ static ssize_t wl1271_sysfs_store_bt_coex_state(struct device *dev, return count; } -static DEVICE_ATTR(bt_coex_state, 0644, - wl1271_sysfs_show_bt_coex_state, - wl1271_sysfs_store_bt_coex_state); +static DEVICE_ATTR_RW(bt_coex_state); -static ssize_t wl1271_sysfs_show_hw_pg_ver(struct device *dev, - struct device_attribute *attr, - char *buf) +static ssize_t hw_pg_ver_show(struct device *dev, + struct device_attribute *attr, + char *buf) { struct wl1271 *wl = dev_get_drvdata(dev); ssize_t len; @@ -94,7 +92,7 @@ static ssize_t wl1271_sysfs_show_hw_pg_ver(struct device *dev, return len; } -static DEVICE_ATTR(hw_pg_ver, 0444, wl1271_sysfs_show_hw_pg_ver, NULL); +static DEVICE_ATTR_RO(hw_pg_ver); static ssize_t wl1271_sysfs_read_fwlog(struct file *filp, struct kobject *kobj, struct bin_attribute *bin_attr, From 11ef6bc846dcdce838f0b00c5f6a562c57e5d43b Mon Sep 17 00:00:00 2001 From: Tony Lindgren Date: Thu, 3 Jun 2021 09:28:14 +0300 Subject: [PATCH 34/91] wlcore/wl12xx: Fix wl12xx get_mac error if device is in ELP At least on wl12xx, reading the MAC after boot can fail with a warning at drivers/net/wireless/ti/wlcore/sdio.c:78 wl12xx_sdio_raw_read. The failed call comes from wl12xx_get_mac() that wlcore_nvs_cb() calls after request_firmware_work_func(). After the error, no wireless interface is created. Reloading the wl12xx module makes the interface work. Turns out the wlan controller can be in a low-power ELP state after the boot from the bootloader or kexec, and needs to be woken up first. Let's wake the hardware and add a sleep after that similar to wl12xx_pre_boot() is already doing. Note that a similar issue could exist for wl18xx, but I have not seen it so far. And a search for wl18xx_get_mac and wl12xx_sdio_raw_read did not produce similar errors. Cc: Carl Philipp Klemm Signed-off-by: Tony Lindgren Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210603062814.19464-1-tony@atomide.com --- drivers/net/wireless/ti/wl12xx/main.c | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/drivers/net/wireless/ti/wl12xx/main.c b/drivers/net/wireless/ti/wl12xx/main.c index 9d7dbfe7fe0c..c6da0cfb4afb 100644 --- a/drivers/net/wireless/ti/wl12xx/main.c +++ b/drivers/net/wireless/ti/wl12xx/main.c @@ -1503,6 +1503,13 @@ static int wl12xx_get_fuse_mac(struct wl1271 *wl) u32 mac1, mac2; int ret; + /* Device may be in ELP from the bootloader or kexec */ + ret = wlcore_write32(wl, WL12XX_WELP_ARM_COMMAND, WELP_ARM_COMMAND_VAL); + if (ret < 0) + goto out; + + usleep_range(500000, 700000); + ret = wlcore_set_partition(wl, &wl->ptable[PART_DRPW]); if (ret < 0) goto out; From 913112398d5e3e64eb3a45b8a0f1c196daed8f0b Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 3 Jun 2021 12:54:14 +0100 Subject: [PATCH 35/91] wlcore: tidy up use of fw_log.actual_buff_size Tidy up the use of fw_log.actual_buff_size - rather than reading it multiple times and applying the endian conversion, read it once into actual_len and use that instead. Signed-off-by: Russell King Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/E1lolvS-0003Ql-NJ@rmk-PC.armlinux.org.uk --- drivers/net/wireless/ti/wlcore/event.c | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/wireless/ti/wlcore/event.c b/drivers/net/wireless/ti/wlcore/event.c index a68bbadae043..a5c261affdc7 100644 --- a/drivers/net/wireless/ti/wlcore/event.c +++ b/drivers/net/wireless/ti/wlcore/event.c @@ -40,7 +40,7 @@ int wlcore_event_fw_logger(struct wl1271 *wl) buffer = kzalloc(WL18XX_LOGGER_SDIO_BUFF_MAX, GFP_KERNEL); if (!buffer) { wl1271_error("Fail to allocate fw logger memory"); - fw_log.actual_buff_size = cpu_to_le32(0); + actual_len = 0; goto out; } @@ -49,30 +49,30 @@ int wlcore_event_fw_logger(struct wl1271 *wl) if (ret < 0) { wl1271_error("Fail to read logger buffer, error_id = %d", ret); - fw_log.actual_buff_size = cpu_to_le32(0); + actual_len = 0; goto free_out; } memcpy(&fw_log, buffer, sizeof(fw_log)); - if (le32_to_cpu(fw_log.actual_buff_size) == 0) + actual_len = le32_to_cpu(fw_log.actual_buff_size); + if (actual_len == 0) goto free_out; - actual_len = le32_to_cpu(fw_log.actual_buff_size); start_loc = (le32_to_cpu(fw_log.buff_read_ptr) - internal_fw_addrbase) - addr; end_buff_addr += le32_to_cpu(fw_log.max_buff_size); available_len = end_buff_addr - (le32_to_cpu(fw_log.buff_read_ptr) - internal_fw_addrbase); - actual_len = min(actual_len, available_len); - len = actual_len; + /* Copy initial part from end of ring buffer */ + len = min(actual_len, available_len); wl12xx_copy_fwlog(wl, &buffer[start_loc], len); - clear_addr = addr + start_loc + le32_to_cpu(fw_log.actual_buff_size) + - internal_fw_addrbase; + clear_addr = addr + start_loc + actual_len + internal_fw_addrbase; - len = le32_to_cpu(fw_log.actual_buff_size) - len; + /* Copy any remaining part from beginning of ring buffer */ + len = actual_len - len; if (len) { wl12xx_copy_fwlog(wl, &buffer[WL18XX_LOGGER_BUFF_OFFSET], @@ -93,7 +93,7 @@ int wlcore_event_fw_logger(struct wl1271 *wl) free_out: kfree(buffer); out: - return le32_to_cpu(fw_log.actual_buff_size); + return actual_len; } EXPORT_SYMBOL_GPL(wlcore_event_fw_logger); From 98e94771cadcef2952d3aa64e72b2b8fecef465b Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 3 Jun 2021 12:54:19 +0100 Subject: [PATCH 36/91] wlcore: make some of the fwlog calculations more obvious Make some of the fwlog calculations more obvious by calculating bits that get used and documenting what they are. Validate the read pointer while we're at it to ensure we do not overflow the data block we have allocated and read. Signed-off-by: Russell King Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/E1lolvX-0003R3-RE@rmk-PC.armlinux.org.uk --- drivers/net/wireless/ti/wlcore/event.c | 43 +++++++++++++++++--------- 1 file changed, 28 insertions(+), 15 deletions(-) diff --git a/drivers/net/wireless/ti/wlcore/event.c b/drivers/net/wireless/ti/wlcore/event.c index a5c261affdc7..875198fb1480 100644 --- a/drivers/net/wireless/ti/wlcore/event.c +++ b/drivers/net/wireless/ti/wlcore/event.c @@ -29,11 +29,13 @@ int wlcore_event_fw_logger(struct wl1271 *wl) u8 *buffer; u32 internal_fw_addrbase = WL18XX_DATA_RAM_BASE_ADDRESS; u32 addr = WL18XX_LOGGER_SDIO_BUFF_ADDR; - u32 end_buff_addr = WL18XX_LOGGER_SDIO_BUFF_ADDR + - WL18XX_LOGGER_BUFF_OFFSET; + u32 addr_ptr; + u32 buff_start_ptr; + u32 buff_read_ptr; + u32 buff_end_ptr; u32 available_len; u32 actual_len; - u32 clear_addr; + u32 clear_ptr; size_t len; u32 start_loc; @@ -59,17 +61,29 @@ int wlcore_event_fw_logger(struct wl1271 *wl) if (actual_len == 0) goto free_out; - start_loc = (le32_to_cpu(fw_log.buff_read_ptr) - - internal_fw_addrbase) - addr; - end_buff_addr += le32_to_cpu(fw_log.max_buff_size); - available_len = end_buff_addr - - (le32_to_cpu(fw_log.buff_read_ptr) - - internal_fw_addrbase); + /* Calculate the internal pointer to the fwlog structure */ + addr_ptr = internal_fw_addrbase + addr; - /* Copy initial part from end of ring buffer */ + /* Calculate the internal pointers to the start and end of log buffer */ + buff_start_ptr = addr_ptr + WL18XX_LOGGER_BUFF_OFFSET; + buff_end_ptr = buff_start_ptr + le32_to_cpu(fw_log.max_buff_size); + + /* Read the read pointer and validate it */ + buff_read_ptr = le32_to_cpu(fw_log.buff_read_ptr); + if (buff_read_ptr < buff_start_ptr || + buff_read_ptr >= buff_end_ptr) { + wl1271_error("buffer read pointer out of bounds: %x not in (%x-%x)\n", + buff_read_ptr, buff_start_ptr, buff_end_ptr); + goto free_out; + } + + start_loc = buff_read_ptr - addr_ptr; + available_len = buff_end_ptr - buff_read_ptr; + + /* Copy initial part up to the end of ring buffer */ len = min(actual_len, available_len); wl12xx_copy_fwlog(wl, &buffer[start_loc], len); - clear_addr = addr + start_loc + actual_len + internal_fw_addrbase; + clear_ptr = addr_ptr + start_loc + actual_len; /* Copy any remaining part from beginning of ring buffer */ len = actual_len - len; @@ -77,14 +91,13 @@ int wlcore_event_fw_logger(struct wl1271 *wl) wl12xx_copy_fwlog(wl, &buffer[WL18XX_LOGGER_BUFF_OFFSET], len); - clear_addr = addr + WL18XX_LOGGER_BUFF_OFFSET + len + - internal_fw_addrbase; + clear_ptr = addr_ptr + WL18XX_LOGGER_BUFF_OFFSET + len; } /* double check that clear address and write pointer are the same */ - if (clear_addr != le32_to_cpu(fw_log.buff_write_ptr)) { + if (clear_ptr != le32_to_cpu(fw_log.buff_write_ptr)) { wl1271_error("Calculate of clear addr Clear = %x, write = %x", - clear_addr, le32_to_cpu(fw_log.buff_write_ptr)); + clear_ptr, le32_to_cpu(fw_log.buff_write_ptr)); } /* indicate FW about Clear buffer */ From 87ab9cbaee7c11dd12587d60fb16f3ec22c1a5b3 Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 3 Jun 2021 12:54:24 +0100 Subject: [PATCH 37/91] wlcore: fix bug reading fwlog With logging enabled, it has been observed that the driver spews messages such as: wlcore: ERROR Calculate of clear addr Clear = 204025b0, write = 204015b0 The problem occurs because 204025b0 is the end of the buffer, and 204015b0 is the beginning, and the calculation for "clear"ing the buffer does not take into account that if we read to the very end of the ring buffer, we are actually at the beginning of the buffer. Fix this. Signed-off-by: Russell King Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/E1lolvc-0003RM-VE@rmk-PC.armlinux.org.uk --- drivers/net/wireless/ti/wlcore/event.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/net/wireless/ti/wlcore/event.c b/drivers/net/wireless/ti/wlcore/event.c index 875198fb1480..8a67a708c96e 100644 --- a/drivers/net/wireless/ti/wlcore/event.c +++ b/drivers/net/wireless/ti/wlcore/event.c @@ -84,6 +84,8 @@ int wlcore_event_fw_logger(struct wl1271 *wl) len = min(actual_len, available_len); wl12xx_copy_fwlog(wl, &buffer[start_loc], len); clear_ptr = addr_ptr + start_loc + actual_len; + if (clear_ptr == buff_end_ptr) + clear_ptr = buff_start_ptr; /* Copy any remaining part from beginning of ring buffer */ len = actual_len - len; From 01de6fe49ca406d4e44c6e4327a7f49d240113c1 Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 3 Jun 2021 12:54:30 +0100 Subject: [PATCH 38/91] wlcore: fix read pointer update When reading the fw_log structure from the device's memory, we could race with the firmware updating the actual_buff_size and buff_write_ptr members of this structure. This would lead to bytes being dropped from the log. Fix this by writing back the actual - now fixed - clear_ptr which reflects where we read up to in the buffer. This also means that we must not check that the clear_ptr matches the current write pointer, so remove that check. Signed-off-by: Russell King Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/E1lolvi-0003Ri-39@rmk-PC.armlinux.org.uk --- drivers/net/wireless/ti/wlcore/event.c | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/drivers/net/wireless/ti/wlcore/event.c b/drivers/net/wireless/ti/wlcore/event.c index 8a67a708c96e..46ab69eab26a 100644 --- a/drivers/net/wireless/ti/wlcore/event.c +++ b/drivers/net/wireless/ti/wlcore/event.c @@ -96,15 +96,9 @@ int wlcore_event_fw_logger(struct wl1271 *wl) clear_ptr = addr_ptr + WL18XX_LOGGER_BUFF_OFFSET + len; } - /* double check that clear address and write pointer are the same */ - if (clear_ptr != le32_to_cpu(fw_log.buff_write_ptr)) { - wl1271_error("Calculate of clear addr Clear = %x, write = %x", - clear_ptr, le32_to_cpu(fw_log.buff_write_ptr)); - } - - /* indicate FW about Clear buffer */ + /* Update the read pointer */ ret = wlcore_write32(wl, addr + WL18XX_LOGGER_READ_POINT_OFFSET, - fw_log.buff_write_ptr); + clear_ptr); free_out: kfree(buffer); out: From 5615eb58b2384bc1d6461c75b8bf77ad96f7842d Mon Sep 17 00:00:00 2001 From: Shubhankar Kuranagatti Date: Wed, 28 Apr 2021 21:37:47 +0530 Subject: [PATCH 39/91] ssb: gpio: Fix alignment of comment MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The closing */ has been shifted to a new line This is done to maintain code uniformity. Acked-by: Michael Büsch Signed-off-by: Shubhankar Kuranagatti Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210428160747.qy23g6zpmheiacpl@kewl-virtual-machine --- drivers/ssb/driver_gpio.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/ssb/driver_gpio.c b/drivers/ssb/driver_gpio.c index 66a76fd83248..2de3896489c8 100644 --- a/drivers/ssb/driver_gpio.c +++ b/drivers/ssb/driver_gpio.c @@ -231,7 +231,8 @@ static int ssb_gpio_chipco_init(struct ssb_bus *bus) chip->ngpio = 16; /* There is just one SoC in one device and its GPIO addresses should be * deterministic to address them more easily. The other buses could get - * a random base number. */ + * a random base number. + */ if (bus->bustype == SSB_BUSTYPE_SSB) chip->base = 0; else @@ -424,7 +425,8 @@ static int ssb_gpio_extif_init(struct ssb_bus *bus) chip->ngpio = 5; /* There is just one SoC in one device and its GPIO addresses should be * deterministic to address them more easily. The other buses could get - * a random base number. */ + * a random base number. + */ if (bus->bustype == SSB_BUSTYPE_SSB) chip->base = 0; else From 2a3d830fa8f9a6148473367085a9eafd665fb20f Mon Sep 17 00:00:00 2001 From: Shubhankar Kuranagatti Date: Wed, 28 Apr 2021 21:48:36 +0530 Subject: [PATCH 40/91] ssb: pcicore: Fix indentation of comment MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Shifted the closing */ to the next line This is done to maintain code uniformity. Acked-by: Michael Büsch Signed-off-by: Shubhankar Kuranagatti Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210428161836.sdrxzcrfiekloucz@kewl-virtual-machine --- drivers/ssb/driver_pcicore.c | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/drivers/ssb/driver_pcicore.c b/drivers/ssb/driver_pcicore.c index c1186415896b..d11b4242b6d2 100644 --- a/drivers/ssb/driver_pcicore.c +++ b/drivers/ssb/driver_pcicore.c @@ -55,7 +55,8 @@ void pcicore_write16(struct ssb_pcicore *pc, u16 offset, u16 value) #include /* Probe a 32bit value on the bus and catch bus exceptions. * Returns nonzero on a bus exception. - * This is MIPS specific */ + * This is MIPS specific + */ #define mips_busprobe32(val, addr) get_dbe((val), ((u32 *)(addr))) /* Assume one-hot slot wiring */ @@ -255,7 +256,8 @@ static struct pci_controller ssb_pcicore_controller = { }; /* This function is called when doing a pci_enable_device(). - * We must first check if the device is a device on the PCI-core bridge. */ + * We must first check if the device is a device on the PCI-core bridge. + */ int ssb_pcicore_plat_dev_init(struct pci_dev *d) { if (d->bus->ops != &ssb_pcicore_pciops) { @@ -381,11 +383,13 @@ static void ssb_pcicore_init_hostmode(struct ssb_pcicore *pc) /* Ok, ready to run, register it to the system. * The following needs change, if we want to port hostmode - * to non-MIPS platform. */ + * to non-MIPS platform. + */ ssb_pcicore_controller.io_map_base = (unsigned long)ioremap(SSB_PCI_MEM, 0x04000000); set_io_port_base(ssb_pcicore_controller.io_map_base); /* Give some time to the PCI controller to configure itself with the new - * values. Not waiting at this point causes crashes of the machine. */ + * values. Not waiting at this point causes crashes of the machine. + */ mdelay(10); register_pci_controller(&ssb_pcicore_controller); } @@ -405,7 +409,8 @@ static int pcicore_is_in_hostmode(struct ssb_pcicore *pc) return 0; /* The 200-pin BCM4712 package does not bond out PCI. Even when - * PCI is bonded out, some boards may leave the pins floating. */ + * PCI is bonded out, some boards may leave the pins floating. + */ if (bus->chip_id == 0x4712) { if (bus->chip_package == SSB_CHIPPACK_BCM4712S) return 0; @@ -685,7 +690,8 @@ int ssb_pcicore_dev_irqvecs_enable(struct ssb_pcicore *pc, if (dev->bus->bustype != SSB_BUSTYPE_PCI) { /* This SSB device is not on a PCI host-bus. So the IRQs are * not routed through the PCI core. - * So we must not enable routing through the PCI core. */ + * So we must not enable routing through the PCI core. + */ goto out; } From f30282129a4d47bf44805c712be1ac4f89eb8783 Mon Sep 17 00:00:00 2001 From: Shubhankar Kuranagatti Date: Wed, 28 Apr 2021 21:59:07 +0530 Subject: [PATCH 41/91] ssb: Fix indentation of comment MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Shifted the closing */ to the next line This is done to maintain code uniformity. Acked-by: Michael Büsch Signed-off-by: Shubhankar Kuranagatti Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210428162907.bn5q3oh3sji6wlh4@kewl-virtual-machine --- drivers/ssb/main.c | 30 ++++++++++++++++++++---------- 1 file changed, 20 insertions(+), 10 deletions(-) diff --git a/drivers/ssb/main.c b/drivers/ssb/main.c index 0a26984acb2c..0e180c36daa4 100644 --- a/drivers/ssb/main.c +++ b/drivers/ssb/main.c @@ -37,7 +37,8 @@ static LIST_HEAD(buses); /* Software ID counter */ static unsigned int next_busnumber; /* buses_mutes locks the two buslists and the next_busnumber. - * Don't lock this directly, but use ssb_buses_[un]lock() below. */ + * Don't lock this directly, but use ssb_buses_[un]lock() below. + */ static DEFINE_MUTEX(buses_mutex); /* There are differences in the codeflow, if the bus is @@ -45,7 +46,8 @@ static DEFINE_MUTEX(buses_mutex); * are not available early. This is a mechanism to delay * these initializations to after early boot has finished. * It's also used to avoid mutex locking, as that's not - * available and needed early. */ + * available and needed early. + */ static bool ssb_is_early_boot = 1; static void ssb_buses_lock(void); @@ -161,7 +163,8 @@ int ssb_bus_resume(struct ssb_bus *bus) int err; /* Reset HW state information in memory, so that HW is - * completely reinitialized. */ + * completely reinitialized. + */ bus->mapped_device = NULL; #ifdef CONFIG_SSB_DRIVER_PCICORE bus->pcicore.setup_done = 0; @@ -467,7 +470,8 @@ static int ssb_devices_register(struct ssb_bus *bus) sdev = &(bus->devices[i]); /* We don't register SSB-system devices to the kernel, - * as the drivers for them are built into SSB. */ + * as the drivers for them are built into SSB. + */ switch (sdev->id.coreid) { case SSB_DEV_CHIPCOMMON: case SSB_DEV_PCI: @@ -521,7 +525,8 @@ static int ssb_devices_register(struct ssb_bus *bus) if (err) { pr_err("Could not register %s\n", dev_name(dev)); /* Set dev to NULL to not unregister - * dev on error unwinding. */ + * dev on error unwinding. + */ sdev->dev = NULL; put_device(dev); goto error; @@ -667,7 +672,8 @@ ssb_bus_register(struct ssb_bus *bus, ssb_bus_may_powerdown(bus); /* Queue it for attach. - * See the comment at the ssb_is_early_boot definition. */ + * See the comment at the ssb_is_early_boot definition. + */ list_add_tail(&bus->list, &attach_queue); if (!ssb_is_early_boot) { /* This is not early boot, so we must attach the bus now */ @@ -1007,7 +1013,8 @@ static void ssb_flush_tmslow(struct ssb_device *dev) * a machine check exception otherwise. * Do this by reading the register back to commit the * PCI write and delay an additional usec for the device - * to react to the change. */ + * to react to the change. + */ ssb_read32(dev, SSB_TMSLOW); udelay(1); } @@ -1044,7 +1051,8 @@ void ssb_device_enable(struct ssb_device *dev, u32 core_specific_flags) EXPORT_SYMBOL(ssb_device_enable); /* Wait for bitmask in a register to get set or cleared. - * timeout is in units of ten-microseconds */ + * timeout is in units of ten-microseconds + */ static int ssb_wait_bits(struct ssb_device *dev, u16 reg, u32 bitmask, int timeout, int set) { @@ -1153,7 +1161,8 @@ int ssb_bus_may_powerdown(struct ssb_bus *bus) /* On buses where more than one core may be working * at a time, we must not powerdown stuff if there are - * still cores that may want to run. */ + * still cores that may want to run. + */ if (bus->bustype == SSB_BUSTYPE_SSB) goto out; @@ -1322,7 +1331,8 @@ static int __init ssb_modinit(void) } /* ssb must be initialized after PCI but before the ssb drivers. * That means we must use some initcall between subsys_initcall - * and device_initcall. */ + * and device_initcall. + */ fs_initcall(ssb_modinit); static void __exit ssb_modexit(void) From 7557dfde1bd1251793fade20a52014f1105c1012 Mon Sep 17 00:00:00 2001 From: Yang Li Date: Thu, 29 Apr 2021 18:47:10 +0800 Subject: [PATCH 42/91] ssb: Remove redundant assignment to err MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Variable 'err' is set to zero but this value is never read as it is overwritten with a new value later on, hence it is a redundant assignment and can be removed. Clean up the following clang-analyzer warning: drivers/ssb/main.c:1306:3: warning: Value stored to 'err' is never read [clang-analyzer-deadcode.DeadStores] drivers/ssb/main.c:1312:3: warning: Value stored to 'err' is never read [clang-analyzer-deadcode.DeadStores] Reported-by: Abaci Robot Signed-off-by: Yang Li Acked-by: Michael Büsch Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1619693230-108804-1-git-send-email-yang.lee@linux.alibaba.com --- drivers/ssb/main.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/drivers/ssb/main.c b/drivers/ssb/main.c index 0e180c36daa4..620cc9dccad7 100644 --- a/drivers/ssb/main.c +++ b/drivers/ssb/main.c @@ -1312,13 +1312,11 @@ static int __init ssb_modinit(void) if (err) { pr_err("Broadcom 43xx PCI-SSB-bridge initialization failed\n"); /* don't fail SSB init because of this */ - err = 0; } err = ssb_host_pcmcia_init(); if (err) { pr_err("PCMCIA host initialization failed\n"); /* don't fail SSB init because of this */ - err = 0; } err = ssb_gige_init(); if (err) { From 77a0989baa427dbd242c5784d05a53ca3d197d43 Mon Sep 17 00:00:00 2001 From: Zhen Lei Date: Sat, 15 May 2021 15:29:49 +0800 Subject: [PATCH 43/91] ssb: Fix error return code in ssb_bus_scan() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fix to return -EINVAL from the error handling case instead of 0, as done elsewhere in this function. Fixes: 61e115a56d1a ("[SSB]: add Sonics Silicon Backplane bus support") Reported-by: Hulk Robot Signed-off-by: Zhen Lei Acked-by: Michael Büsch Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210515072949.7151-1-thunder.leizhen@huawei.com --- drivers/ssb/scan.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/ssb/scan.c b/drivers/ssb/scan.c index f49ab1aa2149..4161e5d1f276 100644 --- a/drivers/ssb/scan.c +++ b/drivers/ssb/scan.c @@ -325,6 +325,7 @@ int ssb_bus_scan(struct ssb_bus *bus, if (bus->nr_devices > ARRAY_SIZE(bus->devices)) { pr_err("More than %d ssb cores found (%d)\n", SSB_MAX_NR_CORES, bus->nr_devices); + err = -EINVAL; goto err_unmap; } if (bus->bustype == SSB_BUSTYPE_SSB) { From 47ec636f7a25aa2549e198c48ecb6b1c25d05456 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Michael=20B=C3=BCsch?= Date: Sat, 15 May 2021 21:02:52 +0200 Subject: [PATCH 44/91] ssb: sdio: Don't overwrite const buffer if block_write fails MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It doesn't make sense to clobber the const driver-side buffer, if a write-to-device attempt failed. All other SSB variants (PCI, PCMCIA and SoC) also don't corrupt the buffer on any failure in block_write. Therefore, remove this memset from the SDIO variant. Signed-off-by: Michael Büsch Cc: stable@vger.kernel.org Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210515210252.318be2ba@wiggum --- drivers/ssb/sdio.c | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/ssb/sdio.c b/drivers/ssb/sdio.c index 7fe0afb42234..66c5c2169704 100644 --- a/drivers/ssb/sdio.c +++ b/drivers/ssb/sdio.c @@ -411,7 +411,6 @@ static void ssb_sdio_block_write(struct ssb_device *dev, const void *buffer, sdio_claim_host(bus->host_sdio); if (unlikely(ssb_sdio_switch_core(bus, dev))) { error = -EIO; - memset((void *)buffer, 0xff, count); goto err_out; } offset |= bus->sdio_sbaddr & 0xffff; From 233bc283728241aa522fd2889649261b742cee5a Mon Sep 17 00:00:00 2001 From: Tian Tao Date: Tue, 18 May 2021 10:52:32 +0800 Subject: [PATCH 45/91] ssb: remove unreachable code MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The return value of ssb_bus_unregister can only be 0 or -1, so this condition if (err == -EBUSY) will not hold, so delete it. Signed-off-by: Tian Tao Acked-by: Michael Büsch Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1621306352-3632-1-git-send-email-tiantao6@hisilicon.com --- drivers/ssb/main.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/drivers/ssb/main.c b/drivers/ssb/main.c index 620cc9dccad7..3a29b5570f9f 100644 --- a/drivers/ssb/main.c +++ b/drivers/ssb/main.c @@ -434,9 +434,7 @@ void ssb_bus_unregister(struct ssb_bus *bus) int err; err = ssb_gpio_unregister(bus); - if (err == -EBUSY) - pr_debug("Some GPIOs are still in use\n"); - else if (err) + if (err) pr_debug("Can not unregister GPIO driver: %i\n", err); ssb_buses_lock(); From 573f1af86891d4ecda9f7f1073dccec28c469387 Mon Sep 17 00:00:00 2001 From: Zhen Lei Date: Thu, 3 Jun 2021 16:22:18 +0800 Subject: [PATCH 46/91] ssb: use DEVICE_ATTR_ADMIN_RW() helper macro Use DEVICE_ATTR_ADMIN_RW() helper macro instead of DEVICE_ATTR(), making it simpler and easier to read. Because the read and write function names of the sysfs attribute have been normalized, there is a natural association. Signed-off-by: Zhen Lei Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210603082218.11718-2-thunder.leizhen@huawei.com --- drivers/ssb/pci.c | 16 +++++++--------- drivers/ssb/pcmcia.c | 16 +++++++--------- 2 files changed, 14 insertions(+), 18 deletions(-) diff --git a/drivers/ssb/pci.c b/drivers/ssb/pci.c index dac54041ad8d..148bcb99c212 100644 --- a/drivers/ssb/pci.c +++ b/drivers/ssb/pci.c @@ -1117,9 +1117,9 @@ const struct ssb_bus_ops ssb_pci_ops = { #endif }; -static ssize_t ssb_pci_attr_sprom_show(struct device *pcidev, - struct device_attribute *attr, - char *buf) +static ssize_t ssb_sprom_show(struct device *pcidev, + struct device_attribute *attr, + char *buf) { struct pci_dev *pdev = container_of(pcidev, struct pci_dev, dev); struct ssb_bus *bus; @@ -1131,9 +1131,9 @@ static ssize_t ssb_pci_attr_sprom_show(struct device *pcidev, return ssb_attr_sprom_show(bus, buf, sprom_do_read); } -static ssize_t ssb_pci_attr_sprom_store(struct device *pcidev, - struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t ssb_sprom_store(struct device *pcidev, + struct device_attribute *attr, + const char *buf, size_t count) { struct pci_dev *pdev = container_of(pcidev, struct pci_dev, dev); struct ssb_bus *bus; @@ -1146,9 +1146,7 @@ static ssize_t ssb_pci_attr_sprom_store(struct device *pcidev, sprom_check_crc, sprom_do_write); } -static DEVICE_ATTR(ssb_sprom, 0600, - ssb_pci_attr_sprom_show, - ssb_pci_attr_sprom_store); +static DEVICE_ATTR_ADMIN_RW(ssb_sprom); void ssb_pci_exit(struct ssb_bus *bus) { diff --git a/drivers/ssb/pcmcia.c b/drivers/ssb/pcmcia.c index d7d730c245c5..45502098e0c7 100644 --- a/drivers/ssb/pcmcia.c +++ b/drivers/ssb/pcmcia.c @@ -723,9 +723,9 @@ int ssb_pcmcia_get_invariants(struct ssb_bus *bus, return -ENODEV; } -static ssize_t ssb_pcmcia_attr_sprom_show(struct device *pcmciadev, - struct device_attribute *attr, - char *buf) +static ssize_t ssb_sprom_show(struct device *pcmciadev, + struct device_attribute *attr, + char *buf) { struct pcmcia_device *pdev = container_of(pcmciadev, struct pcmcia_device, dev); @@ -739,9 +739,9 @@ static ssize_t ssb_pcmcia_attr_sprom_show(struct device *pcmciadev, ssb_pcmcia_sprom_read_all); } -static ssize_t ssb_pcmcia_attr_sprom_store(struct device *pcmciadev, - struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t ssb_sprom_store(struct device *pcmciadev, + struct device_attribute *attr, + const char *buf, size_t count) { struct pcmcia_device *pdev = container_of(pcmciadev, struct pcmcia_device, dev); @@ -756,9 +756,7 @@ static ssize_t ssb_pcmcia_attr_sprom_store(struct device *pcmciadev, ssb_pcmcia_sprom_write_all); } -static DEVICE_ATTR(ssb_sprom, 0600, - ssb_pcmcia_attr_sprom_show, - ssb_pcmcia_attr_sprom_store); +static DEVICE_ATTR_ADMIN_RW(ssb_sprom); static int ssb_pcmcia_cor_setup(struct ssb_bus *bus, u8 cor) { From b0b524f079a23e440dd22b04e369368dde847533 Mon Sep 17 00:00:00 2001 From: Shawn Guo Date: Sun, 25 Apr 2021 19:02:00 +0800 Subject: [PATCH 47/91] brcmfmac: use ISO3166 country code and 0 rev as fallback Instead of aborting country code setup in firmware, use ISO3166 country code and 0 rev as fallback, when country_codes mapping table is not configured. This fallback saves the country_codes table setup for recent brcmfmac chipsets/firmwares, which just use ISO3166 code and require no revision number. Signed-off-by: Shawn Guo Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210425110200.3050-1-shawn.guo@linaro.org --- .../broadcom/brcm80211/brcmfmac/cfg80211.c | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c index f4405d7861b6..6cb09c7c37b6 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c @@ -7442,18 +7442,23 @@ static s32 brcmf_translate_country_code(struct brcmf_pub *drvr, char alpha2[2], s32 found_index; int i; - country_codes = drvr->settings->country_codes; - if (!country_codes) { - brcmf_dbg(TRACE, "No country codes configured for device\n"); - return -EINVAL; - } - if ((alpha2[0] == ccreq->country_abbrev[0]) && (alpha2[1] == ccreq->country_abbrev[1])) { brcmf_dbg(TRACE, "Country code already set\n"); return -EAGAIN; } + country_codes = drvr->settings->country_codes; + if (!country_codes) { + brcmf_dbg(TRACE, "No country codes configured for device, using ISO3166 code and 0 rev\n"); + memset(ccreq, 0, sizeof(*ccreq)); + ccreq->country_abbrev[0] = alpha2[0]; + ccreq->country_abbrev[1] = alpha2[1]; + ccreq->ccode[0] = alpha2[0]; + ccreq->ccode[1] = alpha2[1]; + return 0; + } + found_index = -1; for (i = 0; i < country_codes->table_size; i++) { cc = &country_codes->table[i]; From feb45643762172110cb3a44f99dd54304f33b711 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alvin=20=C5=A0ipraga?= Date: Thu, 6 May 2021 13:20:12 +0000 Subject: [PATCH 48/91] brcmfmac: fix setting of station info chains bitmask MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The sinfo->chains field is a bitmask for filled values in chain_signal and chain_signal_avg, not a count. Treat it as such so that the driver can properly report per-chain RSSI information. Before (MIMO mode): $ iw dev wlan0 station dump ... signal: -51 [-51] dBm After (MIMO mode): $ iw dev wlan0 station dump ... signal: -53 [-53, -54] dBm Fixes: cae355dc90db ("brcmfmac: Add RSSI information to get_station.") Signed-off-by: Alvin Šipraga Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210506132010.3964484-1-alsi@bang-olufsen.dk --- drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c index 6cb09c7c37b6..77458095bbd4 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c @@ -2838,6 +2838,7 @@ brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev, count_rssi = 0; for (i = 0; i < BRCMF_ANT_MAX; i++) { if (sta_info_le.rssi[i]) { + sinfo->chains |= BIT(count_rssi); sinfo->chain_signal_avg[count_rssi] = sta_info_le.rssi[i]; sinfo->chain_signal[count_rssi] = @@ -2848,8 +2849,6 @@ brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev, } if (count_rssi) { sinfo->filled |= BIT_ULL(NL80211_STA_INFO_CHAIN_SIGNAL); - sinfo->chains = count_rssi; - sinfo->filled |= BIT_ULL(NL80211_STA_INFO_SIGNAL); total_rssi /= count_rssi; sinfo->signal = total_rssi; From 9a1590934d9a02e570636432b93052c0c035f31f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alvin=20=C5=A0ipraga?= Date: Thu, 6 May 2021 13:20:12 +0000 Subject: [PATCH 49/91] brcmfmac: correctly report average RSSI in station info MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The rx_lastpkt_rssi field provided by the firmware is suitable for NL80211_STA_INFO_{SIGNAL,CHAIN_SIGNAL}, while the rssi field is an average. Fix up the assignments and set the correct STA_INFO bits. This lets userspace know that the average RSSI is part of the station info. Fixes: cae355dc90db ("brcmfmac: Add RSSI information to get_station.") Signed-off-by: Alvin Šipraga Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210506132010.3964484-2-alsi@bang-olufsen.dk --- .../broadcom/brcm80211/brcmfmac/cfg80211.c | 36 ++++++++++--------- 1 file changed, 20 insertions(+), 16 deletions(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c index 77458095bbd4..65fb038d88e7 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c @@ -2767,8 +2767,9 @@ brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev, struct brcmf_sta_info_le sta_info_le; u32 sta_flags; u32 is_tdls_peer; - s32 total_rssi; - s32 count_rssi; + s32 total_rssi_avg = 0; + s32 total_rssi = 0; + s32 count_rssi = 0; int rssi; u32 i; @@ -2834,24 +2835,27 @@ brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev, sinfo->filled |= BIT_ULL(NL80211_STA_INFO_RX_BYTES); sinfo->rx_bytes = le64_to_cpu(sta_info_le.rx_tot_bytes); } - total_rssi = 0; - count_rssi = 0; for (i = 0; i < BRCMF_ANT_MAX; i++) { - if (sta_info_le.rssi[i]) { - sinfo->chains |= BIT(count_rssi); - sinfo->chain_signal_avg[count_rssi] = - sta_info_le.rssi[i]; - sinfo->chain_signal[count_rssi] = - sta_info_le.rssi[i]; - total_rssi += sta_info_le.rssi[i]; - count_rssi++; - } + if (sta_info_le.rssi[i] == 0 || + sta_info_le.rx_lastpkt_rssi[i] == 0) + continue; + sinfo->chains |= BIT(count_rssi); + sinfo->chain_signal[count_rssi] = + sta_info_le.rx_lastpkt_rssi[i]; + sinfo->chain_signal_avg[count_rssi] = + sta_info_le.rssi[i]; + total_rssi += sta_info_le.rx_lastpkt_rssi[i]; + total_rssi_avg += sta_info_le.rssi[i]; + count_rssi++; } if (count_rssi) { - sinfo->filled |= BIT_ULL(NL80211_STA_INFO_CHAIN_SIGNAL); sinfo->filled |= BIT_ULL(NL80211_STA_INFO_SIGNAL); - total_rssi /= count_rssi; - sinfo->signal = total_rssi; + sinfo->filled |= BIT_ULL(NL80211_STA_INFO_SIGNAL_AVG); + sinfo->filled |= BIT_ULL(NL80211_STA_INFO_CHAIN_SIGNAL); + sinfo->filled |= + BIT_ULL(NL80211_STA_INFO_CHAIN_SIGNAL_AVG); + sinfo->signal = total_rssi / count_rssi; + sinfo->signal_avg = total_rssi_avg / count_rssi; } else if (test_bit(BRCMF_VIF_STATUS_CONNECTED, &ifp->vif->sme_state)) { memset(&scb_val, 0, sizeof(scb_val)); From ea3f903caea08bbda8a5d4e86d1d24f50af40b5e Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:34 +0800 Subject: [PATCH 50/91] brcmfmac: Demote non-compliant kernel-doc headers Fixes the following W=1 kernel build warning(s): drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c:2040: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c:1295: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst Cc: Franky Lin Cc: Hante Meuleman Signed-off-by: Yang Shen Acked-by: Arend van Spriel Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-5-shenyang39@huawei.com --- drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c | 2 +- drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c index 34cd8a7401fe..9ac0d8c73d5a 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c @@ -2037,7 +2037,7 @@ static void brcmf_p2p_get_current_chanspec(struct brcmf_p2p_info *p2p, } /** - * Change a P2P Role. + * brcmf_p2p_ifchange - Change a P2P Role. * @cfg: driver private data for cfg80211 interface. * @if_type: interface type. * Returns 0 if success. diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c index 16ed325795a8..d1dda851e176 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c @@ -1291,7 +1291,7 @@ static void brcmf_sdio_free_glom(struct brcmf_sdio *bus) } } -/** +/* * brcmfmac sdio bus specific header * This is the lowest layer header wrapped on the packets transmitted between * host and WiFi dongle which contains information needed for SDIO core and From 7ea7a1e05c7ff5ffc9f9ec1f0849f6ceb7fcd57c Mon Sep 17 00:00:00 2001 From: Tong Tiangen Date: Tue, 1 Jun 2021 18:01:28 +0800 Subject: [PATCH 51/91] brcmfmac: Fix a double-free in brcmf_sdio_bus_reset brcmf_sdiod_remove has been called inside brcmf_sdiod_probe when fails, so there's no need to call another one. Otherwise, sdiodev->freezer would be double freed. Fixes: 7836102a750a ("brcmfmac: reset SDIO bus on a firmware crash") Signed-off-by: Tong Tiangen Reviewed-by: Arend van Spriel Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210601100128.69561-1-tongtiangen@huawei.com --- drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c index d1dda851e176..27eb83ee2dc9 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c @@ -4162,7 +4162,6 @@ static int brcmf_sdio_bus_reset(struct device *dev) if (ret) { brcmf_err("Failed to probe after sdio device reset: ret %d\n", ret); - brcmf_sdiod_remove(sdiodev); } return ret; From 4a26aafe4886a4ec9965171c280ce16df30dc362 Mon Sep 17 00:00:00 2001 From: Matthias Brugger Date: Wed, 2 Jun 2021 16:43:05 +0200 Subject: [PATCH 52/91] brcmfmac: Delete second brcm folder hierarchy BRCMF_FW_DEFAULT_PATH already defines the brcm folder, delete the second folder to match with Linux firmware repository layout. Fixes: 75729e110e68 ("brcmfmac: expose firmware config files through modinfo") Signed-off-by: Matthias Brugger Reviewed-by: Hans de Goede Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210602144305.4481-1-matthias.bgg@kernel.org --- drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c index 27eb83ee2dc9..bb77a5987faf 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c @@ -626,8 +626,8 @@ BRCMF_FW_DEF(4373, "brcmfmac4373-sdio"); BRCMF_FW_DEF(43012, "brcmfmac43012-sdio"); /* firmware config files */ -MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH "brcm/brcmfmac*-sdio.*.txt"); -MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH "brcm/brcmfmac*-pcie.*.txt"); +MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH "brcmfmac*-sdio.*.txt"); +MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH "brcmfmac*-pcie.*.txt"); static const struct brcmf_firmware_mapping brcmf_sdio_fwnames[] = { BRCMF_FW_ENTRY(BRCM_CC_43143_CHIP_ID, 0xFFFFFFFF, 43143), From 885f256f61f958d494ffdf5084a292808f08daee Mon Sep 17 00:00:00 2001 From: Matthias Brugger Date: Mon, 7 Jun 2021 12:34:33 +0200 Subject: [PATCH 53/91] brcmfmac: Add clm_blob firmware files to modinfo Cypress Wi-Fi chipsets include information regarding regulatory constraints. These are provided to the driver through "Country Local Matrix" (CLM) blobs. Files present in Linux firmware repository are on a generic world-wide safe version with conservative power settings which is designed to comply with regulatory but may not provide best performance on all boards. Never the less, a better functionality can be expected with the file present, so add it to the modinfo of the driver. Signed-off-by: Matthias Brugger Reviewed-by: Hans de Goede Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210607103433.21022-1-matthias.bgg@kernel.org --- .../wireless/broadcom/brcm80211/brcmfmac/firmware.h | 7 +++++++ .../net/wireless/broadcom/brcm80211/brcmfmac/pcie.c | 4 ++-- .../net/wireless/broadcom/brcm80211/brcmfmac/sdio.c | 12 ++++++------ 3 files changed, 15 insertions(+), 8 deletions(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/firmware.h b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/firmware.h index 46c66415b4a6..e290dec9c53d 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/firmware.h +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/firmware.h @@ -32,6 +32,13 @@ static const char BRCM_ ## fw_name ## _FIRMWARE_BASENAME[] = \ BRCMF_FW_DEFAULT_PATH fw_base; \ MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH fw_base ".bin") +/* Firmware and Country Local Matrix files */ +#define BRCMF_FW_CLM_DEF(fw_name, fw_base) \ +static const char BRCM_ ## fw_name ## _FIRMWARE_BASENAME[] = \ + BRCMF_FW_DEFAULT_PATH fw_base; \ +MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH fw_base ".bin"); \ +MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH fw_base ".clm_blob") + #define BRCMF_FW_ENTRY(chipid, mask, name) \ { chipid, mask, BRCM_ ## name ## _FIRMWARE_BASENAME } diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/pcie.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/pcie.c index 143a705b5cb3..c49dd0c36ae4 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/pcie.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/pcie.c @@ -48,8 +48,8 @@ enum brcmf_pcie_state { BRCMF_FW_DEF(43602, "brcmfmac43602-pcie"); BRCMF_FW_DEF(4350, "brcmfmac4350-pcie"); BRCMF_FW_DEF(4350C, "brcmfmac4350c2-pcie"); -BRCMF_FW_DEF(4356, "brcmfmac4356-pcie"); -BRCMF_FW_DEF(43570, "brcmfmac43570-pcie"); +BRCMF_FW_CLM_DEF(4356, "brcmfmac4356-pcie"); +BRCMF_FW_CLM_DEF(43570, "brcmfmac43570-pcie"); BRCMF_FW_DEF(4358, "brcmfmac4358-pcie"); BRCMF_FW_DEF(4359, "brcmfmac4359-pcie"); BRCMF_FW_DEF(4364, "brcmfmac4364-pcie"); diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c index bb77a5987faf..97ee9e2e2e35 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c @@ -616,14 +616,14 @@ BRCMF_FW_DEF(43362, "brcmfmac43362-sdio"); BRCMF_FW_DEF(4339, "brcmfmac4339-sdio"); BRCMF_FW_DEF(43430A0, "brcmfmac43430a0-sdio"); /* Note the names are not postfixed with a1 for backward compatibility */ -BRCMF_FW_DEF(43430A1, "brcmfmac43430-sdio"); -BRCMF_FW_DEF(43455, "brcmfmac43455-sdio"); +BRCMF_FW_CLM_DEF(43430A1, "brcmfmac43430-sdio"); +BRCMF_FW_CLM_DEF(43455, "brcmfmac43455-sdio"); BRCMF_FW_DEF(43456, "brcmfmac43456-sdio"); -BRCMF_FW_DEF(4354, "brcmfmac4354-sdio"); -BRCMF_FW_DEF(4356, "brcmfmac4356-sdio"); +BRCMF_FW_CLM_DEF(4354, "brcmfmac4354-sdio"); +BRCMF_FW_CLM_DEF(4356, "brcmfmac4356-sdio"); BRCMF_FW_DEF(4359, "brcmfmac4359-sdio"); -BRCMF_FW_DEF(4373, "brcmfmac4373-sdio"); -BRCMF_FW_DEF(43012, "brcmfmac43012-sdio"); +BRCMF_FW_CLM_DEF(4373, "brcmfmac4373-sdio"); +BRCMF_FW_CLM_DEF(43012, "brcmfmac43012-sdio"); /* firmware config files */ MODULE_FIRMWARE(BRCMF_FW_DEFAULT_PATH "brcmfmac*-sdio.*.txt"); From c0277e25d28fc534c09e140c19d5b85f9e7f86fd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=8D=C3=B1igo=20Huguet?= Date: Tue, 11 May 2021 09:02:58 +0200 Subject: [PATCH 54/91] brcmsmac: improve readability on addresses copy MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit A static analyzer identified as a potential bug the copy of 12 bytes from a 6 bytes array to a 6 bytes array. Both arrays are 6 bytes addresses. Although not being a real bug, it is not immediately clear why is done this way: next 6 bytes address, contiguous to the first one, must also be copied to next contiguous 6 bytes address of the destination. Copying each one separately will make both static analyzers and reviewers happier. Signed-off-by: Íñigo Huguet Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511070257.7843-1-ihuguet@redhat.com --- drivers/net/wireless/broadcom/brcm80211/brcmsmac/main.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/main.c b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/main.c index 763e0ec583d7..26de1bd7fee9 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/main.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/main.c @@ -6607,7 +6607,8 @@ brcms_c_d11hdrs_mac80211(struct brcms_c_info *wlc, struct ieee80211_hw *hw, rts->frame_control = cpu_to_le16(IEEE80211_FTYPE_CTL | IEEE80211_STYPE_RTS); - memcpy(&rts->ra, &h->addr1, 2 * ETH_ALEN); + memcpy(&rts->ra, &h->addr1, ETH_ALEN); + memcpy(&rts->ta, &h->addr2, ETH_ALEN); } /* mainrate From 34fe7038a3b33b4b50b1e948e005bf3db20b7a54 Mon Sep 17 00:00:00 2001 From: Guenter Roeck Date: Tue, 11 May 2021 16:56:29 -0700 Subject: [PATCH 55/91] brcmsmac: Drop unnecessary NULL check after container_of The parameter passed to ai_detach() is guaranteed to never be NULL because it is checked by the caller. Consequently, the result of container_of() on it is also never NULL, and a NULL check on it is unnecessary. Even without that, the NULL check would still be unnecessary because the subsequent kfree() can handle NULL arguments. On top of all that, it is misleading to check the result of container_of() against NULL because the position of the contained element could change, which would make the check invalid. Remove it. This change was made automatically with the following Coccinelle script. @@ type t; identifier v; statement s; @@ <+... ( t v = container_of(...); | v = container_of(...); ) ... when != v - if (\( !v \| v == NULL \) ) s ...+> Signed-off-by: Guenter Roeck Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210511235629.1686038-1-linux@roeck-us.net --- drivers/net/wireless/broadcom/brcm80211/brcmsmac/aiutils.c | 3 --- 1 file changed, 3 deletions(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/aiutils.c b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/aiutils.c index 53365977bfd6..2084b506a450 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/aiutils.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/aiutils.c @@ -531,9 +531,6 @@ void ai_detach(struct si_pub *sih) sii = container_of(sih, struct si_info, pub); - if (sii == NULL) - return; - kfree(sii); } From 9a25344d5177c2b9285532236dc3d10a091f39a8 Mon Sep 17 00:00:00 2001 From: Christophe JAILLET Date: Wed, 12 May 2021 22:58:30 +0200 Subject: [PATCH 56/91] brcmsmac: mac80211_if: Fix a resource leak in an error handling path If 'brcms_attach()' fails, we must undo the previous 'ieee80211_alloc_hw()' as already done in the remove function. Fixes: 5b435de0d786 ("net: wireless: add brcm80211 drivers") Signed-off-by: Christophe JAILLET Acked-by: Arend van Spriel Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/8fbc171a1a493b38db5a6f0873c6021fca026a6c.1620852921.git.christophe.jaillet@wanadoo.fr --- .../wireless/broadcom/brcm80211/brcmsmac/mac80211_if.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/mac80211_if.c b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/mac80211_if.c index 39f3af2d0439..eadac0f5590f 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/mac80211_if.c +++ b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/mac80211_if.c @@ -1220,6 +1220,7 @@ static int brcms_bcma_probe(struct bcma_device *pdev) { struct brcms_info *wl; struct ieee80211_hw *hw; + int ret; dev_info(&pdev->dev, "mfg %x core %x rev %d class %d irq %d\n", pdev->id.manuf, pdev->id.id, pdev->id.rev, pdev->id.class, @@ -1244,11 +1245,16 @@ static int brcms_bcma_probe(struct bcma_device *pdev) wl = brcms_attach(pdev); if (!wl) { pr_err("%s: brcms_attach failed!\n", __func__); - return -ENODEV; + ret = -ENODEV; + goto err_free_ieee80211; } brcms_led_register(wl); return 0; + +err_free_ieee80211: + ieee80211_free_hw(hw); + return ret; } static int brcms_suspend(struct bcma_device *pdev) From 5a8e5dae2a22d1580f6d72be54bb57ab29305cc6 Mon Sep 17 00:00:00 2001 From: Shaokun Zhang Date: Mon, 24 May 2021 16:20:43 +0800 Subject: [PATCH 57/91] brcmsmac: Remove the repeated declaration Function 'brcms_c_stf_phy_txant_upd' are declared twice, remove the repeated declaration. Cc: Kalle Valo Signed-off-by: Shaokun Zhang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1621844443-38290-1-git-send-email-zhangshaokun@hisilicon.com --- drivers/net/wireless/broadcom/brcm80211/brcmsmac/stf.h | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/stf.h b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/stf.h index aa4ab53bf634..af86c7fc5112 100644 --- a/drivers/net/wireless/broadcom/brcm80211/brcmsmac/stf.h +++ b/drivers/net/wireless/broadcom/brcm80211/brcmsmac/stf.h @@ -29,7 +29,6 @@ void brcms_c_stf_ss_update(struct brcms_c_info *wlc, struct brcms_band *band); void brcms_c_stf_phy_txant_upd(struct brcms_c_info *wlc); int brcms_c_stf_txchain_set(struct brcms_c_info *wlc, s32 int_val, bool force); bool brcms_c_stf_stbc_rx_set(struct brcms_c_info *wlc, s32 int_val); -void brcms_c_stf_phy_txant_upd(struct brcms_c_info *wlc); void brcms_c_stf_phy_chain_calc(struct brcms_c_info *wlc); u16 brcms_c_stf_phytxchain_sel(struct brcms_c_info *wlc, u32 rspec); u16 brcms_c_stf_d11hdrs_phyctl_txant(struct brcms_c_info *wlc, u32 rspec); From 30657b8ee459f3878647d29799bd13b7cf2c95f9 Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:37 +0800 Subject: [PATCH 58/91] libertas_tf: Fix wrong function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/marvell/libertas_tf/if_usb.c:56: warning: expecting prototype for if_usb_wrike_bulk_callback(). Prototype was for if_usb_write_bulk_callback() instead Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-8-shenyang39@huawei.com --- drivers/net/wireless/marvell/libertas_tf/if_usb.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/marvell/libertas_tf/if_usb.c b/drivers/net/wireless/marvell/libertas_tf/if_usb.c index a92916dc81a9..fe0a69e804d8 100644 --- a/drivers/net/wireless/marvell/libertas_tf/if_usb.c +++ b/drivers/net/wireless/marvell/libertas_tf/if_usb.c @@ -48,7 +48,7 @@ static int if_usb_submit_rx_urb(struct if_usb_card *cardp); static int if_usb_reset_device(struct lbtf_private *priv); /** - * if_usb_wrike_bulk_callback - call back to handle URB status + * if_usb_write_bulk_callback - call back to handle URB status * * @urb: pointer to urb structure */ From 9a0fb9502f0dd4c41e59d6c3390794a81fca2bc3 Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:38 +0800 Subject: [PATCH 59/91] rtlwifi: Fix wrong function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/realtek/rtlwifi/rtl8192cu/mac.c:124: warning: expecting prototype for writeLLT(). Prototype was for rtl92c_llt_write() instead drivers/net/wireless/realtek/rtlwifi/rtl8192cu/mac.c:154: warning: expecting prototype for rtl92c_init_LLT_table(). Prototype was for rtl92c_init_llt_table() instead Cc: Ping-Ke Shih Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-9-shenyang39@huawei.com --- drivers/net/wireless/realtek/rtlwifi/rtl8192cu/mac.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/mac.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/mac.c index 8d2c6d8d32d9..4ff0d4118193 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/mac.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/mac.c @@ -112,7 +112,7 @@ void rtl92c_read_chip_version(struct ieee80211_hw *hw) } /** - * writeLLT - LLT table write access + * rtl92c_llt_write - LLT table write access * @hw: Pointer to the ieee80211_hw structure. * @address: LLT logical address. * @data: LLT data content @@ -144,7 +144,7 @@ bool rtl92c_llt_write(struct ieee80211_hw *hw, u32 address, u32 data) } /** - * rtl92c_init_LLT_table - Init LLT table + * rtl92c_init_llt_table - Init LLT table * @hw: Pointer to the ieee80211_hw structure. * @boundary: Page boundary. * From c707db1b2e7ba62e78998544a257fc68a3c4edd7 Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:39 +0800 Subject: [PATCH 60/91] rsi: Fix missing function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/rsi/rsi_91x_mgmt.c:1550: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst Cc: Amitkumar Karwar Cc: Siva Rebbagondla Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-10-shenyang39@huawei.com --- drivers/net/wireless/rsi/rsi_91x_mgmt.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/rsi/rsi_91x_mgmt.c b/drivers/net/wireless/rsi/rsi_91x_mgmt.c index 33c76d39a8e9..dffe1d6cc592 100644 --- a/drivers/net/wireless/rsi/rsi_91x_mgmt.c +++ b/drivers/net/wireless/rsi/rsi_91x_mgmt.c @@ -1547,8 +1547,8 @@ static int rsi_eeprom_read(struct rsi_common *common) } /** - * This function sends a frame to block/unblock - * data queues in the firmware + * rsi_send_block_unblock_frame() - This function sends a frame to block/unblock + * data queues in the firmware * * @common: Pointer to the driver private structure. * @block_event: Event block if true, unblock if false From c3b67ea3d97a5e08f7ccb0e2c90b0913b92c01cc Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:41 +0800 Subject: [PATCH 61/91] wlcore: Fix missing function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/ti/wlcore/cmd.c:824: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/ti/wlcore/cmd.c:853: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/ti/wlcore/cmd.c:882: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-12-shenyang39@huawei.com --- drivers/net/wireless/ti/wlcore/cmd.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/net/wireless/ti/wlcore/cmd.c b/drivers/net/wireless/ti/wlcore/cmd.c index 32a2e27cc561..8b798b5fcaf5 100644 --- a/drivers/net/wireless/ti/wlcore/cmd.c +++ b/drivers/net/wireless/ti/wlcore/cmd.c @@ -821,7 +821,7 @@ int wl12xx_cmd_role_start_ibss(struct wl1271 *wl, struct wl12xx_vif *wlvif) /** - * send test command to firmware + * wl1271_cmd_test - send test command to firmware * * @wl: wl struct * @buf: buffer containing the command, with all headers, must work with dma @@ -850,7 +850,7 @@ int wl1271_cmd_test(struct wl1271 *wl, void *buf, size_t buf_len, u8 answer) EXPORT_SYMBOL_GPL(wl1271_cmd_test); /** - * read acx from firmware + * wl1271_cmd_interrogate - read acx from firmware * * @wl: wl struct * @id: acx id @@ -879,7 +879,7 @@ int wl1271_cmd_interrogate(struct wl1271 *wl, u16 id, void *buf, } /** - * write acx value to firmware + * wlcore_cmd_configure_failsafe - write acx value to firmware * * @wl: wl struct * @id: acx id From bd65fe550973b8fafea9b06aa7435931ad13ae27 Mon Sep 17 00:00:00 2001 From: Hui Tang Date: Wed, 19 May 2021 14:55:43 +0800 Subject: [PATCH 62/91] libertas: remove leading spaces before tabs There are a few leading spaces before tabs and remove it by running the following commard: $ find . -name '*.c' | xargs sed -r -i 's/^[ ]+\t/\t/' $ find . -name '*.h' | xargs sed -r -i 's/^[ ]+\t/\t/' Cc: Ganapathi Bhat Signed-off-by: Hui Tang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1621407345-10625-2-git-send-email-tanghui20@huawei.com --- drivers/net/wireless/marvell/libertas/main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/marvell/libertas/main.c b/drivers/net/wireless/marvell/libertas/main.c index ee4cf3437e28..64fc5e410864 100644 --- a/drivers/net/wireless/marvell/libertas/main.c +++ b/drivers/net/wireless/marvell/libertas/main.c @@ -941,7 +941,7 @@ struct lbs_private *lbs_add_card(void *card, struct device *dmdev) wdev->netdev = dev; priv->dev = dev; - dev->netdev_ops = &lbs_netdev_ops; + dev->netdev_ops = &lbs_netdev_ops; dev->watchdog_timeo = 5 * HZ; dev->ethtool_ops = &lbs_ethtool_ops; dev->flags |= IFF_BROADCAST | IFF_MULTICAST; From 084eb606dbcfe363f228d27d211cfcdd69bc0f2f Mon Sep 17 00:00:00 2001 From: Hui Tang Date: Wed, 19 May 2021 14:55:44 +0800 Subject: [PATCH 63/91] rt2x00: remove leading spaces before tabs There are a few leading spaces before tabs and remove it by running the following commard: $ find . -name '*.c' | xargs sed -r -i 's/^[ ]+\t/\t/' $ find . -name '*.h' | xargs sed -r -i 's/^[ ]+\t/\t/' Cc: Stanislaw Gruszka Signed-off-by: Hui Tang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1621407345-10625-3-git-send-email-tanghui20@huawei.com --- drivers/net/wireless/ralink/rt2x00/rt2800lib.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/ralink/rt2x00/rt2800lib.c b/drivers/net/wireless/ralink/rt2x00/rt2800lib.c index 5264b0a1f098..deddb0afd312 100644 --- a/drivers/net/wireless/ralink/rt2x00/rt2800lib.c +++ b/drivers/net/wireless/ralink/rt2x00/rt2800lib.c @@ -1037,7 +1037,7 @@ void rt2800_txdone_entry(struct queue_entry *entry, u32 status, __le32 *txwi, * FIXME: if we do not find matching entry, we tell that frame was * posted without any retries. We need to find a way to fix that * and provide retry count. - */ + */ if (unlikely((aggr == 1 && ampdu == 0 && real_mcs != mcs)) || !match) { rt2800_rate_from_status(skbdesc, status, rt2x00dev->curr_band); mcs = real_mcs; From 7b7362ba27a23a9042e2423407e6ce16d388aba0 Mon Sep 17 00:00:00 2001 From: Hui Tang Date: Wed, 19 May 2021 14:55:45 +0800 Subject: [PATCH 64/91] wlcore: remove leading spaces before tabs There are a few leading spaces before tabs and remove it by running the following commard: $ find . -name '*.c' | xargs sed -r -i 's/^[ ]+\t/\t/' $ find . -name '*.h' | xargs sed -r -i 's/^[ ]+\t/\t/' Cc: Tony Lindgren Signed-off-by: Hui Tang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1621407345-10625-4-git-send-email-tanghui20@huawei.com --- drivers/net/wireless/ti/wlcore/main.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/ti/wlcore/main.c b/drivers/net/wireless/ti/wlcore/main.c index 8509b989940c..e500b8405f8f 100644 --- a/drivers/net/wireless/ti/wlcore/main.c +++ b/drivers/net/wireless/ti/wlcore/main.c @@ -3242,8 +3242,8 @@ static void wl1271_op_configure_filter(struct ieee80211_hw *hw, * the firmware filters so that all multicast packets are passed * This is mandatory for MDNS based discovery protocols */ - if (wlvif->bss_type == BSS_TYPE_AP_BSS) { - if (*total & FIF_ALLMULTI) { + if (wlvif->bss_type == BSS_TYPE_AP_BSS) { + if (*total & FIF_ALLMULTI) { ret = wl1271_acx_group_address_tbl(wl, wlvif, false, NULL, 0); From ad4d74cd81779e8f33e7365ae98280835604e905 Mon Sep 17 00:00:00 2001 From: zuoqilin Date: Fri, 23 Apr 2021 17:49:40 +0800 Subject: [PATCH 65/91] rndis_wlan: simplify is_associated() It is not necessary to define the variable ret to receive the return value of the get_bssid() method. Signed-off-by: zuoqilin Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210423094940.1593-1-zuoqilin1@163.com --- drivers/net/wireless/rndis_wlan.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/drivers/net/wireless/rndis_wlan.c b/drivers/net/wireless/rndis_wlan.c index 9fe77556858e..63ce2443f136 100644 --- a/drivers/net/wireless/rndis_wlan.c +++ b/drivers/net/wireless/rndis_wlan.c @@ -1036,14 +1036,11 @@ static bool is_associated(struct usbnet *usbdev) { struct rndis_wlan_private *priv = get_rndis_wlan_priv(usbdev); u8 bssid[ETH_ALEN]; - int ret; if (!priv->radio_on) return false; - ret = get_bssid(usbdev, bssid); - - return (ret == 0 && !is_zero_ether_addr(bssid)); + return (get_bssid(usbdev, bssid) == 0 && !is_zero_ether_addr(bssid)); } static int disassociate(struct usbnet *usbdev, bool reset_ssid) From d4f23164cff08de41abfd95ad8610b94137cdf9c Mon Sep 17 00:00:00 2001 From: Tudor Ambarus Date: Wed, 28 Apr 2021 05:54:45 +0300 Subject: [PATCH 66/91] wilc1000: Fix clock name binding Documentation/devicetree/bindings/net/wireless/microchip,wilc1000.yaml requires an "rtc" clock name. drivers/net/wireless/microchip/wilc1000/sdio.c is using "rtc" clock name as well. Comply with the binding in wilc1000/spi.c too. Fixes: 854d66df74ae ("staging: wilc1000: look for rtc_clk clock in spi mode") Signed-off-by: Tudor Ambarus Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210428025445.81953-1-tudor.ambarus@microchip.com --- drivers/net/wireless/microchip/wilc1000/spi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/microchip/wilc1000/spi.c b/drivers/net/wireless/microchip/wilc1000/spi.c index 1472e9843896..8e9aaf03a6fa 100644 --- a/drivers/net/wireless/microchip/wilc1000/spi.c +++ b/drivers/net/wireless/microchip/wilc1000/spi.c @@ -164,7 +164,7 @@ static int wilc_bus_probe(struct spi_device *spi) wilc->bus_data = spi_priv; wilc->dev_irq_num = spi->irq; - wilc->rtc_clk = devm_clk_get(&spi->dev, "rtc_clk"); + wilc->rtc_clk = devm_clk_get(&spi->dev, "rtc"); if (PTR_ERR_OR_ZERO(wilc->rtc_clk) == -EPROBE_DEFER) { kfree(spi_priv); return -EPROBE_DEFER; From d10a87a3535cce2b890897914f5d0d83df669c63 Mon Sep 17 00:00:00 2001 From: Lee Gibson Date: Wed, 28 Apr 2021 12:55:08 +0100 Subject: [PATCH 67/91] wl1251: Fix possible buffer overflow in wl1251_cmd_scan Function wl1251_cmd_scan calls memcpy without checking the length. Harden by checking the length is within the maximum allowed size. Signed-off-by: Lee Gibson Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210428115508.25624-1-leegib@gmail.com --- drivers/net/wireless/ti/wl1251/cmd.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/drivers/net/wireless/ti/wl1251/cmd.c b/drivers/net/wireless/ti/wl1251/cmd.c index 498c8db2eb48..d7a869106782 100644 --- a/drivers/net/wireless/ti/wl1251/cmd.c +++ b/drivers/net/wireless/ti/wl1251/cmd.c @@ -454,9 +454,12 @@ int wl1251_cmd_scan(struct wl1251 *wl, u8 *ssid, size_t ssid_len, cmd->channels[i].channel = channels[i]->hw_value; } - cmd->params.ssid_len = ssid_len; - if (ssid) - memcpy(cmd->params.ssid, ssid, ssid_len); + if (ssid) { + int len = clamp_val(ssid_len, 0, IEEE80211_MAX_SSID_LEN); + + cmd->params.ssid_len = len; + memcpy(cmd->params.ssid, ssid, len); + } ret = wl1251_cmd_send(wl, CMD_SCAN, cmd, sizeof(*cmd)); if (ret < 0) { From 7af305a1245a7ceff2d8577e011d0a0f7cc33e4c Mon Sep 17 00:00:00 2001 From: Stanislaw Gruszka Date: Tue, 4 May 2021 10:12:20 +0200 Subject: [PATCH 68/91] rt2x00: do not set timestamp for injected frames We setup hardware to insert TSF timestamp for beacon and probe response frames. This is undesired for injected frames, which might want to set their own timestamp values, so disable this setting for injected frames. Tested-by: ZeroBeat Tested-by: n0w1re Signed-off-by: Stanislaw Gruszka Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210504081220.666939-1-stf_xl@wp.pl --- drivers/net/wireless/ralink/rt2x00/rt2x00queue.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/ralink/rt2x00/rt2x00queue.c b/drivers/net/wireless/ralink/rt2x00/rt2x00queue.c index d4d389e8f1b4..fb1d31b2d52a 100644 --- a/drivers/net/wireless/ralink/rt2x00/rt2x00queue.c +++ b/drivers/net/wireless/ralink/rt2x00/rt2x00queue.c @@ -446,8 +446,9 @@ static void rt2x00queue_create_tx_descriptor(struct rt2x00_dev *rt2x00dev, * Beacons and probe responses require the tsf timestamp * to be inserted into the frame. */ - if (ieee80211_is_beacon(hdr->frame_control) || - ieee80211_is_probe_resp(hdr->frame_control)) + if ((ieee80211_is_beacon(hdr->frame_control) || + ieee80211_is_probe_resp(hdr->frame_control)) && + !(tx_info->flags & IEEE80211_TX_CTL_INJECTED)) __set_bit(ENTRY_TXD_REQ_TIMESTAMP, &txdesc->flags); if ((tx_info->flags & IEEE80211_TX_CTL_FIRST_FRAGMENT) && From 924599d407928b91cb22d9274a347bb90f6f6129 Mon Sep 17 00:00:00 2001 From: Ping-Ke Shih Date: Thu, 6 May 2021 09:37:38 +0800 Subject: [PATCH 69/91] rtlwifi: 8821a: btcoexist: add comments to explain why if-else branches are identical The coexistence programmers preserve the same code of branches intentionally to fine tune performance easier, because bandwidth and RSSI strength are highly related to coexistence performance. The basic rule of performance tuning is to assign most time slot to BT for realtime application, and WiFi uses remaining time slot but don't lower than low bound. Reported-by: Inigo Huguet Signed-off-by: Ping-Ke Shih Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210506013738.5943-1-pkshih@realtek.com --- .../net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c b/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c index 447caa4aad32..b998a0eb5f09 100644 --- a/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c +++ b/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c @@ -2810,6 +2810,7 @@ static void btc8821a2ant_action_a2dp(struct btc_coexist *btcoexist) 0x4); } + /* preserve identical branches for further fine-tuning */ if ((bt_rssi_state == BTC_RSSI_STATE_HIGH) || (bt_rssi_state == BTC_RSSI_STATE_STAY_HIGH)) { btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 23); @@ -2944,6 +2945,7 @@ static void btc8821a2ant_action_pan_edr(struct btc_coexist *btcoexist) 0x4); } + /* preserve identical branches for further fine-tuning */ if ((bt_rssi_state == BTC_RSSI_STATE_HIGH) || (bt_rssi_state == BTC_RSSI_STATE_STAY_HIGH)) btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 26); @@ -3132,6 +3134,7 @@ static void btc8821a2ant_action_pan_edr_hid(struct btc_coexist *btcoexist) btcoexist->btc_get(btcoexist, BTC_GET_U4_WIFI_BW, &wifi_bw); + /* preserve identical branches for further fine-tuning */ if (wifi_bw == BTC_WIFI_BW_LEGACY) { /* for HID at 11b/g mode */ btc8821a2ant_coex_table(btcoexist, NORMAL_EXEC, 0x55ff55ff, @@ -3321,6 +3324,7 @@ static void btc8821a2ant_action_hid_a2dp(struct btc_coexist *btcoexist) 0x4); } + /* preserve identical branches for further fine-tuning */ if ((bt_rssi_state == BTC_RSSI_STATE_HIGH) || (bt_rssi_state == BTC_RSSI_STATE_STAY_HIGH)) { btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 23); From 29d97219f4035185f229769313021e350972768b Mon Sep 17 00:00:00 2001 From: Saurav Girepunje Date: Thu, 6 May 2021 10:18:38 +0530 Subject: [PATCH 70/91] zd1211rw: Prefer pr_err over printk error msg In zd_usb.c usb_init we can prefer pr_err() over printk KERN_ERR log level. Signed-off-by: Saurav Girepunje Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210506044838.GA7260@user --- drivers/net/wireless/zydas/zd1211rw/zd_usb.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_usb.c b/drivers/net/wireless/zydas/zd1211rw/zd_usb.c index 5c4cd0e1adeb..a7ceef10bf6a 100644 --- a/drivers/net/wireless/zydas/zd1211rw/zd_usb.c +++ b/drivers/net/wireless/zydas/zd1211rw/zd_usb.c @@ -1544,14 +1544,14 @@ static int __init usb_init(void) zd_workqueue = create_singlethread_workqueue(driver.name); if (zd_workqueue == NULL) { - printk(KERN_ERR "%s couldn't create workqueue\n", driver.name); + pr_err("%s couldn't create workqueue\n", driver.name); return -ENOMEM; } r = usb_register(&driver); if (r) { destroy_workqueue(zd_workqueue); - printk(KERN_ERR "%s usb_register() failed. Error number %d\n", + pr_err("%s usb_register() failed. Error number %d\n", driver.name, r); return r; } From b1c3a24897bd528f2f4fda9fea7da08a84ae25b6 Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Fri, 7 May 2021 23:31:05 +0200 Subject: [PATCH 71/91] rsi: Assign beacon rate settings to the correct rate_info descriptor field The RSI_RATE_x bits must be assigned to struct rsi_data_desc rate_info field. The rest of the driver does it correctly, except this one place, so fix it. This is also aligned with the RSI downstream vendor driver. Without this patch, an AP operating at 5 GHz does not transmit any beacons at all, this patch fixes that. Fixes: d26a9559403c ("rsi: add beacon changes for AP mode") Signed-off-by: Marek Vasut Cc: Amitkumar Karwar Cc: Angus Ainslie Cc: David S. Miller Cc: Jakub Kicinski Cc: Kalle Valo Cc: Karun Eagalapati Cc: Martin Kepplinger Cc: Prameela Rani Garnepudi Cc: Sebastian Krzyszkowiak Cc: Siva Rebbagondla Cc: netdev@vger.kernel.org Cc: stable@vger.kernel.org Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210507213105.140138-1-marex@denx.de --- drivers/net/wireless/rsi/rsi_91x_hal.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/rsi/rsi_91x_hal.c b/drivers/net/wireless/rsi/rsi_91x_hal.c index ce9892152f4d..ab837921d9a4 100644 --- a/drivers/net/wireless/rsi/rsi_91x_hal.c +++ b/drivers/net/wireless/rsi/rsi_91x_hal.c @@ -470,9 +470,9 @@ int rsi_prepare_beacon(struct rsi_common *common, struct sk_buff *skb) } if (common->band == NL80211_BAND_2GHZ) - bcn_frm->bbp_info |= cpu_to_le16(RSI_RATE_1); + bcn_frm->rate_info |= cpu_to_le16(RSI_RATE_1); else - bcn_frm->bbp_info |= cpu_to_le16(RSI_RATE_6); + bcn_frm->rate_info |= cpu_to_le16(RSI_RATE_6); if (mac_bcn->data[tim_offset + 2] == 0) bcn_frm->frame_info |= cpu_to_le16(RSI_DATA_DESC_DTIM_BEACON); From 29ca9e6ca5a5f850829c53557bf18912e56da6c9 Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Fri, 7 May 2021 23:31:49 +0200 Subject: [PATCH 72/91] rsi: Add support for changing beacon interval Pick code for changing the beacon interval (e.g. using beacon_int in hostap config) from the downstream RSI driver. Signed-off-by: Marek Vasut Cc: Amitkumar Karwar Cc: Angus Ainslie Cc: David S. Miller Cc: Jakub Kicinski Cc: Kalle Valo Cc: Karun Eagalapati Cc: Martin Kepplinger Cc: Prameela Rani Garnepudi Cc: Sebastian Krzyszkowiak Cc: Siva Rebbagondla Cc: netdev@vger.kernel.org Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210507213149.140192-1-marex@denx.de --- drivers/net/wireless/rsi/rsi_91x_mac80211.c | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/drivers/net/wireless/rsi/rsi_91x_mac80211.c b/drivers/net/wireless/rsi/rsi_91x_mac80211.c index 16025300cddb..d9f1e73293aa 100644 --- a/drivers/net/wireless/rsi/rsi_91x_mac80211.c +++ b/drivers/net/wireless/rsi/rsi_91x_mac80211.c @@ -837,6 +837,23 @@ static void rsi_mac80211_bss_info_changed(struct ieee80211_hw *hw, common->cqm_info.rssi_hyst); } + if (changed & BSS_CHANGED_BEACON_INT) { + rsi_dbg(INFO_ZONE, "%s: Changed Beacon interval: %d\n", + __func__, bss_conf->beacon_int); + if (common->beacon_interval != bss->beacon_int) { + common->beacon_interval = bss->beacon_int; + if (vif->type == NL80211_IFTYPE_AP) { + struct vif_priv *vif_info = (struct vif_priv *)vif->drv_priv; + + rsi_set_vap_capabilities(common, RSI_OPMODE_AP, + vif->addr, vif_info->vap_id, + VAP_UPDATE); + } + } + adapter->ps_info.listen_interval = + bss->beacon_int * adapter->ps_info.num_bcns_per_lis_int; + } + if ((changed & BSS_CHANGED_BEACON_ENABLED) && ((vif->type == NL80211_IFTYPE_AP) || (vif->type == NL80211_IFTYPE_P2P_GO))) { From d56b69c4fbc7fc85d1a232967ff72c99c3ea2b95 Mon Sep 17 00:00:00 2001 From: Zhen Lei Date: Mon, 10 May 2021 16:22:37 +0800 Subject: [PATCH 73/91] rtlwifi: btcoex: 21a 2ant: Delete several duplicate condition branch codes The statements of the "if (max_interval == 3)" branch are the same as those of the "else" branch. Delete them to simplify the code. No functional change. Signed-off-by: Zhen Lei Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210510082237.3315-1-thunder.leizhen@huawei.com --- .../realtek/rtlwifi/btcoexist/halbtc8821a2ant.c | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c b/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c index b998a0eb5f09..c5b8df58d4a2 100644 --- a/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c +++ b/drivers/net/wireless/realtek/rtlwifi/btcoexist/halbtc8821a2ant.c @@ -1721,10 +1721,6 @@ static void btc8821a2ant_tdma_duration_adjust(struct btc_coexist *btcoexist, btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 14); coex_dm->ps_tdma_du_adj_type = 14; - } else if (max_interval == 3) { - btc8821a2ant_ps_tdma(btcoexist, - NORMAL_EXEC, true, 15); - coex_dm->ps_tdma_du_adj_type = 15; } else { btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 15); @@ -1739,10 +1735,6 @@ static void btc8821a2ant_tdma_duration_adjust(struct btc_coexist *btcoexist, btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 10); coex_dm->ps_tdma_du_adj_type = 10; - } else if (max_interval == 3) { - btc8821a2ant_ps_tdma(btcoexist, - NORMAL_EXEC, true, 11); - coex_dm->ps_tdma_du_adj_type = 11; } else { btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 11); @@ -1759,10 +1751,6 @@ static void btc8821a2ant_tdma_duration_adjust(struct btc_coexist *btcoexist, btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 6); coex_dm->ps_tdma_du_adj_type = 6; - } else if (max_interval == 3) { - btc8821a2ant_ps_tdma(btcoexist, - NORMAL_EXEC, true, 7); - coex_dm->ps_tdma_du_adj_type = 7; } else { btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 7); @@ -1777,10 +1765,6 @@ static void btc8821a2ant_tdma_duration_adjust(struct btc_coexist *btcoexist, btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 2); coex_dm->ps_tdma_du_adj_type = 2; - } else if (max_interval == 3) { - btc8821a2ant_ps_tdma(btcoexist, - NORMAL_EXEC, true, 3); - coex_dm->ps_tdma_du_adj_type = 3; } else { btc8821a2ant_ps_tdma(btcoexist, NORMAL_EXEC, true, 3); From dd778f89225cd258e8f0fed2b7256124982c8bb5 Mon Sep 17 00:00:00 2001 From: Zou Wei Date: Wed, 12 May 2021 11:05:14 +0800 Subject: [PATCH 74/91] cw1200: add missing MODULE_DEVICE_TABLE This patch adds missing MODULE_DEVICE_TABLE definition which generates correct modalias for automatic loading of this driver when it is built as an external module. Reported-by: Hulk Robot Signed-off-by: Zou Wei Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1620788714-14300-1-git-send-email-zou_wei@huawei.com --- drivers/net/wireless/st/cw1200/cw1200_sdio.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/wireless/st/cw1200/cw1200_sdio.c b/drivers/net/wireless/st/cw1200/cw1200_sdio.c index b65ec14136c7..4c30b5772ce0 100644 --- a/drivers/net/wireless/st/cw1200/cw1200_sdio.c +++ b/drivers/net/wireless/st/cw1200/cw1200_sdio.c @@ -53,6 +53,7 @@ static const struct sdio_device_id cw1200_sdio_ids[] = { { SDIO_DEVICE(SDIO_VENDOR_ID_STE, SDIO_DEVICE_ID_STE_CW1200) }, { /* end: all zeroes */ }, }; +MODULE_DEVICE_TABLE(sdio, cw1200_sdio_ids); /* hwbus_ops implemetation */ From c362dd84013e53ce354a8069d0795280c683450c Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:40 +0800 Subject: [PATCH 75/91] wl1251: Fix missing function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/ti/wl1251/cmd.c:15: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/ti/wl1251/cmd.c:62: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/ti/wl1251/cmd.c:103: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/ti/wl1251/cmd.c:141: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-11-shenyang39@huawei.com --- drivers/net/wireless/ti/wl1251/cmd.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/net/wireless/ti/wl1251/cmd.c b/drivers/net/wireless/ti/wl1251/cmd.c index d7a869106782..c3be81dc7970 100644 --- a/drivers/net/wireless/ti/wl1251/cmd.c +++ b/drivers/net/wireless/ti/wl1251/cmd.c @@ -12,7 +12,7 @@ #include "acx.h" /** - * send command to firmware + * wl1251_cmd_send - Send command to firmware * * @wl: wl struct * @id: command id @@ -59,7 +59,7 @@ int wl1251_cmd_send(struct wl1251 *wl, u16 id, void *buf, size_t len) } /** - * send test command to firmware + * wl1251_cmd_test - Send test command to firmware * * @wl: wl struct * @buf: buffer containing the command, with all headers, must work with dma @@ -100,7 +100,7 @@ int wl1251_cmd_test(struct wl1251 *wl, void *buf, size_t buf_len, u8 answer) } /** - * read acx from firmware + * wl1251_cmd_interrogate - Read acx from firmware * * @wl: wl struct * @id: acx id @@ -138,7 +138,7 @@ int wl1251_cmd_interrogate(struct wl1251 *wl, u16 id, void *buf, size_t len) } /** - * write acx value to firmware + * wl1251_cmd_configure - Write acx value to firmware * * @wl: wl struct * @id: acx id From 03a1b938cf39469da4f27b48cb47fa7b3a2f440c Mon Sep 17 00:00:00 2001 From: Colin Ian King Date: Thu, 13 May 2021 13:24:09 +0100 Subject: [PATCH 76/91] rtlwifi: rtl8723ae: remove redundant initialization of variable rtstatus The variable rtstatus is being initialized with a value that is never read, it is being updated later on. The assignment is redundant and can be removed. Addresses-Coverity: ("Unused value") Signed-off-by: Colin Ian King Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210513122410.59204-1-colin.king@canonical.com --- drivers/net/wireless/realtek/rtlwifi/rtl8723ae/hw.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8723ae/hw.c b/drivers/net/wireless/realtek/rtlwifi/rtl8723ae/hw.c index f8a1de6e9849..c98f2216734f 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8723ae/hw.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8723ae/hw.c @@ -915,7 +915,7 @@ int rtl8723e_hw_init(struct ieee80211_hw *hw) struct rtl_phy *rtlphy = &(rtlpriv->phy); struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw)); struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw)); - bool rtstatus = true; + bool rtstatus; int err; u8 tmp_u1b; unsigned long flags; From a99086057e031a88474a7432c7ed0800a3943e84 Mon Sep 17 00:00:00 2001 From: Yang Li Date: Tue, 18 May 2021 09:59:59 +0800 Subject: [PATCH 77/91] rtlwifi: Remove redundant assignments to ul_enc_algo Variable ul_enc_algo is being initialized with a value that is never read, it is being set again in the following switch statements in all of the case and default paths. Hence the unitialization is redundant and can be removed. Clean up clang warning: drivers/net/wireless/realtek/rtlwifi/cam.c:170:6: warning: Value stored to 'ul_enc_algo' during its initialization is never read [clang-analyzer-deadcode.DeadStores] Reported-by: Abaci Robot Signed-off-by: Yang Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1621303199-1542-1-git-send-email-yang.lee@linux.alibaba.com --- drivers/net/wireless/realtek/rtlwifi/cam.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/realtek/rtlwifi/cam.c b/drivers/net/wireless/realtek/rtlwifi/cam.c index 7aa28da39409..7a0355dc6bab 100644 --- a/drivers/net/wireless/realtek/rtlwifi/cam.c +++ b/drivers/net/wireless/realtek/rtlwifi/cam.c @@ -167,7 +167,7 @@ void rtl_cam_mark_invalid(struct ieee80211_hw *hw, u8 uc_index) u32 ul_command; u32 ul_content; - u32 ul_enc_algo = rtlpriv->cfg->maps[SEC_CAM_AES]; + u32 ul_enc_algo; switch (rtlpriv->sec.pairwise_enc_algorithm) { case WEP40_ENCRYPTION: From 03611cc526f9d4854dcd7cf3b7d17f5544d967e8 Mon Sep 17 00:00:00 2001 From: Ding Senjie Date: Fri, 21 May 2021 14:27:34 +0800 Subject: [PATCH 78/91] rtlwifi: Fix spelling of 'download' downlaod -> download Signed-off-by: Ding Senjie Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210521062734.21284-1-dingsenjie@163.com --- drivers/net/wireless/realtek/rtlwifi/rtl8192se/trx.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192se/trx.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192se/trx.c index 38034102aacb..e474b4ec17f3 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192se/trx.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192se/trx.c @@ -513,7 +513,7 @@ void rtl92se_tx_fill_cmddesc(struct ieee80211_hw *hw, u8 *pdesc8, /* This bit indicate this packet is used for FW download. */ if (tcb_desc->cmd_or_init == DESC_PACKET_TYPE_INIT) { - /* For firmware downlaod we only need to set LINIP */ + /* For firmware download we only need to set LINIP */ set_tx_desc_linip(pdesc, tcb_desc->last_inipkt); /* 92SE must set as 1 for firmware download HW DMA error */ From 3f60f4685699aa6006e58e424637e8e413e0a94d Mon Sep 17 00:00:00 2001 From: Hang Zhang Date: Fri, 21 May 2021 15:32:38 -0700 Subject: [PATCH 79/91] cw1200: Revert unnecessary patches that fix unreal use-after-free bugs A previous commit 4f68ef64cd7f ("cw1200: Fix concurrency use-after-free bugs in cw1200_hw_scan()") tried to fix a seemingly use-after-free bug between cw1200_bss_info_changed() and cw1200_hw_scan(), where the former frees a sk_buff pointed to by frame.skb, and the latter accesses the sk_buff pointed to by frame.skb. However, this issue should be a false alarm because: (1) "frame.skb" is not a shared variable between the above two functions, because "frame" is a local function variable, each of the two functions has its own local "frame" - they just happen to have the same variable name. (2) the sk_buff(s) pointed to by these two "frame.skb" are also two different object instances, they are individually allocated by different dev_alloc_skb() within the two above functions. To free one object instance will not invalidate the access of another different one. Based on these facts, the previous commit should be unnecessary. Moreover, it also introduced a missing unlock which was addressed in a subsequent commit 51c8d24101c7 ("cw1200: fix missing unlock on error in cw1200_hw_scan()"). Now that the original use-after-free is unreal, these two commits should be reverted. This patch performs the reversion. Fixes: 4f68ef64cd7f ("cw1200: Fix concurrency use-after-free bugs in cw1200_hw_scan()") Fixes: 51c8d24101c7 ("cw1200: fix missing unlock on error in cw1200_hw_scan()") Signed-off-by: Hang Zhang Acked-by: Jia-Ju Bai Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210521223238.25020-1-zh.nvgt@gmail.com --- drivers/net/wireless/st/cw1200/scan.c | 17 +++++++---------- 1 file changed, 7 insertions(+), 10 deletions(-) diff --git a/drivers/net/wireless/st/cw1200/scan.c b/drivers/net/wireless/st/cw1200/scan.c index 988581cc134b..1f856fbbc0ea 100644 --- a/drivers/net/wireless/st/cw1200/scan.c +++ b/drivers/net/wireless/st/cw1200/scan.c @@ -75,30 +75,27 @@ int cw1200_hw_scan(struct ieee80211_hw *hw, if (req->n_ssids > WSM_SCAN_MAX_NUM_OF_SSIDS) return -EINVAL; - /* will be unlocked in cw1200_scan_work() */ - down(&priv->scan.lock); - mutex_lock(&priv->conf_mutex); - frame.skb = ieee80211_probereq_get(hw, priv->vif->addr, NULL, 0, req->ie_len); - if (!frame.skb) { - mutex_unlock(&priv->conf_mutex); - up(&priv->scan.lock); + if (!frame.skb) return -ENOMEM; - } if (req->ie_len) skb_put_data(frame.skb, req->ie, req->ie_len); + /* will be unlocked in cw1200_scan_work() */ + down(&priv->scan.lock); + mutex_lock(&priv->conf_mutex); + ret = wsm_set_template_frame(priv, &frame); if (!ret) { /* Host want to be the probe responder. */ ret = wsm_set_probe_responder(priv, true); } if (ret) { - dev_kfree_skb(frame.skb); mutex_unlock(&priv->conf_mutex); up(&priv->scan.lock); + dev_kfree_skb(frame.skb); return ret; } @@ -120,8 +117,8 @@ int cw1200_hw_scan(struct ieee80211_hw *hw, ++priv->scan.n_ssids; } - dev_kfree_skb(frame.skb); mutex_unlock(&priv->conf_mutex); + dev_kfree_skb(frame.skb); queue_work(priv->workqueue, &priv->scan.work); return 0; } From 8667ab49a6e0942d64b0dafd30cbf4e0c8b08a8f Mon Sep 17 00:00:00 2001 From: YueHaibing Date: Sun, 23 May 2021 12:03:39 +0800 Subject: [PATCH 80/91] libertas: use DEVICE_ATTR_RW macro Use DEVICE_ATTR_RW helper instead of plain DEVICE_ATTR, which makes the code a bit shorter and easier to read. Signed-off-by: YueHaibing Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210523040339.2724-1-yuehaibing@huawei.com --- drivers/net/wireless/marvell/libertas/mesh.c | 149 ++++++++++--------- 1 file changed, 78 insertions(+), 71 deletions(-) diff --git a/drivers/net/wireless/marvell/libertas/mesh.c b/drivers/net/wireless/marvell/libertas/mesh.c index c68814841583..6cbba84989b8 100644 --- a/drivers/net/wireless/marvell/libertas/mesh.c +++ b/drivers/net/wireless/marvell/libertas/mesh.c @@ -151,13 +151,13 @@ static uint16_t lbs_mesh_get_channel(struct lbs_private *priv) */ /** - * lbs_anycast_get - Get function for sysfs attribute anycast_mask + * anycast_mask_show - Get function for sysfs attribute anycast_mask * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t lbs_anycast_get(struct device *dev, - struct device_attribute *attr, char * buf) +static ssize_t anycast_mask_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; struct cmd_ds_mesh_access mesh_access; @@ -173,14 +173,15 @@ static ssize_t lbs_anycast_get(struct device *dev, } /** - * lbs_anycast_set - Set function for sysfs attribute anycast_mask + * anycast_mask_store - Set function for sysfs attribute anycast_mask * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t lbs_anycast_set(struct device *dev, - struct device_attribute *attr, const char * buf, size_t count) +static ssize_t anycast_mask_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; struct cmd_ds_mesh_access mesh_access; @@ -199,13 +200,13 @@ static ssize_t lbs_anycast_set(struct device *dev, } /** - * lbs_prb_rsp_limit_get - Get function for sysfs attribute prb_rsp_limit + * prb_rsp_limit_show - Get function for sysfs attribute prb_rsp_limit * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t lbs_prb_rsp_limit_get(struct device *dev, - struct device_attribute *attr, char *buf) +static ssize_t prb_rsp_limit_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; struct cmd_ds_mesh_access mesh_access; @@ -225,14 +226,15 @@ static ssize_t lbs_prb_rsp_limit_get(struct device *dev, } /** - * lbs_prb_rsp_limit_set - Set function for sysfs attribute prb_rsp_limit + * prb_rsp_limit_store - Set function for sysfs attribute prb_rsp_limit * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t lbs_prb_rsp_limit_set(struct device *dev, - struct device_attribute *attr, const char *buf, size_t count) +static ssize_t prb_rsp_limit_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; struct cmd_ds_mesh_access mesh_access; @@ -259,27 +261,28 @@ static ssize_t lbs_prb_rsp_limit_set(struct device *dev, } /** - * lbs_mesh_get - Get function for sysfs attribute mesh + * lbs_mesh_show - Get function for sysfs attribute mesh * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t lbs_mesh_get(struct device *dev, - struct device_attribute *attr, char * buf) +static ssize_t lbs_mesh_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; return snprintf(buf, 5, "0x%X\n", !!priv->mesh_dev); } /** - * lbs_mesh_set - Set function for sysfs attribute mesh + * lbs_mesh_store - Set function for sysfs attribute mesh * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t lbs_mesh_set(struct device *dev, - struct device_attribute *attr, const char * buf, size_t count) +static ssize_t lbs_mesh_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; int enable; @@ -301,20 +304,19 @@ static ssize_t lbs_mesh_set(struct device *dev, * lbs_mesh attribute to be exported per ethX interface * through sysfs (/sys/class/net/ethX/lbs_mesh) */ -static DEVICE_ATTR(lbs_mesh, 0644, lbs_mesh_get, lbs_mesh_set); +static DEVICE_ATTR_RW(lbs_mesh); /* * anycast_mask attribute to be exported per mshX interface * through sysfs (/sys/class/net/mshX/anycast_mask) */ -static DEVICE_ATTR(anycast_mask, 0644, lbs_anycast_get, lbs_anycast_set); +static DEVICE_ATTR_RW(anycast_mask); /* * prb_rsp_limit attribute to be exported per mshX interface * through sysfs (/sys/class/net/mshX/prb_rsp_limit) */ -static DEVICE_ATTR(prb_rsp_limit, 0644, lbs_prb_rsp_limit_get, - lbs_prb_rsp_limit_set); +static DEVICE_ATTR_RW(prb_rsp_limit); static struct attribute *lbs_mesh_sysfs_entries[] = { &dev_attr_anycast_mask.attr, @@ -351,13 +353,13 @@ static int mesh_get_default_parameters(struct device *dev, } /** - * bootflag_get - Get function for sysfs attribute bootflag + * bootflag_show - Get function for sysfs attribute bootflag * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t bootflag_get(struct device *dev, - struct device_attribute *attr, char *buf) +static ssize_t bootflag_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct mrvl_mesh_defaults defs; int ret; @@ -371,14 +373,14 @@ static ssize_t bootflag_get(struct device *dev, } /** - * bootflag_set - Set function for sysfs attribute bootflag + * bootflag_store - Set function for sysfs attribute bootflag * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t bootflag_set(struct device *dev, struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t bootflag_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; struct cmd_ds_mesh_config cmd; @@ -401,13 +403,13 @@ static ssize_t bootflag_set(struct device *dev, struct device_attribute *attr, } /** - * boottime_get - Get function for sysfs attribute boottime + * boottime_show - Get function for sysfs attribute boottime * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t boottime_get(struct device *dev, - struct device_attribute *attr, char *buf) +static ssize_t boottime_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct mrvl_mesh_defaults defs; int ret; @@ -421,14 +423,15 @@ static ssize_t boottime_get(struct device *dev, } /** - * boottime_set - Set function for sysfs attribute boottime + * boottime_store - Set function for sysfs attribute boottime * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t boottime_set(struct device *dev, - struct device_attribute *attr, const char *buf, size_t count) +static ssize_t boottime_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; struct cmd_ds_mesh_config cmd; @@ -460,13 +463,13 @@ static ssize_t boottime_set(struct device *dev, } /** - * channel_get - Get function for sysfs attribute channel + * channel_show - Get function for sysfs attribute channel * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t channel_get(struct device *dev, - struct device_attribute *attr, char *buf) +static ssize_t channel_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct mrvl_mesh_defaults defs; int ret; @@ -480,14 +483,14 @@ static ssize_t channel_get(struct device *dev, } /** - * channel_set - Set function for sysfs attribute channel + * channel_store - Set function for sysfs attribute channel * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t channel_set(struct device *dev, struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t channel_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) { struct lbs_private *priv = to_net_dev(dev)->ml_priv; struct cmd_ds_mesh_config cmd; @@ -510,13 +513,13 @@ static ssize_t channel_set(struct device *dev, struct device_attribute *attr, } /** - * mesh_id_get - Get function for sysfs attribute mesh_id + * mesh_id_show - Get function for sysfs attribute mesh_id * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t mesh_id_get(struct device *dev, struct device_attribute *attr, - char *buf) +static ssize_t mesh_id_show(struct device *dev, struct device_attribute *attr, + char *buf) { struct mrvl_mesh_defaults defs; int ret; @@ -539,14 +542,14 @@ static ssize_t mesh_id_get(struct device *dev, struct device_attribute *attr, } /** - * mesh_id_set - Set function for sysfs attribute mesh_id + * mesh_id_store - Set function for sysfs attribute mesh_id * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t mesh_id_set(struct device *dev, struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t mesh_id_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) { struct cmd_ds_mesh_config cmd; struct mrvl_mesh_defaults defs; @@ -585,13 +588,14 @@ static ssize_t mesh_id_set(struct device *dev, struct device_attribute *attr, } /** - * protocol_id_get - Get function for sysfs attribute protocol_id + * protocol_id_show - Get function for sysfs attribute protocol_id * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t protocol_id_get(struct device *dev, - struct device_attribute *attr, char *buf) +static ssize_t protocol_id_show(struct device *dev, + struct device_attribute *attr, + char *buf) { struct mrvl_mesh_defaults defs; int ret; @@ -605,14 +609,15 @@ static ssize_t protocol_id_get(struct device *dev, } /** - * protocol_id_set - Set function for sysfs attribute protocol_id + * protocol_id_store - Set function for sysfs attribute protocol_id * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t protocol_id_set(struct device *dev, - struct device_attribute *attr, const char *buf, size_t count) +static ssize_t protocol_id_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct cmd_ds_mesh_config cmd; struct mrvl_mesh_defaults defs; @@ -646,13 +651,13 @@ static ssize_t protocol_id_set(struct device *dev, } /** - * metric_id_get - Get function for sysfs attribute metric_id + * metric_id_show - Get function for sysfs attribute metric_id * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t metric_id_get(struct device *dev, - struct device_attribute *attr, char *buf) +static ssize_t metric_id_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct mrvl_mesh_defaults defs; int ret; @@ -666,14 +671,15 @@ static ssize_t metric_id_get(struct device *dev, } /** - * metric_id_set - Set function for sysfs attribute metric_id + * metric_id_store - Set function for sysfs attribute metric_id * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t metric_id_set(struct device *dev, struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t metric_id_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct cmd_ds_mesh_config cmd; struct mrvl_mesh_defaults defs; @@ -707,13 +713,13 @@ static ssize_t metric_id_set(struct device *dev, struct device_attribute *attr, } /** - * capability_get - Get function for sysfs attribute capability + * capability_show - Get function for sysfs attribute capability * @dev: the &struct device * @attr: device attributes * @buf: buffer where data will be returned */ -static ssize_t capability_get(struct device *dev, - struct device_attribute *attr, char *buf) +static ssize_t capability_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct mrvl_mesh_defaults defs; int ret; @@ -727,14 +733,15 @@ static ssize_t capability_get(struct device *dev, } /** - * capability_set - Set function for sysfs attribute capability + * capability_store - Set function for sysfs attribute capability * @dev: the &struct device * @attr: device attributes * @buf: buffer that contains new attribute value * @count: size of buffer */ -static ssize_t capability_set(struct device *dev, struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t capability_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) { struct cmd_ds_mesh_config cmd; struct mrvl_mesh_defaults defs; @@ -768,13 +775,13 @@ static ssize_t capability_set(struct device *dev, struct device_attribute *attr, } -static DEVICE_ATTR(bootflag, 0644, bootflag_get, bootflag_set); -static DEVICE_ATTR(boottime, 0644, boottime_get, boottime_set); -static DEVICE_ATTR(channel, 0644, channel_get, channel_set); -static DEVICE_ATTR(mesh_id, 0644, mesh_id_get, mesh_id_set); -static DEVICE_ATTR(protocol_id, 0644, protocol_id_get, protocol_id_set); -static DEVICE_ATTR(metric_id, 0644, metric_id_get, metric_id_set); -static DEVICE_ATTR(capability, 0644, capability_get, capability_set); +static DEVICE_ATTR_RW(bootflag); +static DEVICE_ATTR_RW(boottime); +static DEVICE_ATTR_RW(channel); +static DEVICE_ATTR_RW(mesh_id); +static DEVICE_ATTR_RW(protocol_id); +static DEVICE_ATTR_RW(metric_id); +static DEVICE_ATTR_RW(capability); static struct attribute *boot_opts_attrs[] = { &dev_attr_bootflag.attr, From 314538041b5632ffaf64798faaeabaf2793fe029 Mon Sep 17 00:00:00 2001 From: Martin Fuzzey Date: Tue, 1 Jun 2021 18:19:53 +0200 Subject: [PATCH 81/91] rsi: fix AP mode with WPA failure due to encrypted EAPOL In AP mode WPA2-PSK connections were not established. The reason was that the AP was sending the first message of the 4 way handshake encrypted, even though no pairwise key had (correctly) yet been set. Encryption was enabled if the "security_enable" driver flag was set and encryption was not explicitly disabled by IEEE80211_TX_INTFL_DONT_ENCRYPT. However security_enable was set when *any* key, including the AP GTK key, had been set which was causing unwanted encryption even if no key was avaialble for the unicast packet to be sent. Fix this by adding a check that we have a key and drop the old security_enable driver flag which is insufficient and redundant. The Redpine downstream out of tree driver does it this way too. Regarding the Fixes tag the actual code being modified was introduced earlier, with the original driver submission, in dad0d04fa7ba ("rsi: Add RS9113 wireless driver"), however at that time AP mode was not yet supported so there was no bug at that point. So I have tagged the introduction of AP support instead which was part of the patch set "rsi: support for AP mode" [1] It is not clear whether AP WPA has ever worked, I can see nothing on the kernel side that broke it afterwards yet the AP support patch series says "Tests are performed to confirm aggregation, connections in WEP and WPA/WPA2 security." One possibility is that the initial tests were done with a modified userspace (hostapd). [1] https://www.spinics.net/lists/linux-wireless/msg165302.html Signed-off-by: Martin Fuzzey Fixes: 38ef62353acb ("rsi: security enhancements for AP mode") CC: stable@vger.kernel.org Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1622564459-24430-1-git-send-email-martin.fuzzey@flowbird.group --- drivers/net/wireless/rsi/rsi_91x_hal.c | 2 +- drivers/net/wireless/rsi/rsi_91x_mac80211.c | 3 --- drivers/net/wireless/rsi/rsi_91x_mgmt.c | 3 +-- drivers/net/wireless/rsi/rsi_main.h | 1 - 4 files changed, 2 insertions(+), 7 deletions(-) diff --git a/drivers/net/wireless/rsi/rsi_91x_hal.c b/drivers/net/wireless/rsi/rsi_91x_hal.c index ab837921d9a4..99b21a2c8386 100644 --- a/drivers/net/wireless/rsi/rsi_91x_hal.c +++ b/drivers/net/wireless/rsi/rsi_91x_hal.c @@ -203,7 +203,7 @@ int rsi_prepare_data_desc(struct rsi_common *common, struct sk_buff *skb) wh->frame_control |= cpu_to_le16(RSI_SET_PS_ENABLE); if ((!(info->flags & IEEE80211_TX_INTFL_DONT_ENCRYPT)) && - (common->secinfo.security_enable)) { + info->control.hw_key) { if (rsi_is_cipher_wep(common)) ieee80211_size += 4; else diff --git a/drivers/net/wireless/rsi/rsi_91x_mac80211.c b/drivers/net/wireless/rsi/rsi_91x_mac80211.c index d9f1e73293aa..b66975f54567 100644 --- a/drivers/net/wireless/rsi/rsi_91x_mac80211.c +++ b/drivers/net/wireless/rsi/rsi_91x_mac80211.c @@ -1045,7 +1045,6 @@ static int rsi_mac80211_set_key(struct ieee80211_hw *hw, mutex_lock(&common->mutex); switch (cmd) { case SET_KEY: - secinfo->security_enable = true; status = rsi_hal_key_config(hw, vif, key, sta); if (status) { mutex_unlock(&common->mutex); @@ -1064,8 +1063,6 @@ static int rsi_mac80211_set_key(struct ieee80211_hw *hw, break; case DISABLE_KEY: - if (vif->type == NL80211_IFTYPE_STATION) - secinfo->security_enable = false; rsi_dbg(ERR_ZONE, "%s: RSI del key\n", __func__); memset(key, 0, sizeof(struct ieee80211_key_conf)); status = rsi_hal_key_config(hw, vif, key, sta); diff --git a/drivers/net/wireless/rsi/rsi_91x_mgmt.c b/drivers/net/wireless/rsi/rsi_91x_mgmt.c index dffe1d6cc592..891fd5f0fa76 100644 --- a/drivers/net/wireless/rsi/rsi_91x_mgmt.c +++ b/drivers/net/wireless/rsi/rsi_91x_mgmt.c @@ -1803,8 +1803,7 @@ int rsi_send_wowlan_request(struct rsi_common *common, u16 flags, RSI_WIFI_MGMT_Q); cmd_frame->desc.desc_dword0.frame_type = WOWLAN_CONFIG_PARAMS; cmd_frame->host_sleep_status = sleep_status; - if (common->secinfo.security_enable && - common->secinfo.gtk_cipher) + if (common->secinfo.gtk_cipher) flags |= RSI_WOW_GTK_REKEY; if (sleep_status) cmd_frame->wow_flags = flags; diff --git a/drivers/net/wireless/rsi/rsi_main.h b/drivers/net/wireless/rsi/rsi_main.h index a1065e5a92b4..0f535850a383 100644 --- a/drivers/net/wireless/rsi/rsi_main.h +++ b/drivers/net/wireless/rsi/rsi_main.h @@ -151,7 +151,6 @@ enum edca_queue { }; struct security_info { - bool security_enable; u32 ptk_cipher; u32 gtk_cipher; }; From 3b0c7b2415e52c48d47011c393bab7239fb59250 Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:31 +0800 Subject: [PATCH 82/91] ath5k: Fix wrong function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/ath/ath5k/pcu.c:865: warning: expecting prototype for at5k_hw_stop_rx_pcu(). Prototype was for ath5k_hw_stop_rx_pcu() instead Cc: Jiri Slaby Cc: Nick Kossifidis Cc: Luis Chamberlain Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-2-shenyang39@huawei.com --- drivers/net/wireless/ath/ath5k/pcu.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/ath5k/pcu.c b/drivers/net/wireless/ath/ath5k/pcu.c index f2db7cf16566..3f4ce4e9c532 100644 --- a/drivers/net/wireless/ath/ath5k/pcu.c +++ b/drivers/net/wireless/ath/ath5k/pcu.c @@ -855,7 +855,7 @@ ath5k_hw_start_rx_pcu(struct ath5k_hw *ah) } /** - * at5k_hw_stop_rx_pcu() - Stop RX engine + * ath5k_hw_stop_rx_pcu() - Stop RX engine * @ah: The &struct ath5k_hw * * Stops RX engine on PCU From 2d1f8673ad6c38b3e5de646bf7113948a9145e9e Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:32 +0800 Subject: [PATCH 83/91] ath: Fix wrong function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/ath/hw.c:119: warning: expecting prototype for ath_hw_set_bssid_mask(). Prototype was for ath_hw_setbssidmask() instead Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-3-shenyang39@huawei.com --- drivers/net/wireless/ath/hw.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/hw.c b/drivers/net/wireless/ath/hw.c index eae9abf540a7..b53ebb3ac9a2 100644 --- a/drivers/net/wireless/ath/hw.c +++ b/drivers/net/wireless/ath/hw.c @@ -24,7 +24,7 @@ #define REG_WRITE(_ah, _reg, _val) (common->ops->write)(_ah, _val, _reg) /** - * ath_hw_set_bssid_mask - filter out bssids we listen + * ath_hw_setbssidmask - filter out bssids we listen * * @common: the ath_common struct for the device. * From 9d1bb2289b426c9554eeaf78e52e1dc43671dce7 Mon Sep 17 00:00:00 2001 From: Yang Shen Date: Mon, 17 May 2021 13:01:33 +0800 Subject: [PATCH 84/91] wil6210: Fix wrong function name in comments Fixes the following W=1 kernel build warning(s): drivers/net/wireless/ath/wil6210/interrupt.c:28: warning: expecting prototype for Theory of operation(). Prototype was for WIL6210_IRQ_DISABLE() instead drivers/net/wireless/ath/wil6210/wmi.c:227: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/ath/wil6210/wmi.c:245: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst drivers/net/wireless/ath/wil6210/wmi.c:263: warning: This comment starts with '/**', but isn't a kernel-doc comment. Refer Documentation/doc-guide/kernel-doc.rst Cc: Maya Erez Signed-off-by: Yang Shen Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210517050141.61488-4-shenyang39@huawei.com --- drivers/net/wireless/ath/wil6210/interrupt.c | 2 +- drivers/net/wireless/ath/wil6210/wmi.c | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/net/wireless/ath/wil6210/interrupt.c b/drivers/net/wireless/ath/wil6210/interrupt.c index d13d081fdcc6..67172385a5d6 100644 --- a/drivers/net/wireless/ath/wil6210/interrupt.c +++ b/drivers/net/wireless/ath/wil6210/interrupt.c @@ -9,7 +9,7 @@ #include "wil6210.h" #include "trace.h" -/** +/* * Theory of operation: * * There is ISR pseudo-cause register, diff --git a/drivers/net/wireless/ath/wil6210/wmi.c b/drivers/net/wireless/ath/wil6210/wmi.c index 02ad44997e87..2dc8406736f4 100644 --- a/drivers/net/wireless/ath/wil6210/wmi.c +++ b/drivers/net/wireless/ath/wil6210/wmi.c @@ -224,7 +224,7 @@ struct auth_no_hdr { u8 led_polarity = LED_POLARITY_LOW_ACTIVE; /** - * return AHB address for given firmware internal (linker) address + * wmi_addr_remap - return AHB address for given firmware internal (linker) address * @x: internal address * If address have no valid AHB mapping, return 0 */ @@ -242,7 +242,7 @@ static u32 wmi_addr_remap(u32 x) } /** - * find fw_mapping entry by section name + * wil_find_fw_mapping - find fw_mapping entry by section name * @section: section name * * Return pointer to section or NULL if not found @@ -260,7 +260,7 @@ struct fw_map *wil_find_fw_mapping(const char *section) } /** - * Check address validity for WMI buffer; remap if needed + * wmi_buffer_block - Check address validity for WMI buffer; remap if needed * @wil: driver data * @ptr_: internal (linker) fw/ucode address * @size: if non zero, validate the block does not From 515bda1d1e51c64edf2a384a58801f85a80a3f2d Mon Sep 17 00:00:00 2001 From: Christophe JAILLET Date: Sat, 22 May 2021 11:50:54 +0200 Subject: [PATCH 85/91] ath11k: Fix an error handling path in ath11k_core_fetch_board_data_api_n() All error paths but this one 'goto err' in order to release some resources. Fix this. Fixes: d5c65159f289 ("ath11k: driver for Qualcomm IEEE 802.11ax devices") Signed-off-by: Christophe JAILLET Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/e959eb544f3cb04258507d8e25a6f12eab126bde.1621676864.git.christophe.jaillet@wanadoo.fr --- drivers/net/wireless/ath/ath11k/core.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/ath11k/core.c b/drivers/net/wireless/ath/ath11k/core.c index 4a1051418f33..969bf1a590d9 100644 --- a/drivers/net/wireless/ath/ath11k/core.c +++ b/drivers/net/wireless/ath/ath11k/core.c @@ -532,7 +532,8 @@ static int ath11k_core_fetch_board_data_api_n(struct ath11k_base *ab, if (len < ALIGN(ie_len, 4)) { ath11k_err(ab, "invalid length for board ie_id %d ie_len %zu len %zu\n", ie_id, ie_len, len); - return -EINVAL; + ret = -EINVAL; + goto err; } switch (ie_id) { From e9ca70c735ce66fc6a0e02c8b6958434f74ef8de Mon Sep 17 00:00:00 2001 From: Yang Li Date: Tue, 25 May 2021 18:46:17 +0800 Subject: [PATCH 86/91] ath10k: Fix an error code in ath10k_add_interface() When the code execute this if statement, the value of ret is 0. However, we can see from the ath10k_warn() log that the value of ret should be -EINVAL. Clean up smatch warning: drivers/net/wireless/ath/ath10k/mac.c:5596 ath10k_add_interface() warn: missing error code 'ret' Reported-by: Abaci Robot Fixes: ccec9038c721 ("ath10k: enable raw encap mode and software crypto engine") Signed-off-by: Yang Li Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1621939577-62218-1-git-send-email-yang.lee@linux.alibaba.com --- drivers/net/wireless/ath/ath10k/mac.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/wireless/ath/ath10k/mac.c b/drivers/net/wireless/ath/ath10k/mac.c index 5ce4f8d038b9..c272b290fa73 100644 --- a/drivers/net/wireless/ath/ath10k/mac.c +++ b/drivers/net/wireless/ath/ath10k/mac.c @@ -5592,6 +5592,7 @@ static int ath10k_add_interface(struct ieee80211_hw *hw, if (arvif->nohwcrypt && !test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags)) { + ret = -EINVAL; ath10k_warn(ar, "cryptmode module param needed for sw crypto\n"); goto err; } From a8b1de7f4f68d558fb952e765aa25e90b50a2388 Mon Sep 17 00:00:00 2001 From: Shaokun Zhang Date: Mon, 31 May 2021 16:07:39 +0800 Subject: [PATCH 87/91] ath10k: remove the repeated declaration Functions 'ath10k_pci_free_pipes' and 'ath10k_wmi_alloc_skb' are declared twice in their header file, so remove the repeated declaration. Cc: Kalle Valo Signed-off-by: Shaokun Zhang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1622448459-50805-1-git-send-email-zhangshaokun@hisilicon.com --- drivers/net/wireless/ath/ath10k/pci.h | 1 - drivers/net/wireless/ath/ath10k/wmi.h | 1 - 2 files changed, 2 deletions(-) diff --git a/drivers/net/wireless/ath/ath10k/pci.h b/drivers/net/wireless/ath/ath10k/pci.h index 862d0901c5b8..cf64898b9447 100644 --- a/drivers/net/wireless/ath/ath10k/pci.h +++ b/drivers/net/wireless/ath/ath10k/pci.h @@ -235,7 +235,6 @@ u16 ath10k_pci_hif_get_free_queue_number(struct ath10k *ar, u8 pipe); void ath10k_pci_hif_power_down(struct ath10k *ar); int ath10k_pci_alloc_pipes(struct ath10k *ar); void ath10k_pci_free_pipes(struct ath10k *ar); -void ath10k_pci_free_pipes(struct ath10k *ar); void ath10k_pci_rx_replenish_retry(struct timer_list *t); void ath10k_pci_ce_deinit(struct ath10k *ar); void ath10k_pci_init_napi(struct ath10k *ar); diff --git a/drivers/net/wireless/ath/ath10k/wmi.h b/drivers/net/wireless/ath/ath10k/wmi.h index dd980c81793e..41c1a3d339c2 100644 --- a/drivers/net/wireless/ath/ath10k/wmi.h +++ b/drivers/net/wireless/ath/ath10k/wmi.h @@ -7418,7 +7418,6 @@ int ath10k_wmi_wait_for_unified_ready(struct ath10k *ar); struct sk_buff *ath10k_wmi_alloc_skb(struct ath10k *ar, u32 len); int ath10k_wmi_connect(struct ath10k *ar); -struct sk_buff *ath10k_wmi_alloc_skb(struct ath10k *ar, u32 len); int ath10k_wmi_cmd_send(struct ath10k *ar, struct sk_buff *skb, u32 cmd_id); int ath10k_wmi_cmd_send_nowait(struct ath10k *ar, struct sk_buff *skb, u32 cmd_id); From ea1c2023efbc268f3d96b09e945af9648723d393 Mon Sep 17 00:00:00 2001 From: Yang Yingliang Date: Sat, 5 Jun 2021 19:02:27 +0800 Subject: [PATCH 88/91] ath10k: Use devm_platform_get_and_ioremap_resource() Use devm_platform_get_and_ioremap_resource() to simplify code. Signed-off-by: Yang Yingliang Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210605110227.2429420-1-yangyingliang@huawei.com --- drivers/net/wireless/ath/ath10k/ahb.c | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/drivers/net/wireless/ath/ath10k/ahb.c b/drivers/net/wireless/ath/ath10k/ahb.c index 869524852fba..ab8f77ae5e66 100644 --- a/drivers/net/wireless/ath/ath10k/ahb.c +++ b/drivers/net/wireless/ath/ath10k/ahb.c @@ -442,14 +442,7 @@ static int ath10k_ahb_resource_init(struct ath10k *ar) pdev = ar_ahb->pdev; - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (!res) { - ath10k_err(ar, "failed to get memory resource\n"); - ret = -ENXIO; - goto out; - } - - ar_ahb->mem = devm_ioremap_resource(&pdev->dev, res); + ar_ahb->mem = devm_platform_get_and_ioremap_resource(pdev, 0, &res); if (IS_ERR(ar_ahb->mem)) { ath10k_err(ar, "mem ioremap error\n"); ret = PTR_ERR(ar_ahb->mem); From 979ebc54cf13bd1e3eb6e21766d208d5de984fb8 Mon Sep 17 00:00:00 2001 From: Seevalamuthu Mariappan Date: Tue, 25 May 2021 15:30:28 +0200 Subject: [PATCH 89/91] ath11k: send beacon template after vdev_start/restart during csa Firmware has added assert if beacon template is received after vdev_down. Firmware expects beacon template after vdev_start and before vdev_up. This change is needed to support MBSSID EMA cases in firmware. Hence, Change the sequence in ath11k as expected from firmware. This new change is not causing any issues with older firmware. Tested-on: IPQ8074 hw2.0 AHB WLAN.HK.2.5.0.1.r3-00011-QCAHKSWPL_SILICONZ-1 Tested-on: IPQ8074 hw2.0 AHB WLAN.HK.2.5.0.1.r4-00008-QCAHKSWPL_SILICONZ-1 Fixes: d5c65159f289 ("ath11k: driver for Qualcomm IEEE 802.11ax devices") Signed-off-by: Seevalamuthu Mariappan [sven@narfation.org: added tested-on/fixes information] Signed-off-by: Sven Eckelmann Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210525133028.2805615-1-sven@narfation.org --- drivers/net/wireless/ath/ath11k/mac.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/drivers/net/wireless/ath/ath11k/mac.c b/drivers/net/wireless/ath/ath11k/mac.c index 9d0ff150ec30..eb52332dbe3f 100644 --- a/drivers/net/wireless/ath/ath11k/mac.c +++ b/drivers/net/wireless/ath/ath11k/mac.c @@ -5379,11 +5379,6 @@ ath11k_mac_update_vif_chan(struct ath11k *ar, if (WARN_ON(!arvif->is_up)) continue; - ret = ath11k_mac_setup_bcn_tmpl(arvif); - if (ret) - ath11k_warn(ab, "failed to update bcn tmpl during csa: %d\n", - ret); - ret = ath11k_mac_vdev_restart(arvif, &vifs[i].new_ctx->def); if (ret) { ath11k_warn(ab, "failed to restart vdev %d: %d\n", @@ -5391,6 +5386,11 @@ ath11k_mac_update_vif_chan(struct ath11k *ar, continue; } + ret = ath11k_mac_setup_bcn_tmpl(arvif); + if (ret) + ath11k_warn(ab, "failed to update bcn tmpl during csa: %d\n", + ret); + ret = ath11k_wmi_vdev_up(arvif->ar, arvif->vdev_id, arvif->aid, arvif->bssid); if (ret) { From 75596eabd6e46e5afc31568f6f4e4c0c12a8906c Mon Sep 17 00:00:00 2001 From: Jiapeng Chong Date: Wed, 26 May 2021 18:52:56 +0800 Subject: [PATCH 90/91] ath6kl: Fix inconsistent indenting Eliminate the follow smatch warning: drivers/net/wireless/ath/ath6kl/cfg80211.c:3308 ath6kl_cfg80211_sscan_start() warn: inconsistent indenting. Reported-by: Abaci Robot Signed-off-by: Jiapeng Chong Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/1622026376-68524-1-git-send-email-jiapeng.chong@linux.alibaba.com --- drivers/net/wireless/ath/ath6kl/cfg80211.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/ath/ath6kl/cfg80211.c b/drivers/net/wireless/ath/ath6kl/cfg80211.c index 29527e8dcced..fefdc6753acd 100644 --- a/drivers/net/wireless/ath/ath6kl/cfg80211.c +++ b/drivers/net/wireless/ath/ath6kl/cfg80211.c @@ -3303,8 +3303,8 @@ static int ath6kl_cfg80211_sscan_start(struct wiphy *wiphy, if (ret < 0) return ret; } else { - ret = ath6kl_wmi_bssfilter_cmd(ar->wmi, vif->fw_vif_idx, - MATCHED_SSID_FILTER, 0); + ret = ath6kl_wmi_bssfilter_cmd(ar->wmi, vif->fw_vif_idx, + MATCHED_SSID_FILTER, 0); if (ret < 0) return ret; } From 8f78caa2264ece71c2e207cba023f28ab6665138 Mon Sep 17 00:00:00 2001 From: Johannes Berg Date: Mon, 26 Apr 2021 21:29:30 +0200 Subject: [PATCH 91/91] wil6210: remove erroneous wiphy locking We already hold the wiphy lock in all cases when we get here, so this would deadlock, remove the erroneous locking. Fixes: a05829a7222e ("cfg80211: avoid holding the RTNL when calling the driver") Signed-off-by: Johannes Berg Signed-off-by: Kalle Valo Link: https://lore.kernel.org/r/20210426212929.83f1de07c2cd.I630a2a00eff185ba0452324b3d3f645e01128a95@changeid --- drivers/net/wireless/ath/wil6210/cfg80211.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/drivers/net/wireless/ath/wil6210/cfg80211.c b/drivers/net/wireless/ath/wil6210/cfg80211.c index 6746fd206d2a..1ff2679963f0 100644 --- a/drivers/net/wireless/ath/wil6210/cfg80211.c +++ b/drivers/net/wireless/ath/wil6210/cfg80211.c @@ -2842,9 +2842,7 @@ void wil_p2p_wdev_free(struct wil6210_priv *wil) wil->radio_wdev = wil->main_ndev->ieee80211_ptr; mutex_unlock(&wil->vif_mutex); if (p2p_wdev) { - wiphy_lock(wil->wiphy); cfg80211_unregister_wdev(p2p_wdev); - wiphy_unlock(wil->wiphy); kfree(p2p_wdev); } }