diff --git a/net/mac80211/debugfs.c b/net/mac80211/debugfs.c
index be2e486907f9..4f1d3c4fab7d 100644
--- a/net/mac80211/debugfs.c
+++ b/net/mac80211/debugfs.c
@@ -633,6 +633,69 @@ DEBUGFS_DEVSTATS_FILE(dot11RTSFailureCount);
 DEBUGFS_DEVSTATS_FILE(dot11FCSErrorCount);
 DEBUGFS_DEVSTATS_FILE(dot11RTSSuccessCount);
 
+#ifdef CONFIG_MAC80211_DEBUG_COUNTERS
+static ssize_t mgmt_frame_read(struct file *file, char __user *userbuf,
+			       size_t count, loff_t *ppos)
+{
+	struct ieee80211_local *local = file->private_data;
+	int size = 1000;
+	int i, len = 0;
+	static const char *mgmt_frame[IEEE80211_MGMT_FRM_TYPE_NUM_MAX - 1] = {
+		"ASSOC REQ", "ASSOC RESP",
+		"REASSOC REQ", "REASSOC RESP",
+		"PROBE REQ", "PROBE RESP",
+		"TIMING ADV", NULL,
+		"BEACON", "ATIM",
+		"DISASSOC", "AUTH",
+		"DEAUTH", "ACTION",
+		"ACTION NO ACK"};
+
+	char *buf __free(kfree) = kzalloc(size, GFP_KERNEL);
+	if (!buf)
+		return -ENOMEM;
+
+	len += scnprintf(buf + len, size - len, "Tx mgmt stats:\n");
+	for (i = 0; i < IEEE80211_MGMT_FRM_TYPE_NUM_MAX - 1; i++) {
+		if (!mgmt_frame[i])
+			continue;
+		len += scnprintf(buf + len, size - len, "%s\t%u\n",
+				 mgmt_frame[i], local->tx_mgmt_pkts[i]);
+	}
+
+	len += scnprintf(buf + len, size - len, "\nRx mgmt stats:\n");
+	for (i = 0; i < IEEE80211_MGMT_FRM_TYPE_NUM_MAX - 1; i++) {
+		if (!mgmt_frame[i])
+			continue;
+		len += scnprintf(buf + len, size - len, "%s\t%u\n",
+				 mgmt_frame[i], local->rx_mgmt_pkts[i]);
+	}
+
+	len += scnprintf(buf + len, size - len, "\nTx mgmt completion success:\n");
+	for (i = 0; i < IEEE80211_MGMT_FRM_TYPE_NUM_MAX - 1; i++) {
+		if (!mgmt_frame[i])
+			continue;
+		len += scnprintf(buf + len, size - len, "%s\t%u\n",
+				 mgmt_frame[i], local->mgmt_tx_compl_succ[i]);
+	}
+
+	len += scnprintf(buf + len, size - len, "\nTx mgmt completion failure:\n");
+	for (i = 0; i < IEEE80211_MGMT_FRM_TYPE_NUM_MAX - 1; i++) {
+		if (!mgmt_frame[i])
+			continue;
+		len += scnprintf(buf + len, size - len, "%s\t%u\n",
+				 mgmt_frame[i], local->mgmt_tx_compl_fail[i]);
+	}
+
+	return simple_read_from_buffer(userbuf, count, ppos, buf, len);
+}
+
+static const struct file_operations stats_mgmt_frame_ops = {
+	.read = mgmt_frame_read,
+	.open = simple_open,
+	.llseek = default_llseek,
+};
+#endif
+
 void debugfs_hw_add(struct ieee80211_local *local)
 {
 	struct dentry *phyd = local->hw.wiphy->debugfsdir;
@@ -692,6 +755,7 @@ void debugfs_hw_add(struct ieee80211_local *local)
 	DEBUGFS_STATS_ADD(rx_expand_skb_head_defrag);
 	DEBUGFS_STATS_ADD(rx_handlers_fragments);
 	DEBUGFS_STATS_ADD(tx_status_drop);
+	DEBUGFS_DEVSTATS_ADD(mgmt_frame);
 #endif
 	DEBUGFS_DEVSTATS_ADD(dot11ACKFailureCount);
 	DEBUGFS_DEVSTATS_ADD(dot11RTSFailureCount);
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
index 9f0db39b28ff..8418acb8333f 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -1547,8 +1547,19 @@ struct ieee80211_local {
 	unsigned int rx_expand_skb_head_defrag;
 	unsigned int rx_handlers_fragments;
 	unsigned int tx_status_drop;
+
+	/* Management Frame statistics */
+#define IEEE80211_MGMT_FRM_TYPE_NUM_MAX	16
+	u32 tx_mgmt_pkts[IEEE80211_MGMT_FRM_TYPE_NUM_MAX];
+	u32 rx_mgmt_pkts[IEEE80211_MGMT_FRM_TYPE_NUM_MAX];
+	u32 mgmt_tx_compl_succ[IEEE80211_MGMT_FRM_TYPE_NUM_MAX];
+	u32 mgmt_tx_compl_fail[IEEE80211_MGMT_FRM_TYPE_NUM_MAX];
+
+#define I802_DEBUG_MGMT_STATS(_skb, _local, _type) \
+	ieee80211_mgmt_stats_update(_skb, (_local)->(_type))
 #define I802_DEBUG_INC(c) (c)++
 #else /* CONFIG_MAC80211_DEBUG_COUNTERS */
+#define I802_DEBUG_MGMT_STATS(skb, local, type) do { } while (0)
 #define I802_DEBUG_INC(c) do { } while (0)
 #endif /* CONFIG_MAC80211_DEBUG_COUNTERS */
 
@@ -2781,4 +2792,19 @@ void ieee80211_rearrange_tpe_psd(struct ieee80211_parsed_tpe_psd *psd,
 #define VISIBLE_IF_MAC80211_KUNIT static
 #endif
 
+#ifdef CONFIG_MAC80211_DEBUG_COUNTERS
+static inline void ieee80211_mgmt_stats_update(struct sk_buff *skb,
+					       u32 *mgmt_stats_type)
+{
+	struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *)skb->data;
+	u16 stype;
+
+	if (!ieee80211_is_mgmt(mgmt->frame_control))
+		return;
+
+	stype = le16_get_bits(mgmt->frame_control, IEEE80211_FCTL_STYPE);
+	mgmt_stats_type[stype]++;
+}
+#endif
+
 #endif /* IEEE80211_I_H */
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c
index 2bec18fc1b03..acc40aa3e3e4 100644
--- a/net/mac80211/rx.c
+++ b/net/mac80211/rx.c
@@ -3427,6 +3427,8 @@ ieee80211_rx_h_mgmt_check(struct ieee80211_rx_data *rx)
 	if (!ieee80211_is_mgmt(mgmt->frame_control))
 		return RX_DROP_MONITOR;
 
+	I802_DEBUG_MGMT_STATS(rx->skb, rx->local, rx_mgmt_pkts);
+
 	/* drop too small action frames */
 	if (ieee80211_is_action(mgmt->frame_control) &&
 	    rx->skb->len < IEEE80211_MIN_ACTION_SIZE)
diff --git a/net/mac80211/status.c b/net/mac80211/status.c
index 5f28f3633fa0..d4ccf3cb484b 100644
--- a/net/mac80211/status.c
+++ b/net/mac80211/status.c
@@ -1063,6 +1063,7 @@ static void __ieee80211_tx_status(struct ieee80211_hw *hw,
 			if (retry_count > 1)
 				I802_DEBUG_INC(local->dot11MultipleRetryCount);
 		}
+		I802_DEBUG_MGMT_STATS(skb, local, mgmt_tx_compl_succ);
 
 		/* This counter shall be incremented for an acknowledged MPDU
 		 * with an individual address in the address 1 field or an MPDU
@@ -1075,6 +1076,7 @@ static void __ieee80211_tx_status(struct ieee80211_hw *hw,
 	} else {
 		if (ieee80211_is_first_frag(hdr->seq_ctrl))
 			I802_DEBUG_INC(local->dot11FailedCount);
+		I802_DEBUG_MGMT_STATS(skb, local, mgmt_tx_compl_fail);
 	}
 
 	if (ieee80211_is_any_nullfunc(fc) &&
@@ -1238,6 +1240,7 @@ void ieee80211_tx_status_ext(struct ieee80211_hw *hw,
 
 	if (acked || noack_success) {
 		I802_DEBUG_INC(local->dot11TransmittedFrameCount);
+		I802_DEBUG_MGMT_STATS(skb, local, mgmt_tx_compl_succ);
 		if (!pubsta)
 			I802_DEBUG_INC(local->dot11MulticastTransmittedFrameCount);
 		if (retry_count > 0)
@@ -1246,6 +1249,7 @@ void ieee80211_tx_status_ext(struct ieee80211_hw *hw,
 			I802_DEBUG_INC(local->dot11MultipleRetryCount);
 	} else {
 		I802_DEBUG_INC(local->dot11FailedCount);
+		I802_DEBUG_MGMT_STATS(skb, local, mgmt_tx_compl_succ);
 	}
 
 free:
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index a24636bda679..173cdbca01ab 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -1833,6 +1833,8 @@ static int invoke_tx_handlers_early(struct ieee80211_tx_data *tx)
 		return -1;
 	}
 
+	I802_DEBUG_MGMT_STATS(tx->skb, tx->local, tx_mgmt_pkts);
+
 	return 0;
 }
 
