fd0f5a8b71
Replace the single squashed 0001-bes2600-besser-cumulative-series.patch with 20 individual per-commit patches matching the bes2600/besser-danctnix-v3 branch in marfrit/bes2600-dkms. Also remove the duplicate 0003-arm64 entry that was a bug in pkgrel=3. Patch list: 0001 c5.1 defer scan and soften WARN on firmware reject 0002 c5.1.1 widen scan-defer backoff to 30s and decay reject_count 0003 c5.2 recover wedged firmware via mmc_hw_reset on link break 0004 c6.1 gate PM indication completion on pending request 0005 c6.2 short-circuit wake handshake when chip confirmed ACTIVE 0006 c7 self-detect when firmware does not honor PSM and skip 0007 c5.2.1 handle multi-function SDIO cards in mmc_hw_reset 0008 Patch A pre-empt AP-deauth-6 with reassoc on decrypt-fail storm 0009 Patch B bus_reset on connection-loss storm 0010 Patch F3 atomicize atomic_add() calls 0011 Patch F2 fix missing destroy_workqueue() on error in init_common 0012 Patch F1 fix concurrency UAF in bes2600_hw_scan / sched_scan 0013 Patch C v3 drop sdio_rx_work relay, IRQ→bh-direct 0014 Patch G restore SPDX identifiers + ST-Ericsson attribution 0015 Patch D atomicize ba_lock counters, drop the spinlock 0016 Patch E skip ps_state_lock when PSM-known-disabled 0017 Patch C2 replace ieee80211_rx_irqsafe with ieee80211_rx_ni 0018 Patch H bh.c hygiene cleanup (drop fossil blocks, dead stubs) 0019 besser#18 pending_record_lock SOFTIRQ-safe fix 0020 danctnix-flavor: export bus_reset helpers for bes2600_btuart Build pending (pkgrel=4 makepkg in progress on boltzmann). Signed-off-by: Claude (noether) <claude@reauktion.de>
158 lines
6.6 KiB
Diff
158 lines
6.6 KiB
Diff
From 447240cbe8dee9d865683508f7d814e7ffe1d970 Mon Sep 17 00:00:00 2001
|
|
From: Markus Fritsche <fritsche.markus@gmail.com>
|
|
Date: Fri, 8 May 2026 06:40:00 +0200
|
|
Subject: [PATCH 17/20] =?UTF-8?q?bes2600:=20Patch=20C2=20=E2=80=94=20repla?=
|
|
=?UTF-8?q?ce=20ieee80211=5Frx=5Firqsafe=20with=20ieee80211=5Frx=5Fni?=
|
|
MIME-Version: 1.0
|
|
Content-Type: text/plain; charset=UTF-8
|
|
Content-Transfer-Encoding: 8bit
|
|
|
|
Per Phase 4 plan PR #14 + kerneldoc audit (Task #19). Six call sites
|
|
deferred per-RX-frame mac80211 dispatch via tasklet; replace with the
|
|
synchronous-from-process-context API ieee80211_rx_ni() which does its
|
|
own local_bh_disable wrap.
|
|
|
|
Why _ni and not _list:
|
|
|
|
Phase 4 plan originally targeted ieee80211_rx_list for batch
|
|
delivery. Mining mt76 mainline (the only driver using _list)
|
|
showed the canonical pattern requires threading a struct list_head
|
|
through the per-frame call chain. bes2600s WSM dispatcher
|
|
(wsm_handle_rx -> bes2600_rx_cb / wsm.c beacon path) sits between
|
|
the bh threads SDIO read and the mac80211 hand-off; threading a
|
|
list_head through the dispatcher is a non-trivial refactor.
|
|
ieee80211_rx_ni() is the simpler drop-in: no list management, still
|
|
removes the tasklet hop. Per-call local_bh_disable cost is trivial
|
|
vs the saved tasklet schedule. Future refactor can revisit _list
|
|
if measurements warrant.
|
|
|
|
Sites converted:
|
|
|
|
- ap.c:96 (bes2600_sta_add link-id rx_queue drain on AP-mode
|
|
STA add). Was inside spin_lock_bh(&ps_state_lock);
|
|
refactored to splice the queue under the lock then
|
|
deliver after unlock — _ni runs the synchronous
|
|
mac80211 RX path inline, would otherwise hold the
|
|
lock across mac80211 dispatch. splice via
|
|
skb_queue_splice_init into a local sk_buff_head.
|
|
- sta.c:1487 (deauth-frame inject in inactivity-event handler).
|
|
Not under any lock; direct conversion.
|
|
- txrx.c:1960 (early-data + pm_unsupported branch from Patch E).
|
|
- txrx.c:1967 (early-data + LINK_SOFT-not-set branch).
|
|
- txrx.c:1971 (normal RX path in bes2600_rx_cb).
|
|
- wsm.c:2415 (beacon delivery in scan-complete WSM handler).
|
|
beacon SKB ownership is preserved by the existing
|
|
skb_copy(beacon, GFP_ATOMIC) -> beacon_bkp pattern;
|
|
no lifecycle change needed.
|
|
|
|
Mixing constraint (kerneldoc include/net/mac80211.h:5399-5430):
|
|
ieee80211_rx_ni() cannot mix with ieee80211_rx_irqsafe() for a
|
|
single hardware. All 6 sites convert atomically; no mixed state.
|
|
|
|
Build verified clean on ohm sandbox: srcversion 619A51E61BF5479AAC146E6.
|
|
|
|
Predicted Phase 7 delta: +5-15% over v3+D+E baseline (2.35 MB/s mean
|
|
on v3 alone; D+E single-rep was 3.22 MB/s). Modest improvement
|
|
expected from removing the tasklet schedule per RX frame. Smaller
|
|
deltas would still be a net win for upstream-cleanliness — the
|
|
kernel.org submission story benefits from not using _irqsafe from
|
|
process context.
|
|
---
|
|
bes2600/ap.c | 15 +++++++++++++--
|
|
bes2600/sta.c | 2 +-
|
|
bes2600/txrx.c | 6 +++---
|
|
bes2600/wsm.c | 2 +-
|
|
4 files changed, 18 insertions(+), 7 deletions(-)
|
|
|
|
diff --git a/drivers/staging/bes2600/ap.c b/drivers/staging/bes2600/ap.c
|
|
index 8a17545..99e2da2 100644
|
|
--- a/drivers/staging/bes2600/ap.c
|
|
+++ b/drivers/staging/bes2600/ap.c
|
|
@@ -63,8 +63,11 @@ int bes2600_sta_add(struct ieee80211_hw *hw, struct ieee80211_vif *vif,
|
|
struct bes2600_vif *priv = cw12xx_get_vif_from_ieee80211(vif);
|
|
struct bes2600_link_entry *entry;
|
|
struct sk_buff *skb;
|
|
+ struct sk_buff_head local_drain;
|
|
struct bes2600_common *hw_priv = hw->priv;
|
|
|
|
+ __skb_queue_head_init(&local_drain);
|
|
+
|
|
#ifdef P2P_MULTIVIF
|
|
WARN_ON(priv->if_id == CW12XX_GENERIC_IF_ID);
|
|
#endif
|
|
@@ -93,9 +96,17 @@ int bes2600_sta_add(struct ieee80211_hw *hw, struct ieee80211_vif *vif,
|
|
IEEE80211_WMM_IE_STA_QOSINFO_AC_MASK)
|
|
priv->sta_asleep_mask |= BIT(sta_priv->link_id);
|
|
entry->status = BES2600_LINK_HARD;
|
|
- while ((skb = skb_dequeue(&entry->rx_queue)))
|
|
- ieee80211_rx_irqsafe(priv->hw, skb);
|
|
+ /*
|
|
+ * Patch C2: splice the rx_queue out under the lock then deliver
|
|
+ * after unlock. ieee80211_rx_ni() runs the mac80211 RX path
|
|
+ * synchronously (formerly ieee80211_rx_irqsafe deferred to a
|
|
+ * tasklet); calling it from inside spin_lock_bh would hold the
|
|
+ * lock across mac80211's full RX dispatch.
|
|
+ */
|
|
+ skb_queue_splice_init(&entry->rx_queue, &local_drain);
|
|
spin_unlock_bh(&priv->ps_state_lock);
|
|
+ while ((skb = __skb_dequeue(&local_drain)))
|
|
+ ieee80211_rx_ni(priv->hw, skb);
|
|
#ifdef AP_AGGREGATE_FW_FIX
|
|
hw_priv->connected_sta_cnt++;
|
|
if(hw_priv->connected_sta_cnt>1) {
|
|
diff --git a/drivers/staging/bes2600/sta.c b/drivers/staging/bes2600/sta.c
|
|
index 412b2c4..476d875 100644
|
|
--- a/drivers/staging/bes2600/sta.c
|
|
+++ b/drivers/staging/bes2600/sta.c
|
|
@@ -1500,7 +1500,7 @@ void bes2600_event_handler(struct work_struct *work)
|
|
IEEE80211_STYPE_DEAUTH | IEEE80211_FCTL_TODS);
|
|
deauth->u.deauth.reason_code = WLAN_REASON_DEAUTH_LEAVING;
|
|
deauth->seq_ctrl = 0;
|
|
- ieee80211_rx_irqsafe(priv->hw, skb);
|
|
+ ieee80211_rx_ni(priv->hw, skb);
|
|
bes_devel(" Inactivity Deauth Frame sent for MAC SA %pM \t and DA %pM\n", deauth->sa, deauth->da);
|
|
queue_work(priv->hw_priv->workqueue, &priv->set_tim_work);
|
|
break;
|
|
diff --git a/drivers/staging/bes2600/txrx.c b/drivers/staging/bes2600/txrx.c
|
|
index cb718ad..9074972 100644
|
|
--- a/drivers/staging/bes2600/txrx.c
|
|
+++ b/drivers/staging/bes2600/txrx.c
|
|
@@ -1980,18 +1980,18 @@ void bes2600_rx_cb(struct bes2600_vif *priv,
|
|
* path is taken.
|
|
*/
|
|
if (hw_priv->bes_power.pm_unsupported) {
|
|
- ieee80211_rx_irqsafe(priv->hw, skb);
|
|
+ ieee80211_rx_ni(priv->hw, skb);
|
|
} else {
|
|
spin_lock_bh(&priv->ps_state_lock);
|
|
/* Double-check status with lock held */
|
|
if (entry->status == BES2600_LINK_SOFT)
|
|
skb_queue_tail(&entry->rx_queue, skb);
|
|
else
|
|
- ieee80211_rx_irqsafe(priv->hw, skb);
|
|
+ ieee80211_rx_ni(priv->hw, skb);
|
|
spin_unlock_bh(&priv->ps_state_lock);
|
|
}
|
|
} else {
|
|
- ieee80211_rx_irqsafe(priv->hw, skb);
|
|
+ ieee80211_rx_ni(priv->hw, skb);
|
|
}
|
|
*skb_p = NULL;
|
|
|
|
diff --git a/drivers/staging/bes2600/wsm.c b/drivers/staging/bes2600/wsm.c
|
|
index 908c965..2424181 100644
|
|
--- a/drivers/staging/bes2600/wsm.c
|
|
+++ b/drivers/staging/bes2600/wsm.c
|
|
@@ -2412,7 +2412,7 @@ int wsm_handle_rx(struct bes2600_common *hw_priv, int id,
|
|
if (!hw_priv->beacon_bkp)
|
|
hw_priv->beacon_bkp = \
|
|
skb_copy(hw_priv->beacon, GFP_ATOMIC);
|
|
- ieee80211_rx_irqsafe(hw_priv->hw, hw_priv->beacon);
|
|
+ ieee80211_rx_ni(hw_priv->hw, hw_priv->beacon);
|
|
hw_priv->beacon = hw_priv->beacon_bkp;
|
|
|
|
hw_priv->beacon_bkp = NULL;
|
|
--
|
|
2.54.0
|
|
|