diff options
author | Hauke Mehrtens <hauke@hauke-m.de> | 2019-07-07 00:08:20 +0200 |
---|---|---|
committer | Petr Štetiar <ynezz@true.cz> | 2019-07-18 00:22:04 +0200 |
commit | 0b2c42ced21a7bc053e0d729f85041f1e3b54fbc (patch) | |
tree | 5b461df94bf6d46f2700310b3d27a7b5c39e3728 /package/kernel/mac80211/patches/subsys | |
parent | d616b2c906690d2e471144ca12b0a9ed28de21c2 (diff) | |
download | upstream-0b2c42ced21a7bc053e0d729f85041f1e3b54fbc.tar.gz upstream-0b2c42ced21a7bc053e0d729f85041f1e3b54fbc.tar.bz2 upstream-0b2c42ced21a7bc053e0d729f85041f1e3b54fbc.zip |
mac80211: Update to version 5.2-rc7
This updates mac80211 to version 5.2-rc7, this contains all the changes
to the wireless subsystem up to Linux 5.2-rc7.
* The removed patches are applied upstream
* b43 now uses kmod-lib-cordic
* Update the nl80211.h file in iw to match backports version.
* Remove the two backports from kernel 4.9, they were needed for mt76,
but that can use the version from backports now, otherwise they
collide and cause compile errors.
Signed-off-by: Hauke Mehrtens <hauke@hauke-m.de>
Diffstat (limited to 'package/kernel/mac80211/patches/subsys')
41 files changed, 118 insertions, 4244 deletions
diff --git a/package/kernel/mac80211/patches/subsys/100-remove-cryptoapi-dependencies.patch b/package/kernel/mac80211/patches/subsys/100-remove-cryptoapi-dependencies.patch index 0fe6ee196c..1a13fdc56f 100644 --- a/package/kernel/mac80211/patches/subsys/100-remove-cryptoapi-dependencies.patch +++ b/package/kernel/mac80211/patches/subsys/100-remove-cryptoapi-dependencies.patch @@ -20,17 +20,14 @@ ethtool.o \ --- a/net/mac80211/aead_api.c +++ /dev/null -@@ -1,115 +0,0 @@ +@@ -1,112 +0,0 @@ +-// SPDX-License-Identifier: GPL-2.0-only -/* - * Copyright 2003-2004, Instant802 Networks, Inc. - * Copyright 2005-2006, Devicescape Software, Inc. - * Copyright 2014-2015, Qualcomm Atheros, Inc. - * - * Rewrite: Copyright (C) 2013 Linaro Ltd <ard.biesheuvel@linaro.org> -- * -- * This program is free software; you can redistribute it and/or modify -- * it under the terms of the GNU General Public License version 2 as -- * published by the Free Software Foundation. - */ - -#include <linux/kernel.h> @@ -138,12 +135,8 @@ -} --- a/net/mac80211/aead_api.h +++ /dev/null -@@ -1,27 +0,0 @@ --/* -- * This program is free software; you can redistribute it and/or modify -- * it under the terms of the GNU General Public License version 2 as -- * published by the Free Software Foundation. -- */ +@@ -1,23 +0,0 @@ +-/* SPDX-License-Identifier: GPL-2.0-only */ - -#ifndef _AEAD_API_H -#define _AEAD_API_H @@ -168,7 +161,7 @@ -#endif /* _AEAD_API_H */ --- a/net/mac80211/aes_ccm.h +++ b/net/mac80211/aes_ccm.h -@@ -10,39 +10,17 @@ +@@ -7,39 +7,17 @@ #ifndef AES_CCM_H #define AES_CCM_H @@ -333,7 +326,7 @@ +} --- a/net/mac80211/aes_gcm.h +++ b/net/mac80211/aes_gcm.h -@@ -9,38 +9,30 @@ +@@ -6,38 +6,30 @@ #ifndef AES_GCM_H #define AES_GCM_H @@ -385,7 +378,7 @@ #endif /* AES_GCM_H */ --- a/net/mac80211/wpa.c +++ b/net/mac80211/wpa.c -@@ -314,7 +314,8 @@ ieee80211_crypto_tkip_decrypt(struct iee +@@ -311,7 +311,8 @@ ieee80211_crypto_tkip_decrypt(struct iee } @@ -395,7 +388,7 @@ { __le16 mask_fc; int a4_included, mgmt; -@@ -344,14 +345,8 @@ static void ccmp_special_blocks(struct s +@@ -341,14 +342,8 @@ static void ccmp_special_blocks(struct s else qos_tid = 0; @@ -412,7 +405,7 @@ /* Nonce: Nonce Flags | A2 | PN * Nonce Flags: Priority (b0..b3) | Management (b4) | Reserved (b5..b7) -@@ -359,6 +354,8 @@ static void ccmp_special_blocks(struct s +@@ -356,6 +351,8 @@ static void ccmp_special_blocks(struct s b_0[1] = qos_tid | (mgmt << 4); memcpy(&b_0[2], hdr->addr2, ETH_ALEN); memcpy(&b_0[8], pn, IEEE80211_CCMP_PN_LEN); @@ -421,7 +414,7 @@ /* AAD (extra authenticate-only data) / masked 802.11 header * FC | A1 | A2 | A3 | SC | [A4] | [QC] */ -@@ -415,7 +412,7 @@ static int ccmp_encrypt_skb(struct ieee8 +@@ -412,7 +409,7 @@ static int ccmp_encrypt_skb(struct ieee8 u8 *pos; u8 pn[6]; u64 pn64; @@ -430,7 +423,7 @@ u8 b_0[AES_BLOCK_SIZE]; if (info->control.hw_key && -@@ -470,9 +467,11 @@ static int ccmp_encrypt_skb(struct ieee8 +@@ -467,9 +464,11 @@ static int ccmp_encrypt_skb(struct ieee8 return 0; pos += IEEE80211_CCMP_HDR_LEN; @@ -445,7 +438,7 @@ } -@@ -545,13 +544,13 @@ ieee80211_crypto_ccmp_decrypt(struct iee +@@ -542,13 +541,13 @@ ieee80211_crypto_ccmp_decrypt(struct iee u8 aad[2 * AES_BLOCK_SIZE]; u8 b_0[AES_BLOCK_SIZE]; /* hardware didn't decrypt/verify MIC */ @@ -461,7 +454,7 @@ return RX_DROP_UNUSABLE; } -@@ -646,7 +645,7 @@ static int gcmp_encrypt_skb(struct ieee8 +@@ -643,7 +642,7 @@ static int gcmp_encrypt_skb(struct ieee8 u8 *pos; u8 pn[6]; u64 pn64; @@ -470,7 +463,7 @@ u8 j_0[AES_BLOCK_SIZE]; if (info->control.hw_key && -@@ -703,8 +702,10 @@ static int gcmp_encrypt_skb(struct ieee8 +@@ -700,8 +699,10 @@ static int gcmp_encrypt_skb(struct ieee8 pos += IEEE80211_GCMP_HDR_LEN; gcmp_special_blocks(skb, pn, j_0, aad); @@ -483,7 +476,7 @@ } ieee80211_tx_result -@@ -1127,9 +1128,9 @@ ieee80211_crypto_aes_gmac_encrypt(struct +@@ -1124,9 +1125,9 @@ ieee80211_crypto_aes_gmac_encrypt(struct struct ieee80211_key *key = tx->key; struct ieee80211_mmie_16 *mmie; struct ieee80211_hdr *hdr; @@ -495,12 +488,12 @@ if (WARN_ON(skb_queue_len(&tx->skbs) != 1)) return TX_DROP; -@@ -1175,7 +1176,7 @@ ieee80211_crypto_aes_gmac_decrypt(struct +@@ -1172,7 +1173,7 @@ ieee80211_crypto_aes_gmac_decrypt(struct struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); struct ieee80211_key *key = rx->key; struct ieee80211_mmie_16 *mmie; -- u8 aad[GMAC_AAD_LEN], mic[GMAC_MIC_LEN], ipn[6], nonce[GMAC_NONCE_LEN]; -+ u8 aad[20], mic[16], ipn[6], nonce[12]; +- u8 aad[GMAC_AAD_LEN], *mic, ipn[6], nonce[GMAC_NONCE_LEN]; ++ u8 aad[20], *mic, ipn[6], nonce[12]; struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; if (!ieee80211_is_mgmt(hdr->frame_control)) @@ -653,7 +646,7 @@ +} --- a/net/mac80211/Kconfig +++ b/net/mac80211/Kconfig -@@ -5,8 +5,6 @@ config MAC80211 +@@ -6,8 +6,6 @@ config MAC80211 depends on CRYPTO depends on CRYPTO_ARC4 depends on CRYPTO_AES @@ -664,7 +657,7 @@ ---help--- --- a/net/mac80211/aes_gmac.h +++ b/net/mac80211/aes_gmac.h -@@ -15,10 +15,22 @@ +@@ -12,10 +12,22 @@ #define GMAC_MIC_LEN 16 #define GMAC_NONCE_LEN 12 @@ -694,7 +687,7 @@ #endif /* AES_GMAC_H */ --- a/net/mac80211/key.h +++ b/net/mac80211/key.h -@@ -88,7 +88,7 @@ struct ieee80211_key { +@@ -86,7 +86,7 @@ struct ieee80211_key { * Management frames. */ u8 rx_pn[IEEE80211_NUM_TIDS + 1][IEEE80211_CCMP_PN_LEN]; diff --git a/package/kernel/mac80211/patches/subsys/110-mac80211_keep_keys_on_stop_ap.patch b/package/kernel/mac80211/patches/subsys/110-mac80211_keep_keys_on_stop_ap.patch index 6775884a34..59144f7310 100644 --- a/package/kernel/mac80211/patches/subsys/110-mac80211_keep_keys_on_stop_ap.patch +++ b/package/kernel/mac80211/patches/subsys/110-mac80211_keep_keys_on_stop_ap.patch @@ -2,8 +2,8 @@ Used for AP+STA support in OpenWrt - preserve AP mode keys across STA reconnects --- a/net/mac80211/cfg.c +++ b/net/mac80211/cfg.c -@@ -1067,7 +1067,6 @@ static int ieee80211_stop_ap(struct wiph - sdata->u.ap.driver_smps_mode = IEEE80211_SMPS_OFF; +@@ -1162,7 +1162,6 @@ static int ieee80211_stop_ap(struct wiph + sdata->vif.bss_conf.ftmr_params = NULL; __sta_info_flush(sdata, true); - ieee80211_free_keys(sdata, true); diff --git a/package/kernel/mac80211/patches/subsys/120-cfg80211_allow_perm_addr_change.patch b/package/kernel/mac80211/patches/subsys/120-cfg80211_allow_perm_addr_change.patch index ffd8807ccc..172e5b04fd 100644 --- a/package/kernel/mac80211/patches/subsys/120-cfg80211_allow_perm_addr_change.patch +++ b/package/kernel/mac80211/patches/subsys/120-cfg80211_allow_perm_addr_change.patch @@ -1,6 +1,6 @@ --- a/net/wireless/sysfs.c +++ b/net/wireless/sysfs.c -@@ -24,18 +24,35 @@ static inline struct cfg80211_registered +@@ -23,18 +23,35 @@ static inline struct cfg80211_registered return container_of(dev, struct cfg80211_registered_device, wiphy.dev); } diff --git a/package/kernel/mac80211/patches/subsys/130-disable-fils.patch b/package/kernel/mac80211/patches/subsys/130-disable-fils.patch index f1163764a0..dd1ccc8597 100644 --- a/package/kernel/mac80211/patches/subsys/130-disable-fils.patch +++ b/package/kernel/mac80211/patches/subsys/130-disable-fils.patch @@ -2,7 +2,7 @@ Disable FILS support, since it pulls in crypto hash support --- a/net/mac80211/fils_aead.h +++ b/net/mac80211/fils_aead.h -@@ -10,7 +10,7 @@ +@@ -7,7 +7,7 @@ #ifndef FILS_AEAD_H #define FILS_AEAD_H @@ -16,9 +16,9 @@ Disable FILS support, since it pulls in crypto hash support @@ -1,4 +1,4 @@ -#if LINUX_VERSION_IS_GEQ(4,3,0) +#if 0 /* LINUX_VERSION_IS_GEQ(4,3,0) */ + // SPDX-License-Identifier: GPL-2.0-only /* * FILS AEAD for (Re)Association Request/Response frames - * Copyright 2016, Qualcomm Atheros, Inc. --- a/net/mac80211/main.c +++ b/net/mac80211/main.c @@ -570,7 +570,7 @@ struct ieee80211_hw *ieee80211_alloc_hw_ diff --git a/package/kernel/mac80211/patches/subsys/131-Revert-mac80211-aes-cmac-switch-to-shash-CMAC-driver.patch b/package/kernel/mac80211/patches/subsys/131-Revert-mac80211-aes-cmac-switch-to-shash-CMAC-driver.patch index d138b2c5ac..0c5f85236e 100644 --- a/package/kernel/mac80211/patches/subsys/131-Revert-mac80211-aes-cmac-switch-to-shash-CMAC-driver.patch +++ b/package/kernel/mac80211/patches/subsys/131-Revert-mac80211-aes-cmac-switch-to-shash-CMAC-driver.patch @@ -11,7 +11,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> --- a/net/mac80211/aes_cmac.c +++ b/net/mac80211/aes_cmac.c -@@ -22,50 +22,126 @@ +@@ -19,50 +19,126 @@ #define CMAC_TLEN_256 16 /* CMAC TLen = 128 bits (16 octets) */ #define AAD_LEN 20 @@ -166,7 +166,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> } --- a/net/mac80211/aes_cmac.h +++ b/net/mac80211/aes_cmac.h -@@ -10,14 +10,13 @@ +@@ -7,14 +7,13 @@ #define AES_CMAC_H #include <linux/crypto.h> @@ -188,7 +188,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> #endif /* AES_CMAC_H */ --- a/net/mac80211/key.h +++ b/net/mac80211/key.h -@@ -93,7 +93,7 @@ struct ieee80211_key { +@@ -91,7 +91,7 @@ struct ieee80211_key { } ccmp; struct { u8 rx_pn[IEEE80211_CMAC_PN_LEN]; diff --git a/package/kernel/mac80211/patches/subsys/132-mac80211-remove-cmac-dependency.patch b/package/kernel/mac80211/patches/subsys/132-mac80211-remove-cmac-dependency.patch index 9d185e61e7..a259d5816b 100644 --- a/package/kernel/mac80211/patches/subsys/132-mac80211-remove-cmac-dependency.patch +++ b/package/kernel/mac80211/patches/subsys/132-mac80211-remove-cmac-dependency.patch @@ -1,6 +1,6 @@ --- a/net/mac80211/Kconfig +++ b/net/mac80211/Kconfig -@@ -5,7 +5,6 @@ config MAC80211 +@@ -6,7 +6,6 @@ config MAC80211 depends on CRYPTO depends on CRYPTO_ARC4 depends on CRYPTO_AES diff --git a/package/kernel/mac80211/patches/subsys/140-tweak-TSQ-setting.patch b/package/kernel/mac80211/patches/subsys/140-tweak-TSQ-setting.patch index 42a6382209..449179a962 100644 --- a/package/kernel/mac80211/patches/subsys/140-tweak-TSQ-setting.patch +++ b/package/kernel/mac80211/patches/subsys/140-tweak-TSQ-setting.patch @@ -1,6 +1,6 @@ --- a/net/mac80211/tx.c +++ b/net/mac80211/tx.c -@@ -3797,6 +3797,12 @@ out: +@@ -4012,6 +4012,12 @@ out: netdev_tx_t ieee80211_subif_start_xmit(struct sk_buff *skb, struct net_device *dev) { diff --git a/package/kernel/mac80211/patches/subsys/150-disable_addr_notifier.patch b/package/kernel/mac80211/patches/subsys/150-disable_addr_notifier.patch index 1581b3400b..39000e4f05 100644 --- a/package/kernel/mac80211/patches/subsys/150-disable_addr_notifier.patch +++ b/package/kernel/mac80211/patches/subsys/150-disable_addr_notifier.patch @@ -1,6 +1,6 @@ --- a/net/mac80211/main.c +++ b/net/mac80211/main.c -@@ -315,7 +315,7 @@ void ieee80211_restart_hw(struct ieee802 +@@ -313,7 +313,7 @@ void ieee80211_restart_hw(struct ieee802 } EXPORT_SYMBOL(ieee80211_restart_hw); @@ -9,7 +9,7 @@ static int ieee80211_ifa_changed(struct notifier_block *nb, unsigned long data, void *arg) { -@@ -374,7 +374,7 @@ static int ieee80211_ifa_changed(struct +@@ -372,7 +372,7 @@ static int ieee80211_ifa_changed(struct } #endif @@ -18,7 +18,7 @@ static int ieee80211_ifa6_changed(struct notifier_block *nb, unsigned long data, void *arg) { -@@ -1168,14 +1168,14 @@ int ieee80211_register_hw(struct ieee802 +@@ -1269,14 +1269,14 @@ int ieee80211_register_hw(struct ieee802 rtnl_unlock(); @@ -35,7 +35,7 @@ local->ifa6_notifier.notifier_call = ieee80211_ifa6_changed; result = register_inet6addr_notifier(&local->ifa6_notifier); if (result) -@@ -1184,13 +1184,13 @@ int ieee80211_register_hw(struct ieee802 +@@ -1285,13 +1285,13 @@ int ieee80211_register_hw(struct ieee802 return 0; @@ -52,7 +52,7 @@ fail_ifa: #endif rtnl_lock(); -@@ -1219,10 +1219,10 @@ void ieee80211_unregister_hw(struct ieee +@@ -1320,10 +1320,10 @@ void ieee80211_unregister_hw(struct ieee tasklet_kill(&local->tx_pending_tasklet); tasklet_kill(&local->tasklet); diff --git a/package/kernel/mac80211/patches/subsys/210-ap_scan.patch b/package/kernel/mac80211/patches/subsys/210-ap_scan.patch index fcc173da69..7e237a443e 100644 --- a/package/kernel/mac80211/patches/subsys/210-ap_scan.patch +++ b/package/kernel/mac80211/patches/subsys/210-ap_scan.patch @@ -1,6 +1,6 @@ --- a/net/mac80211/cfg.c +++ b/net/mac80211/cfg.c -@@ -2237,7 +2237,7 @@ static int ieee80211_scan(struct wiphy * +@@ -2312,7 +2312,7 @@ static int ieee80211_scan(struct wiphy * * the frames sent while scanning on other channel will be * lost) */ diff --git a/package/kernel/mac80211/patches/subsys/300-mac80211-add-stop-start-logic-for-software-TXQs.patch b/package/kernel/mac80211/patches/subsys/300-mac80211-add-stop-start-logic-for-software-TXQs.patch deleted file mode 100644 index 422e9c2977..0000000000 --- a/package/kernel/mac80211/patches/subsys/300-mac80211-add-stop-start-logic-for-software-TXQs.patch +++ /dev/null @@ -1,272 +0,0 @@ -From: Manikanta Pubbisetty <mpubbise@codeaurora.org> -Date: Wed, 11 Jul 2018 00:12:53 +0530 -Subject: [PATCH] mac80211: add stop/start logic for software TXQs - -Sometimes, it is required to stop the transmissions momentarily and -resume it later; stopping the txqs becomes very critical in scenarios where -the packet transmission has to be ceased completely. For example, during -the hardware restart, during off channel operations, -when initiating CSA(upon detecting a radar on the DFS channel), etc. - -The TX queue stop/start logic in mac80211 works well in stopping the TX -when drivers make use of netdev queues, i.e, when Qdiscs in network layer -take care of traffic scheduling. Since the devices implementing -wake_tx_queue can run without Qdiscs, packets will be handed to mac80211 -directly without queueing them in the netdev queues. - -Also, mac80211 does not invoke any of the -netif_stop_*/netif_wake_* APIs if wake_tx_queue is implemented. -Since the queues are not stopped in this case, transmissions can continue -and this will impact negatively on the operation of the wireless device. - -For example, -During hardware restart, we stop the netdev queues so that packets are -not sent to the driver. Since ath10k implements wake_tx_queue, -TX queues will not be stopped and packets might reach the hardware while -it is restarting; this can make hardware unresponsive and the only -possible option for recovery is to reboot the entire system. - -There is another problem to this, it is observed that the packets -were sent on the DFS channel for a prolonged duration after radar -detection impacting the channel closing time. - -We can still invoke netif stop/wake APIs when wake_tx_queue is implemented -but this could lead to packet drops in network layer; adding stop/start -logic for software TXQs in mac80211 instead makes more sense; the change -proposed adds the same in mac80211. - -Signed-off-by: Manikanta Pubbisetty <mpubbise@codeaurora.org> -Signed-off-by: Johannes Berg <johannes.berg@intel.com> ---- - ---- a/include/net/mac80211.h -+++ b/include/net/mac80211.h -@@ -1504,6 +1504,8 @@ enum ieee80211_vif_flags { - * @drv_priv: data area for driver use, will always be aligned to - * sizeof(void \*). - * @txq: the multicast data TX queue (if driver uses the TXQ abstraction) -+ * @txqs_stopped: per AC flag to indicate that intermediate TXQs are stopped, -+ * protected by fq->lock. - */ - struct ieee80211_vif { - enum nl80211_iftype type; -@@ -1528,6 +1530,8 @@ struct ieee80211_vif { - - unsigned int probe_req_reg; - -+ bool txqs_stopped[IEEE80211_NUM_ACS]; -+ - /* must be last */ - u8 drv_priv[0] __aligned(sizeof(void *)); - }; ---- a/net/mac80211/ieee80211_i.h -+++ b/net/mac80211/ieee80211_i.h -@@ -818,6 +818,7 @@ enum txq_info_flags { - IEEE80211_TXQ_STOP, - IEEE80211_TXQ_AMPDU, - IEEE80211_TXQ_NO_AMSDU, -+ IEEE80211_TXQ_STOP_NETIF_TX, - }; - - /** -@@ -1226,6 +1227,7 @@ struct ieee80211_local { - - struct sk_buff_head pending[IEEE80211_MAX_QUEUES]; - struct tasklet_struct tx_pending_tasklet; -+ struct tasklet_struct wake_txqs_tasklet; - - atomic_t agg_queue_stop[IEEE80211_MAX_QUEUES]; - -@@ -2039,6 +2041,7 @@ void ieee80211_txq_remove_vlan(struct ie - struct ieee80211_sub_if_data *sdata); - void ieee80211_fill_txq_stats(struct cfg80211_txq_stats *txqstats, - struct txq_info *txqi); -+void ieee80211_wake_txqs(unsigned long data); - void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata, - u16 transaction, u16 auth_alg, u16 status, - const u8 *extra, size_t extra_len, const u8 *bssid, ---- a/net/mac80211/main.c -+++ b/net/mac80211/main.c -@@ -686,6 +686,10 @@ struct ieee80211_hw *ieee80211_alloc_hw_ - tasklet_init(&local->tx_pending_tasklet, ieee80211_tx_pending, - (unsigned long)local); - -+ if (ops->wake_tx_queue) -+ tasklet_init(&local->wake_txqs_tasklet, ieee80211_wake_txqs, -+ (unsigned long)local); -+ - tasklet_init(&local->tasklet, - ieee80211_tasklet_handler, - (unsigned long) local); ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -3482,13 +3482,19 @@ struct sk_buff *ieee80211_tx_dequeue(str - struct ieee80211_tx_info *info; - struct ieee80211_tx_data tx; - ieee80211_tx_result r; -- struct ieee80211_vif *vif; -+ struct ieee80211_vif *vif = txq->vif; - - spin_lock_bh(&fq->lock); - -- if (test_bit(IEEE80211_TXQ_STOP, &txqi->flags)) -+ if (test_bit(IEEE80211_TXQ_STOP, &txqi->flags) || -+ test_bit(IEEE80211_TXQ_STOP_NETIF_TX, &txqi->flags)) - goto out; - -+ if (vif->txqs_stopped[ieee80211_ac_from_tid(txq->tid)]) { -+ set_bit(IEEE80211_TXQ_STOP_NETIF_TX, &txqi->flags); -+ goto out; -+ } -+ - /* Make sure fragments stay together. */ - skb = __skb_dequeue(&txqi->frags); - if (skb) -@@ -3583,6 +3589,7 @@ begin: - } - - IEEE80211_SKB_CB(skb)->control.vif = vif; -+ - out: - spin_unlock_bh(&fq->lock); - ---- a/net/mac80211/util.c -+++ b/net/mac80211/util.c -@@ -240,6 +240,99 @@ __le16 ieee80211_ctstoself_duration(stru - } - EXPORT_SYMBOL(ieee80211_ctstoself_duration); - -+static void __ieee80211_wake_txqs(struct ieee80211_sub_if_data *sdata, int ac) -+{ -+ struct ieee80211_local *local = sdata->local; -+ struct ieee80211_vif *vif = &sdata->vif; -+ struct fq *fq = &local->fq; -+ struct ps_data *ps = NULL; -+ struct txq_info *txqi; -+ struct sta_info *sta; -+ int i; -+ -+ spin_lock_bh(&fq->lock); -+ -+ if (sdata->vif.type == NL80211_IFTYPE_AP) -+ ps = &sdata->bss->ps; -+ -+ sdata->vif.txqs_stopped[ac] = false; -+ -+ list_for_each_entry_rcu(sta, &local->sta_list, list) { -+ if (sdata != sta->sdata) -+ continue; -+ -+ for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) { -+ struct ieee80211_txq *txq = sta->sta.txq[i]; -+ -+ txqi = to_txq_info(txq); -+ -+ if (ac != txq->ac) -+ continue; -+ -+ if (!test_and_clear_bit(IEEE80211_TXQ_STOP_NETIF_TX, -+ &txqi->flags)) -+ continue; -+ -+ spin_unlock_bh(&fq->lock); -+ drv_wake_tx_queue(local, txqi); -+ spin_lock_bh(&fq->lock); -+ } -+ } -+ -+ if (!vif->txq) -+ goto out; -+ -+ txqi = to_txq_info(vif->txq); -+ -+ if (!test_and_clear_bit(IEEE80211_TXQ_STOP_NETIF_TX, &txqi->flags) || -+ (ps && atomic_read(&ps->num_sta_ps)) || ac != vif->txq->ac) -+ goto out; -+ -+ spin_unlock_bh(&fq->lock); -+ -+ drv_wake_tx_queue(local, txqi); -+ return; -+out: -+ spin_unlock_bh(&fq->lock); -+} -+ -+void ieee80211_wake_txqs(unsigned long data) -+{ -+ struct ieee80211_local *local = (struct ieee80211_local *)data; -+ struct ieee80211_sub_if_data *sdata; -+ int n_acs = IEEE80211_NUM_ACS; -+ unsigned long flags; -+ int i; -+ -+ rcu_read_lock(); -+ spin_lock_irqsave(&local->queue_stop_reason_lock, flags); -+ -+ if (local->hw.queues < IEEE80211_NUM_ACS) -+ n_acs = 1; -+ -+ for (i = 0; i < local->hw.queues; i++) { -+ if (local->queue_stop_reasons[i]) -+ continue; -+ -+ spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); -+ list_for_each_entry_rcu(sdata, &local->interfaces, list) { -+ int ac; -+ -+ for (ac = 0; ac < n_acs; ac++) { -+ int ac_queue = sdata->vif.hw_queue[ac]; -+ -+ if (ac_queue == i || -+ sdata->vif.cab_queue == i) -+ __ieee80211_wake_txqs(sdata, ac); -+ } -+ } -+ spin_lock_irqsave(&local->queue_stop_reason_lock, flags); -+ } -+ -+ spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); -+ rcu_read_unlock(); -+} -+ - void ieee80211_propagate_queue_wake(struct ieee80211_local *local, int queue) - { - struct ieee80211_sub_if_data *sdata; -@@ -308,6 +401,9 @@ static void __ieee80211_wake_queue(struc - rcu_read_unlock(); - } else - tasklet_schedule(&local->tx_pending_tasklet); -+ -+ if (local->ops->wake_tx_queue) -+ tasklet_schedule(&local->wake_txqs_tasklet); - } - - void ieee80211_wake_queue_by_reason(struct ieee80211_hw *hw, int queue, -@@ -351,9 +447,6 @@ static void __ieee80211_stop_queue(struc - if (__test_and_set_bit(reason, &local->queue_stop_reasons[queue])) - return; - -- if (local->ops->wake_tx_queue) -- return; -- - if (local->hw.queues < IEEE80211_NUM_ACS) - n_acs = 1; - -@@ -366,8 +459,15 @@ static void __ieee80211_stop_queue(struc - - for (ac = 0; ac < n_acs; ac++) { - if (sdata->vif.hw_queue[ac] == queue || -- sdata->vif.cab_queue == queue) -- netif_stop_subqueue(sdata->dev, ac); -+ sdata->vif.cab_queue == queue) { -+ if (!local->ops->wake_tx_queue) { -+ netif_stop_subqueue(sdata->dev, ac); -+ continue; -+ } -+ spin_lock(&local->fq.lock); -+ sdata->vif.txqs_stopped[ac] = true; -+ spin_unlock(&local->fq.lock); -+ } - } - } - rcu_read_unlock(); diff --git a/package/kernel/mac80211/patches/subsys/301-mac80211-do-not-call-driver-wake_tx_queue-op-during-.patch b/package/kernel/mac80211/patches/subsys/301-mac80211-do-not-call-driver-wake_tx_queue-op-during-.patch deleted file mode 100644 index 5bbf4db23b..0000000000 --- a/package/kernel/mac80211/patches/subsys/301-mac80211-do-not-call-driver-wake_tx_queue-op-during-.patch +++ /dev/null @@ -1,33 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Fri, 1 Mar 2019 14:42:56 +0100 -Subject: [PATCH] mac80211: do not call driver wake_tx_queue op during reconfig - -There are several scenarios in which mac80211 can call drv_wake_tx_queue -after ieee80211_restart_hw has been called and has not yet completed. -Driver private structs are considered uninitialized until mac80211 has -uploaded the vifs, stations and keys again, so using private tx queue -data during that time is not safe. - -The driver can also not rely on drv_reconfig_complete to figure out when -it is safe to accept drv_wake_tx_queue calls again, because it is only -called after all tx queues are woken again. - -To fix this, bail out early in drv_wake_tx_queue if local->in_reconfig -is set. - -Cc: stable@vger.kernel.org -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/driver-ops.h -+++ b/net/mac80211/driver-ops.h -@@ -1166,6 +1166,9 @@ static inline void drv_wake_tx_queue(str - { - struct ieee80211_sub_if_data *sdata = vif_to_sdata(txq->txq.vif); - -+ if (local->in_reconfig) -+ return; -+ - if (!check_sdata_in_driver(sdata)) - return; - diff --git a/package/kernel/mac80211/patches/subsys/303-mac80211-minstrel-Enable-STBC-and-LDPC-for-VHT-Rates.patch b/package/kernel/mac80211/patches/subsys/303-mac80211-minstrel-Enable-STBC-and-LDPC-for-VHT-Rates.patch deleted file mode 100644 index 661fb46ea4..0000000000 --- a/package/kernel/mac80211/patches/subsys/303-mac80211-minstrel-Enable-STBC-and-LDPC-for-VHT-Rates.patch +++ /dev/null @@ -1,82 +0,0 @@ -From: Chaitanya T K <chaitanya.mgit@gmail.com> -Date: Mon, 27 Jun 2016 15:23:26 +0530 -Subject: [PATCH] mac80211: minstrel: Enable STBC and LDPC for VHT Rates - -If peer support reception of STBC and LDPC, enable them for better -performance. - -Signed-off-by: Chaitanya TK <chaitanya.mgit@gmail.com> ---- - ---- a/include/linux/ieee80211.h -+++ b/include/linux/ieee80211.h -@@ -1659,6 +1659,7 @@ struct ieee80211_mu_edca_param_set { - #define IEEE80211_VHT_CAP_RXSTBC_3 0x00000300 - #define IEEE80211_VHT_CAP_RXSTBC_4 0x00000400 - #define IEEE80211_VHT_CAP_RXSTBC_MASK 0x00000700 -+#define IEEE80211_VHT_CAP_RXSTBC_SHIFT 8 - #define IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE 0x00000800 - #define IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE 0x00001000 - #define IEEE80211_VHT_CAP_BEAMFORMEE_STS_SHIFT 13 ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -1130,7 +1130,7 @@ minstrel_ht_update_caps(void *priv, stru - struct minstrel_ht_sta_priv *msp = priv_sta; - struct minstrel_ht_sta *mi = &msp->ht; - struct ieee80211_mcs_info *mcs = &sta->ht_cap.mcs; -- u16 sta_cap = sta->ht_cap.cap; -+ u16 ht_cap = sta->ht_cap.cap; - struct ieee80211_sta_vht_cap *vht_cap = &sta->vht_cap; - struct sta_info *sinfo = container_of(sta, struct sta_info, sta); - int use_vht; -@@ -1138,6 +1138,7 @@ minstrel_ht_update_caps(void *priv, stru - int ack_dur; - int stbc; - int i; -+ bool ldpc = false; - - /* fall back to the old minstrel for legacy stations */ - if (!sta->ht_cap.ht_supported) -@@ -1175,16 +1176,24 @@ minstrel_ht_update_caps(void *priv, stru - } - mi->sample_tries = 4; - -- /* TODO tx_flags for vht - ATM the RC API is not fine-grained enough */ - if (!use_vht) { -- stbc = (sta_cap & IEEE80211_HT_CAP_RX_STBC) >> -+ stbc = (ht_cap & IEEE80211_HT_CAP_RX_STBC) >> - IEEE80211_HT_CAP_RX_STBC_SHIFT; -- mi->tx_flags |= stbc << IEEE80211_TX_CTL_STBC_SHIFT; - -- if (sta_cap & IEEE80211_HT_CAP_LDPC_CODING) -- mi->tx_flags |= IEEE80211_TX_CTL_LDPC; -+ if (ht_cap & IEEE80211_HT_CAP_LDPC_CODING) -+ ldpc = true; -+ } else { -+ stbc = (vht_cap->cap & IEEE80211_VHT_CAP_RXSTBC_MASK) >> -+ IEEE80211_VHT_CAP_RXSTBC_SHIFT; -+ -+ if (vht_cap->cap & IEEE80211_VHT_CAP_RXLDPC) -+ ldpc = true; - } - -+ mi->tx_flags |= stbc << IEEE80211_TX_CTL_STBC_SHIFT; -+ if (ldpc) -+ mi->tx_flags |= IEEE80211_TX_CTL_LDPC; -+ - for (i = 0; i < ARRAY_SIZE(mi->groups); i++) { - u32 gflags = minstrel_mcs_groups[i].flags; - int bw, nss; -@@ -1197,10 +1206,10 @@ minstrel_ht_update_caps(void *priv, stru - - if (gflags & IEEE80211_TX_RC_SHORT_GI) { - if (gflags & IEEE80211_TX_RC_40_MHZ_WIDTH) { -- if (!(sta_cap & IEEE80211_HT_CAP_SGI_40)) -+ if (!(ht_cap & IEEE80211_HT_CAP_SGI_40)) - continue; - } else { -- if (!(sta_cap & IEEE80211_HT_CAP_SGI_20)) -+ if (!(ht_cap & IEEE80211_HT_CAP_SGI_20)) - continue; - } - } diff --git a/package/kernel/mac80211/patches/subsys/304-mac80211-minstrel-remove-unnecessary-debugfs-cleanup.patch b/package/kernel/mac80211/patches/subsys/304-mac80211-minstrel-remove-unnecessary-debugfs-cleanup.patch deleted file mode 100644 index 95d4f294aa..0000000000 --- a/package/kernel/mac80211/patches/subsys/304-mac80211-minstrel-remove-unnecessary-debugfs-cleanup.patch +++ /dev/null @@ -1,150 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 10 Feb 2018 12:41:51 +0100 -Subject: [PATCH] mac80211: minstrel: remove unnecessary debugfs cleanup - code - -debugfs entries are cleaned up by debugfs_remove_recursive already. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel.c -+++ b/net/mac80211/rc80211_minstrel.c -@@ -689,8 +689,8 @@ minstrel_alloc(struct ieee80211_hw *hw, - - #ifdef CPTCFG_MAC80211_DEBUGFS - mp->fixed_rate_idx = (u32) -1; -- mp->dbg_fixed_rate = debugfs_create_u32("fixed_rate_idx", -- 0666, debugfsdir, &mp->fixed_rate_idx); -+ debugfs_create_u32("fixed_rate_idx", S_IRUGO | S_IWUGO, debugfsdir, -+ &mp->fixed_rate_idx); - #endif - - minstrel_init_cck_rates(mp); -@@ -701,9 +701,6 @@ minstrel_alloc(struct ieee80211_hw *hw, - static void - minstrel_free(void *priv) - { --#ifdef CPTCFG_MAC80211_DEBUGFS -- debugfs_remove(((struct minstrel_priv *)priv)->dbg_fixed_rate); --#endif - kfree(priv); - } - -@@ -735,7 +732,6 @@ const struct rate_control_ops mac80211_m - .free_sta = minstrel_free_sta, - #ifdef CPTCFG_MAC80211_DEBUGFS - .add_sta_debugfs = minstrel_add_sta_debugfs, -- .remove_sta_debugfs = minstrel_remove_sta_debugfs, - #endif - .get_expected_throughput = minstrel_get_expected_throughput, - }; ---- a/net/mac80211/rc80211_minstrel.h -+++ b/net/mac80211/rc80211_minstrel.h -@@ -109,11 +109,6 @@ struct minstrel_sta_info { - - /* sampling table */ - u8 *sample_table; -- --#ifdef CPTCFG_MAC80211_DEBUGFS -- struct dentry *dbg_stats; -- struct dentry *dbg_stats_csv; --#endif - }; - - struct minstrel_priv { -@@ -137,7 +132,6 @@ struct minstrel_priv { - * - setting will be applied on next update - */ - u32 fixed_rate_idx; -- struct dentry *dbg_fixed_rate; - #endif - }; - -@@ -156,7 +150,6 @@ minstrel_get_ewmsd10(struct minstrel_rat - - extern const struct rate_control_ops mac80211_minstrel; - void minstrel_add_sta_debugfs(void *priv, void *priv_sta, struct dentry *dir); --void minstrel_remove_sta_debugfs(void *priv, void *priv_sta); - - /* Recalculate success probabilities and counters for a given rate using EWMA */ - void minstrel_calc_rate_stats(struct minstrel_rate_stats *mrs); ---- a/net/mac80211/rc80211_minstrel_debugfs.c -+++ b/net/mac80211/rc80211_minstrel_debugfs.c -@@ -214,19 +214,7 @@ minstrel_add_sta_debugfs(void *priv, voi - { - struct minstrel_sta_info *mi = priv_sta; - -- mi->dbg_stats = debugfs_create_file("rc_stats", 0444, dir, mi, -- &minstrel_stat_fops); -- -- mi->dbg_stats_csv = debugfs_create_file("rc_stats_csv", 0444, dir, mi, -- &minstrel_stat_csv_fops); --} -- --void --minstrel_remove_sta_debugfs(void *priv, void *priv_sta) --{ -- struct minstrel_sta_info *mi = priv_sta; -- -- debugfs_remove(mi->dbg_stats); -- -- debugfs_remove(mi->dbg_stats_csv); -+ debugfs_create_file("rc_stats", S_IRUGO, dir, mi, &minstrel_stat_fops); -+ debugfs_create_file("rc_stats_csv", S_IRUGO, dir, mi, -+ &minstrel_stat_csv_fops); - } ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -1393,7 +1393,6 @@ static const struct rate_control_ops mac - .free = minstrel_ht_free, - #ifdef CPTCFG_MAC80211_DEBUGFS - .add_sta_debugfs = minstrel_ht_add_sta_debugfs, -- .remove_sta_debugfs = minstrel_ht_remove_sta_debugfs, - #endif - .get_expected_throughput = minstrel_ht_get_expected_throughput, - }; ---- a/net/mac80211/rc80211_minstrel_ht.h -+++ b/net/mac80211/rc80211_minstrel_ht.h -@@ -110,17 +110,12 @@ struct minstrel_ht_sta_priv { - struct minstrel_ht_sta ht; - struct minstrel_sta_info legacy; - }; --#ifdef CPTCFG_MAC80211_DEBUGFS -- struct dentry *dbg_stats; -- struct dentry *dbg_stats_csv; --#endif - void *ratelist; - void *sample_table; - bool is_ht; - }; - - void minstrel_ht_add_sta_debugfs(void *priv, void *priv_sta, struct dentry *dir); --void minstrel_ht_remove_sta_debugfs(void *priv, void *priv_sta); - int minstrel_ht_get_tp_avg(struct minstrel_ht_sta *mi, int group, int rate, - int prob_ewma); - ---- a/net/mac80211/rc80211_minstrel_ht_debugfs.c -+++ b/net/mac80211/rc80211_minstrel_ht_debugfs.c -@@ -303,17 +303,8 @@ minstrel_ht_add_sta_debugfs(void *priv, - { - struct minstrel_ht_sta_priv *msp = priv_sta; - -- msp->dbg_stats = debugfs_create_file("rc_stats", 0444, dir, msp, -- &minstrel_ht_stat_fops); -- msp->dbg_stats_csv = debugfs_create_file("rc_stats_csv", 0444, dir, msp, -- &minstrel_ht_stat_csv_fops); --} -- --void --minstrel_ht_remove_sta_debugfs(void *priv, void *priv_sta) --{ -- struct minstrel_ht_sta_priv *msp = priv_sta; -- -- debugfs_remove(msp->dbg_stats); -- debugfs_remove(msp->dbg_stats_csv); -+ debugfs_create_file("rc_stats", S_IRUGO, dir, msp, -+ &minstrel_ht_stat_fops); -+ debugfs_create_file("rc_stats_csv", S_IRUGO, dir, msp, -+ &minstrel_ht_stat_csv_fops); - } diff --git a/package/kernel/mac80211/patches/subsys/305-mac80211-minstrel-merge-with-minstrel_ht-always-enab.patch b/package/kernel/mac80211/patches/subsys/305-mac80211-minstrel-merge-with-minstrel_ht-always-enab.patch deleted file mode 100644 index 9a233753ad..0000000000 --- a/package/kernel/mac80211/patches/subsys/305-mac80211-minstrel-merge-with-minstrel_ht-always-enab.patch +++ /dev/null @@ -1,575 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 10 Feb 2018 12:43:30 +0100 -Subject: [PATCH] mac80211: minstrel: merge with minstrel_ht, always enable - VHT support - -Legacy-only devices are not very common and the overhead of the extra -code for HT and VHT rates is not big enough to justify all those extra -lines of code to make it optional. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/Kconfig -+++ b/net/mac80211/Kconfig -@@ -25,20 +25,6 @@ config MAC80211_RC_MINSTREL - ---help--- - This option enables the 'minstrel' TX rate control algorithm - --config MAC80211_RC_MINSTREL_HT -- bool "Minstrel 802.11n support" if EXPERT -- depends on MAC80211_RC_MINSTREL -- default y -- ---help--- -- This option enables the 'minstrel_ht' TX rate control algorithm -- --config MAC80211_RC_MINSTREL_VHT -- bool "Minstrel 802.11ac support" if EXPERT -- depends on MAC80211_RC_MINSTREL_HT -- default n -- ---help--- -- This option enables VHT in the 'minstrel_ht' TX rate control algorithm -- - choice - prompt "Default rate control algorithm" - depends on MAC80211_HAS_RC -@@ -60,8 +46,7 @@ endchoice - - config MAC80211_RC_DEFAULT - string -- default "minstrel_ht" if MAC80211_RC_DEFAULT_MINSTREL && MAC80211_RC_MINSTREL_HT -- default "minstrel" if MAC80211_RC_DEFAULT_MINSTREL -+ default "minstrel_ht" if MAC80211_RC_DEFAULT_MINSTREL - default "" - - endif ---- a/net/mac80211/Makefile -+++ b/net/mac80211/Makefile -@@ -52,13 +52,14 @@ mac80211-$(CONFIG_PM) += pm.o - - CFLAGS_trace.o := -I$(src) - --rc80211_minstrel-y := rc80211_minstrel.o --rc80211_minstrel-$(CPTCFG_MAC80211_DEBUGFS) += rc80211_minstrel_debugfs.o -+rc80211_minstrel-y := \ -+ rc80211_minstrel.o \ -+ rc80211_minstrel_ht.o - --rc80211_minstrel_ht-y := rc80211_minstrel_ht.o --rc80211_minstrel_ht-$(CPTCFG_MAC80211_DEBUGFS) += rc80211_minstrel_ht_debugfs.o -+rc80211_minstrel-$(CPTCFG_MAC80211_DEBUGFS) += \ -+ rc80211_minstrel_debugfs.o \ -+ rc80211_minstrel_ht_debugfs.o - - mac80211-$(CPTCFG_MAC80211_RC_MINSTREL) += $(rc80211_minstrel-y) --mac80211-$(CPTCFG_MAC80211_RC_MINSTREL_HT) += $(rc80211_minstrel_ht-y) - - ccflags-y += -DDEBUG ---- a/net/mac80211/main.c -+++ b/net/mac80211/main.c -@@ -1308,18 +1308,12 @@ static int __init ieee80211_init(void) - if (ret) - return ret; - -- ret = rc80211_minstrel_ht_init(); -- if (ret) -- goto err_minstrel; -- - ret = ieee80211_iface_init(); - if (ret) - goto err_netdev; - - return 0; - err_netdev: -- rc80211_minstrel_ht_exit(); -- err_minstrel: - rc80211_minstrel_exit(); - - return ret; -@@ -1327,7 +1321,6 @@ static int __init ieee80211_init(void) - - static void __exit ieee80211_exit(void) - { -- rc80211_minstrel_ht_exit(); - rc80211_minstrel_exit(); - - ieee80211s_stop(); ---- a/net/mac80211/rate.h -+++ b/net/mac80211/rate.h -@@ -95,18 +95,5 @@ static inline void rc80211_minstrel_exit - } - #endif - --#ifdef CPTCFG_MAC80211_RC_MINSTREL_HT --int rc80211_minstrel_ht_init(void); --void rc80211_minstrel_ht_exit(void); --#else --static inline int rc80211_minstrel_ht_init(void) --{ -- return 0; --} --static inline void rc80211_minstrel_ht_exit(void) --{ --} --#endif -- - - #endif /* IEEE80211_RATE_H */ ---- a/net/mac80211/rc80211_minstrel.c -+++ b/net/mac80211/rc80211_minstrel.c -@@ -572,138 +572,6 @@ minstrel_rate_init(void *priv, struct ie - minstrel_update_rates(mp, mi); - } - --static void * --minstrel_alloc_sta(void *priv, struct ieee80211_sta *sta, gfp_t gfp) --{ -- struct ieee80211_supported_band *sband; -- struct minstrel_sta_info *mi; -- struct minstrel_priv *mp = priv; -- struct ieee80211_hw *hw = mp->hw; -- int max_rates = 0; -- int i; -- -- mi = kzalloc(sizeof(struct minstrel_sta_info), gfp); -- if (!mi) -- return NULL; -- -- for (i = 0; i < NUM_NL80211_BANDS; i++) { -- sband = hw->wiphy->bands[i]; -- if (sband && sband->n_bitrates > max_rates) -- max_rates = sband->n_bitrates; -- } -- -- mi->r = kcalloc(max_rates, sizeof(struct minstrel_rate), gfp); -- if (!mi->r) -- goto error; -- -- mi->sample_table = kmalloc_array(max_rates, SAMPLE_COLUMNS, gfp); -- if (!mi->sample_table) -- goto error1; -- -- mi->last_stats_update = jiffies; -- return mi; -- --error1: -- kfree(mi->r); --error: -- kfree(mi); -- return NULL; --} -- --static void --minstrel_free_sta(void *priv, struct ieee80211_sta *sta, void *priv_sta) --{ -- struct minstrel_sta_info *mi = priv_sta; -- -- kfree(mi->sample_table); -- kfree(mi->r); -- kfree(mi); --} -- --static void --minstrel_init_cck_rates(struct minstrel_priv *mp) --{ -- static const int bitrates[4] = { 10, 20, 55, 110 }; -- struct ieee80211_supported_band *sband; -- u32 rate_flags = ieee80211_chandef_rate_flags(&mp->hw->conf.chandef); -- int i, j; -- -- sband = mp->hw->wiphy->bands[NL80211_BAND_2GHZ]; -- if (!sband) -- return; -- -- for (i = 0, j = 0; i < sband->n_bitrates; i++) { -- struct ieee80211_rate *rate = &sband->bitrates[i]; -- -- if (rate->flags & IEEE80211_RATE_ERP_G) -- continue; -- -- if ((rate_flags & sband->bitrates[i].flags) != rate_flags) -- continue; -- -- for (j = 0; j < ARRAY_SIZE(bitrates); j++) { -- if (rate->bitrate != bitrates[j]) -- continue; -- -- mp->cck_rates[j] = i; -- break; -- } -- } --} -- --static void * --minstrel_alloc(struct ieee80211_hw *hw, struct dentry *debugfsdir) --{ -- struct minstrel_priv *mp; -- -- mp = kzalloc(sizeof(struct minstrel_priv), GFP_ATOMIC); -- if (!mp) -- return NULL; -- -- /* contention window settings -- * Just an approximation. Using the per-queue values would complicate -- * the calculations and is probably unnecessary */ -- mp->cw_min = 15; -- mp->cw_max = 1023; -- -- /* number of packets (in %) to use for sampling other rates -- * sample less often for non-mrr packets, because the overhead -- * is much higher than with mrr */ -- mp->lookaround_rate = 5; -- mp->lookaround_rate_mrr = 10; -- -- /* maximum time that the hw is allowed to stay in one MRR segment */ -- mp->segment_size = 6000; -- -- if (hw->max_rate_tries > 0) -- mp->max_retry = hw->max_rate_tries; -- else -- /* safe default, does not necessarily have to match hw properties */ -- mp->max_retry = 7; -- -- if (hw->max_rates >= 4) -- mp->has_mrr = true; -- -- mp->hw = hw; -- mp->update_interval = 100; -- --#ifdef CPTCFG_MAC80211_DEBUGFS -- mp->fixed_rate_idx = (u32) -1; -- debugfs_create_u32("fixed_rate_idx", S_IRUGO | S_IWUGO, debugfsdir, -- &mp->fixed_rate_idx); --#endif -- -- minstrel_init_cck_rates(mp); -- -- return mp; --} -- --static void --minstrel_free(void *priv) --{ -- kfree(priv); --} -- - static u32 minstrel_get_expected_throughput(void *priv_sta) - { - struct minstrel_sta_info *mi = priv_sta; -@@ -722,28 +590,8 @@ static u32 minstrel_get_expected_through - } - - const struct rate_control_ops mac80211_minstrel = { -- .name = "minstrel", - .tx_status_ext = minstrel_tx_status, - .get_rate = minstrel_get_rate, - .rate_init = minstrel_rate_init, -- .alloc = minstrel_alloc, -- .free = minstrel_free, -- .alloc_sta = minstrel_alloc_sta, -- .free_sta = minstrel_free_sta, --#ifdef CPTCFG_MAC80211_DEBUGFS -- .add_sta_debugfs = minstrel_add_sta_debugfs, --#endif - .get_expected_throughput = minstrel_get_expected_throughput, - }; -- --int __init --rc80211_minstrel_init(void) --{ -- return ieee80211_rate_control_register(&mac80211_minstrel); --} -- --void --rc80211_minstrel_exit(void) --{ -- ieee80211_rate_control_unregister(&mac80211_minstrel); --} ---- a/net/mac80211/rc80211_minstrel.h -+++ b/net/mac80211/rc80211_minstrel.h -@@ -158,7 +158,5 @@ int minstrel_get_tp_avg(struct minstrel_ - /* debugfs */ - int minstrel_stats_open(struct inode *inode, struct file *file); - int minstrel_stats_csv_open(struct inode *inode, struct file *file); --ssize_t minstrel_stats_read(struct file *file, char __user *buf, size_t len, loff_t *ppos); --int minstrel_stats_release(struct inode *inode, struct file *file); - - #endif ---- a/net/mac80211/rc80211_minstrel_debugfs.c -+++ b/net/mac80211/rc80211_minstrel_debugfs.c -@@ -54,22 +54,6 @@ - #include <net/mac80211.h> - #include "rc80211_minstrel.h" - --ssize_t --minstrel_stats_read(struct file *file, char __user *buf, size_t len, loff_t *ppos) --{ -- struct minstrel_debugfs_info *ms; -- -- ms = file->private_data; -- return simple_read_from_buffer(buf, len, ppos, ms->buf, ms->len); --} -- --int --minstrel_stats_release(struct inode *inode, struct file *file) --{ -- kfree(file->private_data); -- return 0; --} -- - int - minstrel_stats_open(struct inode *inode, struct file *file) - { -@@ -135,14 +119,6 @@ minstrel_stats_open(struct inode *inode, - return 0; - } - --static const struct file_operations minstrel_stat_fops = { -- .owner = THIS_MODULE, -- .open = minstrel_stats_open, -- .read = minstrel_stats_read, -- .release = minstrel_stats_release, -- .llseek = default_llseek, --}; -- - int - minstrel_stats_csv_open(struct inode *inode, struct file *file) - { -@@ -200,21 +176,3 @@ minstrel_stats_csv_open(struct inode *in - - return 0; - } -- --static const struct file_operations minstrel_stat_csv_fops = { -- .owner = THIS_MODULE, -- .open = minstrel_stats_csv_open, -- .read = minstrel_stats_read, -- .release = minstrel_stats_release, -- .llseek = default_llseek, --}; -- --void --minstrel_add_sta_debugfs(void *priv, void *priv_sta, struct dentry *dir) --{ -- struct minstrel_sta_info *mi = priv_sta; -- -- debugfs_create_file("rc_stats", S_IRUGO, dir, mi, &minstrel_stat_fops); -- debugfs_create_file("rc_stats_csv", S_IRUGO, dir, mi, -- &minstrel_stat_csv_fops); --} ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -137,12 +137,10 @@ - } \ - } - --#ifdef CPTCFG_MAC80211_RC_MINSTREL_VHT - static bool minstrel_vht_only = true; - module_param(minstrel_vht_only, bool, 0644); - MODULE_PARM_DESC(minstrel_vht_only, - "Use only VHT rates when VHT is supported by sta."); --#endif - - /* - * To enable sufficiently targeted rate sampling, MCS rates are divided into -@@ -171,7 +169,6 @@ const struct mcs_group minstrel_mcs_grou - - CCK_GROUP, - --#ifdef CPTCFG_MAC80211_RC_MINSTREL_VHT - VHT_GROUP(1, 0, BW_20), - VHT_GROUP(2, 0, BW_20), - VHT_GROUP(3, 0, BW_20), -@@ -195,7 +192,6 @@ const struct mcs_group minstrel_mcs_grou - VHT_GROUP(1, 1, BW_80), - VHT_GROUP(2, 1, BW_80), - VHT_GROUP(3, 1, BW_80), --#endif - }; - - static u8 sample_table[SAMPLE_COLUMNS][MCS_GROUP_RATES] __read_mostly; -@@ -1146,12 +1142,10 @@ minstrel_ht_update_caps(void *priv, stru - - BUILD_BUG_ON(ARRAY_SIZE(minstrel_mcs_groups) != MINSTREL_GROUPS_NB); - --#ifdef CPTCFG_MAC80211_RC_MINSTREL_VHT - if (vht_cap->vht_supported) - use_vht = vht_cap->vht_mcs.tx_mcs_map != cpu_to_le16(~0); - else --#endif -- use_vht = 0; -+ use_vht = 0; - - msp->is_ht = true; - memset(mi, 0, sizeof(*mi)); -@@ -1226,10 +1220,9 @@ minstrel_ht_update_caps(void *priv, stru - - /* HT rate */ - if (gflags & IEEE80211_TX_RC_MCS) { --#ifdef CPTCFG_MAC80211_RC_MINSTREL_VHT - if (use_vht && minstrel_vht_only) - continue; --#endif -+ - mi->supported[i] = mcs->rx_mask[nss - 1]; - if (mi->supported[i]) - n_supported++; -@@ -1349,16 +1342,88 @@ minstrel_ht_free_sta(void *priv, struct - kfree(msp); - } - -+static void -+minstrel_ht_init_cck_rates(struct minstrel_priv *mp) -+{ -+ static const int bitrates[4] = { 10, 20, 55, 110 }; -+ struct ieee80211_supported_band *sband; -+ u32 rate_flags = ieee80211_chandef_rate_flags(&mp->hw->conf.chandef); -+ int i, j; -+ -+ sband = mp->hw->wiphy->bands[NL80211_BAND_2GHZ]; -+ if (!sband) -+ return; -+ -+ for (i = 0, j = 0; i < sband->n_bitrates; i++) { -+ struct ieee80211_rate *rate = &sband->bitrates[i]; -+ -+ if (rate->flags & IEEE80211_RATE_ERP_G) -+ continue; -+ -+ if ((rate_flags & sband->bitrates[i].flags) != rate_flags) -+ continue; -+ -+ for (j = 0; j < ARRAY_SIZE(bitrates); j++) { -+ if (rate->bitrate != bitrates[j]) -+ continue; -+ -+ mp->cck_rates[j] = i; -+ break; -+ } -+ } -+} -+ - static void * - minstrel_ht_alloc(struct ieee80211_hw *hw, struct dentry *debugfsdir) - { -- return mac80211_minstrel.alloc(hw, debugfsdir); -+ struct minstrel_priv *mp; -+ -+ mp = kzalloc(sizeof(struct minstrel_priv), GFP_ATOMIC); -+ if (!mp) -+ return NULL; -+ -+ /* contention window settings -+ * Just an approximation. Using the per-queue values would complicate -+ * the calculations and is probably unnecessary */ -+ mp->cw_min = 15; -+ mp->cw_max = 1023; -+ -+ /* number of packets (in %) to use for sampling other rates -+ * sample less often for non-mrr packets, because the overhead -+ * is much higher than with mrr */ -+ mp->lookaround_rate = 5; -+ mp->lookaround_rate_mrr = 10; -+ -+ /* maximum time that the hw is allowed to stay in one MRR segment */ -+ mp->segment_size = 6000; -+ -+ if (hw->max_rate_tries > 0) -+ mp->max_retry = hw->max_rate_tries; -+ else -+ /* safe default, does not necessarily have to match hw properties */ -+ mp->max_retry = 7; -+ -+ if (hw->max_rates >= 4) -+ mp->has_mrr = true; -+ -+ mp->hw = hw; -+ mp->update_interval = 100; -+ -+#ifdef CPTCFG_MAC80211_DEBUGFS -+ mp->fixed_rate_idx = (u32) -1; -+ debugfs_create_u32("fixed_rate_idx", S_IRUGO | S_IWUGO, debugfsdir, -+ &mp->fixed_rate_idx); -+#endif -+ -+ minstrel_ht_init_cck_rates(mp); -+ -+ return mp; - } - - static void - minstrel_ht_free(void *priv) - { -- mac80211_minstrel.free(priv); -+ kfree(priv); - } - - static u32 minstrel_ht_get_expected_throughput(void *priv_sta) -@@ -1417,14 +1482,14 @@ static void __init init_sample_table(voi - } - - int __init --rc80211_minstrel_ht_init(void) -+rc80211_minstrel_init(void) - { - init_sample_table(); - return ieee80211_rate_control_register(&mac80211_minstrel_ht); - } - - void --rc80211_minstrel_ht_exit(void) -+rc80211_minstrel_exit(void) - { - ieee80211_rate_control_unregister(&mac80211_minstrel_ht); - } ---- a/net/mac80211/rc80211_minstrel_ht.h -+++ b/net/mac80211/rc80211_minstrel_ht.h -@@ -15,11 +15,7 @@ - */ - #define MINSTREL_MAX_STREAMS 3 - #define MINSTREL_HT_STREAM_GROUPS 4 /* BW(=2) * SGI(=2) */ --#ifdef CPTCFG_MAC80211_RC_MINSTREL_VHT - #define MINSTREL_VHT_STREAM_GROUPS 6 /* BW(=3) * SGI(=2) */ --#else --#define MINSTREL_VHT_STREAM_GROUPS 0 --#endif - - #define MINSTREL_HT_GROUPS_NB (MINSTREL_MAX_STREAMS * \ - MINSTREL_HT_STREAM_GROUPS) -@@ -34,11 +30,7 @@ - #define MINSTREL_CCK_GROUP (MINSTREL_HT_GROUP_0 + MINSTREL_HT_GROUPS_NB) - #define MINSTREL_VHT_GROUP_0 (MINSTREL_CCK_GROUP + 1) - --#ifdef CPTCFG_MAC80211_RC_MINSTREL_VHT - #define MCS_GROUP_RATES 10 --#else --#define MCS_GROUP_RATES 8 --#endif - - struct mcs_group { - u32 flags; ---- a/net/mac80211/rc80211_minstrel_ht_debugfs.c -+++ b/net/mac80211/rc80211_minstrel_ht_debugfs.c -@@ -15,6 +15,22 @@ - #include "rc80211_minstrel.h" - #include "rc80211_minstrel_ht.h" - -+static ssize_t -+minstrel_stats_read(struct file *file, char __user *buf, size_t len, loff_t *ppos) -+{ -+ struct minstrel_debugfs_info *ms; -+ -+ ms = file->private_data; -+ return simple_read_from_buffer(buf, len, ppos, ms->buf, ms->len); -+} -+ -+static int -+minstrel_stats_release(struct inode *inode, struct file *file) -+{ -+ kfree(file->private_data); -+ return 0; -+} -+ - static char * - minstrel_ht_stats_dump(struct minstrel_ht_sta *mi, int i, char *p) - { diff --git a/package/kernel/mac80211/patches/subsys/306-mac80211-minstrel-reduce-minstrel_mcs_groups-size.patch b/package/kernel/mac80211/patches/subsys/306-mac80211-minstrel-reduce-minstrel_mcs_groups-size.patch deleted file mode 100644 index 02a0ca0a52..0000000000 --- a/package/kernel/mac80211/patches/subsys/306-mac80211-minstrel-reduce-minstrel_mcs_groups-size.patch +++ /dev/null @@ -1,368 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 10 Feb 2018 12:45:47 +0100 -Subject: [PATCH] mac80211: minstrel: reduce minstrel_mcs_groups size - -By storing a shift value for all duration values of a group, we can -reduce precision by a neglegible amount to make it fit into a u16 value. -This improves cache footprint and reduces size: - -Before: - text data bss dec hex filename - 10024 116 0 10140 279c rc80211_minstrel_ht.o - -After: - text data bss dec hex filename - 9368 116 0 9484 250c rc80211_minstrel_ht.o - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -52,22 +52,23 @@ - _streams - 1 - - /* MCS rate information for an MCS group */ --#define MCS_GROUP(_streams, _sgi, _ht40) \ -+#define MCS_GROUP(_streams, _sgi, _ht40, _s) \ - [GROUP_IDX(_streams, _sgi, _ht40)] = { \ - .streams = _streams, \ -+ .shift = _s, \ - .flags = \ - IEEE80211_TX_RC_MCS | \ - (_sgi ? IEEE80211_TX_RC_SHORT_GI : 0) | \ - (_ht40 ? IEEE80211_TX_RC_40_MHZ_WIDTH : 0), \ - .duration = { \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 54 : 26), \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 108 : 52), \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 162 : 78), \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 216 : 104), \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 324 : 156), \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 432 : 208), \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 486 : 234), \ -- MCS_DURATION(_streams, _sgi, _ht40 ? 540 : 260) \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 54 : 26) >> _s, \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 108 : 52) >> _s, \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 162 : 78) >> _s, \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 216 : 104) >> _s, \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 324 : 156) >> _s, \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 432 : 208) >> _s, \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 486 : 234) >> _s, \ -+ MCS_DURATION(_streams, _sgi, _ht40 ? 540 : 260) >> _s \ - } \ - } - -@@ -80,9 +81,10 @@ - #define BW2VBPS(_bw, r3, r2, r1) \ - (_bw == BW_80 ? r3 : _bw == BW_40 ? r2 : r1) - --#define VHT_GROUP(_streams, _sgi, _bw) \ -+#define VHT_GROUP(_streams, _sgi, _bw, _s) \ - [VHT_GROUP_IDX(_streams, _sgi, _bw)] = { \ - .streams = _streams, \ -+ .shift = _s, \ - .flags = \ - IEEE80211_TX_RC_VHT_MCS | \ - (_sgi ? IEEE80211_TX_RC_SHORT_GI : 0) | \ -@@ -90,25 +92,25 @@ - _bw == BW_40 ? IEEE80211_TX_RC_40_MHZ_WIDTH : 0), \ - .duration = { \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 117, 54, 26)), \ -+ BW2VBPS(_bw, 117, 54, 26)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 234, 108, 52)), \ -+ BW2VBPS(_bw, 234, 108, 52)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 351, 162, 78)), \ -+ BW2VBPS(_bw, 351, 162, 78)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 468, 216, 104)), \ -+ BW2VBPS(_bw, 468, 216, 104)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 702, 324, 156)), \ -+ BW2VBPS(_bw, 702, 324, 156)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 936, 432, 208)), \ -+ BW2VBPS(_bw, 936, 432, 208)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 1053, 486, 234)), \ -+ BW2VBPS(_bw, 1053, 486, 234)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 1170, 540, 260)), \ -+ BW2VBPS(_bw, 1170, 540, 260)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 1404, 648, 312)), \ -+ BW2VBPS(_bw, 1404, 648, 312)) >> _s, \ - MCS_DURATION(_streams, _sgi, \ -- BW2VBPS(_bw, 1560, 720, 346)) \ -+ BW2VBPS(_bw, 1560, 720, 346)) >> _s \ - } \ - } - -@@ -121,19 +123,20 @@ - (CCK_DURATION((_bitrate > 10 ? 20 : 10), false, 60) + \ - CCK_DURATION(_bitrate, _short, AVG_PKT_SIZE)) - --#define CCK_DURATION_LIST(_short) \ -- CCK_ACK_DURATION(10, _short), \ -- CCK_ACK_DURATION(20, _short), \ -- CCK_ACK_DURATION(55, _short), \ -- CCK_ACK_DURATION(110, _short) -+#define CCK_DURATION_LIST(_short, _s) \ -+ CCK_ACK_DURATION(10, _short) >> _s, \ -+ CCK_ACK_DURATION(20, _short) >> _s, \ -+ CCK_ACK_DURATION(55, _short) >> _s, \ -+ CCK_ACK_DURATION(110, _short) >> _s - --#define CCK_GROUP \ -+#define CCK_GROUP(_s) \ - [MINSTREL_CCK_GROUP] = { \ - .streams = 0, \ - .flags = 0, \ -+ .shift = _s, \ - .duration = { \ -- CCK_DURATION_LIST(false), \ -- CCK_DURATION_LIST(true) \ -+ CCK_DURATION_LIST(false, _s), \ -+ CCK_DURATION_LIST(true, _s) \ - } \ - } - -@@ -151,47 +154,47 @@ MODULE_PARM_DESC(minstrel_vht_only, - * BW -> SGI -> #streams - */ - const struct mcs_group minstrel_mcs_groups[] = { -- MCS_GROUP(1, 0, BW_20), -- MCS_GROUP(2, 0, BW_20), -- MCS_GROUP(3, 0, BW_20), -- -- MCS_GROUP(1, 1, BW_20), -- MCS_GROUP(2, 1, BW_20), -- MCS_GROUP(3, 1, BW_20), -- -- MCS_GROUP(1, 0, BW_40), -- MCS_GROUP(2, 0, BW_40), -- MCS_GROUP(3, 0, BW_40), -- -- MCS_GROUP(1, 1, BW_40), -- MCS_GROUP(2, 1, BW_40), -- MCS_GROUP(3, 1, BW_40), -- -- CCK_GROUP, -- -- VHT_GROUP(1, 0, BW_20), -- VHT_GROUP(2, 0, BW_20), -- VHT_GROUP(3, 0, BW_20), -- -- VHT_GROUP(1, 1, BW_20), -- VHT_GROUP(2, 1, BW_20), -- VHT_GROUP(3, 1, BW_20), -- -- VHT_GROUP(1, 0, BW_40), -- VHT_GROUP(2, 0, BW_40), -- VHT_GROUP(3, 0, BW_40), -- -- VHT_GROUP(1, 1, BW_40), -- VHT_GROUP(2, 1, BW_40), -- VHT_GROUP(3, 1, BW_40), -- -- VHT_GROUP(1, 0, BW_80), -- VHT_GROUP(2, 0, BW_80), -- VHT_GROUP(3, 0, BW_80), -- -- VHT_GROUP(1, 1, BW_80), -- VHT_GROUP(2, 1, BW_80), -- VHT_GROUP(3, 1, BW_80), -+ MCS_GROUP(1, 0, BW_20, 5), -+ MCS_GROUP(2, 0, BW_20, 4), -+ MCS_GROUP(3, 0, BW_20, 4), -+ -+ MCS_GROUP(1, 1, BW_20, 5), -+ MCS_GROUP(2, 1, BW_20, 4), -+ MCS_GROUP(3, 1, BW_20, 4), -+ -+ MCS_GROUP(1, 0, BW_40, 4), -+ MCS_GROUP(2, 0, BW_40, 4), -+ MCS_GROUP(3, 0, BW_40, 4), -+ -+ MCS_GROUP(1, 1, BW_40, 4), -+ MCS_GROUP(2, 1, BW_40, 4), -+ MCS_GROUP(3, 1, BW_40, 4), -+ -+ CCK_GROUP(8), -+ -+ VHT_GROUP(1, 0, BW_20, 5), -+ VHT_GROUP(2, 0, BW_20, 4), -+ VHT_GROUP(3, 0, BW_20, 4), -+ -+ VHT_GROUP(1, 1, BW_20, 5), -+ VHT_GROUP(2, 1, BW_20, 4), -+ VHT_GROUP(3, 1, BW_20, 4), -+ -+ VHT_GROUP(1, 0, BW_40, 4), -+ VHT_GROUP(2, 0, BW_40, 4), -+ VHT_GROUP(3, 0, BW_40, 4), -+ -+ VHT_GROUP(1, 1, BW_40, 4), -+ VHT_GROUP(2, 1, BW_40, 4), -+ VHT_GROUP(3, 1, BW_40, 4), -+ -+ VHT_GROUP(1, 0, BW_80, 4), -+ VHT_GROUP(2, 0, BW_80, 4), -+ VHT_GROUP(3, 0, BW_80, 4), -+ -+ VHT_GROUP(1, 1, BW_80, 4), -+ VHT_GROUP(2, 1, BW_80, 4), -+ VHT_GROUP(3, 1, BW_80, 4), - }; - - static u8 sample_table[SAMPLE_COLUMNS][MCS_GROUP_RATES] __read_mostly; -@@ -307,7 +310,8 @@ minstrel_ht_get_tp_avg(struct minstrel_h - if (group != MINSTREL_CCK_GROUP) - nsecs = 1000 * mi->overhead / MINSTREL_TRUNC(mi->avg_ampdu_len); - -- nsecs += minstrel_mcs_groups[group].duration[rate]; -+ nsecs += minstrel_mcs_groups[group].duration[rate] << -+ minstrel_mcs_groups[group].shift; - - /* - * For the throughput calculation, limit the probability value to 90% to -@@ -755,12 +759,19 @@ minstrel_ht_tx_status(void *priv, struct - minstrel_ht_update_rates(mp, mi); - } - -+static inline int -+minstrel_get_duration(int index) -+{ -+ const struct mcs_group *group = &minstrel_mcs_groups[index / MCS_GROUP_RATES]; -+ unsigned int duration = group->duration[index % MCS_GROUP_RATES]; -+ return duration << group->shift; -+} -+ - static void - minstrel_calc_retransmit(struct minstrel_priv *mp, struct minstrel_ht_sta *mi, - int index) - { - struct minstrel_rate_stats *mrs; -- const struct mcs_group *group; - unsigned int tx_time, tx_time_rtscts, tx_time_data; - unsigned int cw = mp->cw_min; - unsigned int ctime = 0; -@@ -779,8 +790,7 @@ minstrel_calc_retransmit(struct minstrel - mrs->retry_count_rtscts = 2; - mrs->retry_updated = true; - -- group = &minstrel_mcs_groups[index / MCS_GROUP_RATES]; -- tx_time_data = group->duration[index % MCS_GROUP_RATES] * ampdu_len / 1000; -+ tx_time_data = minstrel_get_duration(index) * ampdu_len / 1000; - - /* Contention time for first 2 tries */ - ctime = (t_slot * cw) >> 1; -@@ -874,20 +884,24 @@ minstrel_ht_get_max_amsdu_len(struct min - int group = mi->max_prob_rate / MCS_GROUP_RATES; - const struct mcs_group *g = &minstrel_mcs_groups[group]; - int rate = mi->max_prob_rate % MCS_GROUP_RATES; -+ unsigned int duration; - - /* Disable A-MSDU if max_prob_rate is bad */ - if (mi->groups[group].rates[rate].prob_ewma < MINSTREL_FRAC(50, 100)) - return 1; - -+ duration = g->duration[rate]; -+ duration <<= g->shift; -+ - /* If the rate is slower than single-stream MCS1, make A-MSDU limit small */ -- if (g->duration[rate] > MCS_DURATION(1, 0, 52)) -+ if (duration > MCS_DURATION(1, 0, 52)) - return 500; - - /* - * If the rate is slower than single-stream MCS4, limit A-MSDU to usual - * data packet size - */ -- if (g->duration[rate] > MCS_DURATION(1, 0, 104)) -+ if (duration > MCS_DURATION(1, 0, 104)) - return 1600; - - /* -@@ -895,7 +909,7 @@ minstrel_ht_get_max_amsdu_len(struct min - * rate success probability is less than 75%, limit A-MSDU to twice the usual - * data packet size - */ -- if (g->duration[rate] > MCS_DURATION(1, 0, 260) || -+ if (duration > MCS_DURATION(1, 0, 260) || - (minstrel_ht_get_prob_ewma(mi, mi->max_tp_rate[0]) < - MINSTREL_FRAC(75, 100))) - return 3200; -@@ -942,13 +956,6 @@ minstrel_ht_update_rates(struct minstrel - rate_control_set_rates(mp->hw, mi->sta, rates); - } - --static inline int --minstrel_get_duration(int index) --{ -- const struct mcs_group *group = &minstrel_mcs_groups[index / MCS_GROUP_RATES]; -- return group->duration[index % MCS_GROUP_RATES]; --} -- - static int - minstrel_get_sample_rate(struct minstrel_priv *mp, struct minstrel_ht_sta *mi) - { ---- a/net/mac80211/rc80211_minstrel_ht.h -+++ b/net/mac80211/rc80211_minstrel_ht.h -@@ -33,9 +33,10 @@ - #define MCS_GROUP_RATES 10 - - struct mcs_group { -- u32 flags; -- unsigned int streams; -- unsigned int duration[MCS_GROUP_RATES]; -+ u16 flags; -+ u8 streams; -+ u8 shift; -+ u16 duration[MCS_GROUP_RATES]; - }; - - extern const struct mcs_group minstrel_mcs_groups[]; ---- a/net/mac80211/rc80211_minstrel_ht_debugfs.c -+++ b/net/mac80211/rc80211_minstrel_ht_debugfs.c -@@ -58,6 +58,7 @@ minstrel_ht_stats_dump(struct minstrel_h - static const int bitrates[4] = { 10, 20, 55, 110 }; - int idx = i * MCS_GROUP_RATES + j; - unsigned int prob_ewmsd; -+ unsigned int duration; - - if (!(mi->supported[i] & BIT(j))) - continue; -@@ -95,7 +96,9 @@ minstrel_ht_stats_dump(struct minstrel_h - p += sprintf(p, " %3u ", idx); - - /* tx_time[rate(i)] in usec */ -- tx_time = DIV_ROUND_CLOSEST(mg->duration[j], 1000); -+ duration = mg->duration[j]; -+ duration <<= mg->shift; -+ tx_time = DIV_ROUND_CLOSEST(duration, 1000); - p += sprintf(p, "%6u ", tx_time); - - tp_max = minstrel_ht_get_tp_avg(mi, i, j, MINSTREL_FRAC(100, 100)); -@@ -204,6 +207,7 @@ minstrel_ht_stats_csv_dump(struct minstr - static const int bitrates[4] = { 10, 20, 55, 110 }; - int idx = i * MCS_GROUP_RATES + j; - unsigned int prob_ewmsd; -+ unsigned int duration; - - if (!(mi->supported[i] & BIT(j))) - continue; -@@ -238,7 +242,10 @@ minstrel_ht_stats_csv_dump(struct minstr - } - - p += sprintf(p, "%u,", idx); -- tx_time = DIV_ROUND_CLOSEST(mg->duration[j], 1000); -+ -+ duration = mg->duration[j]; -+ duration <<= mg->shift; -+ tx_time = DIV_ROUND_CLOSEST(duration, 1000); - p += sprintf(p, "%u,", tx_time); - - tp_max = minstrel_ht_get_tp_avg(mi, i, j, MINSTREL_FRAC(100, 100)); diff --git a/package/kernel/mac80211/patches/subsys/307-mac80211-minstrel-fix-using-short-preamble-CCK-rates.patch b/package/kernel/mac80211/patches/subsys/307-mac80211-minstrel-fix-using-short-preamble-CCK-rates.patch deleted file mode 100644 index 502d8c7768..0000000000 --- a/package/kernel/mac80211/patches/subsys/307-mac80211-minstrel-fix-using-short-preamble-CCK-rates.patch +++ /dev/null @@ -1,31 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 10 Feb 2018 13:43:07 +0100 -Subject: [PATCH] mac80211: minstrel: fix using short preamble CCK rates on - HT clients - -mi->supported[MINSTREL_CCK_GROUP] needs to be updated - -Fixes: 782dda00ab8e ("mac80211: minstrel_ht: move short preamble check out of get_rate") -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -1135,7 +1135,6 @@ minstrel_ht_update_caps(void *priv, stru - struct ieee80211_mcs_info *mcs = &sta->ht_cap.mcs; - u16 ht_cap = sta->ht_cap.cap; - struct ieee80211_sta_vht_cap *vht_cap = &sta->vht_cap; -- struct sta_info *sinfo = container_of(sta, struct sta_info, sta); - int use_vht; - int n_supported = 0; - int ack_dur; -@@ -1267,8 +1266,7 @@ minstrel_ht_update_caps(void *priv, stru - if (!n_supported) - goto use_legacy; - -- if (test_sta_flag(sinfo, WLAN_STA_SHORT_PREAMBLE)) -- mi->cck_supported_short |= mi->cck_supported_short << 4; -+ mi->supported[MINSTREL_CCK_GROUP] |= mi->cck_supported_short << 4; - - /* create an initial rate table with the lowest supported rates */ - minstrel_ht_update_stats(mp, mi); diff --git a/package/kernel/mac80211/patches/subsys/308-mac80211-minstrel-fix-CCK-rate-group-streams-value.patch b/package/kernel/mac80211/patches/subsys/308-mac80211-minstrel-fix-CCK-rate-group-streams-value.patch deleted file mode 100644 index f0ffcd9655..0000000000 --- a/package/kernel/mac80211/patches/subsys/308-mac80211-minstrel-fix-CCK-rate-group-streams-value.patch +++ /dev/null @@ -1,20 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Thu, 1 Mar 2018 13:27:54 +0100 -Subject: [PATCH] mac80211: minstrel: fix CCK rate group streams value - -Fixes a harmless underflow issue when CCK rates are actively being used - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -131,7 +131,7 @@ - - #define CCK_GROUP(_s) \ - [MINSTREL_CCK_GROUP] = { \ -- .streams = 0, \ -+ .streams = 1, \ - .flags = 0, \ - .shift = _s, \ - .duration = { \ diff --git a/package/kernel/mac80211/patches/subsys/309-mac80211-minstrel-fix-sampling-reporting-of-CCK-rate.patch b/package/kernel/mac80211/patches/subsys/309-mac80211-minstrel-fix-sampling-reporting-of-CCK-rate.patch deleted file mode 100644 index e0049c36eb..0000000000 --- a/package/kernel/mac80211/patches/subsys/309-mac80211-minstrel-fix-sampling-reporting-of-CCK-rate.patch +++ /dev/null @@ -1,58 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Thu, 1 Mar 2018 13:28:48 +0100 -Subject: [PATCH] mac80211: minstrel: fix sampling/reporting of CCK rates - in HT mode - -Long/short preamble selection cannot be sampled separately, since it -depends on the BSS state. Because of that, sampling attempts to -currently not used preamble modes are not counted in the statistics, -which leads to CCK rates being sampled too often. - -Fix statistics accounting for long/short preamble by increasing the -index where necessary. -Fix excessive CCK rate sampling by dropping unsupported sample attempts. - -This improves throughput on 2.4 GHz channels - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -281,7 +281,8 @@ minstrel_ht_get_stats(struct minstrel_pr - break; - - /* short preamble */ -- if (!(mi->supported[group] & BIT(idx))) -+ if ((mi->supported[group] & BIT(idx + 4)) && -+ (rate->flags & IEEE80211_TX_RC_USE_SHORT_PREAMBLE)) - idx += 4; - } - return &mi->groups[group].rates[idx]; -@@ -1080,18 +1081,23 @@ minstrel_ht_get_rate(void *priv, struct - return; - - sample_group = &minstrel_mcs_groups[sample_idx / MCS_GROUP_RATES]; -+ sample_idx %= MCS_GROUP_RATES; -+ -+ if (sample_group == &minstrel_mcs_groups[MINSTREL_CCK_GROUP] && -+ (sample_idx >= 4) != txrc->short_preamble) -+ return; -+ - info->flags |= IEEE80211_TX_CTL_RATE_CTRL_PROBE; - rate->count = 1; - -- if (sample_idx / MCS_GROUP_RATES == MINSTREL_CCK_GROUP) { -+ if (sample_group == &minstrel_mcs_groups[MINSTREL_CCK_GROUP]) { - int idx = sample_idx % ARRAY_SIZE(mp->cck_rates); - rate->idx = mp->cck_rates[idx]; - } else if (sample_group->flags & IEEE80211_TX_RC_VHT_MCS) { - ieee80211_rate_set_vht(rate, sample_idx % MCS_GROUP_RATES, - sample_group->streams); - } else { -- rate->idx = sample_idx % MCS_GROUP_RATES + -- (sample_group->streams - 1) * 8; -+ rate->idx = sample_idx + (sample_group->streams - 1) * 8; - } - - rate->flags = sample_group->flags; diff --git a/package/kernel/mac80211/patches/subsys/310-mac80211-minstrel-do-not-sample-rates-3-times-slower.patch b/package/kernel/mac80211/patches/subsys/310-mac80211-minstrel-do-not-sample-rates-3-times-slower.patch deleted file mode 100644 index 414cb137de..0000000000 --- a/package/kernel/mac80211/patches/subsys/310-mac80211-minstrel-do-not-sample-rates-3-times-slower.patch +++ /dev/null @@ -1,40 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 3 Mar 2018 18:48:58 +0100 -Subject: [PATCH] mac80211: minstrel: do not sample rates 3 times slower than - max_prob_rate - -These rates are highly unlikely to be used quickly, even if the link -deteriorates rapidly. This improves throughput in cases where CCK rates -are not reliable enough to be skipped entirely during sampling. -Sampling these rates regularly can cost a lot of airtime. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -1004,10 +1004,13 @@ minstrel_get_sample_rate(struct minstrel - return -1; - - /* -- * Do not sample if the probability is already higher than 95% -- * to avoid wasting airtime. -+ * Do not sample if the probability is already higher than 95%, -+ * or if the rate is 3 times slower than the current max probability -+ * rate, to avoid wasting airtime. - */ -- if (mrs->prob_ewma > MINSTREL_FRAC(95, 100)) -+ sample_dur = minstrel_get_duration(sample_idx); -+ if (mrs->prob_ewma > MINSTREL_FRAC(95, 100) || -+ minstrel_get_duration(mi->max_prob_rate) * 3 < sample_dur) - return -1; - - /* -@@ -1017,7 +1020,6 @@ minstrel_get_sample_rate(struct minstrel - - cur_max_tp_streams = minstrel_mcs_groups[tp_rate1 / - MCS_GROUP_RATES].streams; -- sample_dur = minstrel_get_duration(sample_idx); - if (sample_dur >= minstrel_get_duration(tp_rate2) && - (cur_max_tp_streams - 1 < - minstrel_mcs_groups[sample_group].streams || diff --git a/package/kernel/mac80211/patches/subsys/311-mac80211-fix-memory-accounting-with-A-MSDU-aggregati.patch b/package/kernel/mac80211/patches/subsys/311-mac80211-fix-memory-accounting-with-A-MSDU-aggregati.patch deleted file mode 100644 index 1fd2b25271..0000000000 --- a/package/kernel/mac80211/patches/subsys/311-mac80211-fix-memory-accounting-with-A-MSDU-aggregati.patch +++ /dev/null @@ -1,58 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Thu, 8 Mar 2018 21:00:56 +0100 -Subject: [PATCH] mac80211: fix memory accounting with A-MSDU aggregation - -fq uses skb->truesize for memory usage tracking. Increments/decrements -are done on enqueue/dequeue. -When A-MSDU aggregation is performed on tx side, the packet is -aggregated with the last packet in the queue belonging to the same flow. -There are multiple bugs here: -- The truesize field of the aggregated packet isn't updated, so memory -usage is underestimated -- fq->memory_usage isn't adjusted. - -Because of the combination of both bugs, this only causes tx issues in -rare cases, mainly when the A-MSDU head needs to be reallocated. - -Fix this by adjusting both truesize of the A-MSDU head and adding the -truesize delta to fq->memory_usage. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -3185,6 +3185,7 @@ static bool ieee80211_amsdu_aggregate(st - u8 max_subframes = sta->sta.max_amsdu_subframes; - int max_frags = local->hw.max_tx_fragments; - int max_amsdu_len = sta->sta.max_amsdu_len; -+ int orig_truesize; - __be16 len; - void *data; - bool ret = false; -@@ -3216,12 +3217,13 @@ static bool ieee80211_amsdu_aggregate(st - flow = fq_flow_classify(fq, tin, skb, fq_flow_get_default_func); - head = skb_peek_tail(&flow->queue); - if (!head) -- goto out; -+ goto unlock; - -+ orig_truesize = head->truesize; - orig_len = head->len; - - if (skb->len + head->len > max_amsdu_len) -- goto out; -+ goto unlock; - - nfrags = 1 + skb_shinfo(skb)->nr_frags; - nfrags += 1 + skb_shinfo(head)->nr_frags; -@@ -3279,6 +3281,9 @@ out_recalc: - fq_recalc_backlog(fq, tin, flow); - } - out: -+ fq->memory_usage += head->truesize - orig_truesize; -+ -+unlock: - spin_unlock_bh(&fq->lock); - - return ret; diff --git a/package/kernel/mac80211/patches/subsys/312-mac80211-minstrel_ht-add-flag-to-indicate-missing-in.patch b/package/kernel/mac80211/patches/subsys/312-mac80211-minstrel_ht-add-flag-to-indicate-missing-in.patch deleted file mode 100644 index f221d36bf8..0000000000 --- a/package/kernel/mac80211/patches/subsys/312-mac80211-minstrel_ht-add-flag-to-indicate-missing-in.patch +++ /dev/null @@ -1,122 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Wed, 16 Jan 2019 22:32:12 +0100 -Subject: [PATCH] mac80211: minstrel_ht: add flag to indicate - missing/inaccurate tx A-MPDU length - -Some hardware (e.g. MediaTek MT7603) cannot report A-MPDU length in tx status -information. Add support for a flag to indicate that, to allow minstrel_ht -to use a fixed value in its internal calculation (which gives better results -than just defaulting to 1). - -Signed-off-by: Felix Fietkau <nbd@nbd.name> -Signed-off-by: Johannes Berg <johannes.berg@intel.com> ---- - ---- a/include/net/mac80211.h -+++ b/include/net/mac80211.h -@@ -2131,6 +2131,9 @@ struct ieee80211_txq { - * @IEEE80211_HW_DOESNT_SUPPORT_QOS_NDP: The driver (or firmware) doesn't - * support QoS NDP for AP probing - that's most likely a driver bug. - * -+ * @IEEE80211_HW_TX_STATUS_NO_AMPDU_LEN: Driver does not report accurate A-MPDU -+ * length in tx status information -+ * - * @NUM_IEEE80211_HW_FLAGS: number of hardware flags, used for sizing arrays - */ - enum ieee80211_hw_flags { -@@ -2176,6 +2179,7 @@ enum ieee80211_hw_flags { - IEEE80211_HW_SUPPORTS_TDLS_BUFFER_STA, - IEEE80211_HW_DEAUTH_NEED_MGD_TX_PREP, - IEEE80211_HW_DOESNT_SUPPORT_QOS_NDP, -+ IEEE80211_HW_TX_STATUS_NO_AMPDU_LEN, - - /* keep last, obviously */ - NUM_IEEE80211_HW_FLAGS ---- a/net/mac80211/debugfs.c -+++ b/net/mac80211/debugfs.c -@@ -214,6 +214,7 @@ static const char *hw_flag_names[] = { - FLAG(SUPPORTS_TDLS_BUFFER_STA), - FLAG(DEAUTH_NEED_MGD_TX_PREP), - FLAG(DOESNT_SUPPORT_QOS_NDP), -+ FLAG(TX_STATUS_NO_AMPDU_LEN), - #undef FLAG - }; - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -294,6 +294,15 @@ minstrel_get_ratestats(struct minstrel_h - return &mi->groups[index / MCS_GROUP_RATES].rates[index % MCS_GROUP_RATES]; - } - -+static unsigned int -+minstrel_ht_avg_ampdu_len(struct minstrel_ht_sta *mi) -+{ -+ if (!mi->avg_ampdu_len) -+ return AVG_AMPDU_SIZE; -+ -+ return MINSTREL_TRUNC(mi->avg_ampdu_len); -+} -+ - /* - * Return current throughput based on the average A-MPDU length, taking into - * account the expected number of retransmissions and their expected length -@@ -309,7 +318,7 @@ minstrel_ht_get_tp_avg(struct minstrel_h - return 0; - - if (group != MINSTREL_CCK_GROUP) -- nsecs = 1000 * mi->overhead / MINSTREL_TRUNC(mi->avg_ampdu_len); -+ nsecs = 1000 * mi->overhead / minstrel_ht_avg_ampdu_len(mi); - - nsecs += minstrel_mcs_groups[group].duration[rate] << - minstrel_mcs_groups[group].shift; -@@ -503,8 +512,12 @@ minstrel_ht_update_stats(struct minstrel - u16 tmp_cck_tp_rate[MAX_THR_RATES], index; - - if (mi->ampdu_packets > 0) { -- mi->avg_ampdu_len = minstrel_ewma(mi->avg_ampdu_len, -- MINSTREL_FRAC(mi->ampdu_len, mi->ampdu_packets), EWMA_LEVEL); -+ if (!ieee80211_hw_check(mp->hw, TX_STATUS_NO_AMPDU_LEN)) -+ mi->avg_ampdu_len = minstrel_ewma(mi->avg_ampdu_len, -+ MINSTREL_FRAC(mi->ampdu_len, mi->ampdu_packets), -+ EWMA_LEVEL); -+ else -+ mi->avg_ampdu_len = 0; - mi->ampdu_len = 0; - mi->ampdu_packets = 0; - } -@@ -709,7 +722,9 @@ minstrel_ht_tx_status(void *priv, struct - mi->ampdu_len += info->status.ampdu_len; - - if (!mi->sample_wait && !mi->sample_tries && mi->sample_count > 0) { -- mi->sample_wait = 16 + 2 * MINSTREL_TRUNC(mi->avg_ampdu_len); -+ int avg_ampdu_len = minstrel_ht_avg_ampdu_len(mi); -+ -+ mi->sample_wait = 16 + 2 * avg_ampdu_len; - mi->sample_tries = 1; - mi->sample_count--; - } -@@ -777,7 +792,7 @@ minstrel_calc_retransmit(struct minstrel - unsigned int cw = mp->cw_min; - unsigned int ctime = 0; - unsigned int t_slot = 9; /* FIXME */ -- unsigned int ampdu_len = MINSTREL_TRUNC(mi->avg_ampdu_len); -+ unsigned int ampdu_len = minstrel_ht_avg_ampdu_len(mi); - unsigned int overhead = 0, overhead_rtscts = 0; - - mrs = minstrel_get_ratestats(mi, index); ---- a/net/mac80211/rc80211_minstrel_ht_debugfs.c -+++ b/net/mac80211/rc80211_minstrel_ht_debugfs.c -@@ -163,9 +163,10 @@ minstrel_ht_stats_open(struct inode *ino - "lookaround %d\n", - max(0, (int) mi->total_packets - (int) mi->sample_packets), - mi->sample_packets); -- p += sprintf(p, "Average # of aggregated frames per A-MPDU: %d.%d\n", -- MINSTREL_TRUNC(mi->avg_ampdu_len), -- MINSTREL_TRUNC(mi->avg_ampdu_len * 10) % 10); -+ if (mi->avg_ampdu_len) -+ p += sprintf(p, "Average # of aggregated frames per A-MPDU: %d.%d\n", -+ MINSTREL_TRUNC(mi->avg_ampdu_len), -+ MINSTREL_TRUNC(mi->avg_ampdu_len * 10) % 10); - ms->len = p - ms->buf; - WARN_ON(ms->len + sizeof(*ms) > 32768); - diff --git a/package/kernel/mac80211/patches/subsys/313-mac80211-fix-unaligned-access-in-mesh-table-hash-fun.patch b/package/kernel/mac80211/patches/subsys/313-mac80211-fix-unaligned-access-in-mesh-table-hash-fun.patch deleted file mode 100644 index 2ce23586ca..0000000000 --- a/package/kernel/mac80211/patches/subsys/313-mac80211-fix-unaligned-access-in-mesh-table-hash-fun.patch +++ /dev/null @@ -1,21 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Wed, 13 Mar 2019 18:52:56 +0100 -Subject: [PATCH] mac80211: fix unaligned access in mesh table hash function - -The pointer to the last four bytes of the address is not guaranteed to be -aligned, so we need to use __get_unaligned_cpu32 here - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/mesh_pathtbl.c -+++ b/net/mac80211/mesh_pathtbl.c -@@ -23,7 +23,7 @@ static void mesh_path_free_rcu(struct me - static u32 mesh_table_hash(const void *addr, u32 len, u32 seed) - { - /* Use last four bytes of hw addr as hash index */ -- return jhash_1word(*(u32 *)(addr+2), seed); -+ return jhash_1word(__get_unaligned_cpu32(addr+2), seed); - } - - static const struct rhashtable_params mesh_rht_params = { diff --git a/package/kernel/mac80211/patches/subsys/320-mac80211-Add-TXQ-scheduling-API.patch b/package/kernel/mac80211/patches/subsys/320-mac80211-Add-TXQ-scheduling-API.patch deleted file mode 100644 index 0f7d9e1506..0000000000 --- a/package/kernel/mac80211/patches/subsys/320-mac80211-Add-TXQ-scheduling-API.patch +++ /dev/null @@ -1,292 +0,0 @@ -From: =?UTF-8?q?Toke=20H=C3=B8iland-J=C3=B8rgensen?= <toke@toke.dk> -Date: Tue, 18 Dec 2018 17:02:06 -0800 -Subject: [PATCH] mac80211: Add TXQ scheduling API -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -This adds an API to mac80211 to handle scheduling of TXQs. The interface -between driver and mac80211 for TXQ handling is changed by adding two new -functions: ieee80211_next_txq(), which will return the next TXQ to schedule -in the current round-robin rotation, and ieee80211_return_txq(), which the -driver uses to indicate that it has finished scheduling a TXQ (which will -then be put back in the scheduling rotation if it isn't empty). - -The driver must call ieee80211_txq_schedule_start() at the start of each -scheduling session, and ieee80211_txq_schedule_end() at the end. The API -then guarantees that the same TXQ is not returned twice in the same -session (so a driver can loop on ieee80211_next_txq() without worrying -about breaking the loop. - -Usage of the new API is optional, so drivers can be ported one at a time. -In this patch, the actual scheduling performed by mac80211 is simple -round-robin, but a subsequent commit adds airtime fairness awareness to the -scheduler. - -Signed-off-by: Toke Høiland-Jørgensen <toke@toke.dk> -[minor kernel-doc fix, propagate sparse locking checks out] -Signed-off-by: Johannes Berg <johannes.berg@intel.com> ---- - ---- a/include/net/mac80211.h -+++ b/include/net/mac80211.h -@@ -107,9 +107,15 @@ - * The driver is expected to initialize its private per-queue data for stations - * and interfaces in the .add_interface and .sta_add ops. - * -- * The driver can't access the queue directly. To dequeue a frame, it calls -- * ieee80211_tx_dequeue(). Whenever mac80211 adds a new frame to a queue, it -- * calls the .wake_tx_queue driver op. -+ * The driver can't access the queue directly. To dequeue a frame from a -+ * txq, it calls ieee80211_tx_dequeue(). Whenever mac80211 adds a new frame to a -+ * queue, it calls the .wake_tx_queue driver op. -+ * -+ * Drivers can optionally delegate responsibility for scheduling queues to -+ * mac80211, to take advantage of airtime fairness accounting. In this case, to -+ * obtain the next queue to pull frames from, the driver calls -+ * ieee80211_next_txq(). The driver is then expected to return the txq using -+ * ieee80211_return_txq(). - * - * For AP powersave TIM handling, the driver only needs to indicate if it has - * buffered packets in the driver specific data structures by calling -@@ -5979,7 +5985,8 @@ void ieee80211_unreserve_tid(struct ieee - * ieee80211_tx_dequeue - dequeue a packet from a software tx queue - * - * @hw: pointer as obtained from ieee80211_alloc_hw() -- * @txq: pointer obtained from station or virtual interface -+ * @txq: pointer obtained from station or virtual interface, or from -+ * ieee80211_next_txq() - * - * Returns the skb if successful, %NULL if no frame was available. - */ -@@ -5987,6 +5994,54 @@ struct sk_buff *ieee80211_tx_dequeue(str - struct ieee80211_txq *txq); - - /** -+ * ieee80211_next_txq - get next tx queue to pull packets from -+ * -+ * @hw: pointer as obtained from ieee80211_alloc_hw() -+ * @ac: AC number to return packets from. -+ * -+ * Should only be called between calls to ieee80211_txq_schedule_start() -+ * and ieee80211_txq_schedule_end(). -+ * Returns the next txq if successful, %NULL if no queue is eligible. If a txq -+ * is returned, it should be returned with ieee80211_return_txq() after the -+ * driver has finished scheduling it. -+ */ -+struct ieee80211_txq *ieee80211_next_txq(struct ieee80211_hw *hw, u8 ac); -+ -+/** -+ * ieee80211_return_txq - return a TXQ previously acquired by ieee80211_next_txq() -+ * -+ * @hw: pointer as obtained from ieee80211_alloc_hw() -+ * @txq: pointer obtained from station or virtual interface -+ * -+ * Should only be called between calls to ieee80211_txq_schedule_start() -+ * and ieee80211_txq_schedule_end(). -+ */ -+void ieee80211_return_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq); -+ -+/** -+ * ieee80211_txq_schedule_start - acquire locks for safe scheduling of an AC -+ * -+ * @hw: pointer as obtained from ieee80211_alloc_hw() -+ * @ac: AC number to acquire locks for -+ * -+ * Acquire locks needed to schedule TXQs from the given AC. Should be called -+ * before ieee80211_next_txq() or ieee80211_return_txq(). -+ */ -+void ieee80211_txq_schedule_start(struct ieee80211_hw *hw, u8 ac) -+ __acquires(txq_lock); -+ -+/** -+ * ieee80211_txq_schedule_end - release locks for safe scheduling of an AC -+ * -+ * @hw: pointer as obtained from ieee80211_alloc_hw() -+ * @ac: AC number to acquire locks for -+ * -+ * Release locks previously acquired by ieee80211_txq_schedule_end(). -+ */ -+void ieee80211_txq_schedule_end(struct ieee80211_hw *hw, u8 ac) -+ __releases(txq_lock); -+ -+/** - * ieee80211_txq_get_depth - get pending frame/byte count of given txq - * - * The values are not guaranteed to be coherent with regard to each other, i.e. ---- a/net/mac80211/agg-tx.c -+++ b/net/mac80211/agg-tx.c -@@ -229,7 +229,7 @@ ieee80211_agg_start_txq(struct sta_info - clear_bit(IEEE80211_TXQ_STOP, &txqi->flags); - local_bh_disable(); - rcu_read_lock(); -- drv_wake_tx_queue(sta->sdata->local, txqi); -+ schedule_and_wake_txq(sta->sdata->local, txqi); - rcu_read_unlock(); - local_bh_enable(); - } ---- a/net/mac80211/driver-ops.h -+++ b/net/mac80211/driver-ops.h -@@ -1176,6 +1176,15 @@ static inline void drv_wake_tx_queue(str - local->ops->wake_tx_queue(&local->hw, &txq->txq); - } - -+static inline void schedule_and_wake_txq(struct ieee80211_local *local, -+ struct txq_info *txqi) -+{ -+ spin_lock_bh(&local->active_txq_lock[txqi->txq.ac]); -+ ieee80211_return_txq(&local->hw, &txqi->txq); -+ spin_unlock_bh(&local->active_txq_lock[txqi->txq.ac]); -+ drv_wake_tx_queue(local, txqi); -+} -+ - static inline int drv_start_nan(struct ieee80211_local *local, - struct ieee80211_sub_if_data *sdata, - struct cfg80211_nan_conf *conf) ---- a/net/mac80211/ieee80211_i.h -+++ b/net/mac80211/ieee80211_i.h -@@ -829,6 +829,8 @@ enum txq_info_flags { - * a fq_flow which is already owned by a different tin - * @def_cvars: codel vars for @def_flow - * @frags: used to keep fragments created after dequeue -+ * @schedule_order: used with ieee80211_local->active_txqs -+ * @schedule_round: counter to prevent infinite loops on TXQ scheduling - */ - struct txq_info { - struct fq_tin tin; -@@ -836,6 +838,8 @@ struct txq_info { - struct codel_vars def_cvars; - struct codel_stats cstats; - struct sk_buff_head frags; -+ struct list_head schedule_order; -+ u16 schedule_round; - unsigned long flags; - - /* keep last! */ -@@ -1127,6 +1131,11 @@ struct ieee80211_local { - struct codel_vars *cvars; - struct codel_params cparams; - -+ /* protects active_txqs and txqi->schedule_order */ -+ spinlock_t active_txq_lock[IEEE80211_NUM_ACS]; -+ struct list_head active_txqs[IEEE80211_NUM_ACS]; -+ u16 schedule_round[IEEE80211_NUM_ACS]; -+ - const struct ieee80211_ops *ops; - - /* ---- a/net/mac80211/main.c -+++ b/net/mac80211/main.c -@@ -652,6 +652,11 @@ struct ieee80211_hw *ieee80211_alloc_hw_ - spin_lock_init(&local->rx_path_lock); - spin_lock_init(&local->queue_stop_reason_lock); - -+ for (i = 0; i < IEEE80211_NUM_ACS; i++) { -+ INIT_LIST_HEAD(&local->active_txqs[i]); -+ spin_lock_init(&local->active_txq_lock[i]); -+ } -+ - INIT_LIST_HEAD(&local->chanctx_list); - mutex_init(&local->chanctx_mtx); - ---- a/net/mac80211/sta_info.c -+++ b/net/mac80211/sta_info.c -@@ -1244,7 +1244,7 @@ void ieee80211_sta_ps_deliver_wakeup(str - if (!txq_has_queue(sta->sta.txq[i])) - continue; - -- drv_wake_tx_queue(local, to_txq_info(sta->sta.txq[i])); -+ schedule_and_wake_txq(local, to_txq_info(sta->sta.txq[i])); - } - } - ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -1441,6 +1441,7 @@ void ieee80211_txq_init(struct ieee80211 - codel_vars_init(&txqi->def_cvars); - codel_stats_init(&txqi->cstats); - __skb_queue_head_init(&txqi->frags); -+ INIT_LIST_HEAD(&txqi->schedule_order); - - txqi->txq.vif = &sdata->vif; - -@@ -1464,6 +1465,9 @@ void ieee80211_txq_purge(struct ieee8021 - - fq_tin_reset(fq, tin, fq_skb_free_func); - ieee80211_purge_tx_queue(&local->hw, &txqi->frags); -+ spin_lock_bh(&local->active_txq_lock[txqi->txq.ac]); -+ list_del_init(&txqi->schedule_order); -+ spin_unlock_bh(&local->active_txq_lock[txqi->txq.ac]); - } - - void ieee80211_txq_set_params(struct ieee80211_local *local) -@@ -1580,7 +1584,7 @@ static bool ieee80211_queue_skb(struct i - ieee80211_txq_enqueue(local, txqi, skb); - spin_unlock_bh(&fq->lock); - -- drv_wake_tx_queue(local, txqi); -+ schedule_and_wake_txq(local, txqi); - - return true; - } -@@ -3602,6 +3606,60 @@ out: - } - EXPORT_SYMBOL(ieee80211_tx_dequeue); - -+struct ieee80211_txq *ieee80211_next_txq(struct ieee80211_hw *hw, u8 ac) -+{ -+ struct ieee80211_local *local = hw_to_local(hw); -+ struct txq_info *txqi = NULL; -+ -+ lockdep_assert_held(&local->active_txq_lock[ac]); -+ -+ txqi = list_first_entry_or_null(&local->active_txqs[ac], -+ struct txq_info, -+ schedule_order); -+ -+ if (!txqi || txqi->schedule_round == local->schedule_round[ac]) -+ return NULL; -+ -+ list_del_init(&txqi->schedule_order); -+ txqi->schedule_round = local->schedule_round[ac]; -+ return &txqi->txq; -+} -+EXPORT_SYMBOL(ieee80211_next_txq); -+ -+void ieee80211_return_txq(struct ieee80211_hw *hw, -+ struct ieee80211_txq *txq) -+{ -+ struct ieee80211_local *local = hw_to_local(hw); -+ struct txq_info *txqi = to_txq_info(txq); -+ -+ lockdep_assert_held(&local->active_txq_lock[txq->ac]); -+ -+ if (list_empty(&txqi->schedule_order) && -+ (!skb_queue_empty(&txqi->frags) || txqi->tin.backlog_packets)) -+ list_add_tail(&txqi->schedule_order, -+ &local->active_txqs[txq->ac]); -+} -+EXPORT_SYMBOL(ieee80211_return_txq); -+ -+void ieee80211_txq_schedule_start(struct ieee80211_hw *hw, u8 ac) -+ __acquires(txq_lock) -+{ -+ struct ieee80211_local *local = hw_to_local(hw); -+ -+ spin_lock_bh(&local->active_txq_lock[ac]); -+ local->schedule_round[ac]++; -+} -+EXPORT_SYMBOL(ieee80211_txq_schedule_start); -+ -+void ieee80211_txq_schedule_end(struct ieee80211_hw *hw, u8 ac) -+ __releases(txq_lock) -+{ -+ struct ieee80211_local *local = hw_to_local(hw); -+ -+ spin_unlock_bh(&local->active_txq_lock[ac]); -+} -+EXPORT_SYMBOL(ieee80211_txq_schedule_end); -+ - void __ieee80211_subif_start_xmit(struct sk_buff *skb, - struct net_device *dev, - u32 info_flags) diff --git a/package/kernel/mac80211/patches/subsys/321-cfg80211-Add-airtime-statistics-and-settings.patch b/package/kernel/mac80211/patches/subsys/321-cfg80211-Add-airtime-statistics-and-settings.patch deleted file mode 100644 index 7eb64c4251..0000000000 --- a/package/kernel/mac80211/patches/subsys/321-cfg80211-Add-airtime-statistics-and-settings.patch +++ /dev/null @@ -1,202 +0,0 @@ -From: =?UTF-8?q?Toke=20H=C3=B8iland-J=C3=B8rgensen?= <toke@toke.dk> -Date: Tue, 18 Dec 2018 17:02:07 -0800 -Subject: [PATCH] cfg80211: Add airtime statistics and settings -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -This adds TX airtime statistics to the cfg80211 station dump (to go along -with the RX info already present), and adds a new parameter to set the -airtime weight of each station. The latter allows userspace to implement -policies for different stations by varying their weights. - -Signed-off-by: Toke Høiland-Jørgensen <toke@toke.dk> -[rmanohar@codeaurora.org: fixed checkpatch warnings] -Signed-off-by: Rajkumar Manoharan <rmanohar@codeaurora.org> -[move airtime weight != 0 check into policy] -Signed-off-by: Johannes Berg <johannes.berg@intel.com> ---- - ---- a/include/net/cfg80211.h -+++ b/include/net/cfg80211.h -@@ -988,6 +988,7 @@ enum station_parameters_apply_mask { - * @support_p2p_ps: information if station supports P2P PS mechanism - * @he_capa: HE capabilities of station - * @he_capa_len: the length of the HE capabilities -+ * @airtime_weight: airtime scheduler weight for this station - */ - struct station_parameters { - const u8 *supported_rates; -@@ -1017,6 +1018,7 @@ struct station_parameters { - int support_p2p_ps; - const struct ieee80211_he_cap_elem *he_capa; - u8 he_capa_len; -+ u16 airtime_weight; - }; - - /** -@@ -1284,6 +1286,8 @@ struct cfg80211_tid_stats { - * @rx_beacon_signal_avg: signal strength average (in dBm) for beacons received - * from this peer - * @rx_duration: aggregate PPDU duration(usecs) for all the frames from a peer -+ * @tx_duration: aggregate PPDU duration(usecs) for all the frames to a peer -+ * @airtime_weight: current airtime scheduling weight - * @pertid: per-TID statistics, see &struct cfg80211_tid_stats, using the last - * (IEEE80211_NUM_TIDS) index for MSDUs not encapsulated in QoS-MPDUs. - * Note that this doesn't use the @filled bit, but is used if non-NULL. -@@ -1330,12 +1334,15 @@ struct station_info { - - u32 expected_throughput; - -- u64 rx_beacon; -+ u64 tx_duration; - u64 rx_duration; -+ u64 rx_beacon; - u8 rx_beacon_signal_avg; - struct cfg80211_tid_stats *pertid; - s8 ack_signal; - s8 avg_ack_signal; -+ -+ u16 airtime_weight; - }; - - #if IS_ENABLED(CPTCFG_CFG80211) -@@ -2361,6 +2368,8 @@ enum wiphy_params_flags { - WIPHY_PARAM_TXQ_QUANTUM = 1 << 8, - }; - -+#define IEEE80211_DEFAULT_AIRTIME_WEIGHT 256 -+ - /** - * struct cfg80211_pmksa - PMK Security Association - * ---- a/include/uapi/linux/nl80211.h -+++ b/include/uapi/linux/nl80211.h -@@ -2241,6 +2241,9 @@ enum nl80211_commands { - * association request when used with NL80211_CMD_NEW_STATION). Can be set - * only if %NL80211_STA_FLAG_WME is set. - * -+ * @NL80211_ATTR_AIRTIME_WEIGHT: Station's weight when scheduled by the airtime -+ * scheduler. -+ * - * @NUM_NL80211_ATTR: total number of nl80211_attrs available - * @NL80211_ATTR_MAX: highest attribute number currently defined - * @__NL80211_ATTR_AFTER_LAST: internal use -@@ -2682,6 +2685,14 @@ enum nl80211_attrs { - - NL80211_ATTR_HE_CAPABILITY, - -+ /* not backported yet */ -+ NL80211_ATTR_FTM_RESPONDER, -+ NL80211_ATTR_FTM_RESPONDER_STATS, -+ NL80211_ATTR_TIMEOUT, -+ NL80211_ATTR_PEER_MEASUREMENTS, -+ -+ NL80211_ATTR_AIRTIME_WEIGHT, -+ - /* add attributes here, update the policy in nl80211.c */ - - __NL80211_ATTR_AFTER_LAST, -@@ -3052,6 +3063,9 @@ enum nl80211_sta_bss_param { - * @NL80211_STA_INFO_ACK_SIGNAL: signal strength of the last ACK frame(u8, dBm) - * @NL80211_STA_INFO_DATA_ACK_SIGNAL_AVG: avg signal strength of (data) - * ACK frame (s8, dBm) -+ * @NL80211_STA_INFO_TX_DURATION: aggregate PPDU duration for all frames -+ * sent to the station (u64, usec) -+ * @NL80211_STA_INFO_AIRTIME_WEIGHT: current airtime weight for station (u16) - * @__NL80211_STA_INFO_AFTER_LAST: internal - * @NL80211_STA_INFO_MAX: highest possible station info attribute - */ -@@ -3093,6 +3107,14 @@ enum nl80211_sta_info { - NL80211_STA_INFO_ACK_SIGNAL, - NL80211_STA_INFO_DATA_ACK_SIGNAL_AVG, - -+ /* not backported yet */ -+ NL80211_STA_INFO_RX_MPDUS, -+ NL80211_STA_INFO_FCS_ERROR_COUNT, -+ NL80211_STA_INFO_CONNECTED_TO_GATE, -+ -+ NL80211_STA_INFO_TX_DURATION, -+ NL80211_STA_INFO_AIRTIME_WEIGHT, -+ - /* keep last */ - __NL80211_STA_INFO_AFTER_LAST, - NL80211_STA_INFO_MAX = __NL80211_STA_INFO_AFTER_LAST - 1 -@@ -5224,6 +5246,10 @@ enum nl80211_feature_flags { - * except for supported rates from the probe request content if requested - * by the %NL80211_SCAN_FLAG_MIN_PREQ_CONTENT flag. - * -+ * @NL80211_EXT_FEATURE_AIRTIME_FAIRNESS: Driver supports getting airtime -+ * fairness for transmitted packets and has enabled airtime fairness -+ * scheduling. -+ * - * @NUM_NL80211_EXT_FEATURES: number of extended features. - * @MAX_NL80211_EXT_FEATURES: highest extended feature index. - */ -@@ -5260,6 +5286,12 @@ enum nl80211_ext_feature_index { - NL80211_EXT_FEATURE_SCAN_RANDOM_SN, - NL80211_EXT_FEATURE_SCAN_MIN_PREQ_CONTENT, - -+ /* --- not backported yet --- */ -+ NL80211_EXT_FEATURE_CAN_REPLACE_PTK0, -+ NL80211_EXT_FEATURE_ENABLE_FTM_RESPONDER, -+ -+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS, -+ - /* add new features before the definition below */ - NUM_NL80211_EXT_FEATURES, - MAX_NL80211_EXT_FEATURES = NUM_NL80211_EXT_FEATURES - 1 ---- a/net/wireless/nl80211.c -+++ b/net/wireless/nl80211.c -@@ -430,6 +430,7 @@ static const struct nla_policy nl80211_p - [NL80211_ATTR_TXQ_QUANTUM] = { .type = NLA_U32 }, - [NL80211_ATTR_HE_CAPABILITY] = { .type = NLA_BINARY, - .len = NL80211_HE_MAX_CAPABILITY_LEN }, -+ [NL80211_ATTR_AIRTIME_WEIGHT] = NLA_POLICY_MIN(NLA_U16, 1), - }; - - /* policy for the key attributes */ -@@ -4658,6 +4659,11 @@ static int nl80211_send_station(struct s - PUT_SINFO(PLID, plid, u16); - PUT_SINFO(PLINK_STATE, plink_state, u8); - PUT_SINFO_U64(RX_DURATION, rx_duration); -+ PUT_SINFO_U64(TX_DURATION, tx_duration); -+ -+ if (wiphy_ext_feature_isset(&rdev->wiphy, -+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS)) -+ PUT_SINFO(AIRTIME_WEIGHT, airtime_weight, u16); - - switch (rdev->wiphy.signal_type) { - case CFG80211_SIGNAL_TYPE_MBM: -@@ -5294,6 +5300,15 @@ static int nl80211_set_station(struct sk - nla_get_u8(info->attrs[NL80211_ATTR_OPMODE_NOTIF]); - } - -+ if (info->attrs[NL80211_ATTR_AIRTIME_WEIGHT]) -+ params.airtime_weight = -+ nla_get_u16(info->attrs[NL80211_ATTR_AIRTIME_WEIGHT]); -+ -+ if (params.airtime_weight && -+ !wiphy_ext_feature_isset(&rdev->wiphy, -+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS)) -+ return -EOPNOTSUPP; -+ - /* Include parameters for TDLS peer (will check later) */ - err = nl80211_set_station_tdls(info, ¶ms); - if (err) -@@ -5432,6 +5447,15 @@ static int nl80211_new_station(struct sk - return -EINVAL; - } - -+ if (info->attrs[NL80211_ATTR_AIRTIME_WEIGHT]) -+ params.airtime_weight = -+ nla_get_u16(info->attrs[NL80211_ATTR_AIRTIME_WEIGHT]); -+ -+ if (params.airtime_weight && -+ !wiphy_ext_feature_isset(&rdev->wiphy, -+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS)) -+ return -EOPNOTSUPP; -+ - err = nl80211_parse_sta_channel_info(info, ¶ms); - if (err) - return err; diff --git a/package/kernel/mac80211/patches/subsys/322-mac80211-Add-airtime-accounting-and-scheduling-to-TX.patch b/package/kernel/mac80211/patches/subsys/322-mac80211-Add-airtime-accounting-and-scheduling-to-TX.patch deleted file mode 100644 index d4176eb491..0000000000 --- a/package/kernel/mac80211/patches/subsys/322-mac80211-Add-airtime-accounting-and-scheduling-to-TX.patch +++ /dev/null @@ -1,522 +0,0 @@ -From: =?UTF-8?q?Toke=20H=C3=B8iland-J=C3=B8rgensen?= <toke@toke.dk> -Date: Tue, 18 Dec 2018 17:02:08 -0800 -Subject: [PATCH] mac80211: Add airtime accounting and scheduling to TXQs -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -This adds airtime accounting and scheduling to the mac80211 TXQ -scheduler. A new callback, ieee80211_sta_register_airtime(), is added -that drivers can call to report airtime usage for stations. - -When airtime information is present, mac80211 will schedule TXQs -(through ieee80211_next_txq()) in a way that enforces airtime fairness -between active stations. This scheduling works the same way as the ath9k -in-driver airtime fairness scheduling. If no airtime usage is reported -by the driver, the scheduler will default to round-robin scheduling. - -For drivers that don't control TXQ scheduling in software, a new API -function, ieee80211_txq_may_transmit(), is added which the driver can use -to check if the TXQ is eligible for transmission, or should be throttled to -enforce fairness. Calls to this function must also be enclosed in -ieee80211_txq_schedule_{start,end}() calls to ensure proper locking. - -The API ieee80211_txq_may_transmit() also ensures that TXQ list will be -aligned aginst driver's own round-robin scheduler list. i.e it rotates -the TXQ list till it makes the requested node becomes the first entry -in TXQ list. Thus both the TXQ list and driver's list are in sync. - -Co-developed-by: Rajkumar Manoharan <rmanohar@codeaurora.org> -Signed-off-by: Louie Lu <git@louie.lu> -[added debugfs write op to reset airtime counter] -Signed-off-by: Toke Høiland-Jørgensen <toke@toke.dk> -Signed-off-by: Rajkumar Manoharan <rmanohar@codeaurora.org> -Signed-off-by: Johannes Berg <johannes.berg@intel.com> ---- - ---- a/include/net/mac80211.h -+++ b/include/net/mac80211.h -@@ -2304,6 +2304,9 @@ enum ieee80211_hw_flags { - * supported by HW. - * @max_nan_de_entries: maximum number of NAN DE functions supported by the - * device. -+ * -+ * @weight_multipler: Driver specific airtime weight multiplier used while -+ * refilling deficit of each TXQ. - */ - struct ieee80211_hw { - struct ieee80211_conf conf; -@@ -2339,6 +2342,7 @@ struct ieee80211_hw { - u8 n_cipher_schemes; - const struct ieee80211_cipher_scheme *cipher_schemes; - u8 max_nan_de_entries; -+ u8 weight_multiplier; - }; - - static inline bool _ieee80211_hw_check(struct ieee80211_hw *hw, -@@ -5299,6 +5303,34 @@ void ieee80211_sta_eosp(struct ieee80211 - void ieee80211_send_eosp_nullfunc(struct ieee80211_sta *pubsta, int tid); - - /** -+ * ieee80211_sta_register_airtime - register airtime usage for a sta/tid -+ * -+ * Register airtime usage for a given sta on a given tid. The driver can call -+ * this function to notify mac80211 that a station used a certain amount of -+ * airtime. This information will be used by the TXQ scheduler to schedule -+ * stations in a way that ensures airtime fairness. -+ * -+ * The reported airtime should as a minimum include all time that is spent -+ * transmitting to the remote station, including overhead and padding, but not -+ * including time spent waiting for a TXOP. If the time is not reported by the -+ * hardware it can in some cases be calculated from the rate and known frame -+ * composition. When possible, the time should include any failed transmission -+ * attempts. -+ * -+ * The driver can either call this function synchronously for every packet or -+ * aggregate, or asynchronously as airtime usage information becomes available. -+ * TX and RX airtime can be reported together, or separately by setting one of -+ * them to 0. -+ * -+ * @pubsta: the station -+ * @tid: the TID to register airtime for -+ * @tx_airtime: airtime used during TX (in usec) -+ * @rx_airtime: airtime used during RX (in usec) -+ */ -+void ieee80211_sta_register_airtime(struct ieee80211_sta *pubsta, u8 tid, -+ u32 tx_airtime, u32 rx_airtime); -+ -+/** - * ieee80211_iter_keys - iterate keys programmed into the device - * @hw: pointer obtained from ieee80211_alloc_hw() - * @vif: virtual interface to iterate, may be %NULL for all -@@ -6042,6 +6074,33 @@ void ieee80211_txq_schedule_end(struct i - __releases(txq_lock); - - /** -+ * ieee80211_txq_may_transmit - check whether TXQ is allowed to transmit -+ * -+ * This function is used to check whether given txq is allowed to transmit by -+ * the airtime scheduler, and can be used by drivers to access the airtime -+ * fairness accounting without going using the scheduling order enfored by -+ * next_txq(). -+ * -+ * Returns %true if the airtime scheduler thinks the TXQ should be allowed to -+ * transmit, and %false if it should be throttled. This function can also have -+ * the side effect of rotating the TXQ in the scheduler rotation, which will -+ * eventually bring the deficit to positive and allow the station to transmit -+ * again. -+ * -+ * The API ieee80211_txq_may_transmit() also ensures that TXQ list will be -+ * aligned aginst driver's own round-robin scheduler list. i.e it rotates -+ * the TXQ list till it makes the requested node becomes the first entry -+ * in TXQ list. Thus both the TXQ list and driver's list are in sync. If this -+ * function returns %true, the driver is expected to schedule packets -+ * for transmission, and then return the TXQ through ieee80211_return_txq(). -+ * -+ * @hw: pointer as obtained from ieee80211_alloc_hw() -+ * @txq: pointer obtained from station or virtual interface -+ */ -+bool ieee80211_txq_may_transmit(struct ieee80211_hw *hw, -+ struct ieee80211_txq *txq); -+ -+/** - * ieee80211_txq_get_depth - get pending frame/byte count of given txq - * - * The values are not guaranteed to be coherent with regard to each other, i.e. ---- a/net/mac80211/cfg.c -+++ b/net/mac80211/cfg.c -@@ -1434,6 +1434,9 @@ static int sta_apply_parameters(struct i - if (ieee80211_vif_is_mesh(&sdata->vif)) - sta_apply_mesh_params(local, sta, params); - -+ if (params->airtime_weight) -+ sta->airtime_weight = params->airtime_weight; -+ - /* set the STA state after all sta info from usermode has been set */ - if (test_sta_flag(sta, WLAN_STA_TDLS_PEER) || - set & BIT(NL80211_STA_FLAG_ASSOCIATED)) { ---- a/net/mac80211/debugfs.c -+++ b/net/mac80211/debugfs.c -@@ -380,6 +380,9 @@ void debugfs_hw_add(struct ieee80211_loc - if (local->ops->wake_tx_queue) - DEBUGFS_ADD_MODE(aqm, 0600); - -+ debugfs_create_u16("airtime_flags", 0600, -+ phyd, &local->airtime_flags); -+ - statsd = debugfs_create_dir("statistics", phyd); - - /* if the dir failed, don't put all the other things into the root! */ ---- a/net/mac80211/debugfs_sta.c -+++ b/net/mac80211/debugfs_sta.c -@@ -178,9 +178,9 @@ static ssize_t sta_aqm_read(struct file - txqi->tin.tx_bytes, - txqi->tin.tx_packets, - txqi->flags, -- txqi->flags & (1<<IEEE80211_TXQ_STOP) ? "STOP" : "RUN", -- txqi->flags & (1<<IEEE80211_TXQ_AMPDU) ? " AMPDU" : "", -- txqi->flags & (1<<IEEE80211_TXQ_NO_AMSDU) ? " NO-AMSDU" : ""); -+ test_bit(IEEE80211_TXQ_STOP, &txqi->flags) ? "STOP" : "RUN", -+ test_bit(IEEE80211_TXQ_AMPDU, &txqi->flags) ? " AMPDU" : "", -+ test_bit(IEEE80211_TXQ_NO_AMSDU, &txqi->flags) ? " NO-AMSDU" : ""); - } - - rcu_read_unlock(); -@@ -192,6 +192,64 @@ static ssize_t sta_aqm_read(struct file - } - STA_OPS(aqm); - -+static ssize_t sta_airtime_read(struct file *file, char __user *userbuf, -+ size_t count, loff_t *ppos) -+{ -+ struct sta_info *sta = file->private_data; -+ struct ieee80211_local *local = sta->sdata->local; -+ size_t bufsz = 200; -+ char *buf = kzalloc(bufsz, GFP_KERNEL), *p = buf; -+ u64 rx_airtime = 0, tx_airtime = 0; -+ s64 deficit[IEEE80211_NUM_ACS]; -+ ssize_t rv; -+ int ac; -+ -+ if (!buf) -+ return -ENOMEM; -+ -+ for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) { -+ spin_lock_bh(&local->active_txq_lock[ac]); -+ rx_airtime += sta->airtime[ac].rx_airtime; -+ tx_airtime += sta->airtime[ac].tx_airtime; -+ deficit[ac] = sta->airtime[ac].deficit; -+ spin_unlock_bh(&local->active_txq_lock[ac]); -+ } -+ -+ p += scnprintf(p, bufsz + buf - p, -+ "RX: %llu us\nTX: %llu us\nWeight: %u\n" -+ "Deficit: VO: %lld us VI: %lld us BE: %lld us BK: %lld us\n", -+ rx_airtime, -+ tx_airtime, -+ sta->airtime_weight, -+ deficit[0], -+ deficit[1], -+ deficit[2], -+ deficit[3]); -+ -+ rv = simple_read_from_buffer(userbuf, count, ppos, buf, p - buf); -+ kfree(buf); -+ return rv; -+} -+ -+static ssize_t sta_airtime_write(struct file *file, const char __user *userbuf, -+ size_t count, loff_t *ppos) -+{ -+ struct sta_info *sta = file->private_data; -+ struct ieee80211_local *local = sta->sdata->local; -+ int ac; -+ -+ for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) { -+ spin_lock_bh(&local->active_txq_lock[ac]); -+ sta->airtime[ac].rx_airtime = 0; -+ sta->airtime[ac].tx_airtime = 0; -+ sta->airtime[ac].deficit = sta->airtime_weight; -+ spin_unlock_bh(&local->active_txq_lock[ac]); -+ } -+ -+ return count; -+} -+STA_OPS_RW(airtime); -+ - static ssize_t sta_agg_status_read(struct file *file, char __user *userbuf, - size_t count, loff_t *ppos) - { -@@ -546,6 +604,10 @@ void ieee80211_sta_debugfs_add(struct st - if (local->ops->wake_tx_queue) - DEBUGFS_ADD(aqm); - -+ if (wiphy_ext_feature_isset(local->hw.wiphy, -+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS)) -+ DEBUGFS_ADD(airtime); -+ - if (sizeof(sta->driver_buffered_tids) == sizeof(u32)) - debugfs_create_x32("driver_buffered_tids", 0400, - sta->debugfs_dir, ---- a/net/mac80211/ieee80211_i.h -+++ b/net/mac80211/ieee80211_i.h -@@ -1136,6 +1136,8 @@ struct ieee80211_local { - struct list_head active_txqs[IEEE80211_NUM_ACS]; - u16 schedule_round[IEEE80211_NUM_ACS]; - -+ u16 airtime_flags; -+ - const struct ieee80211_ops *ops; - - /* ---- a/net/mac80211/main.c -+++ b/net/mac80211/main.c -@@ -656,6 +656,7 @@ struct ieee80211_hw *ieee80211_alloc_hw_ - INIT_LIST_HEAD(&local->active_txqs[i]); - spin_lock_init(&local->active_txq_lock[i]); - } -+ local->airtime_flags = AIRTIME_USE_TX | AIRTIME_USE_RX; - - INIT_LIST_HEAD(&local->chanctx_list); - mutex_init(&local->chanctx_mtx); -@@ -1142,6 +1143,9 @@ int ieee80211_register_hw(struct ieee802 - if (!local->hw.max_nan_de_entries) - local->hw.max_nan_de_entries = IEEE80211_MAX_NAN_INSTANCE_ID; - -+ if (!local->hw.weight_multiplier) -+ local->hw.weight_multiplier = 1; -+ - result = ieee80211_wep_init(local); - if (result < 0) - wiphy_debug(local->hw.wiphy, "Failed to initialize wep: %d\n", ---- a/net/mac80211/sta_info.c -+++ b/net/mac80211/sta_info.c -@@ -90,7 +90,6 @@ static void __cleanup_single_sta(struct - struct tid_ampdu_tx *tid_tx; - struct ieee80211_sub_if_data *sdata = sta->sdata; - struct ieee80211_local *local = sdata->local; -- struct fq *fq = &local->fq; - struct ps_data *ps; - - if (test_sta_flag(sta, WLAN_STA_PS_STA) || -@@ -115,9 +114,7 @@ static void __cleanup_single_sta(struct - for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) { - struct txq_info *txqi = to_txq_info(sta->sta.txq[i]); - -- spin_lock_bh(&fq->lock); - ieee80211_txq_purge(local, txqi); -- spin_unlock_bh(&fq->lock); - } - } - -@@ -381,9 +378,12 @@ struct sta_info *sta_info_alloc(struct i - if (sta_prepare_rate_control(local, sta, gfp)) - goto free_txq; - -+ sta->airtime_weight = IEEE80211_DEFAULT_AIRTIME_WEIGHT; -+ - for (i = 0; i < IEEE80211_NUM_ACS; i++) { - skb_queue_head_init(&sta->ps_tx_buf[i]); - skb_queue_head_init(&sta->tx_filtered[i]); -+ sta->airtime[i].deficit = sta->airtime_weight; - } - - for (i = 0; i < IEEE80211_NUM_TIDS; i++) -@@ -1821,6 +1821,27 @@ void ieee80211_sta_set_buffered(struct i - } - EXPORT_SYMBOL(ieee80211_sta_set_buffered); - -+void ieee80211_sta_register_airtime(struct ieee80211_sta *pubsta, u8 tid, -+ u32 tx_airtime, u32 rx_airtime) -+{ -+ struct sta_info *sta = container_of(pubsta, struct sta_info, sta); -+ struct ieee80211_local *local = sta->sdata->local; -+ u8 ac = ieee80211_ac_from_tid(tid); -+ u32 airtime = 0; -+ -+ if (sta->local->airtime_flags & AIRTIME_USE_TX) -+ airtime += tx_airtime; -+ if (sta->local->airtime_flags & AIRTIME_USE_RX) -+ airtime += rx_airtime; -+ -+ spin_lock_bh(&local->active_txq_lock[ac]); -+ sta->airtime[ac].tx_airtime += tx_airtime; -+ sta->airtime[ac].rx_airtime += rx_airtime; -+ sta->airtime[ac].deficit -= airtime; -+ spin_unlock_bh(&local->active_txq_lock[ac]); -+} -+EXPORT_SYMBOL(ieee80211_sta_register_airtime); -+ - int sta_info_move_state(struct sta_info *sta, - enum ieee80211_sta_state new_state) - { -@@ -2183,6 +2204,23 @@ void sta_set_sinfo(struct sta_info *sta, - sinfo->filled |= BIT_ULL(NL80211_STA_INFO_TX_FAILED); - } - -+ if (!(sinfo->filled & BIT_ULL(NL80211_STA_INFO_RX_DURATION))) { -+ for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) -+ sinfo->rx_duration += sta->airtime[ac].rx_airtime; -+ sinfo->filled |= BIT_ULL(NL80211_STA_INFO_RX_DURATION); -+ } -+ -+ if (!(sinfo->filled & BIT_ULL(NL80211_STA_INFO_TX_DURATION))) { -+ for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) -+ sinfo->tx_duration += sta->airtime[ac].tx_airtime; -+ sinfo->filled |= BIT_ULL(NL80211_STA_INFO_TX_DURATION); -+ } -+ -+ if (!(sinfo->filled & BIT_ULL(NL80211_STA_INFO_AIRTIME_WEIGHT))) { -+ sinfo->airtime_weight = sta->airtime_weight; -+ sinfo->filled |= BIT_ULL(NL80211_STA_INFO_AIRTIME_WEIGHT); -+ } -+ - sinfo->rx_dropped_misc = sta->rx_stats.dropped; - if (sta->pcpu_rx_stats) { - for_each_possible_cpu(cpu) { ---- a/net/mac80211/sta_info.h -+++ b/net/mac80211/sta_info.h -@@ -127,6 +127,16 @@ enum ieee80211_agg_stop_reason { - AGG_STOP_DESTROY_STA, - }; - -+/* Debugfs flags to enable/disable use of RX/TX airtime in scheduler */ -+#define AIRTIME_USE_TX BIT(0) -+#define AIRTIME_USE_RX BIT(1) -+ -+struct airtime_info { -+ u64 rx_airtime; -+ u64 tx_airtime; -+ s64 deficit; -+}; -+ - struct sta_info; - - /** -@@ -563,6 +573,9 @@ struct sta_info { - } tx_stats; - u16 tid_seq[IEEE80211_QOS_CTL_TID_MASK + 1]; - -+ struct airtime_info airtime[IEEE80211_NUM_ACS]; -+ u16 airtime_weight; -+ - /* - * Aggregation information, locked with lock. - */ ---- a/net/mac80211/status.c -+++ b/net/mac80211/status.c -@@ -825,6 +825,12 @@ static void __ieee80211_tx_status(struct - ieee80211_sta_tx_notify(sta->sdata, (void *) skb->data, - acked, info->status.tx_time); - -+ if (info->status.tx_time && -+ wiphy_ext_feature_isset(local->hw.wiphy, -+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS)) -+ ieee80211_sta_register_airtime(&sta->sta, tid, -+ info->status.tx_time, 0); -+ - if (ieee80211_hw_check(&local->hw, REPORTS_TX_ACK_STATUS)) { - if (info->flags & IEEE80211_TX_STAT_ACK) { - if (sta->status_stats.lost_packets) ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -1463,8 +1463,11 @@ void ieee80211_txq_purge(struct ieee8021 - struct fq *fq = &local->fq; - struct fq_tin *tin = &txqi->tin; - -+ spin_lock_bh(&fq->lock); - fq_tin_reset(fq, tin, fq_skb_free_func); - ieee80211_purge_tx_queue(&local->hw, &txqi->frags); -+ spin_unlock_bh(&fq->lock); -+ - spin_lock_bh(&local->active_txq_lock[txqi->txq.ac]); - list_del_init(&txqi->schedule_order); - spin_unlock_bh(&local->active_txq_lock[txqi->txq.ac]); -@@ -3613,11 +3616,28 @@ struct ieee80211_txq *ieee80211_next_txq - - lockdep_assert_held(&local->active_txq_lock[ac]); - -+ begin: - txqi = list_first_entry_or_null(&local->active_txqs[ac], - struct txq_info, - schedule_order); -+ if (!txqi) -+ return NULL; -+ -+ if (txqi->txq.sta) { -+ struct sta_info *sta = container_of(txqi->txq.sta, -+ struct sta_info, sta); -+ -+ if (sta->airtime[txqi->txq.ac].deficit < 0) { -+ sta->airtime[txqi->txq.ac].deficit += -+ sta->airtime_weight; -+ list_move_tail(&txqi->schedule_order, -+ &local->active_txqs[txqi->txq.ac]); -+ goto begin; -+ } -+ } -+ - -- if (!txqi || txqi->schedule_round == local->schedule_round[ac]) -+ if (txqi->schedule_round == local->schedule_round[ac]) - return NULL; - - list_del_init(&txqi->schedule_order); -@@ -3635,12 +3655,74 @@ void ieee80211_return_txq(struct ieee802 - lockdep_assert_held(&local->active_txq_lock[txq->ac]); - - if (list_empty(&txqi->schedule_order) && -- (!skb_queue_empty(&txqi->frags) || txqi->tin.backlog_packets)) -- list_add_tail(&txqi->schedule_order, -- &local->active_txqs[txq->ac]); -+ (!skb_queue_empty(&txqi->frags) || txqi->tin.backlog_packets)) { -+ /* If airtime accounting is active, always enqueue STAs at the -+ * head of the list to ensure that they only get moved to the -+ * back by the airtime DRR scheduler once they have a negative -+ * deficit. A station that already has a negative deficit will -+ * get immediately moved to the back of the list on the next -+ * call to ieee80211_next_txq(). -+ */ -+ if (txqi->txq.sta && -+ wiphy_ext_feature_isset(local->hw.wiphy, -+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS)) -+ list_add(&txqi->schedule_order, -+ &local->active_txqs[txq->ac]); -+ else -+ list_add_tail(&txqi->schedule_order, -+ &local->active_txqs[txq->ac]); -+ } - } - EXPORT_SYMBOL(ieee80211_return_txq); - -+bool ieee80211_txq_may_transmit(struct ieee80211_hw *hw, -+ struct ieee80211_txq *txq) -+{ -+ struct ieee80211_local *local = hw_to_local(hw); -+ struct txq_info *iter, *tmp, *txqi = to_txq_info(txq); -+ struct sta_info *sta; -+ u8 ac = txq->ac; -+ -+ lockdep_assert_held(&local->active_txq_lock[ac]); -+ -+ if (!txqi->txq.sta) -+ goto out; -+ -+ if (list_empty(&txqi->schedule_order)) -+ goto out; -+ -+ list_for_each_entry_safe(iter, tmp, &local->active_txqs[ac], -+ schedule_order) { -+ if (iter == txqi) -+ break; -+ -+ if (!iter->txq.sta) { -+ list_move_tail(&iter->schedule_order, -+ &local->active_txqs[ac]); -+ continue; -+ } -+ sta = container_of(iter->txq.sta, struct sta_info, sta); -+ if (sta->airtime[ac].deficit < 0) -+ sta->airtime[ac].deficit += sta->airtime_weight; -+ list_move_tail(&iter->schedule_order, &local->active_txqs[ac]); -+ } -+ -+ sta = container_of(txqi->txq.sta, struct sta_info, sta); -+ if (sta->airtime[ac].deficit >= 0) -+ goto out; -+ -+ sta->airtime[ac].deficit += sta->airtime_weight; -+ list_move_tail(&txqi->schedule_order, &local->active_txqs[ac]); -+ -+ return false; -+out: -+ if (!list_empty(&txqi->schedule_order)) -+ list_del_init(&txqi->schedule_order); -+ -+ return true; -+} -+EXPORT_SYMBOL(ieee80211_txq_may_transmit); -+ - void ieee80211_txq_schedule_start(struct ieee80211_hw *hw, u8 ac) - __acquires(txq_lock) - { diff --git a/package/kernel/mac80211/patches/subsys/323-mac80211-Expose-ieee80211_schedule_txq-function.patch b/package/kernel/mac80211/patches/subsys/323-mac80211-Expose-ieee80211_schedule_txq-function.patch deleted file mode 100644 index 573f9bd135..0000000000 --- a/package/kernel/mac80211/patches/subsys/323-mac80211-Expose-ieee80211_schedule_txq-function.patch +++ /dev/null @@ -1,73 +0,0 @@ -From: =?UTF-8?q?Toke=20H=C3=B8iland-J=C3=B8rgensen?= <toke@redhat.com> -Date: Tue, 22 Jan 2019 15:20:16 +0100 -Subject: [PATCH] mac80211: Expose ieee80211_schedule_txq() function -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -Since we reworked ieee80211_return_txq() so it assumes that the caller -takes care of logging, we need another function that can be called without -holding any locks. Introduce ieee80211_schedule_txq() which serves this -purpose. - -Signed-off-by: Toke Høiland-Jørgensen <toke@redhat.com> -Signed-off-by: Johannes Berg <johannes.berg@intel.com> ---- - ---- a/include/net/mac80211.h -+++ b/include/net/mac80211.h -@@ -6074,6 +6074,19 @@ void ieee80211_txq_schedule_end(struct i - __releases(txq_lock); - - /** -+ * ieee80211_schedule_txq - schedule a TXQ for transmission -+ * -+ * @hw: pointer as obtained from ieee80211_alloc_hw() -+ * @txq: pointer obtained from station or virtual interface -+ * -+ * Schedules a TXQ for transmission if it is not already scheduled. Takes a -+ * lock, which means it must *not* be called between -+ * ieee80211_txq_schedule_start() and ieee80211_txq_schedule_end() -+ */ -+void ieee80211_schedule_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq) -+ __acquires(txq_lock) __releases(txq_lock); -+ -+/** - * ieee80211_txq_may_transmit - check whether TXQ is allowed to transmit - * - * This function is used to check whether given txq is allowed to transmit by ---- a/net/mac80211/driver-ops.h -+++ b/net/mac80211/driver-ops.h -@@ -1179,9 +1179,7 @@ static inline void drv_wake_tx_queue(str - static inline void schedule_and_wake_txq(struct ieee80211_local *local, - struct txq_info *txqi) - { -- spin_lock_bh(&local->active_txq_lock[txqi->txq.ac]); -- ieee80211_return_txq(&local->hw, &txqi->txq); -- spin_unlock_bh(&local->active_txq_lock[txqi->txq.ac]); -+ ieee80211_schedule_txq(&local->hw, &txqi->txq); - drv_wake_tx_queue(local, txqi); - } - ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -3675,6 +3675,19 @@ void ieee80211_return_txq(struct ieee802 - } - EXPORT_SYMBOL(ieee80211_return_txq); - -+void ieee80211_schedule_txq(struct ieee80211_hw *hw, -+ struct ieee80211_txq *txq) -+ __acquires(txq_lock) __releases(txq_lock) -+{ -+ struct ieee80211_local *local = hw_to_local(hw); -+ struct txq_info *txqi = to_txq_info(txq); -+ -+ spin_lock_bh(&local->active_txq_lock[txq->ac]); -+ ieee80211_return_txq(hw, txq); -+ spin_unlock_bh(&local->active_txq_lock[txq->ac]); -+} -+EXPORT_SYMBOL(ieee80211_schedule_txq); -+ - bool ieee80211_txq_may_transmit(struct ieee80211_hw *hw, - struct ieee80211_txq *txq) - { diff --git a/package/kernel/mac80211/patches/subsys/350-mac80211-add-hdrlen-to-ieee80211_tx_data.patch b/package/kernel/mac80211/patches/subsys/350-mac80211-add-hdrlen-to-ieee80211_tx_data.patch index 2759895c98..e88163eb5d 100644 --- a/package/kernel/mac80211/patches/subsys/350-mac80211-add-hdrlen-to-ieee80211_tx_data.patch +++ b/package/kernel/mac80211/patches/subsys/350-mac80211-add-hdrlen-to-ieee80211_tx_data.patch @@ -11,7 +11,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> --- a/net/mac80211/ieee80211_i.h +++ b/net/mac80211/ieee80211_i.h -@@ -179,6 +179,7 @@ struct ieee80211_tx_data { +@@ -176,6 +176,7 @@ struct ieee80211_tx_data { struct ieee80211_tx_rate rate; unsigned int flags; @@ -21,7 +21,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> --- a/net/mac80211/tx.c +++ b/net/mac80211/tx.c -@@ -925,7 +925,7 @@ ieee80211_tx_h_fragment(struct ieee80211 +@@ -921,7 +921,7 @@ ieee80211_tx_h_fragment(struct ieee80211 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); struct ieee80211_hdr *hdr = (void *)skb->data; int frag_threshold = tx->local->hw.wiphy->frag_threshold; @@ -30,7 +30,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> int fragnum; /* no matter what happens, tx->skb moves to tx->skbs */ -@@ -946,8 +946,6 @@ ieee80211_tx_h_fragment(struct ieee80211 +@@ -942,8 +942,6 @@ ieee80211_tx_h_fragment(struct ieee80211 if (WARN_ON(info->flags & IEEE80211_TX_CTL_AMPDU)) return TX_DROP; @@ -39,7 +39,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> /* internal error, why isn't DONTFRAG set? */ if (WARN_ON(skb->len + FCS_LEN <= frag_threshold)) return TX_DROP; -@@ -1178,6 +1176,8 @@ ieee80211_tx_prepare(struct ieee80211_su +@@ -1174,6 +1172,8 @@ ieee80211_tx_prepare(struct ieee80211_su hdr = (struct ieee80211_hdr *) skb->data; @@ -48,7 +48,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (likely(sta)) { if (!IS_ERR(sta)) tx->sta = sta; -@@ -3525,6 +3525,7 @@ begin: +@@ -3577,6 +3577,7 @@ begin: tx.local = local; tx.skb = skb; tx.sdata = vif_to_sdata(info->control.vif); @@ -56,7 +56,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (txq->sta) tx.sta = container_of(txq->sta, struct sta_info, sta); -@@ -3551,7 +3552,7 @@ begin: +@@ -3603,7 +3604,7 @@ begin: if (tx.key && (tx.key->conf.flags & IEEE80211_KEY_FLAG_GENERATE_IV)) @@ -65,7 +65,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> ieee80211_xmit_fast_finish(sta->sdata, sta, pn_offs, tx.key, skb); -@@ -4008,6 +4009,7 @@ ieee80211_build_data_template(struct iee +@@ -4058,6 +4059,7 @@ ieee80211_build_data_template(struct iee hdr = (void *)skb->data; tx.sta = sta_info_get(sdata, hdr->addr1); tx.skb = skb; @@ -75,7 +75,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> rcu_read_unlock(); --- a/net/mac80211/util.c +++ b/net/mac80211/util.c -@@ -1390,6 +1390,7 @@ void ieee80211_send_auth(struct ieee8021 +@@ -1538,6 +1538,7 @@ void ieee80211_send_auth(struct ieee8021 struct ieee80211_local *local = sdata->local; struct sk_buff *skb; struct ieee80211_mgmt *mgmt; @@ -83,7 +83,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> int err; /* 24 + 6 = header + auth_algo + auth_transaction + status_code */ -@@ -1413,8 +1414,10 @@ void ieee80211_send_auth(struct ieee8021 +@@ -1561,8 +1562,10 @@ void ieee80211_send_auth(struct ieee8021 skb_put_data(skb, extra, extra_len); if (auth_alg == WLAN_AUTH_SHARED_KEY && transaction == 3) { @@ -97,7 +97,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> --- a/net/mac80211/wep.c +++ b/net/mac80211/wep.c -@@ -89,11 +89,11 @@ static void ieee80211_wep_get_iv(struct +@@ -86,11 +86,11 @@ static void ieee80211_wep_get_iv(struct static u8 *ieee80211_wep_add_iv(struct ieee80211_local *local, struct sk_buff *skb, @@ -110,7 +110,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> u8 *newhdr; hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED); -@@ -101,7 +101,6 @@ static u8 *ieee80211_wep_add_iv(struct i +@@ -98,7 +98,6 @@ static u8 *ieee80211_wep_add_iv(struct i if (WARN_ON(skb_headroom(skb) < IEEE80211_WEP_IV_LEN)) return NULL; @@ -118,7 +118,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> newhdr = skb_push(skb, IEEE80211_WEP_IV_LEN); memmove(newhdr, newhdr + IEEE80211_WEP_IV_LEN, hdrlen); -@@ -160,6 +159,7 @@ int ieee80211_wep_encrypt_data(struct cr +@@ -157,6 +156,7 @@ int ieee80211_wep_encrypt_data(struct cr */ int ieee80211_wep_encrypt(struct ieee80211_local *local, struct sk_buff *skb, @@ -126,7 +126,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> const u8 *key, int keylen, int keyidx) { u8 *iv; -@@ -169,7 +169,7 @@ int ieee80211_wep_encrypt(struct ieee802 +@@ -166,7 +166,7 @@ int ieee80211_wep_encrypt(struct ieee802 if (WARN_ON(skb_tailroom(skb) < IEEE80211_WEP_ICV_LEN)) return -1; @@ -135,7 +135,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (!iv) return -1; -@@ -307,13 +307,14 @@ static int wep_encrypt_skb(struct ieee80 +@@ -304,13 +304,14 @@ static int wep_encrypt_skb(struct ieee80 struct ieee80211_key_conf *hw_key = info->control.hw_key; if (!hw_key) { @@ -154,7 +154,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> return -1; --- a/net/mac80211/wep.h +++ b/net/mac80211/wep.h -@@ -22,6 +22,7 @@ int ieee80211_wep_encrypt_data(struct cr +@@ -19,6 +19,7 @@ int ieee80211_wep_encrypt_data(struct cr size_t klen, u8 *data, size_t data_len); int ieee80211_wep_encrypt(struct ieee80211_local *local, struct sk_buff *skb, @@ -164,7 +164,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> size_t klen, u8 *data, size_t data_len); --- a/net/mac80211/wpa.c +++ b/net/mac80211/wpa.c -@@ -44,7 +44,7 @@ ieee80211_tx_h_michael_mic_add(struct ie +@@ -41,7 +41,7 @@ ieee80211_tx_h_michael_mic_add(struct ie skb->len < 24 || !ieee80211_is_data_present(hdr->frame_control)) return TX_CONTINUE; @@ -173,7 +173,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (skb->len < hdrlen) return TX_DROP; -@@ -195,7 +195,6 @@ mic_fail_no_key: +@@ -192,7 +192,6 @@ mic_fail_no_key: static int tkip_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb) { @@ -181,7 +181,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> struct ieee80211_key *key = tx->key; struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); unsigned int hdrlen; -@@ -210,7 +209,7 @@ static int tkip_encrypt_skb(struct ieee8 +@@ -207,7 +206,7 @@ static int tkip_encrypt_skb(struct ieee8 return 0; } @@ -190,7 +190,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> len = skb->len - hdrlen; if (info->control.hw_key) -@@ -428,7 +427,7 @@ static int ccmp_encrypt_skb(struct ieee8 +@@ -425,7 +424,7 @@ static int ccmp_encrypt_skb(struct ieee8 return 0; } @@ -199,7 +199,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> len = skb->len - hdrlen; if (info->control.hw_key) -@@ -660,7 +659,7 @@ static int gcmp_encrypt_skb(struct ieee8 +@@ -657,7 +656,7 @@ static int gcmp_encrypt_skb(struct ieee8 return 0; } @@ -208,7 +208,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> len = skb->len - hdrlen; if (info->control.hw_key) -@@ -800,7 +799,6 @@ static ieee80211_tx_result +@@ -797,7 +796,6 @@ static ieee80211_tx_result ieee80211_crypto_cs_encrypt(struct ieee80211_tx_data *tx, struct sk_buff *skb) { @@ -216,7 +216,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> struct ieee80211_key *key = tx->key; struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); int hdrlen; -@@ -816,8 +814,7 @@ ieee80211_crypto_cs_encrypt(struct ieee8 +@@ -813,8 +811,7 @@ ieee80211_crypto_cs_encrypt(struct ieee8 pskb_expand_head(skb, iv_len, 0, GFP_ATOMIC))) return TX_DROP; diff --git a/package/kernel/mac80211/patches/subsys/351-mac80211-add-TX_NEEDS_ALIGNED4_SKBS-hw-flag.patch b/package/kernel/mac80211/patches/subsys/351-mac80211-add-TX_NEEDS_ALIGNED4_SKBS-hw-flag.patch index d8dbecca1b..8d9b6e7de9 100644 --- a/package/kernel/mac80211/patches/subsys/351-mac80211-add-TX_NEEDS_ALIGNED4_SKBS-hw-flag.patch +++ b/package/kernel/mac80211/patches/subsys/351-mac80211-add-TX_NEEDS_ALIGNED4_SKBS-hw-flag.patch @@ -20,9 +20,9 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> --- a/include/net/mac80211.h +++ b/include/net/mac80211.h -@@ -2140,6 +2140,9 @@ struct ieee80211_txq { - * @IEEE80211_HW_TX_STATUS_NO_AMPDU_LEN: Driver does not report accurate A-MPDU - * length in tx status information +@@ -2266,6 +2266,9 @@ struct ieee80211_txq { + * @IEEE80211_HW_EXT_KEY_ID_NATIVE: Driver and hardware are supporting Extended + * Key ID and can handle two unicast keys per station for Rx and Tx. * + * @IEEE80211_HW_TX_NEEDS_ALIGNED4_SKBS: Driver need aligned skbs to four-byte. + * Padding will be added after ieee80211_hdr, before IV/LLC. @@ -30,15 +30,15 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> * @NUM_IEEE80211_HW_FLAGS: number of hardware flags, used for sizing arrays */ enum ieee80211_hw_flags { -@@ -2186,6 +2189,7 @@ enum ieee80211_hw_flags { - IEEE80211_HW_DEAUTH_NEED_MGD_TX_PREP, - IEEE80211_HW_DOESNT_SUPPORT_QOS_NDP, - IEEE80211_HW_TX_STATUS_NO_AMPDU_LEN, +@@ -2318,6 +2321,7 @@ enum ieee80211_hw_flags { + IEEE80211_HW_SUPPORTS_MULTI_BSSID, + IEEE80211_HW_SUPPORTS_ONLY_HE_MULTI_BSSID, + IEEE80211_HW_EXT_KEY_ID_NATIVE, + IEEE80211_HW_TX_NEEDS_ALIGNED4_SKBS, /* keep last, obviously */ NUM_IEEE80211_HW_FLAGS -@@ -2472,6 +2476,40 @@ ieee80211_get_alt_retry_rate(const struc +@@ -2611,6 +2615,40 @@ ieee80211_get_alt_retry_rate(const struc void ieee80211_free_txskb(struct ieee80211_hw *hw, struct sk_buff *skb); /** @@ -81,7 +81,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> * mac80211 is capable of taking advantage of many hardware --- a/net/mac80211/iface.c +++ b/net/mac80211/iface.c -@@ -1871,6 +1871,10 @@ int ieee80211_if_add(struct ieee80211_lo +@@ -1877,6 +1877,10 @@ int ieee80211_if_add(struct ieee80211_lo + 8 /* rfc1042/bridge tunnel */ - ETH_HLEN /* ethernet hard_header_len */ + IEEE80211_ENCRYPT_HEADROOM; @@ -94,7 +94,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> ret = dev_alloc_name(ndev, ndev->name); --- a/net/mac80211/mesh_pathtbl.c +++ b/net/mac80211/mesh_pathtbl.c -@@ -105,13 +105,15 @@ void mesh_path_assign_nexthop(struct mes +@@ -102,13 +102,15 @@ void mesh_path_assign_nexthop(struct mes static void prepare_for_gate(struct sk_buff *skb, char *dst_addr, struct mesh_path *gate_mpath) { @@ -113,7 +113,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (!(mshdr->flags & MESH_FLAGS_AE)) { --- a/net/mac80211/rx.c +++ b/net/mac80211/rx.c -@@ -2597,7 +2597,7 @@ ieee80211_rx_h_mesh_fwding(struct ieee80 +@@ -2673,7 +2673,7 @@ ieee80211_rx_h_mesh_fwding(struct ieee80 struct ieee80211_local *local = rx->local; struct ieee80211_sub_if_data *sdata = rx->sdata; struct ieee80211_if_mesh *ifmsh = &sdata->u.mesh; @@ -122,7 +122,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> int tailroom = 0; hdr = (struct ieee80211_hdr *) skb->data; -@@ -2690,7 +2690,9 @@ ieee80211_rx_h_mesh_fwding(struct ieee80 +@@ -2766,7 +2766,9 @@ ieee80211_rx_h_mesh_fwding(struct ieee80 if (sdata->crypto_tx_tailroom_needed_cnt) tailroom = IEEE80211_ENCRYPT_TAILROOM; @@ -133,7 +133,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> sdata->encrypt_headroom, tailroom, GFP_ATOMIC); if (!fwd_skb) -@@ -2722,6 +2724,12 @@ ieee80211_rx_h_mesh_fwding(struct ieee80 +@@ -2798,6 +2800,12 @@ ieee80211_rx_h_mesh_fwding(struct ieee80 return RX_DROP_MONITOR; } @@ -148,7 +148,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> out: --- a/net/mac80211/sta_info.h +++ b/net/mac80211/sta_info.h -@@ -311,7 +311,7 @@ struct ieee80211_fast_tx { +@@ -308,7 +308,7 @@ struct ieee80211_fast_tx { u8 hdr_len; u8 sa_offs, da_offs, pn_offs; u8 band; @@ -159,7 +159,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> struct rcu_head rcu_head; --- a/net/mac80211/status.c +++ b/net/mac80211/status.c -@@ -515,6 +515,7 @@ static void ieee80211_report_used_skb(st +@@ -512,6 +512,7 @@ static void ieee80211_report_used_skb(st { struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); struct ieee80211_hdr *hdr = (void *)skb->data; @@ -167,7 +167,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> bool acked = info->flags & IEEE80211_TX_STAT_ACK; if (dropped) -@@ -531,7 +532,7 @@ static void ieee80211_report_used_skb(st +@@ -528,7 +529,7 @@ static void ieee80211_report_used_skb(st skb->dev = NULL; } else { unsigned int hdr_size = @@ -176,7 +176,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> /* Check to see if packet is a TDLS teardown packet */ if (ieee80211_is_data(hdr->frame_control) && -@@ -655,9 +656,22 @@ void ieee80211_tx_monitor(struct ieee802 +@@ -652,9 +653,22 @@ void ieee80211_tx_monitor(struct ieee802 struct sk_buff *skb2; struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); struct ieee80211_sub_if_data *sdata; @@ -201,7 +201,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (WARN_ON_ONCE(skb_headroom(skb) < rtap_len)) { --- a/net/mac80211/tkip.c +++ b/net/mac80211/tkip.c -@@ -201,10 +201,12 @@ void ieee80211_get_tkip_p2k(struct ieee8 +@@ -198,10 +198,12 @@ void ieee80211_get_tkip_p2k(struct ieee8 { struct ieee80211_key *key = (struct ieee80211_key *) container_of(keyconf, struct ieee80211_key, conf); @@ -217,7 +217,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> --- a/net/mac80211/tx.c +++ b/net/mac80211/tx.c -@@ -1175,8 +1175,7 @@ ieee80211_tx_prepare(struct ieee80211_su +@@ -1171,8 +1171,7 @@ ieee80211_tx_prepare(struct ieee80211_su info->flags &= ~IEEE80211_TX_INTFL_NEED_TXPROCESSING; hdr = (struct ieee80211_hdr *) skb->data; @@ -227,7 +227,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (likely(sta)) { if (!IS_ERR(sta)) -@@ -2222,7 +2221,7 @@ netdev_tx_t ieee80211_monitor_start_xmit +@@ -2244,7 +2243,7 @@ netdev_tx_t ieee80211_monitor_start_xmit goto fail; hdr = (struct ieee80211_hdr *)(skb->data + len_rthdr); @@ -236,7 +236,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (skb->len < len_rthdr + hdrlen) goto fail; -@@ -2440,7 +2439,7 @@ static struct sk_buff *ieee80211_build_h +@@ -2463,7 +2462,7 @@ static struct sk_buff *ieee80211_build_h struct ieee80211_chanctx_conf *chanctx_conf; struct ieee80211_sub_if_data *ap_sdata; enum nl80211_band band; @@ -245,7 +245,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (IS_ERR(sta)) sta = NULL; -@@ -2739,7 +2738,9 @@ static struct sk_buff *ieee80211_build_h +@@ -2774,7 +2773,9 @@ static struct sk_buff *ieee80211_build_h } skb_pull(skb, skip_header_bytes); @@ -255,7 +255,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> /* * So we need to modify the skb header and hence need a copy of -@@ -2772,6 +2773,9 @@ static struct sk_buff *ieee80211_build_h +@@ -2807,6 +2808,9 @@ static struct sk_buff *ieee80211_build_h memcpy(skb_push(skb, meshhdrlen), &mesh_hdr, meshhdrlen); #endif @@ -265,7 +265,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (ieee80211_is_data_qos(fc)) { __le16 *qos_control; -@@ -2947,6 +2951,8 @@ void ieee80211_check_fast_xmit(struct st +@@ -2983,6 +2987,8 @@ void ieee80211_check_fast_xmit(struct st fc |= cpu_to_le16(IEEE80211_STYPE_QOS_DATA); } @@ -274,7 +274,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> /* We store the key here so there's no point in using rcu_dereference() * but that's fine because the code that changes the pointers will call * this function after doing so. For a single CPU that would be enough, -@@ -3525,7 +3531,7 @@ begin: +@@ -3577,7 +3583,7 @@ begin: tx.local = local; tx.skb = skb; tx.sdata = vif_to_sdata(info->control.vif); @@ -283,7 +283,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (txq->sta) tx.sta = container_of(txq->sta, struct sta_info, sta); -@@ -4009,7 +4015,7 @@ ieee80211_build_data_template(struct iee +@@ -4059,7 +4065,7 @@ ieee80211_build_data_template(struct iee hdr = (void *)skb->data; tx.sta = sta_info_get(sdata, hdr->addr1); tx.skb = skb; @@ -294,10 +294,10 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> rcu_read_unlock(); --- a/net/mac80211/debugfs.c +++ b/net/mac80211/debugfs.c -@@ -215,6 +215,7 @@ static const char *hw_flag_names[] = { - FLAG(DEAUTH_NEED_MGD_TX_PREP), - FLAG(DOESNT_SUPPORT_QOS_NDP), - FLAG(TX_STATUS_NO_AMPDU_LEN), +@@ -272,6 +272,7 @@ static const char *hw_flag_names[] = { + FLAG(SUPPORTS_MULTI_BSSID), + FLAG(SUPPORTS_ONLY_HE_MULTI_BSSID), + FLAG(EXT_KEY_ID_NATIVE), + FLAG(TX_NEEDS_ALIGNED4_SKBS), #undef FLAG }; diff --git a/package/kernel/mac80211/patches/subsys/352-mac80211-rework-locking-for-txq-scheduling-airtime-f.patch b/package/kernel/mac80211/patches/subsys/352-mac80211-rework-locking-for-txq-scheduling-airtime-f.patch deleted file mode 100644 index ef67dd1977..0000000000 --- a/package/kernel/mac80211/patches/subsys/352-mac80211-rework-locking-for-txq-scheduling-airtime-f.patch +++ /dev/null @@ -1,214 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Wed, 13 Mar 2019 19:09:22 +0100 -Subject: [PATCH] mac80211: rework locking for txq scheduling / airtime - fairness - -Holding the lock around the entire duration of tx scheduling can create -some nasty lock contention, especially when processing airtime information -from the tx status or the rx path. -Improve locking by only holding the active_txq_lock for lookups / scheduling -list modifications. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/include/net/mac80211.h -+++ b/include/net/mac80211.h -@@ -6069,8 +6069,6 @@ struct sk_buff *ieee80211_tx_dequeue(str - * @hw: pointer as obtained from ieee80211_alloc_hw() - * @ac: AC number to return packets from. - * -- * Should only be called between calls to ieee80211_txq_schedule_start() -- * and ieee80211_txq_schedule_end(). - * Returns the next txq if successful, %NULL if no queue is eligible. If a txq - * is returned, it should be returned with ieee80211_return_txq() after the - * driver has finished scheduling it. -@@ -6078,51 +6076,41 @@ struct sk_buff *ieee80211_tx_dequeue(str - struct ieee80211_txq *ieee80211_next_txq(struct ieee80211_hw *hw, u8 ac); - - /** -- * ieee80211_return_txq - return a TXQ previously acquired by ieee80211_next_txq() -- * -- * @hw: pointer as obtained from ieee80211_alloc_hw() -- * @txq: pointer obtained from station or virtual interface -- * -- * Should only be called between calls to ieee80211_txq_schedule_start() -- * and ieee80211_txq_schedule_end(). -- */ --void ieee80211_return_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq); -- --/** -- * ieee80211_txq_schedule_start - acquire locks for safe scheduling of an AC -+ * ieee80211_txq_schedule_start - start new scheduling round for TXQs - * - * @hw: pointer as obtained from ieee80211_alloc_hw() - * @ac: AC number to acquire locks for - * -- * Acquire locks needed to schedule TXQs from the given AC. Should be called -- * before ieee80211_next_txq() or ieee80211_return_txq(). -+ * Should be called before ieee80211_next_txq() or ieee80211_return_txq(). - */ --void ieee80211_txq_schedule_start(struct ieee80211_hw *hw, u8 ac) -- __acquires(txq_lock); -+void ieee80211_txq_schedule_start(struct ieee80211_hw *hw, u8 ac); -+ -+/* (deprecated) */ -+static inline void ieee80211_txq_schedule_end(struct ieee80211_hw *hw, u8 ac) -+{ -+} - - /** -- * ieee80211_txq_schedule_end - release locks for safe scheduling of an AC -+ * ieee80211_schedule_txq - schedule a TXQ for transmission - * - * @hw: pointer as obtained from ieee80211_alloc_hw() -- * @ac: AC number to acquire locks for -+ * @txq: pointer obtained from station or virtual interface - * -- * Release locks previously acquired by ieee80211_txq_schedule_end(). -+ * Schedules a TXQ for transmission if it is not already scheduled. - */ --void ieee80211_txq_schedule_end(struct ieee80211_hw *hw, u8 ac) -- __releases(txq_lock); -+void ieee80211_schedule_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq); - - /** -- * ieee80211_schedule_txq - schedule a TXQ for transmission -+ * ieee80211_return_txq - return a TXQ previously acquired by ieee80211_next_txq() - * - * @hw: pointer as obtained from ieee80211_alloc_hw() - * @txq: pointer obtained from station or virtual interface -- * -- * Schedules a TXQ for transmission if it is not already scheduled. Takes a -- * lock, which means it must *not* be called between -- * ieee80211_txq_schedule_start() and ieee80211_txq_schedule_end() - */ --void ieee80211_schedule_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq) -- __acquires(txq_lock) __releases(txq_lock); -+static inline void -+ieee80211_return_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq) -+{ -+ ieee80211_schedule_txq(hw, txq); -+} - - /** - * ieee80211_txq_may_transmit - check whether TXQ is allowed to transmit ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -3619,16 +3619,17 @@ EXPORT_SYMBOL(ieee80211_tx_dequeue); - struct ieee80211_txq *ieee80211_next_txq(struct ieee80211_hw *hw, u8 ac) - { - struct ieee80211_local *local = hw_to_local(hw); -+ struct ieee80211_txq *ret = NULL; - struct txq_info *txqi = NULL; - -- lockdep_assert_held(&local->active_txq_lock[ac]); -+ spin_lock_bh(&local->active_txq_lock[ac]); - - begin: - txqi = list_first_entry_or_null(&local->active_txqs[ac], - struct txq_info, - schedule_order); - if (!txqi) -- return NULL; -+ goto out; - - if (txqi->txq.sta) { - struct sta_info *sta = container_of(txqi->txq.sta, -@@ -3645,21 +3646,25 @@ struct ieee80211_txq *ieee80211_next_txq - - - if (txqi->schedule_round == local->schedule_round[ac]) -- return NULL; -+ goto out; - - list_del_init(&txqi->schedule_order); - txqi->schedule_round = local->schedule_round[ac]; -- return &txqi->txq; -+ ret = &txqi->txq; -+ -+out: -+ spin_unlock_bh(&local->active_txq_lock[ac]); -+ return ret; - } - EXPORT_SYMBOL(ieee80211_next_txq); - --void ieee80211_return_txq(struct ieee80211_hw *hw, -- struct ieee80211_txq *txq) -+void ieee80211_schedule_txq(struct ieee80211_hw *hw, -+ struct ieee80211_txq *txq) - { - struct ieee80211_local *local = hw_to_local(hw); - struct txq_info *txqi = to_txq_info(txq); - -- lockdep_assert_held(&local->active_txq_lock[txq->ac]); -+ spin_lock_bh(&local->active_txq_lock[txq->ac]); - - if (list_empty(&txqi->schedule_order) && - (!skb_queue_empty(&txqi->frags) || txqi->tin.backlog_packets)) { -@@ -3679,18 +3684,7 @@ void ieee80211_return_txq(struct ieee802 - list_add_tail(&txqi->schedule_order, - &local->active_txqs[txq->ac]); - } --} --EXPORT_SYMBOL(ieee80211_return_txq); - --void ieee80211_schedule_txq(struct ieee80211_hw *hw, -- struct ieee80211_txq *txq) -- __acquires(txq_lock) __releases(txq_lock) --{ -- struct ieee80211_local *local = hw_to_local(hw); -- struct txq_info *txqi = to_txq_info(txq); -- -- spin_lock_bh(&local->active_txq_lock[txq->ac]); -- ieee80211_return_txq(hw, txq); - spin_unlock_bh(&local->active_txq_lock[txq->ac]); - } - EXPORT_SYMBOL(ieee80211_schedule_txq); -@@ -3703,7 +3697,7 @@ bool ieee80211_txq_may_transmit(struct i - struct sta_info *sta; - u8 ac = txq->ac; - -- lockdep_assert_held(&local->active_txq_lock[ac]); -+ spin_lock_bh(&local->active_txq_lock[ac]); - - if (!txqi->txq.sta) - goto out; -@@ -3733,34 +3727,27 @@ bool ieee80211_txq_may_transmit(struct i - - sta->airtime[ac].deficit += sta->airtime_weight; - list_move_tail(&txqi->schedule_order, &local->active_txqs[ac]); -+ spin_unlock_bh(&local->active_txq_lock[ac]); - - return false; - out: - if (!list_empty(&txqi->schedule_order)) - list_del_init(&txqi->schedule_order); -+ spin_unlock_bh(&local->active_txq_lock[ac]); - - return true; - } - EXPORT_SYMBOL(ieee80211_txq_may_transmit); - - void ieee80211_txq_schedule_start(struct ieee80211_hw *hw, u8 ac) -- __acquires(txq_lock) - { - struct ieee80211_local *local = hw_to_local(hw); - - spin_lock_bh(&local->active_txq_lock[ac]); - local->schedule_round[ac]++; --} --EXPORT_SYMBOL(ieee80211_txq_schedule_start); -- --void ieee80211_txq_schedule_end(struct ieee80211_hw *hw, u8 ac) -- __releases(txq_lock) --{ -- struct ieee80211_local *local = hw_to_local(hw); -- - spin_unlock_bh(&local->active_txq_lock[ac]); - } --EXPORT_SYMBOL(ieee80211_txq_schedule_end); -+EXPORT_SYMBOL(ieee80211_txq_schedule_start); - - void __ieee80211_subif_start_xmit(struct sk_buff *skb, - struct net_device *dev, diff --git a/package/kernel/mac80211/patches/subsys/353-mac80211-mesh-drop-redundant-rcu_read_lock-unlock-ca.patch b/package/kernel/mac80211/patches/subsys/353-mac80211-mesh-drop-redundant-rcu_read_lock-unlock-ca.patch deleted file mode 100644 index 86300be4ed..0000000000 --- a/package/kernel/mac80211/patches/subsys/353-mac80211-mesh-drop-redundant-rcu_read_lock-unlock-ca.patch +++ /dev/null @@ -1,96 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 16 Mar 2019 17:43:58 +0100 -Subject: [PATCH] mac80211: mesh: drop redundant rcu_read_lock/unlock calls - -The callers of these functions are all within RCU locked sections - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/mesh_hwmp.c -+++ b/net/mac80211/mesh_hwmp.c -@@ -1112,16 +1112,13 @@ int mesh_nexthop_resolve(struct ieee8021 - struct mesh_path *mpath; - struct sk_buff *skb_to_free = NULL; - u8 *target_addr = hdr->addr3; -- int err = 0; - - /* Nulls are only sent to peers for PS and should be pre-addressed */ - if (ieee80211_is_qos_nullfunc(hdr->frame_control)) - return 0; - -- rcu_read_lock(); -- err = mesh_nexthop_lookup(sdata, skb); -- if (!err) -- goto endlookup; -+ if (!mesh_nexthop_lookup(sdata, skb)) -+ return 0; - - /* no nexthop found, start resolving */ - mpath = mesh_path_lookup(sdata, target_addr); -@@ -1129,8 +1126,7 @@ int mesh_nexthop_resolve(struct ieee8021 - mpath = mesh_path_add(sdata, target_addr); - if (IS_ERR(mpath)) { - mesh_path_discard_frame(sdata, skb); -- err = PTR_ERR(mpath); -- goto endlookup; -+ return PTR_ERR(mpath); - } - } - -@@ -1143,13 +1139,10 @@ int mesh_nexthop_resolve(struct ieee8021 - info->flags |= IEEE80211_TX_INTFL_NEED_TXPROCESSING; - ieee80211_set_qos_hdr(sdata, skb); - skb_queue_tail(&mpath->frame_queue, skb); -- err = -ENOENT; - if (skb_to_free) - mesh_path_discard_frame(sdata, skb_to_free); - --endlookup: -- rcu_read_unlock(); -- return err; -+ return -ENOENT; - } - - /** -@@ -1169,13 +1162,10 @@ int mesh_nexthop_lookup(struct ieee80211 - struct sta_info *next_hop; - struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; - u8 *target_addr = hdr->addr3; -- int err = -ENOENT; - -- rcu_read_lock(); - mpath = mesh_path_lookup(sdata, target_addr); -- - if (!mpath || !(mpath->flags & MESH_PATH_ACTIVE)) -- goto endlookup; -+ return -ENOENT; - - if (time_after(jiffies, - mpath->exp_time - -@@ -1190,12 +1180,10 @@ int mesh_nexthop_lookup(struct ieee80211 - memcpy(hdr->addr1, next_hop->sta.addr, ETH_ALEN); - memcpy(hdr->addr2, sdata->vif.addr, ETH_ALEN); - ieee80211_mps_set_frame_flags(sdata, next_hop, hdr); -- err = 0; -+ return 0; - } - --endlookup: -- rcu_read_unlock(); -- return err; -+ return -ENOENT; - } - - void mesh_path_timer(struct timer_list *t) ---- a/net/mac80211/mesh_pathtbl.c -+++ b/net/mac80211/mesh_pathtbl.c -@@ -219,7 +219,7 @@ static struct mesh_path *mpath_lookup(st - { - struct mesh_path *mpath; - -- mpath = rhashtable_lookup_fast(&tbl->rhead, dst, mesh_rht_params); -+ mpath = rhashtable_lookup(&tbl->rhead, dst, mesh_rht_params); - - if (mpath && mpath_expired(mpath)) { - spin_lock_bh(&mpath->state_lock); diff --git a/package/kernel/mac80211/patches/subsys/354-mac80211-calculate-hash-for-fq-without-holding-fq-lo.patch b/package/kernel/mac80211/patches/subsys/354-mac80211-calculate-hash-for-fq-without-holding-fq-lo.patch deleted file mode 100644 index 2b6d8ab525..0000000000 --- a/package/kernel/mac80211/patches/subsys/354-mac80211-calculate-hash-for-fq-without-holding-fq-lo.patch +++ /dev/null @@ -1,124 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 16 Mar 2019 17:57:38 +0100 -Subject: [PATCH] mac80211: calculate hash for fq without holding fq->lock - in itxq enqueue - -Reduces lock contention on enqueue/dequeue of iTXQ packets - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/include/net/fq_impl.h -+++ b/include/net/fq_impl.h -@@ -107,21 +107,23 @@ begin: - return skb; - } - -+static u32 fq_flow_idx(struct fq *fq, struct sk_buff *skb) -+{ -+ u32 hash = skb_get_hash_perturb(skb, fq->perturbation); -+ -+ return reciprocal_scale(hash, fq->flows_cnt); -+} -+ - static struct fq_flow *fq_flow_classify(struct fq *fq, -- struct fq_tin *tin, -+ struct fq_tin *tin, u32 idx, - struct sk_buff *skb, - fq_flow_get_default_t get_default_func) - { - struct fq_flow *flow; -- u32 hash; -- u32 idx; - - lockdep_assert_held(&fq->lock); - -- hash = skb_get_hash_perturb(skb, fq->perturbation); -- idx = reciprocal_scale(hash, fq->flows_cnt); - flow = &fq->flows[idx]; -- - if (flow->tin && flow->tin != tin) { - flow = get_default_func(fq, tin, idx, skb); - tin->collisions++; -@@ -153,7 +155,7 @@ static void fq_recalc_backlog(struct fq - } - - static void fq_tin_enqueue(struct fq *fq, -- struct fq_tin *tin, -+ struct fq_tin *tin, u32 idx, - struct sk_buff *skb, - fq_skb_free_t free_func, - fq_flow_get_default_t get_default_func) -@@ -163,7 +165,7 @@ static void fq_tin_enqueue(struct fq *fq - - lockdep_assert_held(&fq->lock); - -- flow = fq_flow_classify(fq, tin, skb, get_default_func); -+ flow = fq_flow_classify(fq, tin, idx, skb, get_default_func); - - flow->tin = tin; - flow->backlog += skb->len; ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -1390,11 +1390,15 @@ static void ieee80211_txq_enqueue(struct - { - struct fq *fq = &local->fq; - struct fq_tin *tin = &txqi->tin; -+ u32 flow_idx = fq_flow_idx(fq, skb); - - ieee80211_set_skb_enqueue_time(skb); -- fq_tin_enqueue(fq, tin, skb, -+ -+ spin_lock_bh(&fq->lock); -+ fq_tin_enqueue(fq, tin, flow_idx, skb, - fq_skb_free_func, - fq_flow_get_default_func); -+ spin_unlock_bh(&fq->lock); - } - - static bool fq_vlan_filter_func(struct fq *fq, struct fq_tin *tin, -@@ -1564,7 +1568,6 @@ static bool ieee80211_queue_skb(struct i - struct sta_info *sta, - struct sk_buff *skb) - { -- struct fq *fq = &local->fq; - struct ieee80211_vif *vif; - struct txq_info *txqi; - -@@ -1582,9 +1585,7 @@ static bool ieee80211_queue_skb(struct i - if (!txqi) - return false; - -- spin_lock_bh(&fq->lock); - ieee80211_txq_enqueue(local, txqi, skb); -- spin_unlock_bh(&fq->lock); - - schedule_and_wake_txq(local, txqi); - -@@ -3198,6 +3199,7 @@ static bool ieee80211_amsdu_aggregate(st - u8 max_subframes = sta->sta.max_amsdu_subframes; - int max_frags = local->hw.max_tx_fragments; - int max_amsdu_len = sta->sta.max_amsdu_len; -+ u32 flow_idx; - int orig_truesize; - __be16 len; - void *data; -@@ -3220,6 +3222,8 @@ static bool ieee80211_amsdu_aggregate(st - max_amsdu_len = min_t(int, max_amsdu_len, - sta->sta.max_rc_amsdu_len); - -+ flow_idx = fq_flow_idx(fq, skb); -+ - spin_lock_bh(&fq->lock); - - /* TODO: Ideally aggregation should be done on dequeue to remain -@@ -3227,7 +3231,8 @@ static bool ieee80211_amsdu_aggregate(st - */ - - tin = &txqi->tin; -- flow = fq_flow_classify(fq, tin, skb, fq_flow_get_default_func); -+ flow = fq_flow_classify(fq, tin, flow_idx, skb, -+ fq_flow_get_default_func); - head = skb_peek_tail(&flow->queue); - if (!head) - goto unlock; diff --git a/package/kernel/mac80211/patches/subsys/355-mac80211-run-late-dequeue-late-tx-handlers-without-h.patch b/package/kernel/mac80211/patches/subsys/355-mac80211-run-late-dequeue-late-tx-handlers-without-h.patch deleted file mode 100644 index 3127c86822..0000000000 --- a/package/kernel/mac80211/patches/subsys/355-mac80211-run-late-dequeue-late-tx-handlers-without-h.patch +++ /dev/null @@ -1,55 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 16 Mar 2019 18:00:12 +0100 -Subject: [PATCH] mac80211: run late dequeue late tx handlers without - holding fq->lock - -Reduces lock contention on enqueue/dequeue of iTXQ packets - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -3507,6 +3507,7 @@ struct sk_buff *ieee80211_tx_dequeue(str - ieee80211_tx_result r; - struct ieee80211_vif *vif = txq->vif; - -+begin: - spin_lock_bh(&fq->lock); - - if (test_bit(IEEE80211_TXQ_STOP, &txqi->flags) || -@@ -3523,11 +3524,12 @@ struct sk_buff *ieee80211_tx_dequeue(str - if (skb) - goto out; - --begin: - skb = fq_tin_dequeue(fq, tin, fq_tin_dequeue_func); - if (!skb) - goto out; - -+ spin_unlock_bh(&fq->lock); -+ - hdr = (struct ieee80211_hdr *)skb->data; - info = IEEE80211_SKB_CB(skb); - -@@ -3573,8 +3575,11 @@ begin: - - skb = __skb_dequeue(&tx.skbs); - -- if (!skb_queue_empty(&tx.skbs)) -+ if (!skb_queue_empty(&tx.skbs)) { -+ spin_lock_bh(&fq->lock); - skb_queue_splice_tail(&tx.skbs, &txqi->frags); -+ spin_unlock_bh(&fq->lock); -+ } - } - - if (skb && skb_has_frag_list(skb) && -@@ -3613,6 +3618,7 @@ begin: - } - - IEEE80211_SKB_CB(skb)->control.vif = vif; -+ return skb; - - out: - spin_unlock_bh(&fq->lock); diff --git a/package/kernel/mac80211/patches/subsys/356-mac80211-set-NETIF_F_LLTX-when-using-intermediate-tx.patch b/package/kernel/mac80211/patches/subsys/356-mac80211-set-NETIF_F_LLTX-when-using-intermediate-tx.patch deleted file mode 100644 index 95ab3ab9fb..0000000000 --- a/package/kernel/mac80211/patches/subsys/356-mac80211-set-NETIF_F_LLTX-when-using-intermediate-tx.patch +++ /dev/null @@ -1,22 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sat, 16 Mar 2019 18:01:53 +0100 -Subject: [PATCH] mac80211: set NETIF_F_LLTX when using intermediate tx - queues - -When using iTXQ, tx sequence number allocation and statistics are run at -dequeue time. Because of that, it is safe to enable NETIF_F_LLTX, which -allows tx handlers to run on multiple CPUs in parallel. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/iface.c -+++ b/net/mac80211/iface.c -@@ -1301,6 +1301,7 @@ static void ieee80211_if_setup(struct ne - static void ieee80211_if_setup_no_queue(struct net_device *dev) - { - ieee80211_if_setup(dev); -+ dev->features |= NETIF_F_LLTX; - #if LINUX_VERSION_IS_GEQ(4,3,0) - dev->priv_flags |= IFF_NO_QUEUE; - #else diff --git a/package/kernel/mac80211/patches/subsys/357-mac80211-optimize-skb-resizing.patch b/package/kernel/mac80211/patches/subsys/357-mac80211-optimize-skb-resizing.patch index 82ed1723c0..6ed2884d5e 100644 --- a/package/kernel/mac80211/patches/subsys/357-mac80211-optimize-skb-resizing.patch +++ b/package/kernel/mac80211/patches/subsys/357-mac80211-optimize-skb-resizing.patch @@ -24,10 +24,10 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> --- a/net/mac80211/ieee80211_i.h +++ b/net/mac80211/ieee80211_i.h -@@ -1761,6 +1761,9 @@ void ieee80211_clear_fast_xmit(struct st - int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev, - const u8 *buf, size_t len, +@@ -1780,6 +1780,9 @@ int ieee80211_tx_control_port(struct wip const u8 *dest, __be16 proto, bool unencrypted); + int ieee80211_probe_mesh_link(struct wiphy *wiphy, struct net_device *dev, + const u8 *buf, size_t len); +int ieee80211_skb_resize(struct ieee80211_local *local, + struct ieee80211_sub_if_data *sdata, + struct sk_buff *skb, int hdrlen, int hdr_add); @@ -36,7 +36,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> void ieee80211_apply_htcap_overrides(struct ieee80211_sub_if_data *sdata, --- a/net/mac80211/status.c +++ b/net/mac80211/status.c -@@ -672,6 +672,11 @@ void ieee80211_tx_monitor(struct ieee802 +@@ -669,6 +669,11 @@ void ieee80211_tx_monitor(struct ieee802 } } @@ -50,7 +50,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> if (WARN_ON_ONCE(skb_headroom(skb) < rtap_len)) { --- a/net/mac80211/tx.c +++ b/net/mac80211/tx.c -@@ -1914,37 +1914,53 @@ static bool ieee80211_tx(struct ieee8021 +@@ -1935,37 +1935,53 @@ static bool ieee80211_tx(struct ieee8021 } /* device xmit handlers */ @@ -123,7 +123,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> wiphy_debug(local->hw.wiphy, "failed to reallocate TX buffer\n"); return -ENOMEM; -@@ -1960,18 +1976,8 @@ void ieee80211_xmit(struct ieee80211_sub +@@ -1981,18 +1997,8 @@ void ieee80211_xmit(struct ieee80211_sub struct ieee80211_local *local = sdata->local; struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); struct ieee80211_hdr *hdr; @@ -143,7 +143,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> ieee80211_free_txskb(&local->hw, skb); return; } -@@ -2740,30 +2746,14 @@ static struct sk_buff *ieee80211_build_h +@@ -2774,30 +2780,14 @@ static struct sk_buff *ieee80211_build_h skb_pull(skb, skip_header_bytes); padsize = ieee80211_hdr_padsize(&local->hw, hdrlen); @@ -180,7 +180,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> } if (encaps_data) -@@ -3377,7 +3367,6 @@ static bool ieee80211_xmit_fast(struct i +@@ -3417,7 +3407,6 @@ static bool ieee80211_xmit_fast(struct i struct ieee80211_local *local = sdata->local; u16 ethertype = (skb->data[12] << 8) | skb->data[13]; int extra_head = fast_tx->hdr_len - (ETH_HLEN - 2); @@ -188,7 +188,7 @@ Signed-off-by: Felix Fietkau <nbd@nbd.name> struct ethhdr eth; struct ieee80211_tx_info *info; struct ieee80211_hdr *hdr = (void *)fast_tx->hdr; -@@ -3429,10 +3418,7 @@ static bool ieee80211_xmit_fast(struct i +@@ -3469,10 +3458,7 @@ static bool ieee80211_xmit_fast(struct i * as the may-encrypt argument for the resize to not account for * more room than we already have in 'extra_head' */ diff --git a/package/kernel/mac80211/patches/subsys/358-mac80211-make-ieee80211_schedule_txq-schedule-empty-.patch b/package/kernel/mac80211/patches/subsys/358-mac80211-make-ieee80211_schedule_txq-schedule-empty-.patch deleted file mode 100644 index a0a65f35a8..0000000000 --- a/package/kernel/mac80211/patches/subsys/358-mac80211-make-ieee80211_schedule_txq-schedule-empty-.patch +++ /dev/null @@ -1,105 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Sun, 17 Mar 2019 14:26:59 +0100 -Subject: [PATCH] mac80211: make ieee80211_schedule_txq schedule empty TXQs - -Currently there is no way for the driver to signal to mac80211 that it should -schedule a TXQ even if there are no packets on the mac80211 part of that queue. -This is problematic if the driver has an internal retry queue to deal with -software A-MPDU retry. - -This patch changes the behavior of ieee80211_schedule_txq to always schedule -the queue, as its only user (ath9k) seems to expect such behavior already: -it calls this function on tx status and on powersave wakeup whenever its -internal retry queue is not empty. - -Also add an extra argument to ieee80211_return_txq to get the same behavior. - -This fixes an issue on ath9k where tx queues with packets to retry (and no -new packets in mac80211) would not get serviced. - -Fixes: 89cea7493a346 ("ath9k: Switch to mac80211 TXQ scheduling and airtime APIs") -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/include/net/mac80211.h -+++ b/include/net/mac80211.h -@@ -6090,26 +6090,42 @@ static inline void ieee80211_txq_schedul - { - } - -+void __ieee80211_schedule_txq(struct ieee80211_hw *hw, -+ struct ieee80211_txq *txq, bool force); -+ - /** - * ieee80211_schedule_txq - schedule a TXQ for transmission - * - * @hw: pointer as obtained from ieee80211_alloc_hw() - * @txq: pointer obtained from station or virtual interface - * -- * Schedules a TXQ for transmission if it is not already scheduled. -+ * Schedules a TXQ for transmission if it is not already scheduled, -+ * even if mac80211 does not have any packets buffered. -+ * -+ * The driver may call this function if it has buffered packets for -+ * this TXQ internally. - */ --void ieee80211_schedule_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq); -+static inline void -+ieee80211_schedule_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq) -+{ -+ __ieee80211_schedule_txq(hw, txq, true); -+} - - /** - * ieee80211_return_txq - return a TXQ previously acquired by ieee80211_next_txq() - * - * @hw: pointer as obtained from ieee80211_alloc_hw() - * @txq: pointer obtained from station or virtual interface -+ * @force: schedule txq even if mac80211 does not have any buffered packets. -+ * -+ * The driver may set force=true if it has buffered packets for this TXQ -+ * internally. - */ - static inline void --ieee80211_return_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq) -+ieee80211_return_txq(struct ieee80211_hw *hw, struct ieee80211_txq *txq, -+ bool force) - { -- ieee80211_schedule_txq(hw, txq); -+ __ieee80211_schedule_txq(hw, txq, force); - } - - /** ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -3655,8 +3655,9 @@ out: - } - EXPORT_SYMBOL(ieee80211_next_txq); - --void ieee80211_schedule_txq(struct ieee80211_hw *hw, -- struct ieee80211_txq *txq) -+void __ieee80211_schedule_txq(struct ieee80211_hw *hw, -+ struct ieee80211_txq *txq, -+ bool force) - { - struct ieee80211_local *local = hw_to_local(hw); - struct txq_info *txqi = to_txq_info(txq); -@@ -3664,7 +3665,8 @@ void ieee80211_schedule_txq(struct ieee8 - spin_lock_bh(&local->active_txq_lock[txq->ac]); - - if (list_empty(&txqi->schedule_order) && -- (!skb_queue_empty(&txqi->frags) || txqi->tin.backlog_packets)) { -+ (force || !skb_queue_empty(&txqi->frags) || -+ txqi->tin.backlog_packets)) { - /* If airtime accounting is active, always enqueue STAs at the - * head of the list to ensure that they only get moved to the - * back by the airtime DRR scheduler once they have a negative -@@ -3684,7 +3686,7 @@ void ieee80211_schedule_txq(struct ieee8 - - spin_unlock_bh(&local->active_txq_lock[txq->ac]); - } --EXPORT_SYMBOL(ieee80211_schedule_txq); -+EXPORT_SYMBOL(__ieee80211_schedule_txq); - - bool ieee80211_txq_may_transmit(struct ieee80211_hw *hw, - struct ieee80211_txq *txq) diff --git a/package/kernel/mac80211/patches/subsys/359-mac80211-un-schedule-TXQs-on-powersave-start.patch b/package/kernel/mac80211/patches/subsys/359-mac80211-un-schedule-TXQs-on-powersave-start.patch deleted file mode 100644 index 1abb2db7c2..0000000000 --- a/package/kernel/mac80211/patches/subsys/359-mac80211-un-schedule-TXQs-on-powersave-start.patch +++ /dev/null @@ -1,31 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Tue, 19 Mar 2019 11:36:12 +0100 -Subject: [PATCH] mac80211: un-schedule TXQs on powersave start - -Once a station enters powersave, its queues should not be returned by -ieee80211_next_txq() anymore. They will be re-scheduled again after the -station has woken up again - -Fixes: 1866760096bf4 ("mac80211: Add TXQ scheduling API") -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rx.c -+++ b/net/mac80211/rx.c -@@ -1508,7 +1508,15 @@ static void sta_ps_start(struct sta_info - return; - - for (tid = 0; tid < ARRAY_SIZE(sta->sta.txq); tid++) { -- if (txq_has_queue(sta->sta.txq[tid])) -+ struct ieee80211_txq *txq = sta->sta.txq[tid]; -+ struct txq_info *txqi = to_txq_info(txq); -+ -+ spin_lock(&local->active_txq_lock[txq->ac]); -+ if (!list_empty(&txqi->schedule_order)) -+ list_del_init(&txqi->schedule_order); -+ spin_unlock(&local->active_txq_lock[txq->ac]); -+ -+ if (txq_has_queue(txq)) - set_bit(tid, &sta->txq_buffered_tids); - else - clear_bit(tid, &sta->txq_buffered_tids); diff --git a/package/kernel/mac80211/patches/subsys/360-mac80211-when-using-iTXQ-select-the-queue-in-ieee802.patch b/package/kernel/mac80211/patches/subsys/360-mac80211-when-using-iTXQ-select-the-queue-in-ieee802.patch deleted file mode 100644 index bb3af7317a..0000000000 --- a/package/kernel/mac80211/patches/subsys/360-mac80211-when-using-iTXQ-select-the-queue-in-ieee802.patch +++ /dev/null @@ -1,183 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Fri, 22 Mar 2019 18:06:03 +0100 -Subject: [PATCH] mac80211: when using iTXQ, select the queue in - ieee80211_subif_start_xmit - -When using iTXQ, the network stack does not need the real queue number, since -mac80211 is using its internal queues anyway. In that case we can defer -selecting the queue and remove a redundant station lookup in the tx path to save -some CPU cycles. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -3753,6 +3753,7 @@ void __ieee80211_subif_start_xmit(struct - u32 info_flags) - { - struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); -+ struct ieee80211_local *local = sdata->local; - struct sta_info *sta; - struct sk_buff *next; - -@@ -3766,7 +3767,15 @@ void __ieee80211_subif_start_xmit(struct - if (ieee80211_lookup_ra_sta(sdata, skb, &sta)) - goto out_free; - -- if (!IS_ERR_OR_NULL(sta)) { -+ if (IS_ERR(sta)) -+ sta = NULL; -+ -+ if (local->ops->wake_tx_queue) { -+ u16 queue = __ieee80211_select_queue(sdata, sta, skb); -+ skb_set_queue_mapping(skb, queue); -+ } -+ -+ if (sta) { - struct ieee80211_fast_tx *fast_tx; - - /* We need a bit of data queued to build aggregates properly, so ---- a/net/mac80211/wme.c -+++ b/net/mac80211/wme.c -@@ -141,6 +141,42 @@ u16 ieee80211_select_queue_80211(struct - return ieee80211_downgrade_queue(sdata, NULL, skb); - } - -+u16 __ieee80211_select_queue(struct ieee80211_sub_if_data *sdata, -+ struct sta_info *sta, struct sk_buff *skb) -+{ -+ struct mac80211_qos_map *qos_map; -+ bool qos; -+ -+ /* all mesh/ocb stations are required to support WME */ -+ if (sdata->vif.type == NL80211_IFTYPE_MESH_POINT || -+ sdata->vif.type == NL80211_IFTYPE_OCB) -+ qos = true; -+ else if (sta) -+ qos = sta->sta.wme; -+ else -+ qos = false; -+ -+ if (!qos) { -+ skb->priority = 0; /* required for correct WPA/11i MIC */ -+ return IEEE80211_AC_BE; -+ } -+ -+ if (skb->protocol == sdata->control_port_protocol) { -+ skb->priority = 7; -+ goto downgrade; -+ } -+ -+ /* use the data classifier to determine what 802.1d tag the -+ * data frame has */ -+ qos_map = rcu_dereference(sdata->qos_map); -+ skb->priority = cfg80211_classify8021d(skb, qos_map ? -+ &qos_map->qos_map : NULL); -+ -+ downgrade: -+ return ieee80211_downgrade_queue(sdata, sta, skb); -+} -+ -+ - /* Indicate which queue to use. */ - u16 ieee80211_select_queue(struct ieee80211_sub_if_data *sdata, - struct sk_buff *skb) -@@ -148,10 +184,12 @@ u16 ieee80211_select_queue(struct ieee80 - struct ieee80211_local *local = sdata->local; - struct sta_info *sta = NULL; - const u8 *ra = NULL; -- bool qos = false; -- struct mac80211_qos_map *qos_map; - u16 ret; - -+ /* when using iTXQ, we can do this later */ -+ if (local->ops->wake_tx_queue) -+ return 0; -+ - if (local->hw.queues < IEEE80211_NUM_ACS || skb->len < 6) { - skb->priority = 0; /* required for correct WPA/11i MIC */ - return 0; -@@ -161,10 +199,8 @@ u16 ieee80211_select_queue(struct ieee80 - switch (sdata->vif.type) { - case NL80211_IFTYPE_AP_VLAN: - sta = rcu_dereference(sdata->u.vlan.sta); -- if (sta) { -- qos = sta->sta.wme; -+ if (sta) - break; -- } - /* fall through */ - case NL80211_IFTYPE_AP: - ra = skb->data; -@@ -172,56 +208,26 @@ u16 ieee80211_select_queue(struct ieee80 - case NL80211_IFTYPE_WDS: - ra = sdata->u.wds.remote_addr; - break; --#ifdef CPTCFG_MAC80211_MESH -- case NL80211_IFTYPE_MESH_POINT: -- qos = true; -- break; --#endif - case NL80211_IFTYPE_STATION: - /* might be a TDLS station */ - sta = sta_info_get(sdata, skb->data); - if (sta) -- qos = sta->sta.wme; -+ break; - - ra = sdata->u.mgd.bssid; - break; - case NL80211_IFTYPE_ADHOC: - ra = skb->data; - break; -- case NL80211_IFTYPE_OCB: -- /* all stations are required to support WME */ -- qos = true; -- break; - default: - break; - } - -- if (!sta && ra && !is_multicast_ether_addr(ra)) { -+ if (!sta && ra && !is_multicast_ether_addr(ra)) - sta = sta_info_get(sdata, ra); -- if (sta) -- qos = sta->sta.wme; -- } - -- if (!qos) { -- skb->priority = 0; /* required for correct WPA/11i MIC */ -- ret = IEEE80211_AC_BE; -- goto out; -- } -+ ret = __ieee80211_select_queue(sdata, sta, skb); - -- if (skb->protocol == sdata->control_port_protocol) { -- skb->priority = 7; -- goto downgrade; -- } -- -- /* use the data classifier to determine what 802.1d tag the -- * data frame has */ -- qos_map = rcu_dereference(sdata->qos_map); -- skb->priority = cfg80211_classify8021d(skb, qos_map ? -- &qos_map->qos_map : NULL); -- -- downgrade: -- ret = ieee80211_downgrade_queue(sdata, sta, skb); -- out: - rcu_read_unlock(); - return ret; - } ---- a/net/mac80211/wme.h -+++ b/net/mac80211/wme.h -@@ -16,6 +16,8 @@ - u16 ieee80211_select_queue_80211(struct ieee80211_sub_if_data *sdata, - struct sk_buff *skb, - struct ieee80211_hdr *hdr); -+u16 __ieee80211_select_queue(struct ieee80211_sub_if_data *sdata, -+ struct sta_info *sta, struct sk_buff *skb); - u16 ieee80211_select_queue(struct ieee80211_sub_if_data *sdata, - struct sk_buff *skb); - void ieee80211_set_qos_hdr(struct ieee80211_sub_if_data *sdata, diff --git a/package/kernel/mac80211/patches/subsys/361-mac80211-minstrel_ht-add-support-for-rates-with-4-sp.patch b/package/kernel/mac80211/patches/subsys/361-mac80211-minstrel_ht-add-support-for-rates-with-4-sp.patch deleted file mode 100644 index 07b30dfbf7..0000000000 --- a/package/kernel/mac80211/patches/subsys/361-mac80211-minstrel_ht-add-support-for-rates-with-4-sp.patch +++ /dev/null @@ -1,78 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Mon, 25 Mar 2019 09:02:13 +0100 -Subject: [PATCH] mac80211: minstrel_ht: add support for rates with 4 - spatial streams - -This is needed for the upcoming driver for MT7615 4x4 802.11ac chipsets - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -157,44 +157,54 @@ const struct mcs_group minstrel_mcs_grou - MCS_GROUP(1, 0, BW_20, 5), - MCS_GROUP(2, 0, BW_20, 4), - MCS_GROUP(3, 0, BW_20, 4), -+ MCS_GROUP(4, 0, BW_20, 4), - - MCS_GROUP(1, 1, BW_20, 5), - MCS_GROUP(2, 1, BW_20, 4), - MCS_GROUP(3, 1, BW_20, 4), -+ MCS_GROUP(4, 1, BW_20, 4), - - MCS_GROUP(1, 0, BW_40, 4), - MCS_GROUP(2, 0, BW_40, 4), - MCS_GROUP(3, 0, BW_40, 4), -+ MCS_GROUP(4, 0, BW_40, 4), - - MCS_GROUP(1, 1, BW_40, 4), - MCS_GROUP(2, 1, BW_40, 4), - MCS_GROUP(3, 1, BW_40, 4), -+ MCS_GROUP(4, 1, BW_40, 4), - - CCK_GROUP(8), - - VHT_GROUP(1, 0, BW_20, 5), - VHT_GROUP(2, 0, BW_20, 4), - VHT_GROUP(3, 0, BW_20, 4), -+ VHT_GROUP(4, 0, BW_20, 4), - - VHT_GROUP(1, 1, BW_20, 5), - VHT_GROUP(2, 1, BW_20, 4), - VHT_GROUP(3, 1, BW_20, 4), -+ VHT_GROUP(4, 1, BW_20, 4), - - VHT_GROUP(1, 0, BW_40, 4), - VHT_GROUP(2, 0, BW_40, 4), - VHT_GROUP(3, 0, BW_40, 4), -+ VHT_GROUP(4, 0, BW_40, 3), - - VHT_GROUP(1, 1, BW_40, 4), - VHT_GROUP(2, 1, BW_40, 4), - VHT_GROUP(3, 1, BW_40, 4), -+ VHT_GROUP(4, 1, BW_40, 3), - - VHT_GROUP(1, 0, BW_80, 4), - VHT_GROUP(2, 0, BW_80, 4), - VHT_GROUP(3, 0, BW_80, 4), -+ VHT_GROUP(4, 0, BW_80, 2), - - VHT_GROUP(1, 1, BW_80, 4), - VHT_GROUP(2, 1, BW_80, 4), - VHT_GROUP(3, 1, BW_80, 4), -+ VHT_GROUP(4, 1, BW_80, 2), - }; - - static u8 sample_table[SAMPLE_COLUMNS][MCS_GROUP_RATES] __read_mostly; ---- a/net/mac80211/rc80211_minstrel_ht.h -+++ b/net/mac80211/rc80211_minstrel_ht.h -@@ -13,7 +13,7 @@ - * The number of streams can be changed to 2 to reduce code - * size and memory footprint. - */ --#define MINSTREL_MAX_STREAMS 3 -+#define MINSTREL_MAX_STREAMS 4 - #define MINSTREL_HT_STREAM_GROUPS 4 /* BW(=2) * SGI(=2) */ - #define MINSTREL_VHT_STREAM_GROUPS 6 /* BW(=3) * SGI(=2) */ - diff --git a/package/kernel/mac80211/patches/subsys/362-mac80211-minstrel_ht-automatically-calculate-rate-du.patch b/package/kernel/mac80211/patches/subsys/362-mac80211-minstrel_ht-automatically-calculate-rate-du.patch deleted file mode 100644 index 81d14966f7..0000000000 --- a/package/kernel/mac80211/patches/subsys/362-mac80211-minstrel_ht-automatically-calculate-rate-du.patch +++ /dev/null @@ -1,189 +0,0 @@ -From: Felix Fietkau <nbd@nbd.name> -Date: Mon, 25 Mar 2019 09:02:52 +0100 -Subject: [PATCH] mac80211: minstrel_ht: automatically calculate rate - duration shift - -A per-group shift was added to reduce the size of the per-rate transmit -duration field to u16 without sacrificing a lot of precision -This patch changes the macros to automatically calculate the best value for -this shift based on the lowest rate within the group. -This simplifies adding more groups and slightly improves accuracy for some of -the existing groups. - -Signed-off-by: Felix Fietkau <nbd@nbd.name> ---- - ---- a/net/mac80211/rc80211_minstrel_ht.c -+++ b/net/mac80211/rc80211_minstrel_ht.c -@@ -51,8 +51,11 @@ - MINSTREL_MAX_STREAMS * _sgi + \ - _streams - 1 - -+#define GROUP_SHIFT(duration) \ -+ (16 - __builtin_clz(duration)) -+ - /* MCS rate information for an MCS group */ --#define MCS_GROUP(_streams, _sgi, _ht40, _s) \ -+#define __MCS_GROUP(_streams, _sgi, _ht40, _s) \ - [GROUP_IDX(_streams, _sgi, _ht40)] = { \ - .streams = _streams, \ - .shift = _s, \ -@@ -72,6 +75,13 @@ - } \ - } - -+#define MCS_GROUP_SHIFT(_streams, _sgi, _ht40) \ -+ GROUP_SHIFT(MCS_DURATION(_streams, _sgi, _ht40 ? 54 : 26)) -+ -+#define MCS_GROUP(_streams, _sgi, _ht40) \ -+ __MCS_GROUP(_streams, _sgi, _ht40, \ -+ MCS_GROUP_SHIFT(_streams, _sgi, _ht40)) -+ - #define VHT_GROUP_IDX(_streams, _sgi, _bw) \ - (MINSTREL_VHT_GROUP_0 + \ - MINSTREL_MAX_STREAMS * 2 * (_bw) + \ -@@ -81,7 +91,7 @@ - #define BW2VBPS(_bw, r3, r2, r1) \ - (_bw == BW_80 ? r3 : _bw == BW_40 ? r2 : r1) - --#define VHT_GROUP(_streams, _sgi, _bw, _s) \ -+#define __VHT_GROUP(_streams, _sgi, _bw, _s) \ - [VHT_GROUP_IDX(_streams, _sgi, _bw)] = { \ - .streams = _streams, \ - .shift = _s, \ -@@ -114,6 +124,14 @@ - } \ - } - -+#define VHT_GROUP_SHIFT(_streams, _sgi, _bw) \ -+ GROUP_SHIFT(MCS_DURATION(_streams, _sgi, \ -+ BW2VBPS(_bw, 117, 54, 26))) -+ -+#define VHT_GROUP(_streams, _sgi, _bw) \ -+ __VHT_GROUP(_streams, _sgi, _bw, \ -+ VHT_GROUP_SHIFT(_streams, _sgi, _bw)) -+ - #define CCK_DURATION(_bitrate, _short, _len) \ - (1000 * (10 /* SIFS */ + \ - (_short ? 72 + 24 : 144 + 48) + \ -@@ -129,7 +147,7 @@ - CCK_ACK_DURATION(55, _short) >> _s, \ - CCK_ACK_DURATION(110, _short) >> _s - --#define CCK_GROUP(_s) \ -+#define __CCK_GROUP(_s) \ - [MINSTREL_CCK_GROUP] = { \ - .streams = 1, \ - .flags = 0, \ -@@ -140,6 +158,12 @@ - } \ - } - -+#define CCK_GROUP_SHIFT \ -+ GROUP_SHIFT(CCK_ACK_DURATION(10, false)) -+ -+#define CCK_GROUP __CCK_GROUP(CCK_GROUP_SHIFT) -+ -+ - static bool minstrel_vht_only = true; - module_param(minstrel_vht_only, bool, 0644); - MODULE_PARM_DESC(minstrel_vht_only, -@@ -154,57 +178,57 @@ MODULE_PARM_DESC(minstrel_vht_only, - * BW -> SGI -> #streams - */ - const struct mcs_group minstrel_mcs_groups[] = { -- MCS_GROUP(1, 0, BW_20, 5), -- MCS_GROUP(2, 0, BW_20, 4), -- MCS_GROUP(3, 0, BW_20, 4), -- MCS_GROUP(4, 0, BW_20, 4), -+ MCS_GROUP(1, 0, BW_20), -+ MCS_GROUP(2, 0, BW_20), -+ MCS_GROUP(3, 0, BW_20), -+ MCS_GROUP(4, 0, BW_20), - -- MCS_GROUP(1, 1, BW_20, 5), -- MCS_GROUP(2, 1, BW_20, 4), -- MCS_GROUP(3, 1, BW_20, 4), -- MCS_GROUP(4, 1, BW_20, 4), -+ MCS_GROUP(1, 1, BW_20), -+ MCS_GROUP(2, 1, BW_20), -+ MCS_GROUP(3, 1, BW_20), -+ MCS_GROUP(4, 1, BW_20), - -- MCS_GROUP(1, 0, BW_40, 4), -- MCS_GROUP(2, 0, BW_40, 4), -- MCS_GROUP(3, 0, BW_40, 4), -- MCS_GROUP(4, 0, BW_40, 4), -+ MCS_GROUP(1, 0, BW_40), -+ MCS_GROUP(2, 0, BW_40), -+ MCS_GROUP(3, 0, BW_40), -+ MCS_GROUP(4, 0, BW_40), - -- MCS_GROUP(1, 1, BW_40, 4), -- MCS_GROUP(2, 1, BW_40, 4), -- MCS_GROUP(3, 1, BW_40, 4), -- MCS_GROUP(4, 1, BW_40, 4), -+ MCS_GROUP(1, 1, BW_40), -+ MCS_GROUP(2, 1, BW_40), -+ MCS_GROUP(3, 1, BW_40), -+ MCS_GROUP(4, 1, BW_40), - -- CCK_GROUP(8), -+ CCK_GROUP, - -- VHT_GROUP(1, 0, BW_20, 5), -- VHT_GROUP(2, 0, BW_20, 4), -- VHT_GROUP(3, 0, BW_20, 4), -- VHT_GROUP(4, 0, BW_20, 4), -+ VHT_GROUP(1, 0, BW_20), -+ VHT_GROUP(2, 0, BW_20), -+ VHT_GROUP(3, 0, BW_20), -+ VHT_GROUP(4, 0, BW_20), - -- VHT_GROUP(1, 1, BW_20, 5), -- VHT_GROUP(2, 1, BW_20, 4), -- VHT_GROUP(3, 1, BW_20, 4), -- VHT_GROUP(4, 1, BW_20, 4), -+ VHT_GROUP(1, 1, BW_20), -+ VHT_GROUP(2, 1, BW_20), -+ VHT_GROUP(3, 1, BW_20), -+ VHT_GROUP(4, 1, BW_20), - -- VHT_GROUP(1, 0, BW_40, 4), -- VHT_GROUP(2, 0, BW_40, 4), -- VHT_GROUP(3, 0, BW_40, 4), -- VHT_GROUP(4, 0, BW_40, 3), -+ VHT_GROUP(1, 0, BW_40), -+ VHT_GROUP(2, 0, BW_40), -+ VHT_GROUP(3, 0, BW_40), -+ VHT_GROUP(4, 0, BW_40), - -- VHT_GROUP(1, 1, BW_40, 4), -- VHT_GROUP(2, 1, BW_40, 4), -- VHT_GROUP(3, 1, BW_40, 4), -- VHT_GROUP(4, 1, BW_40, 3), -+ VHT_GROUP(1, 1, BW_40), -+ VHT_GROUP(2, 1, BW_40), -+ VHT_GROUP(3, 1, BW_40), -+ VHT_GROUP(4, 1, BW_40), - -- VHT_GROUP(1, 0, BW_80, 4), -- VHT_GROUP(2, 0, BW_80, 4), -- VHT_GROUP(3, 0, BW_80, 4), -- VHT_GROUP(4, 0, BW_80, 2), -+ VHT_GROUP(1, 0, BW_80), -+ VHT_GROUP(2, 0, BW_80), -+ VHT_GROUP(3, 0, BW_80), -+ VHT_GROUP(4, 0, BW_80), - -- VHT_GROUP(1, 1, BW_80, 4), -- VHT_GROUP(2, 1, BW_80, 4), -- VHT_GROUP(3, 1, BW_80, 4), -- VHT_GROUP(4, 1, BW_80, 2), -+ VHT_GROUP(1, 1, BW_80), -+ VHT_GROUP(2, 1, BW_80), -+ VHT_GROUP(3, 1, BW_80), -+ VHT_GROUP(4, 1, BW_80), - }; - - static u8 sample_table[SAMPLE_COLUMNS][MCS_GROUP_RATES] __read_mostly; diff --git a/package/kernel/mac80211/patches/subsys/390-nl-mac-80211-allow-4addr-AP-operation-on-crypto-cont.patch b/package/kernel/mac80211/patches/subsys/390-nl-mac-80211-allow-4addr-AP-operation-on-crypto-cont.patch deleted file mode 100644 index d5b08b4410..0000000000 --- a/package/kernel/mac80211/patches/subsys/390-nl-mac-80211-allow-4addr-AP-operation-on-crypto-cont.patch +++ /dev/null @@ -1,103 +0,0 @@ -From 33d915d9e8ce811d8958915ccd18d71a66c7c495 Mon Sep 17 00:00:00 2001 -From: Manikanta Pubbisetty <mpubbise@codeaurora.org> -Date: Wed, 8 May 2019 14:55:33 +0530 -Subject: [PATCH] {nl,mac}80211: allow 4addr AP operation on crypto controlled - devices - -As per the current design, in the case of sw crypto controlled devices, -it is the device which advertises the support for AP/VLAN iftype based -on it's ability to tranmsit packets encrypted in software -(In VLAN functionality, group traffic generated for a specific -VLAN group is always encrypted in software). Commit db3bdcb9c3ff -("mac80211: allow AP_VLAN operation on crypto controlled devices") -has introduced this change. - -Since 4addr AP operation also uses AP/VLAN iftype, this conditional -way of advertising AP/VLAN support has broken 4addr AP mode operation on -crypto controlled devices which do not support VLAN functionality. - -In the case of ath10k driver, not all firmwares have support for VLAN -functionality but all can support 4addr AP operation. Because AP/VLAN -support is not advertised for these devices, 4addr AP operations are -also blocked. - -Fix this by allowing 4addr operation on devices which do not support -AP/VLAN iftype but can support 4addr AP operation (decision is based on -the wiphy flag WIPHY_FLAG_4ADDR_AP). - -Cc: stable@vger.kernel.org -Fixes: db3bdcb9c3ff ("mac80211: allow AP_VLAN operation on crypto controlled devices") -Signed-off-by: Manikanta Pubbisetty <mpubbise@codeaurora.org> -Signed-off-by: Johannes Berg <johannes.berg@intel.com> ---- - include/net/cfg80211.h | 3 ++- - net/mac80211/util.c | 4 +++- - net/wireless/core.c | 6 +++++- - net/wireless/nl80211.c | 8 ++++++-- - 4 files changed, 16 insertions(+), 5 deletions(-) - ---- a/include/net/cfg80211.h -+++ b/include/net/cfg80211.h -@@ -3457,7 +3457,8 @@ struct cfg80211_ops { - * on wiphy_new(), but can be changed by the driver if it has a good - * reason to override the default - * @WIPHY_FLAG_4ADDR_AP: supports 4addr mode even on AP (with a single station -- * on a VLAN interface) -+ * on a VLAN interface). This flag also serves an extra purpose of -+ * supporting 4ADDR AP mode on devices which do not support AP/VLAN iftype. - * @WIPHY_FLAG_4ADDR_STATION: supports 4addr mode even as a station - * @WIPHY_FLAG_CONTROL_PORT_PROTOCOL: This device supports setting the - * control port protocol ethertype. The device also honours the ---- a/net/mac80211/util.c -+++ b/net/mac80211/util.c -@@ -3626,7 +3626,9 @@ int ieee80211_check_combinations(struct - } - - /* Always allow software iftypes */ -- if (local->hw.wiphy->software_iftypes & BIT(iftype)) { -+ if (local->hw.wiphy->software_iftypes & BIT(iftype) || -+ (iftype == NL80211_IFTYPE_AP_VLAN && -+ local->hw.wiphy->flags & WIPHY_FLAG_4ADDR_AP)) { - if (radar_detect) - return -EINVAL; - return 0; ---- a/net/wireless/core.c -+++ b/net/wireless/core.c -@@ -1351,8 +1351,12 @@ static int cfg80211_netdev_notifier_call - } - break; - case NETDEV_PRE_UP: -- if (!(wdev->wiphy->interface_modes & BIT(wdev->iftype))) -+ if (!(wdev->wiphy->interface_modes & BIT(wdev->iftype)) && -+ !(wdev->iftype == NL80211_IFTYPE_AP_VLAN && -+ rdev->wiphy.flags & WIPHY_FLAG_4ADDR_AP && -+ wdev->use_4addr)) - return notifier_from_errno(-EOPNOTSUPP); -+ - if (rfkill_blocked(rdev->rfkill)) - return notifier_from_errno(-ERFKILL); - break; ---- a/net/wireless/nl80211.c -+++ b/net/wireless/nl80211.c -@@ -3194,8 +3194,7 @@ static int nl80211_new_interface(struct - return -EINVAL; - } - -- if (!rdev->ops->add_virtual_intf || -- !(rdev->wiphy.interface_modes & (1 << type))) -+ if (!rdev->ops->add_virtual_intf) - return -EOPNOTSUPP; - - if ((type == NL80211_IFTYPE_P2P_DEVICE || type == NL80211_IFTYPE_NAN || -@@ -3214,6 +3213,11 @@ static int nl80211_new_interface(struct - return err; - } - -+ if (!(rdev->wiphy.interface_modes & (1 << type)) && -+ !(type == NL80211_IFTYPE_AP_VLAN && params.use_4addr && -+ rdev->wiphy.flags & WIPHY_FLAG_4ADDR_AP)) -+ return -EOPNOTSUPP; -+ - err = nl80211_parse_mon_options(rdev, type, info, ¶ms); - if (err < 0) - return err; diff --git a/package/kernel/mac80211/patches/subsys/522-mac80211_configure_antenna_gain.patch b/package/kernel/mac80211/patches/subsys/522-mac80211_configure_antenna_gain.patch index 4dcd7b5fcc..7960039fd7 100644 --- a/package/kernel/mac80211/patches/subsys/522-mac80211_configure_antenna_gain.patch +++ b/package/kernel/mac80211/patches/subsys/522-mac80211_configure_antenna_gain.patch @@ -1,6 +1,6 @@ --- a/include/net/cfg80211.h +++ b/include/net/cfg80211.h -@@ -2968,6 +2968,7 @@ struct cfg80211_external_auth_params { +@@ -3322,6 +3322,7 @@ struct cfg80211_update_owe_info { * (as advertised by the nl80211 feature flag.) * @get_tx_power: store the current TX power into the dbm variable; * return 0 if successful @@ -8,7 +8,7 @@ * * @set_wds_peer: set the WDS peer for a WDS interface * -@@ -3268,6 +3269,7 @@ struct cfg80211_ops { +@@ -3634,6 +3635,7 @@ struct cfg80211_ops { enum nl80211_tx_power_setting type, int mbm); int (*get_tx_power)(struct wiphy *wiphy, struct wireless_dev *wdev, int *dbm); @@ -18,7 +18,7 @@ const u8 *addr); --- a/include/net/mac80211.h +++ b/include/net/mac80211.h -@@ -1395,6 +1395,7 @@ enum ieee80211_smps_mode { +@@ -1471,6 +1471,7 @@ enum ieee80211_smps_mode { * * @power_level: requested transmit power (in dBm), backward compatibility * value only that is set to the minimum of all interfaces @@ -26,7 +26,7 @@ * * @chandef: the channel definition to tune to * @radar_enabled: whether radar detection is enabled -@@ -1415,6 +1416,7 @@ enum ieee80211_smps_mode { +@@ -1491,6 +1492,7 @@ enum ieee80211_smps_mode { struct ieee80211_conf { u32 flags; int power_level, dynamic_ps_timeout; @@ -36,9 +36,9 @@ u8 ps_dtim_period; --- a/include/uapi/linux/nl80211.h +++ b/include/uapi/linux/nl80211.h -@@ -2244,6 +2244,9 @@ enum nl80211_commands { - * @NL80211_ATTR_AIRTIME_WEIGHT: Station's weight when scheduled by the airtime - * scheduler. +@@ -2341,6 +2341,9 @@ enum nl80211_commands { + * should be picking up the lowest tx power, either tx power per-interface + * or per-station. * + * @NL80211_ATTR_WIPHY_ANTENNA_GAIN: Configured antenna gain. Used to reduce + * transmit power to stay within regulatory limits. u32, dBi. @@ -46,9 +46,9 @@ * @NUM_NL80211_ATTR: total number of nl80211_attrs available * @NL80211_ATTR_MAX: highest attribute number currently defined * @__NL80211_ATTR_AFTER_LAST: internal use -@@ -2693,6 +2696,8 @@ enum nl80211_attrs { - - NL80211_ATTR_AIRTIME_WEIGHT, +@@ -2794,6 +2797,8 @@ enum nl80211_attrs { + NL80211_ATTR_STA_TX_POWER_SETTING, + NL80211_ATTR_STA_TX_POWER, + NL80211_ATTR_WIPHY_ANTENNA_GAIN, + @@ -57,7 +57,7 @@ __NL80211_ATTR_AFTER_LAST, --- a/net/mac80211/cfg.c +++ b/net/mac80211/cfg.c -@@ -2505,6 +2505,19 @@ static int ieee80211_get_tx_power(struct +@@ -2577,6 +2577,19 @@ static int ieee80211_get_tx_power(struct return 0; } @@ -77,7 +77,7 @@ static int ieee80211_set_wds_peer(struct wiphy *wiphy, struct net_device *dev, const u8 *addr) { -@@ -3872,6 +3885,7 @@ const struct cfg80211_ops mac80211_confi +@@ -3990,6 +4003,7 @@ const struct cfg80211_ops mac80211_confi .set_wiphy_params = ieee80211_set_wiphy_params, .set_tx_power = ieee80211_set_tx_power, .get_tx_power = ieee80211_get_tx_power, @@ -87,7 +87,7 @@ CFG80211_TESTMODE_CMD(ieee80211_testmode_cmd) --- a/net/mac80211/ieee80211_i.h +++ b/net/mac80211/ieee80211_i.h -@@ -1365,6 +1365,7 @@ struct ieee80211_local { +@@ -1373,6 +1373,7 @@ struct ieee80211_local { int dynamic_ps_forced_timeout; int user_power_level; /* in dBm, for all interfaces */ @@ -97,7 +97,7 @@ --- a/net/mac80211/main.c +++ b/net/mac80211/main.c -@@ -94,7 +94,7 @@ static u32 ieee80211_hw_conf_chan(struct +@@ -92,7 +92,7 @@ static u32 ieee80211_hw_conf_chan(struct struct ieee80211_sub_if_data *sdata; struct cfg80211_chan_def chandef = {}; u32 changed = 0; @@ -106,7 +106,7 @@ u32 offchannel_flag; offchannel_flag = local->hw.conf.flags & IEEE80211_CONF_OFFCHANNEL; -@@ -151,6 +151,12 @@ static u32 ieee80211_hw_conf_chan(struct +@@ -149,6 +149,12 @@ static u32 ieee80211_hw_conf_chan(struct } rcu_read_unlock(); @@ -119,7 +119,7 @@ if (local->hw.conf.power_level != power) { changed |= IEEE80211_CONF_CHANGE_POWER; local->hw.conf.power_level = power; -@@ -626,6 +632,7 @@ struct ieee80211_hw *ieee80211_alloc_hw_ +@@ -638,6 +644,7 @@ struct ieee80211_hw *ieee80211_alloc_hw_ IEEE80211_RADIOTAP_MCS_HAVE_BW; local->hw.radiotap_vht_details = IEEE80211_RADIOTAP_VHT_KNOWN_GI | IEEE80211_RADIOTAP_VHT_KNOWN_BANDWIDTH; @@ -129,15 +129,15 @@ local->user_power_level = IEEE80211_UNSET_POWER_LEVEL; --- a/net/wireless/nl80211.c +++ b/net/wireless/nl80211.c -@@ -431,6 +431,7 @@ static const struct nla_policy nl80211_p - [NL80211_ATTR_HE_CAPABILITY] = { .type = NLA_BINARY, - .len = NL80211_HE_MAX_CAPABILITY_LEN }, +@@ -571,6 +571,7 @@ const struct nla_policy nl80211_policy[N + [NL80211_ATTR_PEER_MEASUREMENTS] = + NLA_POLICY_NESTED(nl80211_pmsr_attr_policy), [NL80211_ATTR_AIRTIME_WEIGHT] = NLA_POLICY_MIN(NLA_U16, 1), + [NL80211_ATTR_WIPHY_ANTENNA_GAIN] = { .type = NLA_U32 }, }; /* policy for the key attributes */ -@@ -2588,6 +2589,20 @@ static int nl80211_set_wiphy(struct sk_b +@@ -2866,6 +2867,20 @@ static int nl80211_set_wiphy(struct sk_b if (result) return result; } |