]> git.ipfire.org Git - thirdparty/openwrt.git/commitdiff
ath11k: fix transmit queue flushing through flush_sta implementation 20293/head
authorFlorian Maurer <f.maurer@outlook.de>
Fri, 3 Oct 2025 07:30:59 +0000 (09:30 +0200)
committerChristian Marangi <ansuelsmth@gmail.com>
Tue, 4 Nov 2025 19:12:06 +0000 (20:12 +0100)
warning print "ath11k c000000.wifi: failed to flush transmit queue 0"
is observed during busy times.

The mac80211 fallback implementation of `flush_sta` does not handle the per STA queues well.
This is fixed by providing a ath11k specific implementation of flush_sta telling the firmware to flush a given station.
The draining of the transmit queues should therefore stop correctly, even if new packets arrive in the mean time.

An upstream ath11k RFC is available at:
https://patchwork.kernel.org/project/linux-wireless/patch/GV1P250MB14333A5BF24623C4753A10E1E8E0A@GV1P250MB1433.EURP250.PROD.OUTLOOK.COM/

The patch was tested on a Xiaomi AX3600.

Signed-off-by: Florian Maurer <f.maurer@outlook.de>
Tested-by: Florian Maurer <f.maurer@outlook.de>
Co-authored-by: Benjamin Berg <benjamin@sipsolutions.net>
Tested-by: Flole <flole@flole.de>
Link: https://github.com/openwrt/openwrt/pull/20293
Signed-off-by: Christian Marangi <ansuelsmth@gmail.com>
package/kernel/mac80211/patches/ath11k/453-ath11k-add-ath11k_mac_op_flush_sta-to-properly-flush.patch [new file with mode: 0644]
package/kernel/mac80211/patches/ath11k/941-ath11k-fix_sleeping-in-atomic_in_ath11k_mac_op_set_bitrate_mask.patch
package/kernel/mac80211/patches/ath11k/945-ath11k-fix_group_data_packet_drops_during_rekey.patch

diff --git a/package/kernel/mac80211/patches/ath11k/453-ath11k-add-ath11k_mac_op_flush_sta-to-properly-flush.patch b/package/kernel/mac80211/patches/ath11k/453-ath11k-add-ath11k_mac_op_flush_sta-to-properly-flush.patch
new file mode 100644 (file)
index 0000000..baba7ef
--- /dev/null
@@ -0,0 +1,65 @@
+From b5ade0e0e1c1622a85fbfd2c93b41caff479f305 Mon Sep 17 00:00:00 2001
+From: Florian Maurer <f.maurer@outlook.de>
+Date: Fri, 3 Oct 2025 12:56:13 +0200
+Subject: [PATCH] ath11k: add ath11k_mac_op_flush_sta to properly flush pending
+ packets
+
+When a STA is marked as no longer authorized, if the driver doesn't
+implement flush_sta(), mac80211 calls ieee80211_flush_queues() to
+flush hardware queues to avoid sending unencrypted frames.
+
+This has became a problem for ath11k because ieee80211_flush_queues()
+will stop all traffic and call ath11k_flush, which waits until the
+whole HW queue is empty. In a busy environment this will trigger a
+timeout warning and stalls other STAs.
+
+Fix this by implementing flush_sta method using WMI command to flush
+frames of a specific STA.
+Flushed frames will be marked as discard in tx complete indication.
+
+warning print "ath11k c000000.wifi: failed to flush transmit queue 0"
+was observed on various openwrt devices, and is fixed through this patch.
+
+Tested-by: Florian Maurer  <f.maurer@outlook.de>
+Tested-by: Flole <flole@flole.de>
+Co-developed-by: Benjamin Berg <benjamin@sipsolutions.net>
+Signed-off-by: Benjamin Berg <benjamin@sipsolutions.net>
+Signed-off-by: Florian Maurer <f.maurer@outlook.de>
+---
+ drivers/net/wireless/ath/ath11k/mac.c | 18 ++++++++++++++++++
+ 1 file changed, 18 insertions(+)
+
+--- a/drivers/net/wireless/ath/ath11k/mac.c
++++ b/drivers/net/wireless/ath/ath11k/mac.c
+@@ -8248,6 +8248,23 @@ static void ath11k_mac_op_flush(struct i
+       ath11k_mac_flush_tx_complete(ar);
+ }
++static void ath11k_mac_op_flush_sta(struct ieee80211_hw *hw,
++                                  struct ieee80211_vif *vif,
++                                  struct ieee80211_sta *sta)
++{
++      struct ath11k_vif *arvif = (void *)vif->drv_priv;
++      struct ath11k *ar = hw->priv;
++      struct peer_flush_params params = {
++              .peer_tid_bitmap = 0xFF,
++              .vdev_id = arvif->vdev_id,
++      };
++      int ret;
++
++      ret = ath11k_wmi_send_peer_flush_tids_cmd(ar, sta->addr, &params);
++      if (ret)
++              ath11k_warn(ar->ab, "failed to flush sta %pM: %d\n", sta->addr, ret);
++}
++
+ static bool
+ ath11k_mac_has_single_legacy_rate(struct ath11k *ar,
+                                 enum nl80211_band band,
+@@ -9823,6 +9840,7 @@ static const struct ieee80211_ops ath11k
+       .set_bitrate_mask               = ath11k_mac_op_set_bitrate_mask,
+       .get_survey                     = ath11k_mac_op_get_survey,
+       .flush                          = ath11k_mac_op_flush,
++      .flush_sta                      = ath11k_mac_op_flush_sta,
+       .sta_statistics                 = ath11k_mac_op_sta_statistics,
+       CFG80211_TESTMODE_CMD(ath11k_tm_cmd)
index 834021610609cdbfdacda38ec629f7856fa4bc61..2fa7123b6ded38eef7f636f6013691aa92a96cdc 100644 (file)
@@ -39,7 +39,7 @@ Signed-off-by: Sasha Levin <sashal@kernel.org>
 
 --- a/drivers/net/wireless/ath/ath11k/mac.c
 +++ b/drivers/net/wireless/ath/ath11k/mac.c
-@@ -8740,9 +8740,9 @@ ath11k_mac_op_set_bitrate_mask(struct ie
+@@ -8757,9 +8757,9 @@ ath11k_mac_op_set_bitrate_mask(struct ie
                                    arvif->vdev_id, ret);
                        return ret;
                }
@@ -52,7 +52,7 @@ Signed-off-by: Sasha Levin <sashal@kernel.org>
        } else if (ath11k_mac_bitrate_mask_get_single_nss(ar, arvif, band, mask,
                                                          &single_nss)) {
                rate = WMI_FIXED_RATE_NONE;
-@@ -8809,9 +8809,9 @@ ath11k_mac_op_set_bitrate_mask(struct ie
+@@ -8826,9 +8826,9 @@ ath11k_mac_op_set_bitrate_mask(struct ie
                }
  
                mutex_lock(&ar->conf_mutex);
index b7b66ef5da7320f0bfbb9f399778128009a51dd1..8e7e8b9b00fa85316cef8516940dc7b35c69d288 100644 (file)
@@ -213,7 +213,7 @@ Signed-off-by: Sasha Levin <sashal@kernel.org>
  }
  
  static u32 ath11k_mac_ieee80211_sta_bw_to_wmi(struct ath11k *ar,
-@@ -9536,6 +9614,21 @@ static int ath11k_mac_station_add(struct
+@@ -9553,6 +9631,21 @@ static int ath11k_mac_station_add(struct
                goto exit;
        }