From: Julius Bairaktaris <julius@bairaktaris.de>
To: Jeff Johnson <jjohnson@kernel.org>
Cc: linux-wireless@vger.kernel.org, ath11k@lists.infradead.org,
"Toke Høiland-Jørgensen" <toke@toke.dk>
Subject: [PATCH v1 4/4] wifi: ath11k: report tx airtime and enable airtime fairness
Date: Sun, 23 Aug 2026 21:57:03 +0200 [thread overview]
Message-ID: <20260823195703.49198-5-julius@bairaktaris.de> (raw)
In-Reply-To: <20260823195703.49198-1-julius@bairaktaris.de>
mac80211's airtime scheduler charges sta->airtime[ac].deficit from one
place, ieee80211_sta_register_airtime(). Unlike AQL there is no estimator
fallback, and ath11k never calls it, so the ATF feature bit cannot be
advertised on its own: the deficit would only ever be
replenished, every station would stay permanently in credit, and the DRR
would be inert. The bit is not a no-op in that state either, because it
also moves txq insertion to the head of the active list, which
__ieee80211_schedule_txq() documents as safe only because the DRR moves a
station back once its deficit goes negative.
fes_duration_us arrives with every PPDU's stats and is already
accumulated into arsta->tx_duration a few lines above. Register it, and
set the feature bit in the same change so the two cannot be separated.
Measured on an IPQ8074 AP with two stations on one radio, a 1x1 VHT
client at 433 Mbit/s and a 2x2 HE client, both receiving at once. Before,
'iw station set <mac> airtime_weight' is refused with -EOPNOTSUPP and the
per-station airtime file reads zero. After, the weight is accepted and
read back, TX airtime accumulates, and the per-AC deficits move.
The fairness this delivers is coarse. Weighting the fast station 4:1 moves
the slow station's share of airtime from 59.5% to 52.1% and the fast
station's throughput from 315 to 392 Mbit/s: the direction is correct, the
magnitude is not the ratio requested. The granularity is bounded by the
driver's push model, since ieee80211_handle_wake_tx_queue() drains a
selected txq whole into the hardware and the scheduler therefore reorders
only between selections. Tightening the AQL limit to shorten those drains
does not improve it: the share moves by one point and aggregate
throughput falls from 401 to 178 Mbit/s. Finer control would require a TXQ
scheduler in the driver.
Two properties of the source are worth stating. fes_duration_us spans the
frame exchange sequence, so it includes the SIFS and the responding
BlockAck, time the radio spends receiving; the airtime registered is
therefore larger than the airtime transmitted. And it is a per-PPDU field,
so on a downlink MU PPDU each user is charged the whole sequence. No
per-user duration is reported in these stats. On the firmware tested here
every PPDU carried exactly one user, measured over 21051 PPDUs, so the MU
case is latent rather than observed.
Tested-on: IPQ8074 hw2.0 AHB WLAN.HK.2.9.0.1-02146-QCAHKSWPL_SILICONZ-1
Assisted-by: Claude:claude-opus-5
Signed-off-by: Julius Bairaktaris <julius@bairaktaris.de>
---
drivers/net/wireless/ath/ath11k/dp_rx.c | 9 +++++++++
drivers/net/wireless/ath/ath11k/mac.c | 2 ++
2 files changed, 11 insertions(+)
diff --git a/drivers/net/wireless/ath/ath11k/dp_rx.c b/drivers/net/wireless/ath/ath11k/dp_rx.c
index 33425707c084..33c6fd9553a6 100644
--- a/drivers/net/wireless/ath/ath11k/dp_rx.c
+++ b/drivers/net/wireless/ath/ath11k/dp_rx.c
@@ -1485,6 +1485,15 @@ ath11k_update_per_peer_tx_stats(struct ath11k *ar,
arsta->txrate.bw = ath11k_mac_bw_to_mac80211_bw(bw);
arsta->tx_duration += tx_duration;
+
+ /* tid is HTT_PPDU_STATS_NON_QOS_TID when no ack/BA TLV came with the
+ * PPDU; mask it so that airtime lands in a real access category rather
+ * than one chosen by the spare bits.
+ */
+ if (tx_duration)
+ ieee80211_sta_register_airtime(sta,
+ tid & IEEE80211_QOS_CTL_TID_MASK,
+ tx_duration, 0);
memcpy(&arsta->last_txrate, &arsta->txrate, sizeof(struct rate_info));
/* PPDU stats reported for mgmt packet doesn't have valid tx bytes.
diff --git a/drivers/net/wireless/ath/ath11k/mac.c b/drivers/net/wireless/ath/ath11k/mac.c
index 38f641bbc53c..40a2b6d2f804 100644
--- a/drivers/net/wireless/ath/ath11k/mac.c
+++ b/drivers/net/wireless/ath/ath11k/mac.c
@@ -10593,6 +10593,8 @@ static int __ath11k_mac_register(struct ath11k *ar)
wiphy_ext_feature_set(ar->hw->wiphy, NL80211_EXT_FEATURE_CQM_RSSI_LIST);
wiphy_ext_feature_set(ar->hw->wiphy, NL80211_EXT_FEATURE_AQL);
+ wiphy_ext_feature_set(ar->hw->wiphy,
+ NL80211_EXT_FEATURE_AIRTIME_FAIRNESS);
wiphy_ext_feature_set(ar->hw->wiphy, NL80211_EXT_FEATURE_STA_TX_PWR);
if (test_bit(WMI_TLV_SERVICE_BSS_COLOR_OFFLOAD,
ar->ab->wmi_ab.svc_map)) {
--
2.53.0
next prev parent reply other threads:[~2026-08-23 19:57 UTC|newest]
Thread overview: 7+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-08-23 19:56 [PATCH v1 0/4] wifi: ath11k: enable airtime queue limits and fairness Julius Bairaktaris
2026-08-23 19:57 ` [PATCH v1 1/4] wifi: ath11k: free tx skbs through ieee80211_free_txskb() Julius Bairaktaris
2026-08-23 19:57 ` [PATCH v1 2/4] wifi: ath11k: enable airtime queue limits Julius Bairaktaris
2026-08-24 10:46 ` Toke Høiland-Jørgensen
2026-08-23 19:57 ` [PATCH v1 3/4] wifi: ath11k: report the pending tx MSDU count in soc_dp_stats Julius Bairaktaris
2026-08-23 19:57 ` Julius Bairaktaris [this message]
2026-08-24 10:53 ` [PATCH v1 4/4] wifi: ath11k: report tx airtime and enable airtime fairness Toke Høiland-Jørgensen
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260823195703.49198-5-julius@bairaktaris.de \
--to=julius@bairaktaris.de \
--cc=ath11k@lists.infradead.org \
--cc=jjohnson@kernel.org \
--cc=linux-wireless@vger.kernel.org \
--cc=toke@toke.dk \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox