drivers/net/ethernet/microsoft/mana/mana_en.c

Source file repositories/reference/linux-study-clean/drivers/net/ethernet/microsoft/mana/mana_en.c

File Facts

System
Linux kernel
Corpus path
drivers/net/ethernet/microsoft/mana/mana_en.c
Extension
.c
Size
102780 bytes
Lines
4027
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.

Dependency Surface

Detected Declarations

Annotated Snippet

static const struct file_operations mana_dbg_q_fops = {
	.owner  = THIS_MODULE,
	.open   = simple_open,
	.read   = mana_dbg_q_read,
};

static bool mana_en_need_log(struct mana_port_context *apc, int err)
{
	if (apc && apc->ac && apc->ac->gdma_dev &&
	    apc->ac->gdma_dev->gdma_context)
		return mana_need_log(apc->ac->gdma_dev->gdma_context, err);
	else
		return true;
}

static void mana_put_rx_page(struct mana_rxq *rxq, struct page *page,
			     bool from_pool)
{
	if (from_pool)
		page_pool_put_full_page(rxq->page_pool, page, false);
	else
		put_page(page);
}

/* Microsoft Azure Network Adapter (MANA) functions */

static int mana_open(struct net_device *ndev)
{
	struct mana_port_context *apc = netdev_priv(ndev);
	int err;
	err = mana_alloc_queues(ndev);

	if (err) {
		netdev_err(ndev, "%s failed to allocate queues: %d\n", __func__, err);
		return err;
	}

	apc->port_is_up = true;

	/* Ensure port state updated before txq state */
	smp_wmb();

	netif_tx_wake_all_queues(ndev);
	netdev_dbg(ndev, "%s successful\n", __func__);
	return 0;
}

static int mana_close(struct net_device *ndev)
{
	struct mana_port_context *apc = netdev_priv(ndev);

	if (!apc->port_is_up)
		return 0;

	return mana_detach(ndev, true);
}

static void mana_link_state_handle(struct work_struct *w)
{
	struct mana_context *ac;
	struct net_device *ndev;
	u32 link_event;
	bool link_up;
	int i;

	ac = container_of(w, struct mana_context, link_change_work);

	rtnl_lock();

	link_event = READ_ONCE(ac->link_event);

	if (link_event == HWC_DATA_HW_LINK_CONNECT)
		link_up = true;
	else if (link_event == HWC_DATA_HW_LINK_DISCONNECT)
		link_up = false;
	else
		goto out;

	/* Process all ports */
	for (i = 0; i < ac->num_ports; i++) {
		ndev = ac->ports[i];
		if (!ndev)
			continue;

		if (link_up) {
			netif_carrier_on(ndev);

			__netdev_notify_peers(ndev);
		} else {
			netif_carrier_off(ndev);

Annotation

Implementation Notes