[PATCH v2 2/2] wifi: ath9k_htc: count WMI commands and timeouts in debugfs
From: Nerijus Bendžiūnas <hidden>
Date: 2026-09-04 19:03:43
Also in:
lkml
Subsystem:
atheros ath generic utilities, qualcomm atheros ath9k wireless driver, the rest · Maintainers:
Jeff Johnson, Toke Høiland-Jørgensen, Linus Torvalds
A WMI command that times out is only visible with CONFIG_ATH_DEBUG and the WMI debug bit set. A register read that returns -1 gives no indication whether the register holds all ones or the command never completed. Count the commands issued and the commands that timed out in struct wmi and expose both in a new "wmi" debugfs file, so timeouts can be seen on a kernel built without debug output. Assisted-by: Claude:claude-fable-5-1 Signed-off-by: Nerijus Bendžiūnas <redacted> --- .../net/wireless/ath/ath9k/htc_drv_debug.c | 25 +++++++++++++++++++ drivers/net/wireless/ath/ath9k/wmi.c | 2 ++ drivers/net/wireless/ath/ath9k/wmi.h | 2 ++ 3 files changed, 29 insertions(+)
diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_debug.c b/drivers/net/wireless/ath/ath9k/htc_drv_debug.c
index 9437d69877cc..fab613199ca2 100644
--- a/drivers/net/wireless/ath/ath9k/htc_drv_debug.c
+++ b/drivers/net/wireless/ath/ath9k/htc_drv_debug.c@@ -310,6 +310,29 @@ static const struct file_operations fops_slot = { .llseek = default_llseek, }; +static ssize_t read_file_wmi(struct file *file, char __user *user_buf, + size_t count, loff_t *ppos) +{ + struct ath9k_htc_priv *priv = file->private_data; + char buf[128]; + unsigned int len; + + len = scnprintf(buf, sizeof(buf), + "%20s : %10u\n" + "%20s : %10u\n", + "Issued", priv->wmi->cmds_issued, + "Timeouts", priv->wmi->cmds_timed_out); + + return simple_read_from_buffer(user_buf, count, ppos, buf, len); +} + +static const struct file_operations fops_wmi = { + .read = read_file_wmi, + .open = simple_open, + .owner = THIS_MODULE, + .llseek = default_llseek, +}; + static ssize_t read_file_queue(struct file *file, char __user *user_buf, size_t count, loff_t *ppos) {
@@ -505,6 +528,8 @@ int ath9k_htc_init_debug(struct ath_hw *ah) debugfs_create_file("slot", 0400, priv->debug.debugfs_phy, priv, &fops_slot); + debugfs_create_file("wmi", 0400, priv->debug.debugfs_phy, + priv, &fops_wmi); debugfs_create_file("queue", 0400, priv->debug.debugfs_phy, priv, &fops_queue); debugfs_create_file("debug", 0600, priv->debug.debugfs_phy,
diff --git a/drivers/net/wireless/ath/ath9k/wmi.c b/drivers/net/wireless/ath/ath9k/wmi.c
index 284e8c13b043..552ae9f8bdaf 100644
--- a/drivers/net/wireless/ath/ath9k/wmi.c
+++ b/drivers/net/wireless/ath/ath9k/wmi.c@@ -345,8 +345,10 @@ int ath9k_wmi_cmd(struct wmi *wmi, enum wmi_cmd_id cmd_id, if (ret) goto out; + wmi->cmds_issued++; time_left = wait_for_completion_timeout(&wmi->cmd_wait, timeout); if (!time_left) { + wmi->cmds_timed_out++; ath_dbg(common, WMI, "Timeout waiting for WMI command: %s\n", wmi_cmd_to_name(cmd_id)); spin_lock_irqsave(&wmi->wmi_lock, flags);
diff --git a/drivers/net/wireless/ath/ath9k/wmi.h b/drivers/net/wireless/ath/ath9k/wmi.h
index 5c3b710b8f31..ee72b0fba31b 100644
--- a/drivers/net/wireless/ath/ath9k/wmi.h
+++ b/drivers/net/wireless/ath/ath9k/wmi.h@@ -158,6 +158,8 @@ struct wmi { u8 *cmd_rsp_buf; u32 cmd_rsp_len; bool stopped; + u32 cmds_issued; + u32 cmds_timed_out; struct list_head pending_tx_events; spinlock_t event_lock;
--
2.55.0