drivers/net/wireless/mediatek/mt76/sdio.c
Source file repositories/reference/linux-study-clean/drivers/net/wireless/mediatek/mt76/sdio.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/net/wireless/mediatek/mt76/sdio.c- Extension
.c- Size
- 14573 bytes
- Lines
- 682
- Domain
- Driver Families
- Bucket
- drivers/net
- Inferred role
- Driver Families: exported/initcall integration point
- Status
- integration implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Exports symbols or registers init work; inspect boot/module ordering and who consumes the exported contract.
- Uses kernel synchronization; read lock ordering, sleepability, and interrupt context assumptions before translating.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/iopoll.hlinux/kernel.hlinux/module.hlinux/mmc/sdio_func.hlinux/mmc/card.hlinux/mmc/host.hlinux/sched.hlinux/kthread.hmt76.hsdio.h
Detected Declarations
function mt76s_read_whisrfunction mt76s_read_pcrfunction mt76s_read_mailboxfunction mt76s_write_mailboxfunction mt76s_rrfunction mt76s_wrfunction mt76s_rmwfunction mt76s_write_copyfunction mt76s_read_copyfunction mt76s_wr_rpfunction mt76s_rd_rpfunction mt76s_hw_initfunction mt76s_alloc_rx_queuefunction mt76s_alloc_txfunction mt76s_get_next_rx_entryfunction mt76s_process_rx_queuefunction mt76s_net_workerfunction mt76s_process_tx_queuefunction mt76s_status_workerfunction mt76s_tx_status_datafunction mt76s_tx_queue_skbfunction mt76s_tx_queue_skb_rawfunction mt76s_tx_kickfunction mt76s_deinitfunction mt76_for_each_q_rxfunction mt76s_initexport mt76s_read_pcrexport mt76s_rrexport mt76s_wrexport mt76s_rmwexport mt76s_write_copyexport mt76s_read_copyexport mt76s_wr_rpexport mt76s_rd_rpexport mt76s_hw_initexport mt76s_alloc_rx_queueexport mt76s_alloc_txexport mt76s_deinitexport mt76s_init
Annotated Snippet
if (mcu) {
dev_kfree_skb(entry.skb);
entry.skb = NULL;
}
mt76_queue_tx_complete(dev, q, &entry);
nframes++;
}
if (!q->queued)
wake_up(&dev->tx_wait);
return nframes;
}
static void mt76s_status_worker(struct mt76_worker *w)
{
struct mt76_sdio *sdio = container_of(w, struct mt76_sdio,
status_worker);
struct mt76_dev *dev = container_of(sdio, struct mt76_dev, sdio);
bool resched = false;
int i, nframes;
do {
int ndata_frames = 0;
nframes = mt76s_process_tx_queue(dev, dev->q_mcu[MT_MCUQ_WM]);
for (i = 0; i <= MT_TXQ_PSD; i++)
ndata_frames += mt76s_process_tx_queue(dev,
dev->phy.q_tx[i]);
nframes += ndata_frames;
if (ndata_frames > 0)
resched = true;
if (dev->drv->tx_status_data && ndata_frames > 0 &&
!test_and_set_bit(MT76_READING_STATS, &dev->phy.state) &&
!test_bit(MT76_STATE_SUSPEND, &dev->phy.state))
mt76_worker_schedule(&sdio->stat_worker);
} while (nframes > 0);
if (resched)
mt76_worker_schedule(&dev->tx_worker);
}
static void mt76s_tx_status_data(struct mt76_worker *worker)
{
struct mt76_sdio *sdio;
struct mt76_dev *dev;
u8 update = 1;
u16 count = 0;
sdio = container_of(worker, struct mt76_sdio, stat_worker);
dev = container_of(sdio, struct mt76_dev, sdio);
while (true) {
if (test_bit(MT76_RESET, &dev->phy.state) ||
test_bit(MT76_REMOVED, &dev->phy.state))
break;
if (!dev->drv->tx_status_data(dev, &update))
break;
count++;
}
if (count && test_bit(MT76_STATE_RUNNING, &dev->phy.state))
mt76_worker_schedule(&sdio->status_worker);
else
clear_bit(MT76_READING_STATS, &dev->phy.state);
}
static int
mt76s_tx_queue_skb(struct mt76_phy *phy, struct mt76_queue *q,
enum mt76_txq_id qid, struct sk_buff *skb,
struct mt76_wcid *wcid, struct ieee80211_sta *sta)
{
struct mt76_tx_info tx_info = {
.skb = skb,
};
struct mt76_dev *dev = phy->dev;
int err, len = skb->len;
u16 idx = q->head;
if (q->queued == q->ndesc)
return -ENOSPC;
skb->prev = skb->next = NULL;
err = dev->drv->tx_prepare_skb(dev, NULL, qid, wcid, sta, &tx_info);
if (err < 0)
return err;
Annotation
- Immediate include surface: `linux/iopoll.h`, `linux/kernel.h`, `linux/module.h`, `linux/mmc/sdio_func.h`, `linux/mmc/card.h`, `linux/mmc/host.h`, `linux/sched.h`, `linux/kthread.h`.
- Detected declarations: `function mt76s_read_whisr`, `function mt76s_read_pcr`, `function mt76s_read_mailbox`, `function mt76s_write_mailbox`, `function mt76s_rr`, `function mt76s_wr`, `function mt76s_rmw`, `function mt76s_write_copy`, `function mt76s_read_copy`, `function mt76s_wr_rp`.
- Atlas domain: Driver Families / drivers/net.
- Implementation status: integration implementation candidate.
- Synchronization appears in or near this file; preserve lock ordering, sleepability, and interrupt-context constraints.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.