From 1e570aa871f0ce535770a9390b833dc865c28d59 Mon Sep 17 00:00:00 2001 From: Sean Wang Date: Sat, 25 Apr 2026 14:50:04 -0500 Subject: [PATCH] wifi: mt76: mt792x: factor out common DMA queue allocation 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 Link: https://patch.msgid.link/20260425195011.790265-15-sean.wang@kernel.org Signed-off-by: Felix Fietkau --- 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) {