drivers/net/ethernet/amd/xgbe/xgbe-hwtstamp.c

Source file repositories/reference/linux-study-clean/drivers/net/ethernet/amd/xgbe/xgbe-hwtstamp.c

File Facts

System
Linux kernel
Corpus path
drivers/net/ethernet/amd/xgbe/xgbe-hwtstamp.c
Extension
.c
Size
11239 bytes
Lines
400
Domain
Driver Families
Bucket
drivers/net
Inferred role
Driver Families: implementation source
Status
source 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

if (nsec != 0xffffffffffffffffULL) {
			packet->rx_tstamp = nsec;
			XGMAC_SET_BITS(packet->attributes, RX_PACKET_ATTRIBUTES,
				       RX_TSTAMP, 1);
		}
	}
}

void xgbe_config_tstamp(struct xgbe_prv_data *pdata, unsigned int mac_tscr)
{
	unsigned int value = 0;

	value = XGMAC_IOREAD(pdata, MAC_TSCR);
	value |= mac_tscr;
	XGMAC_IOWRITE(pdata, MAC_TSCR, value);
}

void xgbe_tx_tstamp(struct work_struct *work)
{
	struct xgbe_prv_data *pdata = container_of(work,
						   struct xgbe_prv_data,
						   tx_tstamp_work);
	struct skb_shared_hwtstamps hwtstamps;
	unsigned long flags;

	spin_lock_irqsave(&pdata->tstamp_lock, flags);
	if (!pdata->tx_tstamp_skb)
		goto unlock;

	if (pdata->tx_tstamp) {
		memset(&hwtstamps, 0, sizeof(hwtstamps));
		hwtstamps.hwtstamp = ns_to_ktime(pdata->tx_tstamp);
		skb_tstamp_tx(pdata->tx_tstamp_skb, &hwtstamps);
	}

	dev_kfree_skb_any(pdata->tx_tstamp_skb);

	pdata->tx_tstamp_skb = NULL;

unlock:
	spin_unlock_irqrestore(&pdata->tstamp_lock, flags);
}

int xgbe_get_hwtstamp_settings(struct net_device *netdev,
			       struct kernel_hwtstamp_config *config)
{
	struct xgbe_prv_data *pdata = netdev_priv(netdev);

	*config = pdata->tstamp_config;

	return 0;
}

int xgbe_set_hwtstamp_settings(struct net_device *netdev,
			       struct kernel_hwtstamp_config *config,
			       struct netlink_ext_ack *extack)
{
	struct xgbe_prv_data *pdata = netdev_priv(netdev);
	unsigned int mac_tscr = 0;

	switch (config->tx_type) {
	case HWTSTAMP_TX_OFF:
		break;

	case HWTSTAMP_TX_ON:
		XGMAC_SET_BITS(mac_tscr, MAC_TSCR, TSENA, 1);
		break;

	default:
		return -ERANGE;
	}

	switch (config->rx_filter) {
	case HWTSTAMP_FILTER_NONE:
		break;

	case HWTSTAMP_FILTER_NTP_ALL:
	case HWTSTAMP_FILTER_ALL:
		XGMAC_SET_BITS(mac_tscr, MAC_TSCR, TSENALL, 1);
		XGMAC_SET_BITS(mac_tscr, MAC_TSCR, TSENA, 1);
		break;

		/* PTP v2, UDP, any kind of event packet */
	case HWTSTAMP_FILTER_PTP_V2_L4_EVENT:
		XGMAC_SET_BITS(mac_tscr, MAC_TSCR, TSVER2ENA, 1);
		fallthrough;    /* to PTP v1, UDP, any kind of event packet */
	case HWTSTAMP_FILTER_PTP_V1_L4_EVENT:
		XGMAC_SET_BITS(mac_tscr, MAC_TSCR, TSIPV4ENA, 1);
		XGMAC_SET_BITS(mac_tscr, MAC_TSCR, TSIPV6ENA, 1);
		XGMAC_SET_BITS(mac_tscr, MAC_TSCR, SNAPTYPSEL, 1);

Annotation

Implementation Notes