drivers/net/ethernet/qualcomm/emac/emac.c
Source file repositories/reference/linux-study-clean/drivers/net/ethernet/qualcomm/emac/emac.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/net/ethernet/qualcomm/emac/emac.c- Extension
.c- Size
- 18851 bytes
- Lines
- 777
- Domain
- Driver Families
- Bucket
- drivers/net
- Inferred role
- Driver Families: operation-table or driver-model contract
- Status
- pattern 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.
- Defines an operation table; this is where Linux turns generic core objects into subsystem-specific behavior.
- Uses kernel synchronization; read lock ordering, sleepability, and interrupt context assumptions before translating.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/if_ether.hlinux/if_vlan.hlinux/interrupt.hlinux/io.hlinux/module.hlinux/of.hlinux/of_net.hlinux/phy.hlinux/platform_device.hlinux/acpi.hemac.hemac-mac.hemac-phy.hemac-sgmii.h
Detected Declarations
function emac_reg_update32function emac_reinit_lockedfunction emac_napi_rtxfunction emac_start_xmitfunction emac_isrfunction emac_set_featuresfunction emac_rx_mode_setfunction emac_change_mtufunction emac_openfunction emac_closefunction emac_tx_timeoutfunction emac_update_hw_statsfunction emac_get_stats64function emac_work_threadfunction emac_init_adapterfunction emac_clks_getfunction emac_clks_phase1_initfunction emac_clks_phase2_initfunction emac_clks_teardownfunction emac_probe_resourcesfunction emac_probefunction emac_removefunction emac_shutdown
Annotated Snippet
static const struct net_device_ops emac_netdev_ops = {
.ndo_open = emac_open,
.ndo_stop = emac_close,
.ndo_validate_addr = eth_validate_addr,
.ndo_start_xmit = emac_start_xmit,
.ndo_set_mac_address = eth_mac_addr,
.ndo_change_mtu = emac_change_mtu,
.ndo_eth_ioctl = phy_do_ioctl_running,
.ndo_tx_timeout = emac_tx_timeout,
.ndo_get_stats64 = emac_get_stats64,
.ndo_set_features = emac_set_features,
.ndo_set_rx_mode = emac_rx_mode_set,
};
/* Watchdog task routine, called to reinitialize the EMAC */
static void emac_work_thread(struct work_struct *work)
{
struct emac_adapter *adpt =
container_of(work, struct emac_adapter, work_thread);
emac_reinit_locked(adpt);
}
/* Initialize various data structures */
static void emac_init_adapter(struct emac_adapter *adpt)
{
u32 reg;
adpt->rrd_size = EMAC_RRD_SIZE;
adpt->tpd_size = EMAC_TPD_SIZE;
adpt->rfd_size = EMAC_RFD_SIZE;
/* descriptors */
adpt->tx_desc_cnt = EMAC_DEF_TX_DESCS;
adpt->rx_desc_cnt = EMAC_DEF_RX_DESCS;
/* dma */
adpt->dma_order = emac_dma_ord_out;
adpt->dmar_block = emac_dma_req_4096;
adpt->dmaw_block = emac_dma_req_128;
adpt->dmar_dly_cnt = DMAR_DLY_CNT_DEF;
adpt->dmaw_dly_cnt = DMAW_DLY_CNT_DEF;
adpt->tpd_burst = TXQ0_NUM_TPD_PREF_DEF;
adpt->rfd_burst = RXQ0_NUM_RFD_PREF_DEF;
/* irq moderator */
reg = ((EMAC_DEF_RX_IRQ_MOD >> 1) << IRQ_MODERATOR2_INIT_SHFT) |
((EMAC_DEF_TX_IRQ_MOD >> 1) << IRQ_MODERATOR_INIT_SHFT);
adpt->irq_mod = reg;
/* others */
adpt->preamble = EMAC_PREAMBLE_DEF;
/* default to automatic flow control */
adpt->automatic = true;
/* Disable single-pause-frame mode by default */
adpt->single_pause_mode = false;
}
/* Get the clock */
static int emac_clks_get(struct platform_device *pdev,
struct emac_adapter *adpt)
{
unsigned int i;
for (i = 0; i < EMAC_CLK_CNT; i++) {
struct clk *clk = devm_clk_get(&pdev->dev, emac_clk_name[i]);
if (IS_ERR(clk)) {
dev_err(&pdev->dev,
"could not claim clock %s (error=%li)\n",
emac_clk_name[i], PTR_ERR(clk));
return PTR_ERR(clk);
}
adpt->clk[i] = clk;
}
return 0;
}
/* Initialize clocks */
static int emac_clks_phase1_init(struct platform_device *pdev,
struct emac_adapter *adpt)
{
int ret;
/* On ACPI platforms, clocks are controlled by firmware and/or
Annotation
- Immediate include surface: `linux/if_ether.h`, `linux/if_vlan.h`, `linux/interrupt.h`, `linux/io.h`, `linux/module.h`, `linux/of.h`, `linux/of_net.h`, `linux/phy.h`.
- Detected declarations: `function emac_reg_update32`, `function emac_reinit_locked`, `function emac_napi_rtx`, `function emac_start_xmit`, `function emac_isr`, `function emac_set_features`, `function emac_rx_mode_set`, `function emac_change_mtu`, `function emac_open`, `function emac_close`.
- Atlas domain: Driver Families / drivers/net.
- Implementation status: pattern implementation candidate.
- Synchronization appears in or near this file; preserve lock ordering, sleepability, and interrupt-context constraints.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
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.