public inbox for linux-wireless@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support
@ 2026-04-25 19:49 Sean Wang
  2026-04-25 19:49 ` [PATCH v5 01/21] wifi: mt76: mt7925: fix stale pointer comparisons in change_vif_links Sean Wang
                   ` (20 more replies)
  0 siblings, 21 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

This series adds support for MediaTek MT7927 (Filogic 380), a combo
WiFi 7 + BT 5.4 device, in the mt7925 driver.

Patches 1-5 add generic 320MHz EHT support without MT7927-specific
references.

Patches 6-9 add the initial MT7927 enablement pieces, including chip ID
helpers, firmware paths, per-chip IRQ map handling, and disabling ASPM
and runtime PM for MT7927.

Patches 10-21 add the remaining MT7927 support needed to make the device
usable, including connac3 helper cleanup, non-MLD link removal handling,
inactive BSS deactivation tolerance, WFSYS reset support, common DMA queue
helper refactoring, MT7927 PCIe DMA configuration, BSS band assignment
sync, MBMC event handling, CNM ops enablement, and PCIe/USB device support.

The follow-up MT7927 support patches are folded into this version so users
and testers can apply one complete series for MT7927 enablement.

Tested hardware:
- ASUS ROG Crosshair X870E Hero (BT 0489:e13a, WiFi 14c3:6639)
- ASUS ProArt X870E-Creator WiFi (BT 0489:e13a / 13d3:3588, WiFi 14c3:6639)
- ASUS ROG Strix X870-I (WiFi 14c3:7927)
- ASUS ROG Strix X870-F Gaming WiFi (BT 0489:e13a, WiFi 14c3:7927)
- ASUS ROG Strix X870E-E (BT 13d3:3588, WiFi 14c3:7927)
- ASUS ROG STRIX B850-E GAMING WIFI (BT 0489:e13a, WiFi 14c3:7927)
- Gigabyte X870E Aorus Master X3D (BT 0489:e10f, WiFi 14c3:7927)
- Gigabyte Z790 AORUS MASTER X (BT 0489:e10f, WiFi 14c3:7927)
- Gigabyte Z790 AORUS ELITE X WiFi7 (BT 0489:e10f, WiFi 14c3:7927)
- MSI MEG X870E ACE MAX (BT 0489:e110, WiFi 14c3:7927)
- Lenovo Legion Pro 7 16ARX9 (BT 0489:e0fa, WiFi 14c3:7927)
- Lenovo Legion Pro 7 16AFR10H (BT 0489:e0fa, WiFi 14c3:7927)
- TP-Link Archer TBE550E PCIe (BT 0489:e116, WiFi 14c3:7927)
- EDUP EP-MT7927BE M.2 card (WiFi 14c3:7927)
- Foxconn/Azurewave M.2 modules (WiFi 14c3:6639)
- AMD RZ738 reference design (WiFi 14c3:0738)

Tested on Arch Linux, CachyOS, EndeavourOS, Fedora (Bazzite), NixOS,
openSUSE Tumbleweed, and Ubuntu across kernels 6.13-6.19.

Changes since v4:
- Add Reviewed-by tags to patches 1-9.
- Add MT7927 follow-up support:
  - replace is_mt7925() with is_connac3()
  - use link-specific removal for non-MLD STA
  - tolerate inactive BSS deactivation
  - add MT7927 WFSYS reset support
  - factor out common DMA queue allocation
  - switch mt7925 DMA init to common mt792x queue helpers
  - add MT7927-specific PCIe DMA support
  - sync MT7927 BSS band assignment
  - add MBMC event handling
  - enable CNM ops for MT7927
  - add MT7927 PCIe support
  - add MT7927 USB support

Changes since v3:
- Dropped patches 9-13 (DMA, HW init, band_idx, PCI IDs). Sean Wang
  will submit these as part of a generic layer refactor. The CNM quirk
  (v3 patch 13 feedback) will be folded into mt792x_get_mac80211_ops()
  as part of that work.
- Fixed is_320mhz_supported() to use mt76_chip() directly instead of
  is_mt7927() which was not yet defined at that point (patch 5).
- Trimmed verbose inline comments in ASPM/PM patch per review feedback.
  Detail kept in commit message (patch 9).
- Added tested hardware: ASUS ROG STRIX B850-E GAMING WIFI.

Changes since v2 (suggested by Sean Wang):
- Fixed is_320mhz_supported() to check for MT7927 only, not the
  entire mt7925 family. MT7925 does not support 320MHz (patch 5).
- Dropped phy_cap_info[7] 320MHz additions (NON_OFDMA_UL_MU_MIMO
  and MU_BEAMFORMER) to keep capabilities conservative (patch 5).
- Disabled runtime PM for MT7927 (patch 9). The combo chip shares a
  CONNINFRA power domain between WiFi and BT; SET_OWN/CLR_OWN
  transitions crash BT firmware. Discovered via user reports of BT
  lockups after enabling power_save=1 (Reported-by: Nitin Gurram).

Changes since v1 (suggested by Sean Wang):
- Reorganized from 18 patches into 13 across 8 logical groups
- Common 320MHz patches first, chip-specific changes later
- Introduced mt792x_dma_config struct to reuse mt7925_dma_init()
- Replaced is_mt7927() with is_320mhz_supported() in common patches

Link to v4: https://lore.kernel.org/linux-wireless/20260326-mt7927-wifi-support-v4-v4-0-8ab465addcfe@jetm.me/
Link to v3: https://lore.kernel.org/linux-wireless/20260325-mt7927-wifi-support-v2-v3-0-826feb8fef8e@jetm.me/
Link to v2: https://lore.kernel.org/linux-wireless/20260319-mt7927-wifi-support-v2-v2-0-d627a7fad70d@jetm.me/
Link to v1: https://lore.kernel.org/linux-wireless/20260306-mt7927-wifi-support-v1-0-c77e7445511d@jetm.me/

Javier Tia (9):
  wifi: mt76: mt7925: fix stale pointer comparisons in change_vif_links
  wifi: mt76: mt7925: add 320MHz bandwidth to bss_rlm_tlv
  wifi: mt76: mt7925: handle 320MHz bandwidth in RXV and TXS
  wifi: mt76: mt7925: populate EHT 320MHz MCS map in sta_rec
  wifi: mt76: mt7925: advertise EHT 320MHz capabilities for 6GHz band
  wifi: mt76: mt7925: add MT7927 chip ID helpers
  wifi: mt76: mt7925: add MT7927 firmware paths
  wifi: mt76: mt7925: use irq_map for chip-specific interrupt handling
  wifi: mt76: mt7925: disable ASPM and runtime PM for MT7927

Sean Wang (12):
  wifi: mt76: connac: replace is_mt7925() with is_connac3()
  wifi: mt76: mt7925: use link-specific removal for non-MLD STA
  wifi: mt76: connac: tolerate inactive BSS deactivation
  wifi: mt76: mt792x: add MT7927 WFSYS reset support
  wifi: mt76: mt792x: factor out common DMA queue allocation
  wifi: mt76: mt7925: switch DMA init to common mt792x queue helpers
  wifi: mt76: mt792x: add MT7927-specific PCIe DMA support
  wifi: mt76: mt7925: sync MT7927 BSS band assignment
  wifi: mt76: mt7925: add MBMC event handling
  wifi: mt76: mt792x: enable CNM ops for MT7927
  wifi: mt76: mt7925: add MT7927 PCIe support
  wifi: mt76: mt7925: add MT7927 USB support

 .../net/wireless/mediatek/mt76/mt76_connac.h  |  16 ++
 .../wireless/mediatek/mt76/mt76_connac_mac.c  |   4 +-
 .../wireless/mediatek/mt76/mt76_connac_mcu.c  |  13 +-
 .../wireless/mediatek/mt76/mt76_connac_mcu.h  |  26 ++-
 .../net/wireless/mediatek/mt76/mt7925/init.c  |  12 +-
 .../net/wireless/mediatek/mt76/mt7925/mac.c   |   9 +
 .../net/wireless/mediatek/mt76/mt7925/main.c  |  80 ++++++-
 .../net/wireless/mediatek/mt76/mt7925/mcu.c   |  43 +++-
 .../net/wireless/mediatek/mt76/mt7925/mcu.h   |   3 +-
 .../wireless/mediatek/mt76/mt7925/mt7925.h    |  25 +++
 .../net/wireless/mediatek/mt76/mt7925/pci.c   | 133 +++++++++---
 .../wireless/mediatek/mt76/mt7925/pci_mac.c   |  12 +-
 .../net/wireless/mediatek/mt76/mt7925/usb.c   |  15 ++
 drivers/net/wireless/mediatek/mt76/mt792x.h   |  25 +++
 .../net/wireless/mediatek/mt76/mt792x_core.c  |  11 +
 .../net/wireless/mediatek/mt76/mt792x_dma.c   | 198 ++++++++++++++++--
 .../net/wireless/mediatek/mt76/mt792x_regs.h  |  23 ++
 .../net/wireless/mediatek/mt76/mt792x_usb.c   |   2 +-
 drivers/net/wireless/mediatek/mt76/usb.c      |   1 +
 19 files changed, 578 insertions(+), 73 deletions(-)


base-commit: e8c819df02436f2c2379766946735e1f06a7c923
-- 
2.43.0


^ permalink raw reply	[flat|nested] 22+ messages in thread

* [PATCH v5 01/21] wifi: mt76: mt7925: fix stale pointer comparisons in change_vif_links
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 02/21] wifi: mt76: mt7925: add 320MHz bandwidth to bss_rlm_tlv Sean Wang
                   ` (19 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Marcin FM,
	Cristian-Florin Radoi, George Salukvadze, Evgeny Kapusta,
	Samu Toljamo, Ariel Rosenfeld, Chapuis Dario,
	Thibaut François, 张旭涵, Sean Wang

From: Javier Tia <floss@jetm.me>

In the error path of mt7925_change_vif_links(), the free: label iterates
over link_ids to clean up, but compares against `mconf` and `mlink`
which hold stale values from the last loop iteration rather than the
current link_id being freed.

Use array-indexed access (mconfs[link_id] / mlinks[link_id]) to compare
against the correct per-link pointers.

Fixes: 69acd6d910b0 ("wifi: mt76: mt7925: add mt7925_change_vif_links")
Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 drivers/net/wireless/mediatek/mt76/mt7925/main.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/main.c b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
index 73d3722739d0..4d8ca04a128b 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/main.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
@@ -2179,9 +2179,9 @@ mt7925_change_vif_links(struct ieee80211_hw *hw, struct ieee80211_vif *vif,
 		rcu_assign_pointer(mvif->link_conf[link_id], NULL);
 		rcu_assign_pointer(mvif->sta.link[link_id], NULL);
 
-		if (mconf != &mvif->bss_conf)
+		if (mconfs[link_id] != &mvif->bss_conf)
 			devm_kfree(dev->mt76.dev, mconfs[link_id]);
-		if (mlink != &mvif->sta.deflink)
+		if (mlinks[link_id] != &mvif->sta.deflink)
 			devm_kfree(dev->mt76.dev, mlinks[link_id]);
 	}
 
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 02/21] wifi: mt76: mt7925: add 320MHz bandwidth to bss_rlm_tlv
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
  2026-04-25 19:49 ` [PATCH v5 01/21] wifi: mt76: mt7925: fix stale pointer comparisons in change_vif_links Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 03/21] wifi: mt76: mt7925: handle 320MHz bandwidth in RXV and TXS Sean Wang
                   ` (18 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia,
	张旭涵, Marcin FM, Cristian-Florin Radoi,
	George Salukvadze, Evgeny Kapusta, Samu Toljamo, Ariel Rosenfeld,
	Chapuis Dario, Thibaut François, Sean Wang

From: Javier Tia <floss@jetm.me>

bss_rlm_tlv() in mt7925_mcu_bss_rlm_tlv() has no case for
NL80211_CHAN_WIDTH_320. When associated to a 320MHz BSS, the switch
falls through to default and sends bw=0 (CMD_CBW_20MHZ) to firmware
via BSS_RLM TLV. Firmware then configures the RX radio for 20MHz
and cannot decode the AP's 320MHz frames, resulting in complete data
path failure at 320MHz.

Add the missing NL80211_CHAN_WIDTH_320 case with CMD_CBW_320MHZ and
center_chan2.

Tested on ASUS RT-BE92U: 320MHz throughput goes from 0 Mbps to
841 Mbps (iperf3 -t30 -P8), PHY 4803 Mbps EHT-MCS11.

Reported-by: 张旭涵 <Loong.0x00@gmail.com>
Closes: https://github.com/openwrt/mt76/issues/927
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 drivers/net/wireless/mediatek/mt76/mt7925/mcu.c | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
index 37cdf3e8a067..016c534f748c 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
@@ -2334,6 +2334,10 @@ void mt7925_mcu_bss_rlm_tlv(struct sk_buff *skb, struct mt76_phy *phy,
 	case NL80211_CHAN_WIDTH_160:
 		req->bw = CMD_CBW_160MHZ;
 		break;
+	case NL80211_CHAN_WIDTH_320:
+		req->bw = CMD_CBW_320MHZ;
+		req->center_chan2 = ieee80211_frequency_to_channel(freq2);
+		break;
 	case NL80211_CHAN_WIDTH_5:
 		req->bw = CMD_CBW_5MHZ;
 		break;
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 03/21] wifi: mt76: mt7925: handle 320MHz bandwidth in RXV and TXS
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
  2026-04-25 19:49 ` [PATCH v5 01/21] wifi: mt76: mt7925: fix stale pointer comparisons in change_vif_links Sean Wang
  2026-04-25 19:49 ` [PATCH v5 02/21] wifi: mt76: mt7925: add 320MHz bandwidth to bss_rlm_tlv Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 04/21] wifi: mt76: mt7925: populate EHT 320MHz MCS map in sta_rec Sean Wang
                   ` (17 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Marcin FM,
	Cristian-Florin Radoi, George Salukvadze, Evgeny Kapusta,
	Samu Toljamo, Ariel Rosenfeld, Chapuis Dario,
	Thibaut François, 张旭涵, Sean Wang

From: Javier Tia <floss@jetm.me>

The RX vector (RXV) and TX status (TXS) parsing in mac.c lack handling
for 320MHz channel width. When the hardware reports 320MHz in the
bandwidth field, mt7925_mac_fill_rx_rate() returns -EINVAL and
mt7925_mac_add_txs_skb() records no bandwidth stats.

Add IEEE80211_STA_RX_BW_320 cases to both functions. The RXV parser
also handles BW_320+1 since the hardware can report 320MHz in two
adjacent encoding positions.

Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 drivers/net/wireless/mediatek/mt76/mt7925/mac.c | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mac.c b/drivers/net/wireless/mediatek/mt76/mt7925/mac.c
index c47bd812b66b..d681005cc6ff 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mac.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mac.c
@@ -339,6 +339,11 @@ mt7925_mac_fill_rx_rate(struct mt792x_dev *dev,
 	case IEEE80211_STA_RX_BW_160:
 		status->bw = RATE_INFO_BW_160;
 		break;
+	/* RXV can report 320 in two positions */
+	case IEEE80211_STA_RX_BW_320:
+	case IEEE80211_STA_RX_BW_320 + 1:
+		status->bw = RATE_INFO_BW_320;
+		break;
 	default:
 		return -EINVAL;
 	}
@@ -997,6 +1002,10 @@ mt7925_mac_add_txs_skb(struct mt792x_dev *dev, struct mt76_wcid *wcid,
 	stats->tx_mode[mode]++;
 
 	switch (FIELD_GET(MT_TXS0_BW, txs)) {
+	case IEEE80211_STA_RX_BW_320:
+		rate.bw = RATE_INFO_BW_320;
+		stats->tx_bw[4]++;
+		break;
 	case IEEE80211_STA_RX_BW_160:
 		rate.bw = RATE_INFO_BW_160;
 		stats->tx_bw[3]++;
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 04/21] wifi: mt76: mt7925: populate EHT 320MHz MCS map in sta_rec
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (2 preceding siblings ...)
  2026-04-25 19:49 ` [PATCH v5 03/21] wifi: mt76: mt7925: handle 320MHz bandwidth in RXV and TXS Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 05/21] wifi: mt76: mt7925: advertise EHT 320MHz capabilities for 6GHz band Sean Wang
                   ` (16 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Marcin FM,
	Cristian-Florin Radoi, George Salukvadze, Evgeny Kapusta,
	Samu Toljamo, Ariel Rosenfeld, Chapuis Dario,
	Thibaut François, 张旭涵, Sean Wang

From: Javier Tia <floss@jetm.me>

The sta_rec_eht structure has a mcs_map_bw320 field, and the channel
width mapping includes NL80211_CHAN_WIDTH_320, but the 320MHz MCS/NSS
map was never copied from the station's EHT capabilities to the MCU TLV.
This prevents negotiation of 320MHz channel width even when both the
hardware and firmware advertise support for it.

Add the missing memcpy for the 320MHz MCS map, matching the existing
pattern for BW20, BW80, and BW160.

Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 drivers/net/wireless/mediatek/mt76/mt7925/mcu.c | 1 +
 1 file changed, 1 insertion(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
index 016c534f748c..f403d9d925e3 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
@@ -1667,6 +1667,7 @@ mt7925_mcu_sta_eht_tlv(struct sk_buff *skb, struct ieee80211_link_sta *link_sta)
 		memcpy(eht->mcs_map_bw20, &mcs_map->only_20mhz, sizeof(eht->mcs_map_bw20));
 	memcpy(eht->mcs_map_bw80, &mcs_map->bw._80, sizeof(eht->mcs_map_bw80));
 	memcpy(eht->mcs_map_bw160, &mcs_map->bw._160, sizeof(eht->mcs_map_bw160));
+	memcpy(eht->mcs_map_bw320, &mcs_map->bw._320, sizeof(eht->mcs_map_bw320));
 }
 
 static void
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 05/21] wifi: mt76: mt7925: advertise EHT 320MHz capabilities for 6GHz band
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (3 preceding siblings ...)
  2026-04-25 19:49 ` [PATCH v5 04/21] wifi: mt76: mt7925: populate EHT 320MHz MCS map in sta_rec Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 06/21] wifi: mt76: mt7925: add MT7927 chip ID helpers Sean Wang
                   ` (15 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Marcin FM,
	Cristian-Florin Radoi, George Salukvadze, Evgeny Kapusta,
	Samu Toljamo, Ariel Rosenfeld, Chapuis Dario,
	Thibaut François, 张旭涵, Sean Wang

From: Javier Tia <floss@jetm.me>

mt7925_init_eht_caps() only populates EHT MCS/NSS maps for BW <= 80
and BW = 160, but never sets BW = 320. This means iw phy shows no
320MHz MCS map entries even though the hardware supports 320MHz
operation in the 6GHz band.

Add the missing 320MHz capability bits for 6GHz:
  - PHY_CAP0: IEEE80211_EHT_PHY_CAP0_320MHZ_IN_6GHZ
  - PHY_CAP1: beamformee SS for 320MHz
  - PHY_CAP2: sounding dimensions for 320MHz
  - PHY_CAP6: MCS15 support for 320MHz width
  - MCS/NSS: populate bw._320 maps for 6GHz band

Introduce is_320mhz_supported() to gate 320MHz on MT7927 only, since
MT7925 does not support 320MHz operation.

Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 .../net/wireless/mediatek/mt76/mt76_connac.h  |  5 +++++
 .../net/wireless/mediatek/mt76/mt7925/main.c  | 22 ++++++++++++++++++-
 2 files changed, 26 insertions(+), 1 deletion(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac.h b/drivers/net/wireless/mediatek/mt76/mt76_connac.h
index 51423c7740bd..802cb26ed6e3 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac.h
@@ -177,6 +177,11 @@ static inline bool is_mt7925(struct mt76_dev *dev)
 	return mt76_chip(dev) == 0x7925;
 }
 
+static inline bool is_320mhz_supported(struct mt76_dev *dev)
+{
+	return mt76_chip(dev) == 0x7927;
+}
+
 static inline bool is_mt7920(struct mt76_dev *dev)
 {
 	return mt76_chip(dev) == 0x7920;
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/main.c b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
index 4d8ca04a128b..bf38d6502970 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/main.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
@@ -183,6 +183,10 @@ mt7925_init_eht_caps(struct mt792x_phy *phy, enum nl80211_band band,
 		IEEE80211_EHT_PHY_CAP0_SU_BEAMFORMER |
 		IEEE80211_EHT_PHY_CAP0_SU_BEAMFORMEE;
 
+	if (band == NL80211_BAND_6GHZ && is_320mhz_supported(&phy->dev->mt76))
+		eht_cap_elem->phy_cap_info[0] |=
+			IEEE80211_EHT_PHY_CAP0_320MHZ_IN_6GHZ;
+
 	eht_cap_elem->phy_cap_info[0] |=
 		u8_encode_bits(u8_get_bits(sts - 1, BIT(0)),
 			       IEEE80211_EHT_PHY_CAP0_BEAMFORMEE_SS_80MHZ_MASK);
@@ -193,10 +197,20 @@ mt7925_init_eht_caps(struct mt792x_phy *phy, enum nl80211_band band,
 		u8_encode_bits(sts - 1,
 			       IEEE80211_EHT_PHY_CAP1_BEAMFORMEE_SS_160MHZ_MASK);
 
+	if (band == NL80211_BAND_6GHZ && is_320mhz_supported(&phy->dev->mt76))
+		eht_cap_elem->phy_cap_info[1] |=
+			u8_encode_bits(sts - 1,
+				       IEEE80211_EHT_PHY_CAP1_BEAMFORMEE_SS_320MHZ_MASK);
+
 	eht_cap_elem->phy_cap_info[2] =
 		u8_encode_bits(sts - 1, IEEE80211_EHT_PHY_CAP2_SOUNDING_DIM_80MHZ_MASK) |
 		u8_encode_bits(sts - 1, IEEE80211_EHT_PHY_CAP2_SOUNDING_DIM_160MHZ_MASK);
 
+	if (band == NL80211_BAND_6GHZ && is_320mhz_supported(&phy->dev->mt76))
+		eht_cap_elem->phy_cap_info[2] |=
+			u8_encode_bits(sts - 1,
+				       IEEE80211_EHT_PHY_CAP2_SOUNDING_DIM_320MHZ_MASK);
+
 	eht_cap_elem->phy_cap_info[3] =
 		IEEE80211_EHT_PHY_CAP3_NG_16_SU_FEEDBACK |
 		IEEE80211_EHT_PHY_CAP3_NG_16_MU_FEEDBACK |
@@ -217,7 +231,8 @@ mt7925_init_eht_caps(struct mt792x_phy *phy, enum nl80211_band band,
 		u8_encode_bits(u8_get_bits(0x11, GENMASK(1, 0)),
 			       IEEE80211_EHT_PHY_CAP5_MAX_NUM_SUPP_EHT_LTF_MASK);
 
-	val = width == NL80211_CHAN_WIDTH_160 ? 0x7 :
+	val = width == NL80211_CHAN_WIDTH_320 ? 0xf :
+	      width == NL80211_CHAN_WIDTH_160 ? 0x7 :
 	      width == NL80211_CHAN_WIDTH_80 ? 0x3 : 0x1;
 	eht_cap_elem->phy_cap_info[6] =
 		u8_encode_bits(u8_get_bits(0x11, GENMASK(4, 2)),
@@ -239,6 +254,11 @@ mt7925_init_eht_caps(struct mt792x_phy *phy, enum nl80211_band band,
 	eht_nss->bw._160.rx_tx_mcs9_max_nss = val;
 	eht_nss->bw._160.rx_tx_mcs11_max_nss = val;
 	eht_nss->bw._160.rx_tx_mcs13_max_nss = val;
+	if (band == NL80211_BAND_6GHZ && is_320mhz_supported(&phy->dev->mt76)) {
+		eht_nss->bw._320.rx_tx_mcs9_max_nss = val;
+		eht_nss->bw._320.rx_tx_mcs11_max_nss = val;
+		eht_nss->bw._320.rx_tx_mcs13_max_nss = val;
+	}
 }
 
 int mt7925_init_mlo_caps(struct mt792x_phy *phy)
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 06/21] wifi: mt76: mt7925: add MT7927 chip ID helpers
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (4 preceding siblings ...)
  2026-04-25 19:49 ` [PATCH v5 05/21] wifi: mt76: mt7925: advertise EHT 320MHz capabilities for 6GHz band Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 07/21] wifi: mt76: mt7925: add MT7927 firmware paths Sean Wang
                   ` (14 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Marcin FM,
	Cristian-Florin Radoi, George Salukvadze, Evgeny Kapusta,
	Samu Toljamo, Ariel Rosenfeld, Chapuis Dario,
	Thibaut François, 张旭涵, Sean Wang

From: Javier Tia <floss@jetm.me>

The MediaTek MT7927 (Filogic 380) combo chip uses MT7927 WiFi silicon
that is architecturally compatible with MT7925. Extend is_mt7925() to
match chip ID 0x7927, and add is_mt7927() for code paths that need
MT7927-specific handling.

Also add 0x7927 to is_mt76_fw_txp() to match MT7925's TXP format.

Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 drivers/net/wireless/mediatek/mt76/mt76_connac.h | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac.h b/drivers/net/wireless/mediatek/mt76/mt76_connac.h
index 802cb26ed6e3..45479cc29134 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac.h
@@ -174,7 +174,12 @@ extern const struct wiphy_wowlan_support mt76_connac_wowlan_support;
 
 static inline bool is_mt7925(struct mt76_dev *dev)
 {
-	return mt76_chip(dev) == 0x7925;
+	return mt76_chip(dev) == 0x7925 || mt76_chip(dev) == 0x7927;
+}
+
+static inline bool is_mt7927(struct mt76_dev *dev)
+{
+	return mt76_chip(dev) == 0x7927;
 }
 
 static inline bool is_320mhz_supported(struct mt76_dev *dev)
@@ -284,6 +289,7 @@ static inline bool is_mt76_fw_txp(struct mt76_dev *dev)
 	case 0x7922:
 	case 0x7902:
 	case 0x7925:
+	case 0x7927:
 	case 0x7663:
 	case 0x7622:
 		return false;
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 07/21] wifi: mt76: mt7925: add MT7927 firmware paths
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (5 preceding siblings ...)
  2026-04-25 19:49 ` [PATCH v5 06/21] wifi: mt76: mt7925: add MT7927 chip ID helpers Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 08/21] wifi: mt76: mt7925: use irq_map for chip-specific interrupt handling Sean Wang
                   ` (13 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Marcin FM,
	Cristian-Florin Radoi, George Salukvadze, Evgeny Kapusta,
	Samu Toljamo, Ariel Rosenfeld, Chapuis Dario,
	Thibaut François, 张旭涵, Sean Wang

From: Javier Tia <floss@jetm.me>

Add firmware path definitions for MT7927 WiFi firmware (WIFI_RAM_CODE
and PATCH_MCU) and the corresponding MODULE_FIRMWARE declarations. Add
MT7927 cases to mt792x_ram_name() and mt792x_patch_name() so the driver
loads the correct firmware for the 0x7927 chip ID.

PCI device table entries are deferred to a later patch to allow
infrastructure setup before device enablement.

Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 drivers/net/wireless/mediatek/mt76/mt7925/pci.c | 2 ++
 drivers/net/wireless/mediatek/mt76/mt792x.h     | 6 ++++++
 2 files changed, 8 insertions(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
index c4161754c01d..f820d5aeb723 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
@@ -633,6 +633,8 @@ module_pci_driver(mt7925_pci_driver);
 MODULE_DEVICE_TABLE(pci, mt7925_pci_device_table);
 MODULE_FIRMWARE(MT7925_FIRMWARE_WM);
 MODULE_FIRMWARE(MT7925_ROM_PATCH);
+MODULE_FIRMWARE(MT7927_FIRMWARE_WM);
+MODULE_FIRMWARE(MT7927_ROM_PATCH);
 MODULE_AUTHOR("Deren Wu <deren.wu@mediatek.com>");
 MODULE_AUTHOR("Lorenzo Bianconi <lorenzo@kernel.org>");
 MODULE_DESCRIPTION("MediaTek MT7925E (PCIe) wireless driver");
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x.h b/drivers/net/wireless/mediatek/mt76/mt792x.h
index 4ff93f2cd624..09840483fe2a 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x.h
+++ b/drivers/net/wireless/mediatek/mt76/mt792x.h
@@ -46,12 +46,14 @@
 #define MT7921_FIRMWARE_WM	"mediatek/WIFI_RAM_CODE_MT7961_1.bin"
 #define MT7922_FIRMWARE_WM	"mediatek/WIFI_RAM_CODE_MT7922_1.bin"
 #define MT7925_FIRMWARE_WM	"mediatek/mt7925/WIFI_RAM_CODE_MT7925_1_1.bin"
+#define MT7927_FIRMWARE_WM	"mediatek/mt7927/WIFI_RAM_CODE_MT6639_2_1.bin"
 
 #define MT7902_ROM_PATCH	"mediatek/WIFI_MT7902_patch_mcu_1_1_hdr.bin"
 #define MT7920_ROM_PATCH	"mediatek/WIFI_MT7961_patch_mcu_1a_2_hdr.bin"
 #define MT7921_ROM_PATCH	"mediatek/WIFI_MT7961_patch_mcu_1_2_hdr.bin"
 #define MT7922_ROM_PATCH	"mediatek/WIFI_MT7922_patch_mcu_1_1_hdr.bin"
 #define MT7925_ROM_PATCH	"mediatek/mt7925/WIFI_MT7925_PATCH_MCU_1_1_hdr.bin"
+#define MT7927_ROM_PATCH	"mediatek/mt7927/WIFI_MT6639_PATCH_MCU_2_1_hdr.bin"
 
 #define MT792x_SDIO_HDR_TX_BYTES	GENMASK(15, 0)
 #define MT792x_SDIO_HDR_PKT_TYPE	GENMASK(17, 16)
@@ -459,6 +461,8 @@ static inline char *mt792x_ram_name(struct mt792x_dev *dev)
 		return MT7922_FIRMWARE_WM;
 	case 0x7925:
 		return MT7925_FIRMWARE_WM;
+	case 0x7927:
+		return MT7927_FIRMWARE_WM;
 	default:
 		return MT7921_FIRMWARE_WM;
 	}
@@ -475,6 +479,8 @@ static inline char *mt792x_patch_name(struct mt792x_dev *dev)
 		return MT7922_ROM_PATCH;
 	case 0x7925:
 		return MT7925_ROM_PATCH;
+	case 0x7927:
+		return MT7927_ROM_PATCH;
 	default:
 		return MT7921_ROM_PATCH;
 	}
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 08/21] wifi: mt76: mt7925: use irq_map for chip-specific interrupt handling
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (6 preceding siblings ...)
  2026-04-25 19:49 ` [PATCH v5 07/21] wifi: mt76: mt7925: add MT7927 firmware paths Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:49 ` [PATCH v5 09/21] wifi: mt76: mt7925: disable ASPM and runtime PM for MT7927 Sean Wang
                   ` (12 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Marcin FM,
	Cristian-Florin Radoi, George Salukvadze, Evgeny Kapusta,
	Samu Toljamo, Ariel Rosenfeld, Chapuis Dario,
	Thibaut François, 张旭涵, Sean Wang

From: Javier Tia <floss@jetm.me>

The mac_reset and resume paths use the hardcoded MT_INT_RX_DONE_ALL
constant (bits 0-2) to re-enable RX interrupts. This is correct for
MT7925 (RX rings 0, 1, 2) but wrong for chips using different ring
indices.

Define a per-chip irq_map with the correct RX interrupt enable bits and
replace hardcoded MT_INT_RX_DONE_ALL with irq_map field reads in the
resume and mac_reset paths. Add the MT7927 irq_map with interrupt bits
matching its RX ring layout (rings 4, 6, 7), selected at probe time
based on PCI device ID.

This ensures the correct interrupt bits are enabled regardless of the
chip variant.

Tested-by: Marcin FM <marcin@lgic.pl>
Tested-by: Cristian-Florin Radoi <radoi.chris@gmail.com>
Tested-by: George Salukvadze <giosal90@gmail.com>
Tested-by: Evgeny Kapusta <3193631@gmail.com>
Tested-by: Samu Toljamo <samu.toljamo@gmail.com>
Tested-by: Ariel Rosenfeld <ariel.rosenfeld.750@gmail.com>
Tested-by: Chapuis Dario <chapuisdario4@gmail.com>
Tested-by: Thibaut François <tibo@humeurlibre.fr>
Tested-by: 张旭涵 <Loong.0x00@gmail.com>
Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 .../net/wireless/mediatek/mt76/mt7925/pci.c   | 21 +++++++++++++++++--
 .../wireless/mediatek/mt76/mt7925/pci_mac.c   |  5 ++++-
 .../net/wireless/mediatek/mt76/mt792x_regs.h  |  3 +++
 3 files changed, 26 insertions(+), 3 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
index f820d5aeb723..604c0e9ae7ba 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
@@ -266,6 +266,18 @@ static int mt7925_dma_init(struct mt792x_dev *dev)
 	return mt792x_dma_enable(dev);
 }
 
+static const struct mt792x_irq_map mt7927_irq_map = {
+	.host_irq_enable = MT_WFDMA0_HOST_INT_ENA,
+	.tx = {
+		.all_complete_mask = MT_INT_TX_DONE_ALL,
+		.mcu_complete_mask = MT_INT_TX_DONE_MCU,
+	},
+	.rx = {
+		.data_complete_mask = MT7927_RX_DONE_INT_ENA4,
+		.wm_complete_mask = MT7927_RX_DONE_INT_ENA6,
+		.wm2_complete_mask = MT7927_RX_DONE_INT_ENA7,
+	},
+};
 static int mt7925_pci_probe(struct pci_dev *pdev,
 			    const struct pci_device_id *id)
 {
@@ -310,6 +322,7 @@ static int mt7925_pci_probe(struct pci_dev *pdev,
 	struct mt76_bus_ops *bus_ops;
 	struct mt792x_dev *dev;
 	struct mt76_dev *mdev;
+	bool is_mt7927_hw;
 	u8 features;
 	int ret;
 	u16 cmd;
@@ -358,7 +371,8 @@ static int mt7925_pci_probe(struct pci_dev *pdev,
 	dev = container_of(mdev, struct mt792x_dev, mt76);
 	dev->fw_features = features;
 	dev->hif_ops = &mt7925_pcie_ops;
-	dev->irq_map = &irq_map;
+	is_mt7927_hw = (pdev->device == 0x6639 || pdev->device == 0x7927);
+	dev->irq_map = is_mt7927_hw ? &mt7927_irq_map : &irq_map;
 	mt76_mmio_init(&dev->mt76, pcim_iomap_table(pdev)[0]);
 	tasklet_init(&mdev->irq_tasklet, mt792x_irq_tasklet, (unsigned long)dev);
 
@@ -549,7 +563,10 @@ static int _mt7925_pci_resume(struct device *device, bool restore)
 	mt76_wr(dev, MT_PCIE_MAC_INT_ENABLE, 0xff);
 	mt76_connac_irq_enable(&dev->mt76,
 			       dev->irq_map->tx.all_complete_mask |
-			       MT_INT_RX_DONE_ALL | MT_INT_MCU_CMD);
+			       dev->irq_map->rx.data_complete_mask |
+			       dev->irq_map->rx.wm_complete_mask |
+			       dev->irq_map->rx.wm2_complete_mask |
+			       MT_INT_MCU_CMD);
 	mt76_set(dev, MT_MCU2HOST_SW_INT_ENA, MT_MCU_CMD_WAKE_RX_PCIE);
 
 	/* put dma enabled */
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c
index 3072850c2752..1626a3684082 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c
@@ -118,7 +118,10 @@ int mt7925e_mac_reset(struct mt792x_dev *dev)
 
 	mt76_wr(dev, dev->irq_map->host_irq_enable,
 		dev->irq_map->tx.all_complete_mask |
-		MT_INT_RX_DONE_ALL | MT_INT_MCU_CMD);
+		dev->irq_map->rx.data_complete_mask |
+		dev->irq_map->rx.wm_complete_mask |
+		dev->irq_map->rx.wm2_complete_mask |
+		MT_INT_MCU_CMD);
 	mt76_wr(dev, MT_PCIE_MAC_INT_ENABLE, 0xff);
 
 	err = mt792xe_mcu_fw_pmctrl(dev);
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_regs.h b/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
index d2a8b2b0df32..20d27ae89aca 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
@@ -310,6 +310,9 @@
 #define HOST_RX_DONE_INT_ENA1		BIT(1)
 #define HOST_RX_DONE_INT_ENA2		BIT(2)
 #define HOST_RX_DONE_INT_ENA3		BIT(3)
+#define MT7927_RX_DONE_INT_ENA4		BIT(12)
+#define MT7927_RX_DONE_INT_ENA6		BIT(14)
+#define MT7927_RX_DONE_INT_ENA7		BIT(15)
 #define HOST_TX_DONE_INT_ENA0		BIT(4)
 #define HOST_TX_DONE_INT_ENA1		BIT(5)
 #define HOST_TX_DONE_INT_ENA2		BIT(6)
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 09/21] wifi: mt76: mt7925: disable ASPM and runtime PM for MT7927
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (7 preceding siblings ...)
  2026-04-25 19:49 ` [PATCH v5 08/21] wifi: mt76: mt7925: use irq_map for chip-specific interrupt handling Sean Wang
@ 2026-04-25 19:49 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 10/21] wifi: mt76: connac: replace is_mt7925() with is_connac3() Sean Wang
                   ` (11 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:49 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Javier Tia, Sean Wang

From: Javier Tia <floss@jetm.me>

Disable PCIe ASPM unconditionally for MT7927. The CONNINFRA power
domain and WFDMA register access are unreliable with PCIe L1 active,
causing throughput to drop from 1+ Gbps to ~200 Mbps.

Disable runtime PM and deep sleep for MT7927. The combo chip shares
a CONNINFRA power domain between WiFi (PCIe) and BT (USB).
SET_OWN/CLR_OWN transitions on the LPCTL register crash the BT
firmware, requiring a full power cycle to recover. PM enablement will
be addressed in a follow-up once safe power state transitions are
determined.

Reviewed-by: Sean Wang <sean.wang@mediatek.com>
Signed-off-by: Javier Tia <floss@jetm.me>
---
 drivers/net/wireless/mediatek/mt76/mt7925/init.c | 3 ++-
 drivers/net/wireless/mediatek/mt76/mt7925/pci.c  | 6 ++++--
 2 files changed, 6 insertions(+), 3 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/init.c b/drivers/net/wireless/mediatek/mt76/mt7925/init.c
index c0c5cb9aff75..a8c2ca7c0efc 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/init.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/init.c
@@ -232,7 +232,8 @@ int mt7925_register_device(struct mt792x_dev *dev)
 	dev->pm.idle_timeout = MT792x_PM_TIMEOUT;
 	dev->pm.stats.last_wake_event = jiffies;
 	dev->pm.stats.last_doze_event = jiffies;
-	if (!mt76_is_usb(&dev->mt76)) {
+	/* MT7927: runtime PM crashes BT firmware on the shared CONNINFRA domain */
+	if (!mt76_is_usb(&dev->mt76) && !is_mt7927(&dev->mt76)) {
 		dev->pm.enable_user = true;
 		dev->pm.enable = true;
 		dev->pm.ds_enable_user = true;
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
index 604c0e9ae7ba..1f05c212be02 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
@@ -350,7 +350,10 @@ static int mt7925_pci_probe(struct pci_dev *pdev,
 	if (ret)
 		goto err_free_pci_vec;
 
-	if (mt7925_disable_aspm)
+	is_mt7927_hw = (pdev->device == 0x6639 || pdev->device == 0x7927);
+
+	/* MT7927: ASPM L1 causes unreliable WFDMA register access */
+	if (mt7925_disable_aspm || is_mt7927_hw)
 		mt76_pci_disable_aspm(pdev);
 
 	ops = mt792x_get_mac80211_ops(&pdev->dev, &mt7925_ops,
@@ -371,7 +374,6 @@ static int mt7925_pci_probe(struct pci_dev *pdev,
 	dev = container_of(mdev, struct mt792x_dev, mt76);
 	dev->fw_features = features;
 	dev->hif_ops = &mt7925_pcie_ops;
-	is_mt7927_hw = (pdev->device == 0x6639 || pdev->device == 0x7927);
 	dev->irq_map = is_mt7927_hw ? &mt7927_irq_map : &irq_map;
 	mt76_mmio_init(&dev->mt76, pcim_iomap_table(pdev)[0]);
 	tasklet_init(&mdev->irq_tasklet, mt792x_irq_tasklet, (unsigned long)dev);
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 10/21] wifi: mt76: connac: replace is_mt7925() with is_connac3()
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (8 preceding siblings ...)
  2026-04-25 19:49 ` [PATCH v5 09/21] wifi: mt76: mt7925: disable ASPM and runtime PM for MT7927 Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 11/21] wifi: mt76: mt7925: use link-specific removal for non-MLD STA Sean Wang
                   ` (10 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

Use is_connac3() instead of is_mt7925() to avoid confusion
when more chips join.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 drivers/net/wireless/mediatek/mt76/mt76_connac.h     | 7 ++++++-
 drivers/net/wireless/mediatek/mt76/mt76_connac_mac.c | 4 ++--
 drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c | 4 ++--
 drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h | 2 +-
 drivers/net/wireless/mediatek/mt76/mt792x_usb.c      | 2 +-
 5 files changed, 12 insertions(+), 7 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac.h b/drivers/net/wireless/mediatek/mt76/mt76_connac.h
index 45479cc29134..1994863dc59d 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac.h
@@ -172,11 +172,16 @@ struct mt76_connac_tx_free {
 
 extern const struct wiphy_wowlan_support mt76_connac_wowlan_support;
 
-static inline bool is_mt7925(struct mt76_dev *dev)
+static inline bool is_connac3(struct mt76_dev *dev)
 {
 	return mt76_chip(dev) == 0x7925 || mt76_chip(dev) == 0x7927;
 }
 
+static inline bool is_mt7925(struct mt76_dev *dev)
+{
+	return mt76_chip(dev) == 0x7925;
+}
+
 static inline bool is_mt7927(struct mt76_dev *dev)
 {
 	return mt76_chip(dev) == 0x7927;
diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac_mac.c b/drivers/net/wireless/mediatek/mt76/mt76_connac_mac.c
index 0339e2e7ab60..c341595e9138 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac_mac.c
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac_mac.c
@@ -173,7 +173,7 @@ void mt76_connac_write_hw_txp(struct mt76_dev *dev,
 
 	txp->msdu_id[0] = cpu_to_le16(id | MT_MSDU_ID_VALID);
 
-	if (is_mt7663(dev) || is_connac2(dev) || is_mt7925(dev))
+	if (is_mt7663(dev) || is_connac2(dev) || is_connac3(dev))
 		last_mask = MT_TXD_LEN_LAST;
 	else
 		last_mask = MT_TXD_LEN_AMSDU_LAST |
@@ -217,7 +217,7 @@ mt76_connac_txp_skb_unmap_hw(struct mt76_dev *dev,
 	u32 last_mask;
 	int i;
 
-	if (is_mt7663(dev) || is_connac2(dev) || is_mt7925(dev))
+	if (is_mt7663(dev) || is_connac2(dev) || is_connac3(dev))
 		last_mask = MT_TXD_LEN_LAST;
 	else
 		last_mask = MT_TXD_LEN_MSDU_LAST;
diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c
index 89bd52ea8bf7..2b1c887d6709 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c
@@ -67,7 +67,7 @@ int mt76_connac_mcu_init_download(struct mt76_dev *dev, u32 addr, u32 len,
 
 	if ((!is_connac_v1(dev) && addr == MCU_PATCH_ADDRESS) ||
 	    (is_connac2(dev) && addr == 0x900000) ||
-	    (is_mt7925(dev) && (addr == 0x900000 || addr == 0xe0002800)) ||
+	    (is_connac3(dev) && (addr == 0x900000 || addr == 0xe0002800)) ||
 	    (is_mt799x(dev) && addr == 0x900000))
 		cmd = MCU_CMD(PATCH_START_REQ);
 	else
@@ -3084,7 +3084,7 @@ static u32 mt76_connac2_get_data_mode(struct mt76_dev *dev, u32 info)
 {
 	u32 mode = DL_MODE_NEED_RSP;
 
-	if ((!is_connac2(dev) && !is_mt7925(dev)) || info == PATCH_SEC_NOT_SUPPORT)
+	if ((!is_connac2(dev) && !is_connac3(dev)) || info == PATCH_SEC_NOT_SUPPORT)
 		return mode;
 
 	switch (FIELD_GET(PATCH_SEC_ENC_TYPE_MASK, info)) {
diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
index ac5126ab68ff..552cb94edaa0 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
@@ -1878,7 +1878,7 @@ mt76_connac_mcu_gen_dl_mode(struct mt76_dev *dev, u8 feature_set, bool is_wa)
 
 	ret |= feature_set & FW_FEATURE_SET_ENCRYPT ?
 	       DL_MODE_ENCRYPT | DL_MODE_RESET_SEC_IV : 0;
-	if (is_connac2(dev) || is_mt7925(dev))
+	if (is_connac2(dev) || is_connac3(dev))
 		ret |= feature_set & FW_FEATURE_ENCRY_MODE ?
 		       DL_CONFIG_ENCRY_MODE_SEL : 0;
 	ret |= FIELD_PREP(DL_MODE_KEY_IDX,
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_usb.c b/drivers/net/wireless/mediatek/mt76/mt792x_usb.c
index 47827d1c5ccb..7bb9840112ac 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_usb.c
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_usb.c
@@ -263,7 +263,7 @@ EXPORT_SYMBOL_GPL(mt792xu_dma_init);
 
 int mt792xu_wfsys_reset(struct mt792x_dev *dev)
 {
-	const struct mt792xu_wfsys_desc *desc = is_mt7925(&dev->mt76) ?
+	const struct mt792xu_wfsys_desc *desc = is_connac3(&dev->mt76) ?
 						&mt7925_wfsys_desc :
 						&mt7921_wfsys_desc;
 	u32 val;
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 11/21] wifi: mt76: mt7925: use link-specific removal for non-MLD STA
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (9 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 10/21] wifi: mt76: connac: replace is_mt7925() with is_connac3() Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 12/21] wifi: mt76: connac: tolerate inactive BSS deactivation Sean Wang
                   ` (9 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

Use the default link removal path for non-MLD STA instead of the
multi-link flow.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 drivers/net/wireless/mediatek/mt76/mt7925/main.c | 12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/main.c b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
index bf38d6502970..044043a8768d 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/main.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
@@ -1338,14 +1338,14 @@ void mt7925_mac_sta_remove(struct mt76_dev *mdev, struct ieee80211_vif *vif,
 	struct mt792x_dev *dev = container_of(mdev, struct mt792x_dev, mt76);
 	struct mt792x_sta *msta = (struct mt792x_sta *)sta->drv_priv;
 	struct mt792x_vif *mvif = (struct mt792x_vif *)vif->drv_priv;
-	unsigned long rem;
 
-	rem = ieee80211_vif_is_mld(vif) ? msta->valid_links : BIT(0);
-
-	mt7925_mac_sta_remove_links(dev, vif, sta, rem);
-
-	if (ieee80211_vif_is_mld(vif))
+	if (ieee80211_vif_is_mld(vif)) {
+		mt7925_mac_sta_remove_links(dev, vif, sta, msta->valid_links);
 		mt7925_mcu_del_dev(mdev, vif);
+	} else {
+		mt7925_mac_link_sta_remove(mdev, vif, &sta->deflink,
+					   &msta->deflink);
+	}
 
 	if (vif->type == NL80211_IFTYPE_STATION) {
 		mvif->wep_sta = NULL;
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 12/21] wifi: mt76: connac: tolerate inactive BSS deactivation
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (10 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 11/21] wifi: mt76: mt7925: use link-specific removal for non-MLD STA Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 13/21] wifi: mt76: mt792x: add MT7927 WFSYS reset support Sean Wang
                   ` (8 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

Firmware may return wlan_failure when deactivating a BSS that is already
inactive. This is a valid teardown case and should not fail the remove
path.

Keep activation failures unchanged since they still indicate that firmware
failed to create or activate the BSS state.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 .../wireless/mediatek/mt76/mt76_connac_mcu.c  |  9 +++++++-
 .../wireless/mediatek/mt76/mt76_connac_mcu.h  | 23 +++++++++++++++++++
 .../net/wireless/mediatek/mt76/mt7925/mcu.c   |  6 +++--
 3 files changed, 35 insertions(+), 3 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c
index 2b1c887d6709..0f2d580c7b4a 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.c
@@ -1227,6 +1227,9 @@ int mt76_connac_mcu_uni_add_dev(struct mt76_phy *phy,
 	len = enable ? sizeof(dev_req) : sizeof(basic_req);
 
 	err = mt76_mcu_send_msg(dev, cmd, data, len, true);
+	if (err && cmd == MCU_UNI_CMD(BSS_INFO_UPDATE))
+		err = mt76_connac_mcu_bss_deact_err(dev, err, enable);
+
 	if (err < 0)
 		return err;
 
@@ -1234,7 +1237,11 @@ int mt76_connac_mcu_uni_add_dev(struct mt76_phy *phy,
 	data = enable ? (void *)&basic_req : (void *)&dev_req;
 	len = enable ? sizeof(basic_req) : sizeof(dev_req);
 
-	return mt76_mcu_send_msg(dev, cmd, data, len, true);
+	err = mt76_mcu_send_msg(dev, cmd, data, len, true);
+	if (err && cmd == MCU_UNI_CMD(BSS_INFO_UPDATE))
+		err = mt76_connac_mcu_bss_deact_err(dev, err, enable);
+
+	return err;
 }
 EXPORT_SYMBOL_GPL(mt76_connac_mcu_uni_add_dev);
 
diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
index 552cb94edaa0..4691b9b5e2be 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
@@ -1906,6 +1906,29 @@ mt76_connac_mcu_get_wlan_idx(struct mt76_dev *dev, struct mt76_wcid *wcid,
 	}
 }
 
+#define MT76_CONNAC_MCU_STATUS_WLAN_FAILURE	0xc0000001
+
+static inline int
+mt76_connac_mcu_bss_deact_err(struct mt76_dev *mdev, int err, bool enable)
+{
+	if (err != (int)MT76_CONNAC_MCU_STATUS_WLAN_FAILURE)
+		return err;
+
+	/* Ignore wlan_failure state false alarm when deactivating an
+	 * inactive network. It does not harm the firmware state.
+	 */
+	if (!enable) {
+		dev_dbg(mdev->dev,
+			"ignore wlan_failure when bss is deactivated\n");
+		return 0;
+	}
+
+	dev_warn(mdev->dev,
+		 "wlan_failure when bss is activated\n");
+
+	return err;
+}
+
 struct sk_buff *
 __mt76_connac_mcu_alloc_sta_req(struct mt76_dev *dev, struct mt76_vif_link *mvif,
 				struct mt76_wcid *wcid, int len);
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
index f403d9d925e3..b338d6bf02f5 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
@@ -2832,6 +2832,7 @@ int mt7925_mcu_add_bss_info_sta(struct mt792x_phy *phy,
 	struct mt792x_bss_conf *mconf = mt792x_link_conf_to_mconf(link_conf);
 	struct mt792x_dev *dev = phy->dev;
 	struct sk_buff *skb;
+	int err;
 
 	skb = __mt7925_mcu_alloc_bss_req(&dev->mt76, &mconf->mt76,
 					 MT7925_BSS_UPDATE_MAX_SIZE);
@@ -2857,8 +2858,9 @@ int mt7925_mcu_add_bss_info_sta(struct mt792x_phy *phy,
 		mt7925_mcu_bss_mbssid_tlv(skb, link_conf, enable);
 	}
 
-	return mt76_mcu_skb_send_msg(&dev->mt76, skb,
-				     MCU_UNI_CMD(BSS_INFO_UPDATE), true);
+	err = mt76_mcu_skb_send_msg(&dev->mt76, skb,
+				    MCU_UNI_CMD(BSS_INFO_UPDATE), true);
+	return mt76_connac_mcu_bss_deact_err(&dev->mt76, err, enable);
 }
 
 int mt7925_mcu_add_bss_info(struct mt792x_phy *phy,
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 13/21] wifi: mt76: mt792x: add MT7927 WFSYS reset support
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (11 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 12/21] wifi: mt76: connac: tolerate inactive BSS deactivation Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 14/21] wifi: mt76: mt792x: factor out common DMA queue allocation Sean Wang
                   ` (7 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

Add a dedicated MT7927 WFSYS reset path in mt792x_wfsys_reset().

Unlike the existing connac2/connac3 reset flow that toggles the WFSYS
software reset bit and waits for init-done, MT7927 reset is driven
through CBInfra and requires polling ROMCODE_INDEX until the MCU returns
to the idle value after reset.

Keep this dormant for now: no MT7927 PCI IDs are added by this patch, so
it only prepares the reset logic without making the driver bind to MT7927
hardware yet.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 .../net/wireless/mediatek/mt76/mt792x_dma.c   | 57 ++++++++++++++++++-
 .../net/wireless/mediatek/mt76/mt792x_regs.h  | 11 ++++
 2 files changed, 67 insertions(+), 1 deletion(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
index 002aece857b2..2835bf273154 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
@@ -370,7 +370,54 @@ int mt792x_poll_rx(struct napi_struct *napi, int budget)
 }
 EXPORT_SYMBOL_GPL(mt792x_poll_rx);
 
-int mt792x_wfsys_reset(struct mt792x_dev *dev)
+static void mt7927_sema_status_read(struct mt792x_dev *dev, u32 addr)
+{
+	u32 remap;
+
+	remap = mt76_rr(dev, MT7927_PCIE2AP_REMAP_WF_0_54);
+	mt76_wr(dev, MT7927_PCIE2AP_REMAP_WF_0_54,
+		(remap & ~MT7927_PCIE2AP_REMAP_WF_0_54_MASK) |
+		MT7927_PCIE2AP_REMAP_WF_0_54_VAL);
+	usleep_range(10, 20);
+
+	mt76_rr(dev, addr);
+
+	mt76_wr(dev, MT7927_PCIE2AP_REMAP_WF_0_54, remap);
+	usleep_range(10, 20);
+}
+
+static int mt7927_wfsys_reset(struct mt792x_dev *dev)
+{
+	struct mt76_dev *mdev = &dev->mt76;
+	u32 val;
+
+	mt7927_sema_status_read(dev, MT7927_SEMA_OWN_STA);
+
+	mt76_set(dev, MT7927_CBINFRA_RGU_WF_RST,
+		 MT7927_CBINFRA_RGU_WF_RST_WF_SUBSYS);
+	usleep_range(1000, 2000);
+
+	mt76_clear(dev, MT7927_CBINFRA_RGU_WF_RST,
+		   MT7927_CBINFRA_RGU_WF_RST_WF_SUBSYS);
+	usleep_range(5000, 10000);
+
+	mt76_wr(dev, MT7927_CBINFRA_MCU_OWN_SET, BIT(0));
+
+	if (!__mt76_poll_msec(mdev, MT7927_ROMCODE_INDEX, 0xffff,
+			      MT7927_MCU_IDLE_VALUE, 200)) {
+		val = mt76_rr(dev, MT7927_ROMCODE_INDEX);
+		dev_err(mdev->dev,
+			"MT7927 WFSYS reset timeout (ROMCODE_INDEX=0x%04x)\n",
+			val & 0xffff);
+		return -ETIMEDOUT;
+	}
+
+	mt7927_sema_status_read(dev, MT7927_SEMA_OWN_STA_REP);
+
+	return 0;
+}
+
+static int mt792x_wfsys_reset_default(struct mt792x_dev *dev)
 {
 	u32 addr = is_connac2(&dev->mt76) ? 0x18000140 : 0x7c000140;
 
@@ -384,5 +431,13 @@ int mt792x_wfsys_reset(struct mt792x_dev *dev)
 
 	return 0;
 }
+
+int mt792x_wfsys_reset(struct mt792x_dev *dev)
+{
+	if (is_mt7927(&dev->mt76))
+		return mt7927_wfsys_reset(dev);
+
+	return mt792x_wfsys_reset_default(dev);
+}
 EXPORT_SYMBOL_GPL(mt792x_wfsys_reset);
 
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_regs.h b/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
index 20d27ae89aca..17504ef8e80d 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
@@ -493,4 +493,15 @@
 #define WFSYS_SW_RST_B			BIT(0)
 #define WFSYS_SW_INIT_DONE		BIT(4)
 
+/* CBInfra registers - MT7927 combo chip */
+#define MT7927_CBINFRA_RGU_WF_RST		0x1f8600
+#define MT7927_CBINFRA_RGU_WF_RST_WF_SUBSYS	BIT(4)
+#define MT7927_CBINFRA_MCU_OWN_SET		0x1f5034
+#define MT7927_ROMCODE_INDEX			0xc1604
+#define MT7927_MCU_IDLE_VALUE			0x1d1e
+#define MT7927_PCIE2AP_REMAP_WF_0_54		0x21008
+#define MT7927_PCIE2AP_REMAP_WF_0_54_MASK	GENMASK(15, 0)
+#define MT7927_PCIE2AP_REMAP_WF_0_54_VAL	0x00001807
+#define MT7927_SEMA_OWN_STA			0x40000
+#define MT7927_SEMA_OWN_STA_REP			0x40400
 #endif /* __MT792X_REGS_H */
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 14/21] wifi: mt76: mt792x: factor out common DMA queue allocation
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (12 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 13/21] wifi: mt76: mt792x: add MT7927 WFSYS reset support Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 15/21] wifi: mt76: mt7925: switch DMA init to common mt792x queue helpers Sean Wang
                   ` (6 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

The mt792x PCIe DMA setup uses the same standard queue allocation
sequence for data, MCU, firmware download and RX rings.

Factor this part out into a small common helper so later chip support
can reuse the existing flow without duplicating the queue setup logic.

This keeps the common DMA skeleton in one place and makes follow-up
chip-specific DMA changes smaller and easier to review.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 drivers/net/wireless/mediatek/mt76/mt792x.h   | 19 +++++++
 .../net/wireless/mediatek/mt76/mt792x_dma.c   | 56 +++++++++++++++++++
 2 files changed, 75 insertions(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt792x.h b/drivers/net/wireless/mediatek/mt76/mt792x.h
index 09840483fe2a..59562567cc13 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x.h
+++ b/drivers/net/wireless/mediatek/mt76/mt792x.h
@@ -206,6 +206,23 @@ struct mt792x_irq_map {
 	} rx;
 };
 
+struct mt792x_dma_ring {
+	u8 qid;
+	u16 n_desc;
+	u32 ring_base;
+};
+
+struct mt792x_dma_layout {
+	struct mt792x_dma_ring tx_data0;
+	struct mt792x_dma_ring tx_mcu;
+	struct mt792x_dma_ring tx_fwdl;
+	struct mt792x_dma_ring rx_data;
+	struct mt792x_dma_ring rx_mcu;
+};
+
+#define mt792x_dma_ring(_qid, _n_desc, _ring_base) \
+	{ .qid = (_qid), .n_desc = (_n_desc), .ring_base = (_ring_base) }
+
 #define mt792x_init_reset(dev)		((dev)->hif_ops->init_reset(dev))
 #define mt792x_dev_reset(dev)		((dev)->hif_ops->reset(dev))
 #define mt792x_mcu_init(dev)		((dev)->hif_ops->mcu_init(dev))
@@ -421,6 +438,8 @@ void mt792x_sta_statistics(struct ieee80211_hw *hw,
 void mt792x_set_coverage_class(struct ieee80211_hw *hw, int radio_idx,
 			       s16 coverage_class);
 void mt792x_dma_cleanup(struct mt792x_dev *dev);
+int mt792x_dma_alloc_queues(struct mt792x_dev *dev,
+			    const struct mt792x_dma_layout *layout);
 int mt792x_dma_enable(struct mt792x_dev *dev);
 int mt792x_wpdma_reset(struct mt792x_dev *dev, bool force);
 int mt792x_wpdma_reinit_cond(struct mt792x_dev *dev);
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
index 2835bf273154..c52d0c85913c 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
@@ -87,6 +87,62 @@ void mt792x_rx_poll_complete(struct mt76_dev *mdev, enum mt76_rxq_id q)
 }
 EXPORT_SYMBOL_GPL(mt792x_rx_poll_complete);
 
+int mt792x_dma_alloc_queues(struct mt792x_dev *dev,
+			    const struct mt792x_dma_layout *layout)
+{
+	int ret;
+
+	mt76_dma_attach(&dev->mt76);
+
+	ret = mt792x_dma_disable(dev, true);
+	if (ret)
+		return ret;
+
+	/* init tx queue */
+	ret = mt76_connac_init_tx_queues(dev->phy.mt76, layout->tx_data0.qid,
+					 layout->tx_data0.n_desc,
+					 layout->tx_data0.ring_base,
+					 NULL, 0);
+	if (ret)
+		return ret;
+
+	mt76_wr(dev, MT_WFDMA0_TX_RING0_EXT_CTRL, 0x4);
+
+	/* command to WM */
+	ret = mt76_init_mcu_queue(&dev->mt76, MT_MCUQ_WM,
+				  layout->tx_mcu.qid,
+				  layout->tx_mcu.n_desc,
+				  layout->tx_mcu.ring_base);
+	if (ret)
+		return ret;
+
+	/* firmware download */
+	ret = mt76_init_mcu_queue(&dev->mt76, MT_MCUQ_FWDL,
+				  layout->tx_fwdl.qid,
+				  layout->tx_fwdl.n_desc,
+				  layout->tx_fwdl.ring_base);
+	if (ret)
+		return ret;
+
+	/* rx event */
+	ret = mt76_queue_alloc(dev, &dev->mt76.q_rx[MT_RXQ_MCU],
+			       layout->rx_mcu.qid,
+			       layout->rx_mcu.n_desc,
+			       MT_RX_BUF_SIZE,
+			       layout->rx_mcu.ring_base);
+	if (ret)
+		return ret;
+
+	/* rx data */
+	ret = mt76_queue_alloc(dev, &dev->mt76.q_rx[MT_RXQ_MAIN],
+			       layout->rx_data.qid,
+			       layout->rx_data.n_desc,
+			       MT_RX_BUF_SIZE,
+			       layout->rx_data.ring_base);
+	return ret;
+}
+EXPORT_SYMBOL_GPL(mt792x_dma_alloc_queues);
+
 #define PREFETCH(base, depth)	((base) << 16 | (depth))
 static void mt792x_dma_prefetch(struct mt792x_dev *dev)
 {
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 15/21] wifi: mt76: mt7925: switch DMA init to common mt792x queue helpers
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (13 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 14/21] wifi: mt76: mt792x: factor out common DMA queue allocation Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 16/21] wifi: mt76: mt792x: add MT7927-specific PCIe DMA support Sean Wang
                   ` (5 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

Convert mt7925 DMA init to use the common mt792x queue allocation
helper and isolate the mt7925-specific prefetch/WFDMA setup.

This removes duplicated DMA setup code and prepares the path for
follow-up chip-specific DMA support with smaller deltas.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 .../net/wireless/mediatek/mt76/mt7925/pci.c   | 57 +++++++------------
 .../net/wireless/mediatek/mt76/mt792x_dma.c   | 46 +++++++++------
 2 files changed, 48 insertions(+), 55 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
index 1f05c212be02..39c663687c3c 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
@@ -210,48 +210,29 @@ static u32 mt7925_rmw(struct mt76_dev *mdev, u32 offset, u32 mask, u32 val)
 	return dev->bus_ops->rmw(mdev, addr, mask, val);
 }
 
+static const struct mt792x_dma_layout mt7925_dma_layout = {
+	.tx_data0 = mt792x_dma_ring(MT7925_TXQ_BAND0,
+				    MT7925_TX_RING_SIZE,
+				    MT_TX_RING_BASE),
+	.tx_mcu = mt792x_dma_ring(MT7925_TXQ_MCU_WM,
+				  MT7925_TX_MCU_RING_SIZE,
+				  MT_TX_RING_BASE),
+	.tx_fwdl = mt792x_dma_ring(MT7925_TXQ_FWDL,
+				   MT7925_TX_FWDL_RING_SIZE,
+				   MT_TX_RING_BASE),
+	.rx_mcu = mt792x_dma_ring(MT7925_RXQ_MCU_WM,
+				  MT7925_RX_MCU_RING_SIZE,
+				  MT_RX_EVENT_RING_BASE),
+	.rx_data = mt792x_dma_ring(MT7925_RXQ_BAND0,
+				   MT7925_RX_RING_SIZE,
+				   MT_RX_DATA_RING_BASE),
+};
+
 static int mt7925_dma_init(struct mt792x_dev *dev)
 {
 	int ret;
 
-	mt76_dma_attach(&dev->mt76);
-
-	ret = mt792x_dma_disable(dev, true);
-	if (ret)
-		return ret;
-
-	/* init tx queue */
-	ret = mt76_connac_init_tx_queues(dev->phy.mt76, MT7925_TXQ_BAND0,
-					 MT7925_TX_RING_SIZE,
-					 MT_TX_RING_BASE, NULL, 0);
-	if (ret)
-		return ret;
-
-	mt76_wr(dev, MT_WFDMA0_TX_RING0_EXT_CTRL, 0x4);
-
-	/* command to WM */
-	ret = mt76_init_mcu_queue(&dev->mt76, MT_MCUQ_WM, MT7925_TXQ_MCU_WM,
-				  MT7925_TX_MCU_RING_SIZE, MT_TX_RING_BASE);
-	if (ret)
-		return ret;
-
-	/* firmware download */
-	ret = mt76_init_mcu_queue(&dev->mt76, MT_MCUQ_FWDL, MT7925_TXQ_FWDL,
-				  MT7925_TX_FWDL_RING_SIZE, MT_TX_RING_BASE);
-	if (ret)
-		return ret;
-
-	/* rx event */
-	ret = mt76_queue_alloc(dev, &dev->mt76.q_rx[MT_RXQ_MCU],
-			       MT7925_RXQ_MCU_WM, MT7925_RX_MCU_RING_SIZE,
-			       MT_RX_BUF_SIZE, MT_RX_EVENT_RING_BASE);
-	if (ret)
-		return ret;
-
-	/* rx data */
-	ret = mt76_queue_alloc(dev, &dev->mt76.q_rx[MT_RXQ_MAIN],
-			       MT7925_RXQ_BAND0, MT7925_RX_RING_SIZE,
-			       MT_RX_BUF_SIZE, MT_RX_DATA_RING_BASE);
+	ret = mt792x_dma_alloc_queues(dev, &mt7925_dma_layout);
 	if (ret)
 		return ret;
 
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
index c52d0c85913c..7b36f0761dd1 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
@@ -144,21 +144,35 @@ int mt792x_dma_alloc_queues(struct mt792x_dev *dev,
 EXPORT_SYMBOL_GPL(mt792x_dma_alloc_queues);
 
 #define PREFETCH(base, depth)	((base) << 16 | (depth))
+
+static void mt7925_dma_prefetch_setup(struct mt792x_dev *dev)
+{
+	/* rx ring */
+	mt76_wr(dev, MT_WFDMA0_RX_RING0_EXT_CTRL, PREFETCH(0x0000, 0x4));
+	mt76_wr(dev, MT_WFDMA0_RX_RING1_EXT_CTRL, PREFETCH(0x0040, 0x4));
+	mt76_wr(dev, MT_WFDMA0_RX_RING2_EXT_CTRL, PREFETCH(0x0080, 0x4));
+	mt76_wr(dev, MT_WFDMA0_RX_RING3_EXT_CTRL, PREFETCH(0x00c0, 0x4));
+
+	/* tx ring */
+	mt76_wr(dev, MT_WFDMA0_TX_RING0_EXT_CTRL, PREFETCH(0x0100, 0x10));
+	mt76_wr(dev, MT_WFDMA0_TX_RING1_EXT_CTRL, PREFETCH(0x0200, 0x10));
+	mt76_wr(dev, MT_WFDMA0_TX_RING2_EXT_CTRL, PREFETCH(0x0300, 0x10));
+	mt76_wr(dev, MT_WFDMA0_TX_RING3_EXT_CTRL, PREFETCH(0x0400, 0x10));
+	mt76_wr(dev, MT_WFDMA0_TX_RING15_EXT_CTRL, PREFETCH(0x0500, 0x4));
+	mt76_wr(dev, MT_WFDMA0_TX_RING16_EXT_CTRL, PREFETCH(0x0540, 0x4));
+}
+
+static void mt7925_wfdma_setup(struct mt792x_dev *dev)
+{
+	mt76_rmw(dev, MT_UWFDMA0_GLO_CFG_EXT1, BIT(28), BIT(28));
+	mt76_set(dev, MT_WFDMA0_INT_RX_PRI, 0x0F00);
+	mt76_set(dev, MT_WFDMA0_INT_TX_PRI, 0x7F00);
+}
+
 static void mt792x_dma_prefetch(struct mt792x_dev *dev)
 {
 	if (is_mt7925(&dev->mt76)) {
-		/* rx ring */
-		mt76_wr(dev, MT_WFDMA0_RX_RING0_EXT_CTRL, PREFETCH(0x0000, 0x4));
-		mt76_wr(dev, MT_WFDMA0_RX_RING1_EXT_CTRL, PREFETCH(0x0040, 0x4));
-		mt76_wr(dev, MT_WFDMA0_RX_RING2_EXT_CTRL, PREFETCH(0x0080, 0x4));
-		mt76_wr(dev, MT_WFDMA0_RX_RING3_EXT_CTRL, PREFETCH(0x00c0, 0x4));
-		/* tx ring */
-		mt76_wr(dev, MT_WFDMA0_TX_RING0_EXT_CTRL, PREFETCH(0x0100, 0x10));
-		mt76_wr(dev, MT_WFDMA0_TX_RING1_EXT_CTRL, PREFETCH(0x0200, 0x10));
-		mt76_wr(dev, MT_WFDMA0_TX_RING2_EXT_CTRL, PREFETCH(0x0300, 0x10));
-		mt76_wr(dev, MT_WFDMA0_TX_RING3_EXT_CTRL, PREFETCH(0x0400, 0x10));
-		mt76_wr(dev, MT_WFDMA0_TX_RING15_EXT_CTRL, PREFETCH(0x0500, 0x4));
-		mt76_wr(dev, MT_WFDMA0_TX_RING16_EXT_CTRL, PREFETCH(0x0540, 0x4));
+		mt7925_dma_prefetch_setup(dev);
 	} else if (is_mt7902(&dev->mt76)) {
 		/* rx ring */
 		mt76_wr(dev, MT_WFDMA0_RX_RING0_EXT_CTRL, PREFETCH(0x0000, 0x4));
@@ -222,11 +236,9 @@ int mt792x_dma_enable(struct mt792x_dev *dev)
 	mt76_set(dev, MT_WFDMA0_GLO_CFG,
 		 MT_WFDMA0_GLO_CFG_TX_DMA_EN | MT_WFDMA0_GLO_CFG_RX_DMA_EN);
 
-	if (is_mt7925(&dev->mt76)) {
-		mt76_rmw(dev, MT_UWFDMA0_GLO_CFG_EXT1, BIT(28), BIT(28));
-		mt76_set(dev, MT_WFDMA0_INT_RX_PRI, 0x0F00);
-		mt76_set(dev, MT_WFDMA0_INT_TX_PRI, 0x7F00);
-	}
+	if (is_mt7925(&dev->mt76))
+		mt7925_wfdma_setup(dev);
+
 	mt76_set(dev, MT_WFDMA_DUMMY_CR, MT_WFDMA_NEED_REINIT);
 
 	/* enable interrupts for TX/RX rings */
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 16/21] wifi: mt76: mt792x: add MT7927-specific PCIe DMA support
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (14 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 15/21] wifi: mt76: mt7925: switch DMA init to common mt792x queue helpers Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 17/21] wifi: mt76: mt7925: sync MT7927 BSS band assignment Sean Wang
                   ` (4 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Sean Wang, Javier Tia

From: Sean Wang <sean.wang@mediatek.com>

Add the MT7927-specific PCIe DMA queue layout and local DMA setup,
including the extra RX ring and WFDMA/prefetch programming.

MT7927 does not follow the mt7925 DMA configuration, so provide a
separate DMA init path while reusing the existing common queue setup.

This keeps the chip-specific changes local and prepares the driver
for later MT7927 enablement without affecting existing devices.

Co-developed-by: Javier Tia <floss@jetm.me>
Signed-off-by: Javier Tia <floss@jetm.me>
Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 .../wireless/mediatek/mt76/mt7925/mt7925.h    | 13 +++++
 .../net/wireless/mediatek/mt76/mt7925/pci.c   | 53 ++++++++++++++++++-
 .../net/wireless/mediatek/mt76/mt792x_dma.c   | 41 +++++++++++++-
 .../net/wireless/mediatek/mt76/mt792x_regs.h  |  9 ++++
 4 files changed, 113 insertions(+), 3 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h b/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h
index 46b480f7d813..984be40ca76d 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h
@@ -126,6 +126,19 @@ enum mt7925_rxq_id {
 	MT7925_RXQ_MCU_WM2, /* for tx done */
 };
 
+enum mt7927_txq_id {
+	MT7927_TXQ_BAND0 = MT7925_TXQ_BAND0,
+	MT7927_TXQ_BAND1 = MT7925_TXQ_BAND1,
+	MT7927_TXQ_MCU_WM = MT7925_TXQ_MCU_WM,
+	MT7927_TXQ_FWDL = MT7925_TXQ_FWDL,
+};
+
+enum mt7927_rxq_id {
+	MT7927_RXQ_BAND0 = 4,
+	MT7927_RXQ_MCU_WM = 6,
+	MT7927_RXQ_DATA2 = 7,
+};
+
 enum {
 	MODE_OPEN = 0,
 	MODE_SHARED = 1,
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
index 39c663687c3c..7455cf7eddc5 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
@@ -228,6 +228,51 @@ static const struct mt792x_dma_layout mt7925_dma_layout = {
 				   MT_RX_DATA_RING_BASE),
 };
 
+static const struct mt792x_dma_layout mt7927_dma_layout = {
+	.tx_data0 = mt792x_dma_ring(MT7927_TXQ_BAND0,
+				    MT7925_TX_RING_SIZE,
+				    MT_TX_RING_BASE),
+	.tx_mcu = mt792x_dma_ring(MT7927_TXQ_MCU_WM,
+				  MT7925_TX_MCU_RING_SIZE,
+				  MT_TX_RING_BASE),
+	.tx_fwdl = mt792x_dma_ring(MT7927_TXQ_FWDL,
+				   MT7925_TX_FWDL_RING_SIZE,
+				   MT_TX_RING_BASE),
+	.rx_mcu = mt792x_dma_ring(MT7927_RXQ_MCU_WM,
+				  MT7925_RX_MCU_RING_SIZE,
+				  MT_RX_EVENT_RING_BASE),
+	.rx_data = mt792x_dma_ring(MT7927_RXQ_BAND0,
+				   MT7925_RX_RING_SIZE,
+				   MT_RX_DATA_RING_BASE),
+};
+
+static int mt7927_dma_init(struct mt792x_dev *dev)
+{
+	int ret;
+
+	ret = mt792x_dma_alloc_queues(dev, &mt7927_dma_layout);
+	if (ret)
+		return ret;
+
+	ret = mt76_queue_alloc(dev, &dev->mt76.q_rx[MT_RXQ_MCU_WA],
+			       MT7927_RXQ_DATA2,
+			       MT7925_RX_MCU_RING_SIZE,
+			       MT_RX_BUF_SIZE,
+			       MT_RX_DATA_RING_BASE);
+	if (ret)
+		return ret;
+
+	ret = mt76_init_queues(dev, mt792x_poll_rx);
+	if (ret < 0)
+		return ret;
+
+	netif_napi_add_tx(dev->mt76.tx_napi_dev, &dev->mt76.tx_napi,
+			  mt792x_poll_tx);
+	napi_enable(&dev->mt76.tx_napi);
+
+	return mt792x_dma_enable(dev);
+}
+
 static int mt7925_dma_init(struct mt792x_dev *dev)
 {
 	int ret;
@@ -406,7 +451,13 @@ static int mt7925_pci_probe(struct pci_dev *pdev,
 	if (ret)
 		goto err_free_dev;
 
-	ret = mt7925_dma_init(dev);
+	if (is_mt7927(&dev->mt76))
+		ret = mt7927_dma_init(dev);
+	else if (is_mt7925(&dev->mt76))
+		ret = mt7925_dma_init(dev);
+	else
+		ret = -EINVAL;
+
 	if (ret)
 		goto err_free_irq;
 
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
index 7b36f0761dd1..fc326447c792 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_dma.c
@@ -169,9 +169,39 @@ static void mt7925_wfdma_setup(struct mt792x_dev *dev)
 	mt76_set(dev, MT_WFDMA0_INT_TX_PRI, 0x7F00);
 }
 
+static void mt7927_dma_prefetch_setup(struct mt792x_dev *dev)
+{
+	mt76_wr(dev, MT_WFDMA_PREFETCH_CTRL,
+		mt76_rr(dev, MT_WFDMA_PREFETCH_CTRL));
+	mt76_wr(dev, MT_WFDMA_PREFETCH_CFG0, 0x660077);
+	mt76_wr(dev, MT_WFDMA_PREFETCH_CFG1, 0x1100);
+	mt76_wr(dev, MT_WFDMA_PREFETCH_CFG2, 0x30004f);
+	mt76_wr(dev, MT_WFDMA_PREFETCH_CFG3, 0x542200);
+	mt76_wr(dev, MT_WFDMA0_RX_RING4_EXT_CTRL, PREFETCH(0x0000, 0x8));
+	mt76_wr(dev, MT_WFDMA0_RX_RING6_EXT_CTRL, PREFETCH(0x0080, 0x8));
+	mt76_wr(dev, MT_WFDMA0_RX_RING7_EXT_CTRL, PREFETCH(0x0100, 0x4));
+	mt76_wr(dev, MT_WFDMA0_TX_RING16_EXT_CTRL, PREFETCH(0x0140, 0x4));
+	mt76_wr(dev, MT_WFDMA0_TX_RING15_EXT_CTRL, PREFETCH(0x0180, 0x10));
+	mt76_wr(dev, MT_WFDMA0_TX_RING0_EXT_CTRL, PREFETCH(0x0280, 0x4));
+}
+
+static void mt7927_wfdma_setup(struct mt792x_dev *dev)
+{
+	mt76_set(dev, MT_WFDMA0_GLO_CFG,
+		 MT_WFDMA0_GLO_CFG_ADDR_EXT_EN |
+		 MT_WFDMA0_GLO_CFG_FW_DWLD_BYPASS_DMASHDL);
+	mt76_clear(dev, MT_WFDMA0_GLO_CFG,
+		   MT_WFDMA0_GLO_CFG_CSR_LBK_RX_Q_SEL_EN);
+	mt76_rmw(dev, MT_WFDMA0_GLO_CFG_EXT1, BIT(28), BIT(28));
+	mt76_set(dev, MT_WFDMA0_INT_RX_PRI, 0x0F00);
+	mt76_set(dev, MT_WFDMA0_INT_TX_PRI, 0x7F00);
+}
+
 static void mt792x_dma_prefetch(struct mt792x_dev *dev)
 {
-	if (is_mt7925(&dev->mt76)) {
+	if (is_mt7927(&dev->mt76)) {
+		mt7927_dma_prefetch_setup(dev);
+	} else if (is_mt7925(&dev->mt76)) {
 		mt7925_dma_prefetch_setup(dev);
 	} else if (is_mt7902(&dev->mt76)) {
 		/* rx ring */
@@ -236,7 +266,9 @@ int mt792x_dma_enable(struct mt792x_dev *dev)
 	mt76_set(dev, MT_WFDMA0_GLO_CFG,
 		 MT_WFDMA0_GLO_CFG_TX_DMA_EN | MT_WFDMA0_GLO_CFG_RX_DMA_EN);
 
-	if (is_mt7925(&dev->mt76))
+	if (is_mt7927(&dev->mt76))
+		mt7927_wfdma_setup(dev);
+	else if (is_mt7925(&dev->mt76))
 		mt7925_wfdma_setup(dev);
 
 	mt76_set(dev, MT_WFDMA_DUMMY_CR, MT_WFDMA_NEED_REINIT);
@@ -349,6 +381,11 @@ int mt792x_dma_disable(struct mt792x_dev *dev, bool force)
 				 MT_WFDMA0_GLO_CFG_RX_DMA_BUSY, 0, 100, 1))
 		return -ETIMEDOUT;
 
+	if (is_mt7927(&dev->mt76)) {
+		mt76_wr(dev, MT_WFDMA0_RST_DTX_PTR, ~0);
+		mt76_wr(dev, MT_WFDMA0_RST_DRX_PTR, ~0);
+	}
+
 	/* disable dmashdl */
 	mt76_clear(dev, MT_WFDMA0_GLO_CFG_EXT0,
 		   MT_WFDMA0_CSR_TX_DMASHDL_ENABLE);
diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_regs.h b/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
index 17504ef8e80d..4cd5b33b640e 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_regs.h
@@ -301,7 +301,9 @@
 #define MT_WFDMA0_GLO_CFG_FIFO_LITTLE_ENDIAN	BIT(12)
 #define MT_WFDMA0_GLO_CFG_RX_WB_DDONE	BIT(13)
 #define MT_WFDMA0_GLO_CFG_CSR_DISP_BASE_PTR_CHAIN_EN BIT(15)
+#define MT_WFDMA0_GLO_CFG_CSR_LBK_RX_Q_SEL_EN	BIT(20)
 #define MT_WFDMA0_GLO_CFG_OMIT_RX_INFO_PFET2	BIT(21)
+#define MT_WFDMA0_GLO_CFG_ADDR_EXT_EN		BIT(26)
 #define MT_WFDMA0_GLO_CFG_OMIT_RX_INFO	BIT(27)
 #define MT_WFDMA0_GLO_CFG_OMIT_TX_INFO	BIT(28)
 #define MT_WFDMA0_GLO_CFG_CLK_GAT_DIS	BIT(30)
@@ -368,6 +370,13 @@
 #define MT_WFDMA_EXT_CSR_HIF_MISC	MT_WFDMA_EXT_CSR(0x44)
 #define MT_WFDMA_EXT_CSR_HIF_MISC_BUSY	BIT(0)
 
+#define MT_WFDMA_PREFETCH_CTRL		MT_WFDMA_EXT_CSR(0x30)
+#define MT_WFDMA_PREFETCH_CFG0		MT_WFDMA_EXT_CSR(0xf0)
+#define MT_WFDMA_PREFETCH_CFG1		MT_WFDMA_EXT_CSR(0xf4)
+#define MT_WFDMA_PREFETCH_CFG2		MT_WFDMA_EXT_CSR(0xf8)
+#define MT_WFDMA_PREFETCH_CFG3		MT_WFDMA_EXT_CSR(0xfc)
+#define MT_WFDMA0_GLO_CFG_EXT1		MT_WFDMA0(0x2b4)
+
 #define MT_SWDEF_BASE			0x41f200
 #define MT_SWDEF(ofs)			(MT_SWDEF_BASE + (ofs))
 #define MT_SWDEF_MODE			MT_SWDEF(0x3c)
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 17/21] wifi: mt76: mt7925: sync MT7927 BSS band assignment
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (15 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 16/21] wifi: mt76: mt792x: add MT7927-specific PCIe DMA support Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 18/21] wifi: mt76: mt7925: add MBMC event handling Sean Wang
                   ` (3 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Sean Wang, Javier Tia

From: Sean Wang <sean.wang@mediatek.com>

MT7927 needs DBDC enabled and uses a fixed firmware band assignment for
2.4GHz and 5/6GHz BSS contexts.

Reprogram the STA dev context when the channel context is assigned so the
firmware sees the updated band_idx before the BSS is used. This avoids
stale band programming after band changes.

Co-developed-by: Javier Tia <floss@jetm.me>
Signed-off-by: Javier Tia <floss@jetm.me>
Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 .../net/wireless/mediatek/mt76/mt7925/init.c  |  9 ++++
 .../net/wireless/mediatek/mt76/mt7925/main.c  | 42 +++++++++++++++++++
 .../net/wireless/mediatek/mt76/mt7925/mcu.c   |  1 +
 .../wireless/mediatek/mt76/mt7925/mt7925.h    | 12 ++++++
 .../wireless/mediatek/mt76/mt7925/pci_mac.c   |  7 ++++
 5 files changed, 71 insertions(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/init.c b/drivers/net/wireless/mediatek/mt76/mt7925/init.c
index a8c2ca7c0efc..e85b0d104fbe 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/init.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/init.c
@@ -117,6 +117,15 @@ static int __mt7925_init_hardware(struct mt792x_dev *dev)
 	if (ret)
 		goto out;
 
+	if (is_mt7927(&dev->mt76)) {
+		ret = mt7925_mcu_set_dbdc(&dev->mphy, true);
+		if (ret) {
+			dev_warn(dev->mt76.dev,
+				 "MT7927 DBDC enable failed: %d\n", ret);
+			ret = 0;
+		}
+	}
+
 out:
 	return ret;
 }
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/main.c b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
index 044043a8768d..b36f5eb30371 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/main.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/main.c
@@ -396,6 +396,18 @@ static int mt7925_mac_link_bss_add(struct mt792x_dev *dev,
 	mconf->mt76.omac_idx = ieee80211_vif_is_mld(vif) ?
 			       0 : mconf->mt76.idx;
 	mconf->mt76.band_idx = 0xff;
+
+	if (is_mt7927(&dev->mt76)) {
+		struct ieee80211_channel *chan = NULL;
+
+		if (link_conf->chanreq.oper.chan)
+			chan = link_conf->chanreq.oper.chan;
+		else if (mvif->phy->mt76->chandef.chan)
+			chan = mvif->phy->mt76->chandef.chan;
+
+		mconf->mt76.band_idx = mt7927_band_idx(chan->band);
+	}
+
 	mconf->mt76.wmm_idx = ieee80211_vif_is_mld(vif) ?
 			      0 : mconf->mt76.idx % MT76_CONNAC_MAX_WMM_SETS;
 	mconf->mt76.link_idx = hweight16(mvif->valid_links);
@@ -2238,6 +2250,29 @@ mt7925_change_sta_links(struct ieee80211_hw *hw, struct ieee80211_vif *vif,
 	return err;
 }
 
+static int
+mt7927_reconfig_band(struct mt792x_dev *dev, struct ieee80211_vif *vif,
+		     struct ieee80211_bss_conf *link_conf,
+		     struct mt792x_bss_conf *mconf,
+		     u8 band_idx)
+{
+	struct mt792x_vif *mvif = (struct mt792x_vif *)vif->drv_priv;
+	struct mt792x_link_sta *mlink = &mvif->sta.deflink;
+	int ret;
+
+	ret = mt76_connac_mcu_uni_add_dev(&dev->mphy, link_conf,
+					  &mconf->mt76, &mlink->wcid,
+					  false);
+	if (ret)
+		return ret;
+
+	mconf->mt76.band_idx = band_idx;
+
+	return mt76_connac_mcu_uni_add_dev(&dev->mphy, link_conf,
+					   &mconf->mt76, &mlink->wcid,
+					   true);
+}
+
 static int mt7925_assign_vif_chanctx(struct ieee80211_hw *hw,
 				     struct ieee80211_vif *vif,
 				     struct ieee80211_bss_conf *link_conf,
@@ -2248,6 +2283,7 @@ static int mt7925_assign_vif_chanctx(struct ieee80211_hw *hw,
 	struct mt792x_dev *dev = mt792x_hw_dev(hw);
 	struct ieee80211_bss_conf *pri_link_conf;
 	struct mt792x_bss_conf *mconf;
+	u8 band_idx;
 
 	mutex_lock(&dev->mt76.mutex);
 
@@ -2261,6 +2297,12 @@ static int mt7925_assign_vif_chanctx(struct ieee80211_hw *hw,
 						NULL, true);
 	} else {
 		mconf = &mvif->bss_conf;
+
+		if (is_mt7927(&dev->mt76)) {
+			band_idx = mt7927_band_idx(ctx->def.chan->band);
+
+			mt7927_reconfig_band(dev, vif, link_conf, mconf, band_idx);
+		}
 	}
 
 	mconf->mt76.ctx = ctx;
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
index b338d6bf02f5..f7e14cc53dac 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
@@ -2918,6 +2918,7 @@ int mt7925_mcu_set_dbdc(struct mt76_phy *phy, bool enable)
 
 	return err;
 }
+EXPORT_SYMBOL_GPL(mt7925_mcu_set_dbdc);
 
 static void
 mt7925_mcu_build_scan_ie_tlv(struct mt76_dev *mdev,
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h b/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h
index 984be40ca76d..242f83f90dd4 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mt7925.h
@@ -252,6 +252,18 @@ struct mt7925_txpwr {
 	s8 eht996x3_484[16][2];
 };
 
+static inline u8 mt7927_band_idx(enum nl80211_band band)
+{
+	switch (band) {
+	case NL80211_BAND_2GHZ:
+		return 0;
+	case NL80211_BAND_5GHZ:
+	case NL80211_BAND_6GHZ:
+	default:
+		return 1;
+	}
+}
+
 extern const struct ieee80211_ops mt7925_ops;
 
 int __mt7925_start(struct mt792x_phy *phy);
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c
index 1626a3684082..97683949a305 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci_mac.c
@@ -3,6 +3,7 @@
 
 #include "mt7925.h"
 #include "../dma.h"
+#include "mcu.h"
 #include "mac.h"
 
 int mt7925e_tx_prepare_skb(struct mt76_dev *mdev, void *txwi_ptr,
@@ -144,6 +145,12 @@ int mt7925e_mac_reset(struct mt792x_dev *dev)
 	if (err)
 		goto out;
 
+	if (is_mt7927(&dev->mt76)) {
+		err = mt7925_mcu_set_dbdc(&dev->mphy, true);
+		if (err)
+			goto out;
+	}
+
 	err = __mt7925_start(&dev->phy);
 out:
 	clear_bit(MT76_RESET, &dev->mphy.state);
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 18/21] wifi: mt76: mt7925: add MBMC event handling
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (16 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 17/21] wifi: mt76: mt7925: sync MT7927 BSS band assignment Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 19/21] wifi: mt76: mt792x: enable CNM ops for MT7927 Sean Wang
                   ` (2 subsequent siblings)
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

Handle MBMC unsolicited events from firmware to report the current MBMC
state. This helps validate MT7927 band setup.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 .../wireless/mediatek/mt76/mt76_connac_mcu.h  |  1 +
 .../net/wireless/mediatek/mt76/mt7925/mcu.c   | 31 +++++++++++++++++++
 .../net/wireless/mediatek/mt76/mt7925/mcu.h   |  3 +-
 3 files changed, 34 insertions(+), 1 deletion(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
index 4691b9b5e2be..6d0429f40b0f 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76_connac_mcu.h
@@ -1069,6 +1069,7 @@ enum {
 	MCU_UNI_EVENT_SCAN_DONE = 0x0e,
 	MCU_UNI_EVENT_RDD_REPORT = 0x11,
 	MCU_UNI_EVENT_ROC = 0x27,
+	MCU_UNI_EVENT_MBMC = 0x28,
 	MCU_UNI_EVENT_TX_DONE = 0x2d,
 	MCU_UNI_EVENT_THERMAL = 0x35,
 	MCU_UNI_EVENT_RSSI_MONITOR = 0x41,
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
index f7e14cc53dac..4a06f0a1ce03 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.c
@@ -566,6 +566,34 @@ mt7925_mcu_uni_debug_msg_event(struct mt792x_dev *dev, struct sk_buff *skb)
 	}
 }
 
+static void
+mt7925_mcu_handle_mbmc_event(struct mt792x_dev *dev, struct sk_buff *skb)
+{
+	struct mbmc_conf_tlv *tlv;
+	u32 tlv_len;
+
+	skb_pull(skb, sizeof(struct mt7925_mcu_rxd) + 4);
+	tlv_len = skb->len;
+	tlv = (struct mbmc_conf_tlv *)skb->data;
+
+	while (tlv_len >= sizeof(*tlv) &&
+	       le16_to_cpu(tlv->len) >= sizeof(*tlv) &&
+	       le16_to_cpu(tlv->len) <= tlv_len) {
+		u16 tag = le16_to_cpu(tlv->tag);
+
+		if (tag == UNI_MBMC_SETTING || tag == UNI_MBMC_NO_RESP_SETTING) {
+			dev_dbg(dev->mt76.dev,
+				"MBMC event: tag=%u mbmc_en=%u\n",
+				tag, tlv->mbmc_en);
+			break;
+		}
+
+		tlv_len -= le16_to_cpu(tlv->len);
+		tlv = (struct mbmc_conf_tlv *)
+			((u8 *)tlv + le16_to_cpu(tlv->len));
+	}
+}
+
 static void
 mt7925_mcu_uni_rx_unsolicited_event(struct mt792x_dev *dev,
 				    struct sk_buff *skb)
@@ -584,6 +612,9 @@ mt7925_mcu_uni_rx_unsolicited_event(struct mt792x_dev *dev,
 	case MCU_UNI_EVENT_ROC:
 		mt7925_mcu_uni_roc_event(dev, skb);
 		break;
+	case MCU_UNI_EVENT_MBMC:
+		mt7925_mcu_handle_mbmc_event(dev, skb);
+		break;
 	case MCU_UNI_EVENT_SCAN_DONE:
 		mt7925_mcu_scan_event(dev, skb);
 		return;
diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.h b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.h
index 56e2772f3ffe..293f173b23dd 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/mcu.h
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/mcu.h
@@ -143,7 +143,8 @@ enum {
 };
 
 enum {
-	UNI_MBMC_SETTING,
+	UNI_MBMC_SETTING = 0,
+	UNI_MBMC_NO_RESP_SETTING = 1,
 };
 
 enum {
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 19/21] wifi: mt76: mt792x: enable CNM ops for MT7927
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (17 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 18/21] wifi: mt76: mt7925: add MBMC event handling Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 20/21] wifi: mt76: mt7925: add MT7927 PCIe support Sean Wang
  2026-04-25 19:50 ` [PATCH v5 21/21] wifi: mt76: mt7925: add MT7927 USB support Sean Wang
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Sean Wang, Javier Tia

From: Sean Wang <sean.wang@mediatek.com>

Enable CNM support for MT7927 so mac80211 keeps remain-on-channel callbacks
available. MT7927 needs them at runtime even when the capability is not
advertised through the normal firmware feature path.

Co-developed-by: Javier Tia <floss@jetm.me>
Signed-off-by: Javier Tia <floss@jetm.me>
Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 drivers/net/wireless/mediatek/mt76/mt792x_core.c | 11 +++++++++++
 1 file changed, 11 insertions(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt792x_core.c b/drivers/net/wireless/mediatek/mt76/mt792x_core.c
index 152cfcca2f90..3fdcd0599ff2 100644
--- a/drivers/net/wireless/mediatek/mt76/mt792x_core.c
+++ b/drivers/net/wireless/mediatek/mt76/mt792x_core.c
@@ -759,6 +759,13 @@ mt792x_get_offload_capability(struct device *dev, const char *fw_wm)
 	return offload_caps;
 }
 
+static bool mt792x_needs_cnm_runtime(const void *drv_data)
+{
+	const char *fw_wm = drv_data;
+
+	return fw_wm && !strcmp(fw_wm, MT7927_FIRMWARE_WM);
+}
+
 struct ieee80211_ops *
 mt792x_get_mac80211_ops(struct device *dev,
 			const struct ieee80211_ops *mac80211_ops,
@@ -772,6 +779,10 @@ mt792x_get_mac80211_ops(struct device *dev,
 		return NULL;
 
 	*fw_features = mt792x_get_offload_capability(dev, drv_data);
+
+	if (mt792x_needs_cnm_runtime(drv_data))
+		*fw_features |= MT792x_FW_CAP_CNM;
+
 	if (!(*fw_features & MT792x_FW_CAP_CNM)) {
 		ops->remain_on_channel = NULL;
 		ops->cancel_remain_on_channel = NULL;
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 20/21] wifi: mt76: mt7925: add MT7927 PCIe support
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (18 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 19/21] wifi: mt76: mt792x: enable CNM ops for MT7927 Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  2026-04-25 19:50 ` [PATCH v5 21/21] wifi: mt76: mt7925: add MT7927 USB support Sean Wang
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi
  Cc: linux-wireless, linux-mediatek, Sean Wang, Javier Tia

From: Sean Wang <sean.wang@mediatek.com>

Add the missing MT7927 device support in the mt7925 PCI path.
This ensures MT7927 is identified correctly and uses the proper
initialization flow.

Co-developed-by: Javier Tia <floss@jetm.me>
Signed-off-by: Javier Tia <floss@jetm.me>
Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 drivers/net/wireless/mediatek/mt76/mt7925/pci.c | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
index 7455cf7eddc5..41e6ec9223e9 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/pci.c
@@ -16,6 +16,12 @@ static const struct pci_device_id mt7925_pci_device_table[] = {
 		.driver_data = (kernel_ulong_t)MT7925_FIRMWARE_WM },
 	{ PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, 0x0717),
 		.driver_data = (kernel_ulong_t)MT7925_FIRMWARE_WM },
+	{ PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, 0x7927),
+		.driver_data = (kernel_ulong_t)MT7927_FIRMWARE_WM },
+	{ PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, 0x6639),
+		.driver_data = (kernel_ulong_t)MT7927_FIRMWARE_WM },
+	{ PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, 0x0738),
+		.driver_data = (kernel_ulong_t)MT7927_FIRMWARE_WM },
 	{ },
 };
 
@@ -376,7 +382,8 @@ static int mt7925_pci_probe(struct pci_dev *pdev,
 	if (ret)
 		goto err_free_pci_vec;
 
-	is_mt7927_hw = (pdev->device == 0x6639 || pdev->device == 0x7927);
+	is_mt7927_hw = (pdev->device == 0x6639 || pdev->device == 0x7927 ||
+			pdev->device == 0x0738);
 
 	/* MT7927: ASPM L1 causes unreliable WFDMA register access */
 	if (mt7925_disable_aspm || is_mt7927_hw)
@@ -436,6 +443,13 @@ static int mt7925_pci_probe(struct pci_dev *pdev,
 
 	dev_info(mdev->dev, "ASIC revision: %04x\n", mdev->rev);
 
+	if (is_mt7927_hw && mt76_chip(mdev) != 0x7927) {
+		dev_info(mdev->dev,
+			 "MT7927 raw CHIPID=0x%04x, forcing chip=0x7927\n",
+			 mt76_chip(mdev));
+		mdev->rev = (0x7927 << 16) | (mdev->rev & 0xff);
+	}
+
 	mt76_rmw_field(dev, MT_HW_EMI_CTL, MT_HW_EMI_CTL_SLPPROT_EN, 1);
 
 	ret = mt792x_wfsys_reset(dev);
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH v5 21/21] wifi: mt76: mt7925: add MT7927 USB support
  2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
                   ` (19 preceding siblings ...)
  2026-04-25 19:50 ` [PATCH v5 20/21] wifi: mt76: mt7925: add MT7927 PCIe support Sean Wang
@ 2026-04-25 19:50 ` Sean Wang
  20 siblings, 0 replies; 22+ messages in thread
From: Sean Wang @ 2026-04-25 19:50 UTC (permalink / raw)
  To: nbd, lorenzo.bianconi; +Cc: linux-wireless, linux-mediatek, Sean Wang

From: Sean Wang <sean.wang@mediatek.com>

Add the MT7927 USB device ID and normalize the raw 0x6639 CHIPID to
MT7927 so the shared mt7925u code can use the proper chip-specific paths.

Restore the required band setup after USB MAC reset before restarting
the device.

Signed-off-by: Sean Wang <sean.wang@mediatek.com>
---
 drivers/net/wireless/mediatek/mt76/mt7925/usb.c | 15 +++++++++++++++
 drivers/net/wireless/mediatek/mt76/usb.c        |  1 +
 2 files changed, 16 insertions(+)

diff --git a/drivers/net/wireless/mediatek/mt76/mt7925/usb.c b/drivers/net/wireless/mediatek/mt76/mt7925/usb.c
index d9968f03856d..7c64f3c1a2d9 100644
--- a/drivers/net/wireless/mediatek/mt76/mt7925/usb.c
+++ b/drivers/net/wireless/mediatek/mt76/mt7925/usb.c
@@ -10,6 +10,8 @@
 #include "mac.h"
 
 static const struct usb_device_id mt7925u_device_table[] = {
+	{ USB_DEVICE_AND_INTERFACE_INFO(0x0e8d, 0x6639, 0xff, 0xff, 0xff),
+		.driver_info = (kernel_ulong_t)MT7925_FIRMWARE_WM },
 	{ USB_DEVICE_AND_INTERFACE_INFO(0x0e8d, 0x7925, 0xff, 0xff, 0xff),
 		.driver_info = (kernel_ulong_t)MT7925_FIRMWARE_WM },
 	/* Netgear, Inc. A9000 */
@@ -120,6 +122,12 @@ static int mt7925u_mac_reset(struct mt792x_dev *dev)
 	if (err)
 		goto out;
 
+	if (is_mt7927(&dev->mt76)) {
+		err = mt7925_mcu_set_dbdc(&dev->mphy, true);
+		if (err)
+			goto out;
+	}
+
 	err = __mt7925_start(&dev->phy);
 out:
 	clear_bit(MT76_RESET, &dev->mphy.state);
@@ -198,6 +206,13 @@ static int mt7925u_probe(struct usb_interface *usb_intf,
 		    (mt76_rr(dev, MT_HW_REV) & 0xff);
 	dev_dbg(mdev->dev, "ASIC revision: %04x\n", mdev->rev);
 
+	if (mt76_chip(mdev) == 0x6639) {
+		dev_dbg(mdev->dev,
+			"MT7927 raw CHIPID=0x%04x, forcing chip=0x7927\n",
+			mt76_chip(mdev));
+		mdev->rev = (0x7927 << 16) | (mdev->rev & 0xff);
+	}
+
 	if (mt76_get_field(dev, MT_CONN_ON_MISC, MT_TOP_MISC2_FW_N9_RDY)) {
 		ret = mt792xu_wfsys_reset(dev);
 		if (ret)
diff --git a/drivers/net/wireless/mediatek/mt76/usb.c b/drivers/net/wireless/mediatek/mt76/usb.c
index 632ae755c7a6..9bd61c9e94ed 100644
--- a/drivers/net/wireless/mediatek/mt76/usb.c
+++ b/drivers/net/wireless/mediatek/mt76/usb.c
@@ -925,6 +925,7 @@ mt76u_ac_to_hwq(struct mt76_dev *dev, struct mt76_queue *q, u8 qid)
 		q->ep = q->hw_idx + 1;
 		break;
 	}
+	case 0x6639:
 	case 0x7961:
 	case 0x7925:
 		q->hw_idx = mt76_ac_to_hwq(ac);
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 22+ messages in thread

end of thread, other threads:[~2026-04-25 19:52 UTC | newest]

Thread overview: 22+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-04-25 19:49 [PATCH v5 00/21] wifi: mt76: mt7925: MT7927 (Filogic 380) support Sean Wang
2026-04-25 19:49 ` [PATCH v5 01/21] wifi: mt76: mt7925: fix stale pointer comparisons in change_vif_links Sean Wang
2026-04-25 19:49 ` [PATCH v5 02/21] wifi: mt76: mt7925: add 320MHz bandwidth to bss_rlm_tlv Sean Wang
2026-04-25 19:49 ` [PATCH v5 03/21] wifi: mt76: mt7925: handle 320MHz bandwidth in RXV and TXS Sean Wang
2026-04-25 19:49 ` [PATCH v5 04/21] wifi: mt76: mt7925: populate EHT 320MHz MCS map in sta_rec Sean Wang
2026-04-25 19:49 ` [PATCH v5 05/21] wifi: mt76: mt7925: advertise EHT 320MHz capabilities for 6GHz band Sean Wang
2026-04-25 19:49 ` [PATCH v5 06/21] wifi: mt76: mt7925: add MT7927 chip ID helpers Sean Wang
2026-04-25 19:49 ` [PATCH v5 07/21] wifi: mt76: mt7925: add MT7927 firmware paths Sean Wang
2026-04-25 19:49 ` [PATCH v5 08/21] wifi: mt76: mt7925: use irq_map for chip-specific interrupt handling Sean Wang
2026-04-25 19:49 ` [PATCH v5 09/21] wifi: mt76: mt7925: disable ASPM and runtime PM for MT7927 Sean Wang
2026-04-25 19:50 ` [PATCH v5 10/21] wifi: mt76: connac: replace is_mt7925() with is_connac3() Sean Wang
2026-04-25 19:50 ` [PATCH v5 11/21] wifi: mt76: mt7925: use link-specific removal for non-MLD STA Sean Wang
2026-04-25 19:50 ` [PATCH v5 12/21] wifi: mt76: connac: tolerate inactive BSS deactivation Sean Wang
2026-04-25 19:50 ` [PATCH v5 13/21] wifi: mt76: mt792x: add MT7927 WFSYS reset support Sean Wang
2026-04-25 19:50 ` [PATCH v5 14/21] wifi: mt76: mt792x: factor out common DMA queue allocation Sean Wang
2026-04-25 19:50 ` [PATCH v5 15/21] wifi: mt76: mt7925: switch DMA init to common mt792x queue helpers Sean Wang
2026-04-25 19:50 ` [PATCH v5 16/21] wifi: mt76: mt792x: add MT7927-specific PCIe DMA support Sean Wang
2026-04-25 19:50 ` [PATCH v5 17/21] wifi: mt76: mt7925: sync MT7927 BSS band assignment Sean Wang
2026-04-25 19:50 ` [PATCH v5 18/21] wifi: mt76: mt7925: add MBMC event handling Sean Wang
2026-04-25 19:50 ` [PATCH v5 19/21] wifi: mt76: mt792x: enable CNM ops for MT7927 Sean Wang
2026-04-25 19:50 ` [PATCH v5 20/21] wifi: mt76: mt7925: add MT7927 PCIe support Sean Wang
2026-04-25 19:50 ` [PATCH v5 21/21] wifi: mt76: mt7925: add MT7927 USB support Sean Wang

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox