summaryrefslogtreecommitdiffstats
path: root/net/mac80211/ht.c
diff options
context:
space:
mode:
authorAlexander Wetzel <alexander@wetzel-home.de>2023-01-06 23:31:41 +0100
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2023-02-01 08:34:36 +0100
commit63cccc92768dabe2a1aa09e858d69a16ce9814f9 (patch)
tree19d65484c99e7ef2e0f8a993cd11e66adfd8fc8e /net/mac80211/ht.c
parent7b8fe53d2a1da48db02ae961b29b8ee2f5515861 (diff)
downloadlinux-stable-63cccc92768dabe2a1aa09e858d69a16ce9814f9.tar.gz
linux-stable-63cccc92768dabe2a1aa09e858d69a16ce9814f9.tar.bz2
linux-stable-63cccc92768dabe2a1aa09e858d69a16ce9814f9.zip
wifi: mac80211: Fix iTXQ AMPDU fragmentation handling
commit 592234e941f1addaa598601c9227e3b72d608625 upstream. mac80211 must not enable aggregation wile transmitting a fragmented MPDU. Enforce that for mac80211 internal TX queues (iTXQs). Reported-by: kernel test robot <oliver.sang@intel.com> Link: https://lore.kernel.org/oe-lkp/202301021738.7cd3e6ae-oliver.sang@intel.com Signed-off-by: Alexander Wetzel <alexander@wetzel-home.de> Link: https://lore.kernel.org/r/20230106223141.98696-1-alexander@wetzel-home.de Cc: stable@vger.kernel.org Signed-off-by: Johannes Berg <johannes.berg@intel.com> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'net/mac80211/ht.c')
-rw-r--r--net/mac80211/ht.c37
1 files changed, 37 insertions, 0 deletions
diff --git a/net/mac80211/ht.c b/net/mac80211/ht.c
index 83bc41346ae7..ae42e956eff5 100644
--- a/net/mac80211/ht.c
+++ b/net/mac80211/ht.c
@@ -391,6 +391,43 @@ void ieee80211_ba_session_work(struct work_struct *work)
tid_tx = sta->ampdu_mlme.tid_start_tx[tid];
if (!blocked && tid_tx) {
+ struct ieee80211_sub_if_data *sdata = sta->sdata;
+ struct ieee80211_local *local = sdata->local;
+
+ if (local->ops->wake_tx_queue) {
+ struct txq_info *txqi =
+ to_txq_info(sta->sta.txq[tid]);
+ struct fq *fq = &local->fq;
+
+ spin_lock_bh(&fq->lock);
+
+ /* Allow only frags to be dequeued */
+ set_bit(IEEE80211_TXQ_STOP, &txqi->flags);
+
+ if (!skb_queue_empty(&txqi->frags)) {
+ /* Fragmented Tx is ongoing, wait for it
+ * to finish. Reschedule worker to retry
+ * later.
+ */
+
+ spin_unlock_bh(&fq->lock);
+ spin_unlock_bh(&sta->lock);
+
+ /* Give the task working on the txq a
+ * chance to send out the queued frags
+ */
+ synchronize_net();
+
+ mutex_unlock(&sta->ampdu_mlme.mtx);
+
+ ieee80211_queue_work(&sdata->local->hw,
+ work);
+ return;
+ }
+
+ spin_unlock_bh(&fq->lock);
+ }
+
/*
* Assign it over to the normal tid_tx array
* where it "goes live".