drivers/net/ieee802154/adf7242.c

Source file repositories/reference/linux-study-clean/drivers/net/ieee802154/adf7242.c

File Facts

System
Linux kernel
Corpus path
drivers/net/ieee802154/adf7242.c
Extension
.c
Size
36722 bytes
Lines
1354
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

struct adf7242_local {
	struct spi_device *spi;
	struct completion tx_complete;
	struct ieee802154_hw *hw;
	struct mutex bmux; /* protect SPI messages */
	struct spi_message stat_msg;
	struct spi_transfer stat_xfer;
	struct dentry *debugfs_root;
	struct delayed_work work;
	struct workqueue_struct *wqueue;
	unsigned long flags;
	int tx_stat;
	bool promiscuous;
	s8 rssi;
	u8 max_frame_retries;
	u8 max_cca_retries;
	u8 max_be;
	u8 min_be;

	/* DMA (thus cache coherency maintenance) requires the
	 * transfer buffers to live in their own cache lines.
	 */

	u8 buf[3] ____cacheline_aligned;
	u8 buf_reg_tx[3];
	u8 buf_read_tx[4];
	u8 buf_read_rx[4];
	u8 buf_stat_rx;
	u8 buf_stat_tx;
	u8 buf_cmd;
};

static int adf7242_soft_reset(struct adf7242_local *lp, int line);

static int adf7242_status(struct adf7242_local *lp, u8 *stat)
{
	int status;

	mutex_lock(&lp->bmux);
	status = spi_sync(lp->spi, &lp->stat_msg);
	*stat = lp->buf_stat_rx;
	mutex_unlock(&lp->bmux);

	return status;
}

static int adf7242_wait_status(struct adf7242_local *lp, unsigned int status,
			       unsigned int mask, int line)
{
	int cnt = 0, ret = 0;
	u8 stat;

	do {
		adf7242_status(lp, &stat);
		cnt++;
	} while (((stat & mask) != status) && (cnt < MAX_POLL_LOOPS));

	if (cnt >= MAX_POLL_LOOPS) {
		ret = -ETIMEDOUT;

		if (!(stat & STAT_RC_READY)) {
			adf7242_soft_reset(lp, line);
			adf7242_status(lp, &stat);

			if ((stat & mask) == status)
				ret = 0;
		}

		if (ret < 0)
			dev_warn(&lp->spi->dev,
				 "%s:line %d Timeout status 0x%x (%d)\n",
				 __func__, line, stat, cnt);
	}

	dev_vdbg(&lp->spi->dev, "%s : loops=%d line %d\n", __func__, cnt, line);

	return ret;
}

static int adf7242_wait_rc_ready(struct adf7242_local *lp, int line)
{
	return adf7242_wait_status(lp, STAT_RC_READY | STAT_SPI_READY,
				   STAT_RC_READY | STAT_SPI_READY, line);
}

static int adf7242_wait_spi_ready(struct adf7242_local *lp, int line)
{
	return adf7242_wait_status(lp, STAT_SPI_READY,
				   STAT_SPI_READY, line);
}

Annotation

Implementation Notes