/* ieee802154_mcr20a.c - NXP MCR20A driver */

#define DT_DRV_COMPAT nxp_mcr20a

/*
 * Copyright (c) 2017 PHYTEC Messtechnik GmbH
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#define LOG_MODULE_NAME ieee802154_mcr20a
#define LOG_LEVEL CONFIG_IEEE802154_DRIVER_LOG_LEVEL

#include <logging/log.h>
LOG_MODULE_REGISTER(LOG_MODULE_NAME);

#include <errno.h>

#include <kernel.h>
#include <arch/cpu.h>
#include <debug/stack.h>

#include <device.h>
#include <init.h>
#include <net/net_if.h>
#include <net/net_pkt.h>

#include <sys/byteorder.h>
#include <string.h>
#include <random/rand32.h>
#include <debug/stack.h>

#include <drivers/gpio.h>

#include <net/ieee802154_radio.h>

#include "ieee802154_mcr20a.h"
#include "MCR20Overwrites.h"

/*
 * max. TX duraton = (PR + SFD + FLI + PDU + FCS)
 *                 + RX_warmup + cca + TX_warmup
 * TODO: Calculate the value from frame length.
 * Invalid for the SLOTTED mode.
 */
#define _MAX_PKT_TX_DURATION		(133 + 9 + 8 + 9)

#if LOG_LEVEL == LOG_LEVEL_DBG
/* Prevent timer overflow during LOG_* output */
#define _MACACKWAITDURATION		(864 / 16 + 11625)
#define MCR20A_SEQ_SYNC_TIMEOUT		(200)
#else
#define MCR20A_SEQ_SYNC_TIMEOUT		(20)
#define _MACACKWAITDURATION		(864 / 16) /* 864us * 62500Hz */
#endif

#define MCR20A_FCS_LENGTH		(2)
#define MCR20A_PSDU_LENGTH		(125)
#define MCR20A_GET_SEQ_STATE_RETRIES	(3)

/* Values for the clock output (CLK_OUT) configuration */
#ifdef CONFIG_MCR20A_CLK_OUT_DISABLED
#define MCR20A_CLK_OUT_CONFIG	(MCR20A_CLK_OUT_HIZ)

#elif CONFIG_MCR20A_CLK_OUT_32MHZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(0) | MCR20A_CLK_OUT_DS |\
				 MCR20A_CLK_OUT_EN)

#elif CONFIG_MCR20A_CLK_OUT_16MHZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(1) | MCR20A_CLK_OUT_DS |\
				 MCR20A_CLK_OUT_EN)

#elif CONFIG_MCR20A_CLK_OUT_8MHZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(2) | MCR20A_CLK_OUT_EN)

#elif CONFIG_MCR20A_CLK_OUT_4MHZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(3) | MCR20A_CLK_OUT_EN)

#elif CONFIG_MCR20A_CLK_OUT_1MHZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(4) | MCR20A_CLK_OUT_EN)

#elif CONFIG_MCR20A_CLK_OUT_250KHZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(5) | MCR20A_CLK_OUT_EN)

#elif CONFIG_MCR20A_CLK_OUT_62500HZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(6) | MCR20A_CLK_OUT_EN)

#elif CONFIG_MCR20A_CLK_OUT_32768HZ
#define MCR20A_CLK_OUT_CONFIG	(set_bits_clk_out_div(7) | MCR20A_CLK_OUT_EN)

#endif

#ifdef CONFIG_MCR20A_IS_PART_OF_KW2XD_SIP
#define PART_OF_KW2XD_SIP	1
#else
#define PART_OF_KW2XD_SIP	0
#endif

/* Values for the power mode (PM) configuration */
#define MCR20A_PM_HIBERNATE	0
#define MCR20A_PM_DOZE		MCR20A_PWR_MODES_XTALEN
#define MCR20A_PM_IDLE		(MCR20A_PWR_MODES_XTALEN |\
				 MCR20A_PWR_MODES_PMC_MODE)
#define MCR20A_PM_AUTODOZE	(MCR20A_PWR_MODES_XTALEN |\
				 MCR20A_PWR_MODES_AUTODOZE)

/* Default settings for the device initialization */
#define MCR20A_DEFAULT_TX_POWER	(0)
#define MCR20A_DEFAULT_CHANNEL	(26)

/* RF TX power max/min values (dBm) */
#define MCR20A_OUTPUT_POWER_MAX	(8)
#define MCR20A_OUTPUT_POWER_MIN	(-35)

/* Lookup table for the Power Control register */
static const uint8_t pow_lt[44] = {
	3, 4, 5, 6,
	6, 7, 7, 8,
	8, 9, 9, 10,
	11, 11, 12, 13,
	13, 14, 14, 15,
	16, 16, 17, 18,
	18, 19, 20, 20,
	21, 21, 22, 23,
	23, 24, 25, 25,
	26, 27, 27, 28,
	28, 29, 30, 31
};

/* PLL integer and fractional lookup tables
 *
 * Fc = 2405 + 5(k - 11) , k = 11,12,...,26
 *
 * Equation for PLL frequency, MKW2xD Reference Manual, p.255 :
 * F = ((PLL_INT0 + 64) + (PLL_FRAC0/65536))32MHz
 *
 */
static const uint8_t pll_int_lt[16] = {
	11, 11, 11, 11,
	11, 11, 12, 12,
	12, 12, 12, 12,
	13, 13, 13, 13
};

static const uint16_t pll_frac_lt[16] = {
	10240, 20480, 30720, 40960,
	51200, 61440, 6144, 16384,
	26624, 36864, 47104, 57344,
	2048, 12288, 22528, 32768
};

#define z_usleep(usec) k_busy_wait(usec)

/* Read direct (dreg is true) or indirect register (dreg is false) */
uint8_t z_mcr20a_read_reg(struct mcr20a_context *dev, bool dreg, uint8_t addr)
{
	uint8_t cmd_buf[3] = {
		dreg ? (MCR20A_REG_READ | addr) :
		(MCR20A_IAR_INDEX | MCR20A_REG_WRITE),
		dreg ? 0 : (addr | MCR20A_REG_READ),
		0
	};
	uint8_t len = dreg ? 2 : 3;
	const struct spi_buf buf = {
		.buf = cmd_buf,
		.len = len
	};
	const struct spi_buf_set tx = {
		.buffers = &buf,
		.count = 1
	};
	const struct spi_buf_set rx = {
		.buffers = &buf,
		.count = 1
	};

	if (spi_transceive(dev->spi, &dev->spi_cfg, &tx, &rx) == 0) {
		return cmd_buf[len - 1];
	}

	LOG_ERR("Failed");

	return 0;
}

/* Write direct (dreg is true) or indirect register (dreg is false) */
bool z_mcr20a_write_reg(struct mcr20a_context *dev, bool dreg, uint8_t addr,
		       uint8_t value)
{
	uint8_t cmd_buf[3] = {
		dreg ? (MCR20A_REG_WRITE | addr) :
		(MCR20A_IAR_INDEX | MCR20A_REG_WRITE),
		dreg ? value : (addr | MCR20A_REG_WRITE),
		dreg ? 0 : value
	};
	const struct spi_buf buf = {
		.buf = cmd_buf,
		.len = dreg ? 2 : 3
	};
	const struct spi_buf_set tx = {
		.buffers = &buf,
		.count = 1
	};

	return (spi_write(dev->spi, &dev->spi_cfg, &tx) == 0);
}

/* Write multiple bytes to direct or indirect register */
bool z_mcr20a_write_burst(struct mcr20a_context *dev, bool dreg, uint16_t addr,
			 uint8_t *data_buf, uint8_t len)
{
	uint8_t cmd_buf[2] = {
		dreg ? MCR20A_REG_WRITE | addr :
		MCR20A_IAR_INDEX | MCR20A_REG_WRITE,
		dreg ? 0 : addr | MCR20A_REG_WRITE
	};
	struct spi_buf bufs[2] = {
		{
			.buf = cmd_buf,
			.len = dreg ? 1 : 2
		},
		{
			.buf = data_buf,
			.len = len
		}
	};
	const struct spi_buf_set tx = {
		.buffers = bufs,
		.count = 2
	};

	return (spi_write(dev->spi, &dev->spi_cfg, &tx) == 0);
}

/* Read multiple bytes from direct or indirect register */
bool z_mcr20a_read_burst(struct mcr20a_context *dev, bool dreg, uint16_t addr,
			uint8_t *data_buf, uint8_t len)
{
	uint8_t cmd_buf[2] = {
		dreg ? MCR20A_REG_READ | addr :
		MCR20A_IAR_INDEX | MCR20A_REG_WRITE,
		dreg ? 0 : addr | MCR20A_REG_READ
	};
	struct spi_buf bufs[2] = {
		{
			.buf = cmd_buf,
			.len = dreg ? 1 : 2
		},
		{
			.buf = data_buf,
			.len = len
		}
	};
	const struct spi_buf_set tx = {
		.buffers = bufs,
		.count = 1
	};
	const struct spi_buf_set rx = {
		.buffers = bufs,
		.count = 2
	};

	return (spi_transceive(dev->spi, &dev->spi_cfg, &tx, &rx) == 0);
}

/* Mask (msk is true) or unmask all interrupts from asserting IRQ_B */
static bool mcr20a_mask_irqb(struct mcr20a_context *dev, bool msk)
{
	uint8_t ctrl4 = read_reg_phy_ctrl4(dev);

	if (msk) {
		ctrl4 |= MCR20A_PHY_CTRL4_TRCV_MSK;
	} else {
		ctrl4 &= ~MCR20A_PHY_CTRL4_TRCV_MSK;
	}

	return write_reg_phy_ctrl4(dev, ctrl4);
}

/** Set an timeout value for the given compare register */
static int mcr20a_timer_set(struct mcr20a_context *mcr20a,
			    uint8_t cmp_reg,
			    uint32_t timeout)
{
	uint32_t now = 0U;
	uint32_t next;
	bool retval;

	if (!read_burst_event_timer(mcr20a, (uint8_t *)&now)) {
		goto error;
	}

	now = sys_le32_to_cpu(now);
	next = now + timeout;
	LOG_DBG("now: 0x%x set 0x%x", now, next);
	next = sys_cpu_to_le32(next);

	switch (cmp_reg) {
	case 1:
		retval = write_burst_t1cmp(mcr20a, (uint8_t *)&next);
		break;
	case 2:
		retval = write_burst_t2cmp(mcr20a, (uint8_t *)&next);
		break;
	case 3:
		retval = write_burst_t3cmp(mcr20a, (uint8_t *)&next);
		break;
	case 4:
		retval = write_burst_t4cmp(mcr20a, (uint8_t *)&next);
		break;
	default:
		goto error;
	}

	if (!retval) {
		goto error;
	}

	return 0;

error:
	LOG_ERR("Failed");
	return -EIO;
}

static int mcr20a_timer_init(const struct device *dev, uint8_t tb)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t buf[3] = {0, 0, 0};
	uint8_t ctrl4;

	if (!write_reg_tmr_prescale(mcr20a,
				    set_bits_tmr_prescale(tb))) {
		goto error;
	}

	if (!write_burst_t1cmp(mcr20a, buf)) {
		goto error;
	}

	ctrl4 = read_reg_phy_ctrl4(mcr20a);
	ctrl4 |= MCR20A_PHY_CTRL4_TMRLOAD;
	if (!write_reg_phy_ctrl4(mcr20a, ctrl4)) {
		goto error;
	}

	LOG_DBG("done, timebase %d", tb);
	return 0;

error:
	LOG_ERR("Failed");
	return -EIO;
}

/* Set Timer Comparator 4 */
static int mcr20a_t4cmp_set(struct mcr20a_context *mcr20a,
			    uint32_t timeout)
{
	uint8_t irqsts3;
	uint8_t ctrl3;

	if (mcr20a_timer_set(mcr20a, 4, timeout)) {
		goto error;
	}

	/* enable and clear irq for the timer 4 */
	irqsts3 = read_reg_irqsts3(mcr20a);
	irqsts3 &= ~MCR20A_IRQSTS3_TMR4MSK;
	irqsts3 |= MCR20A_IRQSTS3_TMR4IRQ;
	if (!write_reg_irqsts3(mcr20a, irqsts3)) {
		goto error;
	}

	ctrl3 = read_reg_phy_ctrl3(mcr20a);
	ctrl3 |= MCR20A_PHY_CTRL3_TMR4CMP_EN;
	if (!write_reg_phy_ctrl3(mcr20a, ctrl3)) {
		goto error;
	}

	return 0;

error:
	LOG_DBG("Failed");
	return -EIO;
}

/* Clear Timer Comparator 4 */
static int mcr20a_t4cmp_clear(struct mcr20a_context *mcr20a)
{
	uint8_t irqsts3;
	uint8_t ctrl3;

	ctrl3 = read_reg_phy_ctrl3(mcr20a);
	ctrl3 &= ~MCR20A_PHY_CTRL3_TMR4CMP_EN;
	if (!write_reg_phy_ctrl3(mcr20a, ctrl3)) {
		goto error;
	}

	irqsts3 = read_reg_irqsts3(mcr20a);
	irqsts3 |= MCR20A_IRQSTS3_TMR4IRQ;
	if (!write_reg_irqsts3(mcr20a, irqsts3)) {
		goto error;
	}

	return 0;

error:
	LOG_DBG("Failed");
	return -EIO;
}

static inline void xcvseq_wait_until_idle(struct mcr20a_context *mcr20a)
{
	uint8_t state;
	uint8_t retries = MCR20A_GET_SEQ_STATE_RETRIES;

	do {
		state = read_reg_seq_state(mcr20a);
		retries--;
	} while ((state & MCR20A_SEQ_STATE_MASK) && retries);

	if (state & MCR20A_SEQ_STATE_MASK) {
		LOG_ERR("Timeout");
	}
}

static inline int mcr20a_abort_sequence(struct mcr20a_context *mcr20a,
					bool force)
{
	uint8_t ctrl1;

	ctrl1 = read_reg_phy_ctrl1(mcr20a);
	LOG_DBG("CTRL1 0x%02x", ctrl1);

	if (((ctrl1 & MCR20A_PHY_CTRL1_XCVSEQ_MASK) == MCR20A_XCVSEQ_TX) ||
	    ((ctrl1 & MCR20A_PHY_CTRL1_XCVSEQ_MASK) == MCR20A_XCVSEQ_TX_RX)) {
		if (!force) {
			return -1;
		}
	}

	/* Abort ongoing sequence */
	ctrl1 &= ~MCR20A_PHY_CTRL1_XCVSEQ_MASK;
	if (!write_reg_phy_ctrl1(mcr20a, ctrl1)) {
		return -1;
	}

	xcvseq_wait_until_idle(mcr20a);

	/* Clear relevant interrupt flags */
	if (!write_reg_irqsts1(mcr20a, MCR20A_IRQSTS1_IRQ_MASK)) {
		return -1;
	}

	return 0;
}

/* Initiate a (new) Transceiver Sequence */
static inline int mcr20a_set_sequence(struct mcr20a_context *mcr20a,
				      uint8_t seq)
{
	uint8_t ctrl1 = 0U;

	seq = set_bits_phy_ctrl1_xcvseq(seq);
	ctrl1 = read_reg_phy_ctrl1(mcr20a);
	ctrl1 &= ~MCR20A_PHY_CTRL1_XCVSEQ_MASK;

	if ((seq == MCR20A_XCVSEQ_TX_RX) &&
	    (ctrl1 & MCR20A_PHY_CTRL1_RXACKRQD)) {
		/* RXACKRQD enabled, timer should be set. */
		mcr20a_t4cmp_set(mcr20a, _MACACKWAITDURATION +
				 _MAX_PKT_TX_DURATION);
	}

	ctrl1 |= seq;
	if (!write_reg_phy_ctrl1(mcr20a, ctrl1)) {
		return -EIO;
	}

	return 0;
}

static inline uint32_t mcr20a_get_rssi(uint32_t lqi)
{
	/* Get rssi (Received Signal Strength Indicator, unit is dBm)
	 * from lqi (Link Quality Indicator) value.
	 * There are two different equations for RSSI:
	 * RF = (LQI – 286.6) / 2.69333 (MKW2xD Reference Manual)
	 * RF = (LQI – 295.4) / 2.84 (MCR20A Reference Manual)
	 * The last appears more to match the graphic (Figure 3-10).
	 * Since RSSI value is always positive and we want to
	 * avoid the floating point computation:
	 * -RF * 65536 = (LQI / 2.84 - 295.4 / 2.84) * 65536
	 * RF * 65536 = (295.4 * 65536 / 2.84) - (LQI * 65536 / 2.84)
	 */
	uint32_t a = (uint32_t)(295.4 * 65536 / 2.84);
	uint32_t b = (uint32_t)(65536 / 2.84);

	return (a - (b * lqi)) >> 16;
}

static inline uint8_t *get_mac(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint32_t *ptr = (uint32_t *)(mcr20a->mac_addr);

	UNALIGNED_PUT(sys_rand32_get(), ptr);
	ptr = (uint32_t *)(mcr20a->mac_addr + 4);
	UNALIGNED_PUT(sys_rand32_get(), ptr);

	mcr20a->mac_addr[0] = (mcr20a->mac_addr[0] & ~0x01) | 0x02;

	return mcr20a->mac_addr;
}

static inline bool read_rxfifo_content(struct mcr20a_context *dev,
				       struct net_buf *buf, uint8_t len)
{
	uint8_t cmd = MCR20A_BUF_READ;
	struct spi_buf bufs[2] = {
		{
			.buf = &cmd,
			.len = 1
		},
		{
			.buf = buf->data,
			.len = len
		}
	};
	const struct spi_buf_set tx = {
		.buffers = bufs,
		.count = 1
	};
	const struct spi_buf_set rx = {
		.buffers = bufs,
		.count = 2
	};

	if (spi_transceive(dev->spi, &dev->spi_cfg, &tx, &rx) != 0) {
		return false;
	}

	net_buf_add(buf, len);

	return true;
}

static inline void mcr20a_rx(struct mcr20a_context *mcr20a, uint8_t len)
{
	struct net_pkt *pkt = NULL;
	uint8_t pkt_len;

	pkt_len = len - MCR20A_FCS_LENGTH;

	pkt = net_pkt_alloc_with_buffer(mcr20a->iface, pkt_len,
					AF_UNSPEC, 0, K_NO_WAIT);
	if (!pkt) {
		LOG_ERR("No buf available");
		goto out;
	}

	if (!read_rxfifo_content(mcr20a, pkt->buffer, pkt_len)) {
		LOG_ERR("No content read");
		goto out;
	}

	if (ieee802154_radio_handle_ack(mcr20a->iface, pkt) == NET_OK) {
		LOG_DBG("ACK packet handled");
		goto out;
	}

	net_pkt_set_ieee802154_lqi(pkt, read_reg_lqi_value(mcr20a));
	net_pkt_set_ieee802154_rssi(pkt, mcr20a_get_rssi(
					    net_pkt_ieee802154_lqi(pkt)));

	LOG_DBG("Caught a packet (%u) (LQI: %u, RSSI: %u)",
		    pkt_len, net_pkt_ieee802154_lqi(pkt),
		    net_pkt_ieee802154_rssi(pkt));

	if (net_recv_data(mcr20a->iface, pkt) < 0) {
		LOG_DBG("Packet dropped by NET stack");
		goto out;
	}

	log_stack_usage(&mcr20a->mcr20a_rx_thread);
	return;
out:
	if (pkt) {
		net_pkt_unref(pkt);
	}
}

/*
 * The function checks how the XCV sequence has been completed
 * and sets the variable seq_retval accordingly. It returns true
 * if a new sequence is to be set. This function is only to be called
 * when a sequence has been completed.
 */
static inline bool irqsts1_event(struct mcr20a_context *mcr20a,
				  uint8_t *dregs)
{
	uint8_t seq = dregs[MCR20A_PHY_CTRL1] & MCR20A_PHY_CTRL1_XCVSEQ_MASK;
	uint8_t new_seq = MCR20A_XCVSEQ_RECEIVE;
	bool retval = false;

	switch (seq) {
	case MCR20A_XCVSEQ_RECEIVE:
		if ((dregs[MCR20A_IRQSTS1] & MCR20A_IRQSTS1_RXIRQ)) {
			if ((dregs[MCR20A_IRQSTS1] & MCR20A_IRQSTS1_TXIRQ)) {
				LOG_DBG("Finished RxSeq + TxAck");
			} else {
				LOG_DBG("Finished RxSeq");
			}

			mcr20a_rx(mcr20a, dregs[MCR20A_RX_FRM_LEN]);
			retval = true;
		}
		break;
	case MCR20A_XCVSEQ_TX:
	case MCR20A_XCVSEQ_TX_RX:
		if (dregs[MCR20A_IRQSTS1] & MCR20A_IRQSTS1_CCAIRQ) {
			if (dregs[MCR20A_IRQSTS2] & MCR20A_IRQSTS2_CCA) {
				LOG_DBG("Finished CCA, CH busy");
				atomic_set(&mcr20a->seq_retval, -EBUSY);
				retval = true;
				break;
			}
		}

		if (dregs[MCR20A_IRQSTS1] & MCR20A_IRQSTS1_TXIRQ) {
			atomic_set(&mcr20a->seq_retval, 0);

			if ((dregs[MCR20A_IRQSTS1] & MCR20A_IRQSTS1_RXIRQ)) {
				LOG_DBG("Finished TxSeq + RxAck");
				/* Got Ack, timer should be disabled. */
				mcr20a_t4cmp_clear(mcr20a);
			} else {
				LOG_DBG("Finished TxSeq");
			}

			retval = true;
		}
		break;
	case MCR20A_XCVSEQ_CONTINUOUS_CCA:
	case MCR20A_XCVSEQ_CCA:
		if ((dregs[MCR20A_IRQSTS1] & MCR20A_IRQSTS1_CCAIRQ)) {

			/* If CCCA, then timer should be disabled. */
			/* mcr20a_t4cmp_clear(mcr20a); */

			if (dregs[MCR20A_IRQSTS2] & MCR20A_IRQSTS2_CCA) {
				LOG_DBG("Finished CCA, CH busy");
				atomic_set(&mcr20a->seq_retval, -EBUSY);
			} else {
				/**
				 * Assume that after the CCA,
				 * a transmit sequence follows and
				 * set here the sequence manager to Idle.
				 */
				LOG_DBG("Finished CCA, CH idle");
				new_seq = MCR20A_XCVSEQ_IDLE;
				atomic_set(&mcr20a->seq_retval, 0);
			}

			retval = true;
		}
		break;
	case MCR20A_XCVSEQ_IDLE:
	default:
		LOG_ERR("SEQ triggered, but XCVSEQ is in the Idle state");
		LOG_ERR("IRQSTS: 0x%02x", dregs[MCR20A_IRQSTS1]);
		break;
	}

	dregs[MCR20A_PHY_CTRL1] &= ~MCR20A_PHY_CTRL1_XCVSEQ_MASK;
	dregs[MCR20A_PHY_CTRL1] |= new_seq;

	return retval;
}

/*
 * Check the Timer Comparator IRQ register IRQSTS3.
 * Currently we use only T4CMP to cancel the running sequence,
 * usually the TR.
 */
static inline bool irqsts3_event(struct mcr20a_context *mcr20a,
				  uint8_t *dregs)
{
	bool retval = false;

	if (dregs[MCR20A_IRQSTS3] & MCR20A_IRQSTS3_TMR4IRQ) {
		LOG_DBG("Sequence timeout, IRQSTSs 0x%02x 0x%02x 0x%02x",
			    dregs[MCR20A_IRQSTS1],
			    dregs[MCR20A_IRQSTS2],
			    dregs[MCR20A_IRQSTS3]);

		atomic_set(&mcr20a->seq_retval, -EBUSY);
		mcr20a_t4cmp_clear(mcr20a);
		dregs[MCR20A_PHY_CTRL1] &= ~MCR20A_PHY_CTRL1_XCVSEQ_MASK;
		dregs[MCR20A_PHY_CTRL1] |= MCR20A_XCVSEQ_RECEIVE;

		/* Clear all interrupts */
		dregs[MCR20A_IRQSTS1] = MCR20A_IRQSTS1_IRQ_MASK;
		retval = true;
	} else {
		LOG_ERR("IRQSTS3 contains untreated IRQs: 0x%02x",
			    dregs[MCR20A_IRQSTS3]);
	}

	return retval;
}

static void mcr20a_thread_main(void *arg)
{
	struct mcr20a_context *mcr20a = (struct mcr20a_context *)arg;
	uint8_t dregs[MCR20A_PHY_CTRL4 + 1];
	bool set_new_seq;
	uint8_t ctrl1 = 0U;

	while (true) {
		k_sem_take(&mcr20a->isr_sem, K_FOREVER);

		k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);
		set_new_seq = false;

		if (!mcr20a_mask_irqb(mcr20a, true)) {
			LOG_ERR("Failed to mask IRQ_B");
			goto unmask_irqb;
		}

		/* Read the register from IRQSTS1 until CTRL4 */
		if (!read_burst_irqsts1_ctrl4(mcr20a, dregs)) {
			LOG_ERR("Failed to read register");
			goto unmask_irqb;
		}
		/* make backup from PHY_CTRL1 register */
		ctrl1 = dregs[MCR20A_PHY_CTRL1];

		if (dregs[MCR20A_IRQSTS3] & MCR20A_IRQSTS3_IRQ_MASK) {
			set_new_seq = irqsts3_event(mcr20a, dregs);
		} else if (dregs[MCR20A_IRQSTS1] & MCR20A_IRQSTS1_SEQIRQ) {
			set_new_seq = irqsts1_event(mcr20a, dregs);
		}

		if (dregs[MCR20A_IRQSTS2] & MCR20A_IRQSTS2_IRQ_MASK) {
			LOG_ERR("IRQSTS2 contains untreated IRQs: 0x%02x",
				    dregs[MCR20A_IRQSTS2]);
		}

		LOG_DBG("WB: 0x%02x | 0x%02x | 0x%02x",
			     dregs[MCR20A_IRQSTS1],
			     dregs[MCR20A_IRQSTS2],
			     dregs[MCR20A_IRQSTS3]);

		/* Write back register, clear IRQs and set new sequence */
		if (set_new_seq) {
			/* Reset sequence manager */
			ctrl1 &= ~MCR20A_PHY_CTRL1_XCVSEQ_MASK;
			if (!write_reg_phy_ctrl1(mcr20a, ctrl1)) {
				LOG_ERR("Failed to reset SEQ manager");
			}

			xcvseq_wait_until_idle(mcr20a);

			if (!write_burst_irqsts1_ctrl1(mcr20a, dregs)) {
				LOG_ERR("Failed to write CTRL1");
			}
		} else {
			if (!write_burst_irqsts1_irqsts3(mcr20a, dregs)) {
				LOG_ERR("Failed to write IRQSTS3");
			}
		}

unmask_irqb:
		if (!mcr20a_mask_irqb(mcr20a, false)) {
			LOG_ERR("Failed to unmask IRQ_B");
		}

		k_mutex_unlock(&mcr20a->phy_mutex);

		if (set_new_seq) {
			k_sem_give(&mcr20a->seq_sync);
		}
	}
}

static inline void irqb_int_handler(const struct device *port,
				    struct gpio_callback *cb, uint32_t pins)
{
	struct mcr20a_context *mcr20a = CONTAINER_OF(cb,
						     struct mcr20a_context,
						     irqb_cb);
	k_sem_give(&mcr20a->isr_sem);
}

static void enable_irqb_interrupt(struct mcr20a_context *mcr20a,
				 bool enable)
{
	gpio_flags_t flags = enable
		? GPIO_INT_EDGE_TO_ACTIVE
		: GPIO_INT_DISABLE;

	gpio_pin_interrupt_configure(mcr20a->irq_gpio,
				     DT_INST_GPIO_PIN(0, irqb_gpios),
				     flags);
}

static inline void setup_gpio_callbacks(struct mcr20a_context *mcr20a)
{
	gpio_init_callback(&mcr20a->irqb_cb,
			   irqb_int_handler,
			   BIT(DT_INST_GPIO_PIN(0, irqb_gpios)));
	gpio_add_callback(mcr20a->irq_gpio, &mcr20a->irqb_cb);
}

static int mcr20a_set_cca_mode(const struct device *dev, uint8_t mode)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t ctrl4;

	ctrl4 = read_reg_phy_ctrl4(mcr20a);
	ctrl4 &= ~MCR20A_PHY_CTRL4_CCATYPE_MASK;
	ctrl4 |= set_bits_phy_ctrl4_ccatype(mode);

	if (!write_reg_phy_ctrl4(mcr20a, ctrl4)) {
		LOG_ERR("Failed");
		return -EIO;
	}

	return 0;
}

static enum ieee802154_hw_caps mcr20a_get_capabilities(const struct device *dev)
{
	return IEEE802154_HW_FCS |
		IEEE802154_HW_2_4_GHZ |
		IEEE802154_HW_TX_RX_ACK |
		IEEE802154_HW_FILTER;
}

/* Note: CCA before TX is enabled by default */
static int mcr20a_cca(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;
	int retval;

	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);

	if (!mcr20a_mask_irqb(mcr20a, true)) {
		LOG_ERR("Failed to mask IRQ_B");
		goto error;
	}

	k_sem_init(&mcr20a->seq_sync, 0, 1);

	if (mcr20a_abort_sequence(mcr20a, false)) {
		LOG_ERR("Failed to reset XCV sequence");
		goto error;
	}

	LOG_DBG("start CCA sequence");

	if (mcr20a_set_sequence(mcr20a, MCR20A_XCVSEQ_CCA)) {
		LOG_ERR("Failed to reset XCV sequence");
		goto error;
	}

	if (!mcr20a_mask_irqb(mcr20a, false)) {
		LOG_ERR("Failed to unmask IRQ_B");
		goto error;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);
	retval = k_sem_take(&mcr20a->seq_sync,
			    K_MSEC(MCR20A_SEQ_SYNC_TIMEOUT));
	if (retval) {
		LOG_ERR("Timeout occurred, %d", retval);
		return retval;
	}

	LOG_DBG("done");

	return mcr20a->seq_retval;

error:
	k_mutex_unlock(&mcr20a->phy_mutex);
	return -EIO;
}

static int mcr20a_set_channel(const struct device *dev, uint16_t channel)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t buf[3];
	uint8_t ctrl1;
	int retval = -EIO;

	if (channel < 11 || channel > 26) {
		LOG_ERR("Unsupported channel %u", channel);
		return -EINVAL;
	}

	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);

	if (!mcr20a_mask_irqb(mcr20a, true)) {
		LOG_ERR("Failed to mask IRQ_B");
		goto out;
	}

	ctrl1 = read_reg_phy_ctrl1(mcr20a);

	if (mcr20a_abort_sequence(mcr20a, true)) {
		LOG_ERR("Failed to reset XCV sequence");
		goto out;
	}

	LOG_DBG("%u", channel);
	channel -= 11U;
	buf[0] = set_bits_pll_int0_val(pll_int_lt[channel]);
	buf[1] = (uint8_t)pll_frac_lt[channel];
	buf[2] = (uint8_t)(pll_frac_lt[channel] >> 8);

	if (!write_burst_pll_int0(mcr20a, buf)) {
		LOG_ERR("Failed to set PLL");
		goto out;
	}

	if (mcr20a_set_sequence(mcr20a, ctrl1)) {
		LOG_ERR("Failed to restore XCV sequence");
		goto out;
	}

	retval = 0;

out:
	if (!mcr20a_mask_irqb(mcr20a, false)) {
		LOG_ERR("Failed to unmask IRQ_B");
		retval = -EIO;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);

	return retval;
}

static int mcr20a_set_pan_id(const struct device *dev, uint16_t pan_id)
{
	struct mcr20a_context *mcr20a = dev->data;

	pan_id = sys_le16_to_cpu(pan_id);
	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);

	if (!write_burst_pan_id(mcr20a, (uint8_t *) &pan_id)) {
		LOG_ERR("Failed");
		k_mutex_unlock(&mcr20a->phy_mutex);
		return -EIO;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);
	LOG_DBG("0x%x", pan_id);

	return 0;
}

static int mcr20a_set_short_addr(const struct device *dev,
				 uint16_t short_addr)
{
	struct mcr20a_context *mcr20a = dev->data;

	short_addr = sys_le16_to_cpu(short_addr);
	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);

	if (!write_burst_short_addr(mcr20a, (uint8_t *) &short_addr)) {
		LOG_ERR("Failed");
		k_mutex_unlock(&mcr20a->phy_mutex);
		return -EIO;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);
	LOG_DBG("0x%x", short_addr);

	return 0;
}

static int mcr20a_set_ieee_addr(const struct device *dev,
				const uint8_t *ieee_addr)
{
	struct mcr20a_context *mcr20a = dev->data;

	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);

	if (!write_burst_ext_addr(mcr20a, (void *)ieee_addr)) {
		LOG_ERR("Failed");
		k_mutex_unlock(&mcr20a->phy_mutex);
		return -EIO;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);
	LOG_DBG("IEEE address %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x",
		    ieee_addr[7], ieee_addr[6], ieee_addr[5], ieee_addr[4],
		    ieee_addr[3], ieee_addr[2], ieee_addr[1], ieee_addr[0]);

	return 0;
}

static int mcr20a_filter(const struct device *dev,
			 bool set,
			 enum ieee802154_filter_type type,
			 const struct ieee802154_filter *filter)
{
	LOG_DBG("Applying filter %u", type);

	if (!set) {
		return -ENOTSUP;
	}

	if (type == IEEE802154_FILTER_TYPE_IEEE_ADDR) {
		return mcr20a_set_ieee_addr(dev, filter->ieee_addr);
	} else if (type == IEEE802154_FILTER_TYPE_SHORT_ADDR) {
		return mcr20a_set_short_addr(dev, filter->short_addr);
	} else if (type == IEEE802154_FILTER_TYPE_PAN_ID) {
		return mcr20a_set_pan_id(dev, filter->pan_id);
	}

	return -ENOTSUP;
}

static int mcr20a_set_txpower(const struct device *dev, int16_t dbm)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t pwr;

	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);
	LOG_DBG("%d", dbm);

	if ((dbm > MCR20A_OUTPUT_POWER_MAX) ||
	    (dbm < MCR20A_OUTPUT_POWER_MIN)) {
		goto error;
	}

	pwr = pow_lt[dbm - MCR20A_OUTPUT_POWER_MIN];
	if (!write_reg_pa_pwr(mcr20a, set_bits_pa_pwr_val(pwr))) {
		goto error;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);
	return 0;

error:
	k_mutex_unlock(&mcr20a->phy_mutex);
	LOG_DBG("Failed");
	return -EIO;
}

static inline bool write_txfifo_content(struct mcr20a_context *dev,
					struct net_pkt *pkt,
					struct net_buf *frag)
{
	size_t payload_len = frag->len;
	uint8_t cmd_buf[2] = {
		MCR20A_BUF_WRITE,
		payload_len + MCR20A_FCS_LENGTH
	};
	const struct spi_buf bufs[2] = {
		{
			.buf = cmd_buf,
			.len = 2
		},
		{
			.buf = frag->data,
			.len = payload_len
		}
	};
	const struct spi_buf_set tx = {
		.buffers = bufs,
		.count = 2
	};

	if (payload_len > MCR20A_PSDU_LENGTH) {
		LOG_ERR("Payload too long");
		return 0;
	}

	return (spi_write(dev->spi, &dev->spi_cfg, &tx) == 0);
}

static int mcr20a_tx(const struct device *dev,
		     enum ieee802154_tx_mode mode,
		     struct net_pkt *pkt,
		     struct net_buf *frag)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t seq = ieee802154_is_ar_flag_set(frag) ? MCR20A_XCVSEQ_TX_RX :
						     MCR20A_XCVSEQ_TX;
	int retval;

	if (mode != IEEE802154_TX_MODE_DIRECT) {
		NET_ERR("TX mode %d not supported", mode);
		return -ENOTSUP;
	}

	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);

	LOG_DBG("%p (%u)", frag, frag->len);

	if (!mcr20a_mask_irqb(mcr20a, true)) {
		LOG_ERR("Failed to mask IRQ_B");
		goto error;
	}

	if (mcr20a_abort_sequence(mcr20a, false)) {
		LOG_ERR("Failed to reset XCV sequence");
		goto error;
	}

	if (!write_txfifo_content(mcr20a, pkt, frag)) {
		LOG_ERR("Did not write properly into TX FIFO");
		goto error;
	}

	k_sem_init(&mcr20a->seq_sync, 0, 1);

	if (mcr20a_set_sequence(mcr20a, seq)) {
		LOG_ERR("Cannot start transmission");
		goto error;
	}

	if (!mcr20a_mask_irqb(mcr20a, false)) {
		LOG_ERR("Failed to unmask IRQ_B");
		goto error;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);
	retval = k_sem_take(&mcr20a->seq_sync,
			    K_MSEC(MCR20A_SEQ_SYNC_TIMEOUT));
	if (retval) {
		LOG_ERR("Timeout occurred, %d", retval);
		return retval;
	}

	LOG_DBG("done");

	return mcr20a->seq_retval;

error:
	k_mutex_unlock(&mcr20a->phy_mutex);
	return -EIO;
}

static int mcr20a_start(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t timeout = 6U;
	uint8_t status;

	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);
	enable_irqb_interrupt(mcr20a, false);

	if (!write_reg_pwr_modes(mcr20a, MCR20A_PM_AUTODOZE)) {
		LOG_ERR("Error starting MCR20A");
		goto error;
	}

	do {
		z_usleep(50);
		timeout--;
		status = read_reg_pwr_modes(mcr20a);
	} while (!(status & MCR20A_PWR_MODES_XTAL_READY) && timeout);

	if (!(status & MCR20A_PWR_MODES_XTAL_READY)) {
		LOG_ERR("Timeout, failed to wake up");
		goto error;
	}

	/* Clear all interrupt flags */
	write_reg_irqsts1(mcr20a, MCR20A_IRQSTS1_IRQ_MASK);
	write_reg_irqsts2(mcr20a, MCR20A_IRQSTS2_IRQ_MASK);
	write_reg_irqsts3(mcr20a, MCR20A_IRQSTS3_IRQ_MASK |
			  MCR20A_IRQSTS3_TMR_MASK);

	if (mcr20a_abort_sequence(mcr20a, true)) {
		LOG_ERR("Failed to reset XCV sequence");
		goto error;
	}

	if (mcr20a_set_sequence(mcr20a, MCR20A_XCVSEQ_RECEIVE)) {
		LOG_ERR("Failed to set XCV sequence");
		goto error;
	}

	enable_irqb_interrupt(mcr20a, true);

	if (!mcr20a_mask_irqb(mcr20a, false)) {
		LOG_ERR("Failed to unmask IRQ_B");
		goto error;
	}

	k_mutex_unlock(&mcr20a->phy_mutex);
	LOG_DBG("started");

	return 0;

error:
	k_mutex_unlock(&mcr20a->phy_mutex);
	return -EIO;
}

static int mcr20a_stop(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t power_mode;

	k_mutex_lock(&mcr20a->phy_mutex, K_FOREVER);

	if (!mcr20a_mask_irqb(mcr20a, true)) {
		LOG_ERR("Failed to mask IRQ_B");
		goto error;
	}

	if (mcr20a_abort_sequence(mcr20a, true)) {
		LOG_ERR("Failed to reset XCV sequence");
		goto error;
	}

	enable_irqb_interrupt(mcr20a, false);

	if (PART_OF_KW2XD_SIP) {
		power_mode = MCR20A_PM_DOZE;
	} else {
		power_mode = MCR20A_PM_HIBERNATE;
	}

	if (!write_reg_pwr_modes(mcr20a, power_mode)) {
		goto error;
	}

	LOG_DBG("stopped");
	k_mutex_unlock(&mcr20a->phy_mutex);

	return 0;

error:
	k_mutex_unlock(&mcr20a->phy_mutex);
	LOG_ERR("Error stopping MCR20A");
	return -EIO;
}

static int mcr20a_update_overwrites(struct mcr20a_context *dev)
{
	if (!write_reg_overwrite_ver(dev, overwrites_direct[0].data)) {
		goto error;
	}

	for (uint8_t i = 0;
	     i < sizeof(overwrites_indirect) / sizeof(overwrites_t);
	     i++) {

		if (!z_mcr20a_write_reg(dev, false,
					overwrites_indirect[i].address,
					overwrites_indirect[i].data)) {
			goto error;
		}
	}

	return 0;

error:
	LOG_ERR("Error update overwrites");
	return -EIO;
}

static int power_on_and_setup(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t timeout = 6U;
	int pin;
	uint8_t tmp = 0U;

	if (!PART_OF_KW2XD_SIP) {
		gpio_pin_set(mcr20a->reset_gpio,
			     DT_INST_GPIO_PIN(0, reset_gpios), 1);
		z_usleep(150);
		gpio_pin_set(mcr20a->reset_gpio,
			     DT_INST_GPIO_PIN(0, reset_gpios), 0);

		do {
			z_usleep(50);
			timeout--;
			pin = gpio_pin_get(mcr20a->irq_gpio,
					   DT_INST_GPIO_PIN(0, irqb_gpios));
		} while (pin > 0 && timeout);

		if (pin) {
			LOG_ERR("Timeout, failed to get WAKE IRQ");
			return -EIO;
		}

	}

	tmp = MCR20A_CLK_OUT_CONFIG | MCR20A_CLK_OUT_EXTEND;
	write_reg_clk_out_ctrl(mcr20a, tmp);

	if (read_reg_clk_out_ctrl(mcr20a) != tmp) {
		LOG_ERR("Failed to get device up");
		return -EIO;
	}

	/* Clear all interrupt flags */
	write_reg_irqsts1(mcr20a, MCR20A_IRQSTS1_IRQ_MASK);
	write_reg_irqsts2(mcr20a, MCR20A_IRQSTS2_IRQ_MASK);
	write_reg_irqsts3(mcr20a, MCR20A_IRQSTS3_IRQ_MASK |
			  MCR20A_IRQSTS3_TMR_MASK);

	mcr20a_update_overwrites(mcr20a);
	mcr20a_timer_init(dev, MCR20A_TIMEBASE_62500HZ);

	mcr20a_set_txpower(dev, MCR20A_DEFAULT_TX_POWER);
	mcr20a_set_channel(dev, MCR20A_DEFAULT_CHANNEL);
	mcr20a_set_cca_mode(dev, 1);
	write_reg_rx_wtr_mark(mcr20a, 8);

	/* Configure PHY behaviour */
	tmp = MCR20A_PHY_CTRL1_CCABFRTX |
	      MCR20A_PHY_CTRL1_AUTOACK |
	      MCR20A_PHY_CTRL1_RXACKRQD;
	write_reg_phy_ctrl1(mcr20a, tmp);

	/* Enable Sequence-end interrupt */
	tmp = MCR20A_PHY_CTRL2_SEQMSK;
	write_reg_phy_ctrl2(mcr20a, ~tmp);

	setup_gpio_callbacks(mcr20a);

	return 0;
}


static inline int configure_gpios(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;

	/* setup gpio for the modem interrupt */
	mcr20a->irq_gpio =
		device_get_binding(DT_INST_GPIO_LABEL(0, irqb_gpios));
	if (mcr20a->irq_gpio == NULL) {
		LOG_ERR("Failed to get pointer to %s device",
			DT_INST_GPIO_LABEL(0, irqb_gpios));
		return -EINVAL;
	}

	gpio_pin_configure(mcr20a->irq_gpio,
			   DT_INST_GPIO_PIN(0, irqb_gpios),
			   GPIO_INPUT | DT_INST_GPIO_FLAGS(0, irqb_gpios));

	if (!PART_OF_KW2XD_SIP) {
		/* setup gpio for the modems reset */
		mcr20a->reset_gpio =
			device_get_binding(
				DT_INST_GPIO_LABEL(0, reset_gpios));
		if (mcr20a->reset_gpio == NULL) {
			LOG_ERR("Failed to get pointer to %s device",
				DT_INST_GPIO_LABEL(0, reset_gpios));
			return -EINVAL;
		}

		gpio_pin_configure(mcr20a->reset_gpio,
				   DT_INST_GPIO_PIN(0, reset_gpios),
				   GPIO_OUTPUT_ACTIVE |
				   DT_INST_GPIO_FLAGS(0, reset_gpios));
	}

	return 0;
}

static inline int configure_spi(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;

	mcr20a->spi = device_get_binding(DT_INST_BUS_LABEL(0));
	if (!mcr20a->spi) {
		LOG_ERR("Unable to get SPI device");
		return -ENODEV;
	}

#if DT_INST_SPI_DEV_HAS_CS_GPIOS(0)
	mcr20a->cs_ctrl.gpio_dev = device_get_binding(
		DT_INST_SPI_DEV_CS_GPIOS_LABEL(0));
	if (!mcr20a->cs_ctrl.gpio_dev) {
		LOG_ERR("Unable to get GPIO SPI CS device");
		return -ENODEV;
	}

	mcr20a->cs_ctrl.gpio_pin = DT_INST_SPI_DEV_CS_GPIOS_PIN(0);
	mcr20a->cs_ctrl.gpio_flags = DT_INST_SPI_DEV_CS_GPIOS_FLAGS(0);
	mcr20a->cs_ctrl.delay = 0U;

	mcr20a->spi_cfg.cs = &mcr20a->cs_ctrl;

	LOG_DBG("SPI GPIO CS configured on %s:%u",
		DT_INST_SPI_DEV_CS_GPIOS_LABEL(0),
		DT_INST_SPI_DEV_CS_GPIOS_PIN(0));
#endif /* DT_INST_SPI_DEV_HAS_CS_GPIOS(0) */

	mcr20a->spi_cfg.frequency = DT_INST_PROP(0, spi_max_frequency);
	mcr20a->spi_cfg.operation = SPI_WORD_SET(8);
	mcr20a->spi_cfg.slave = DT_INST_REG_ADDR(0);

	LOG_DBG("SPI configured %s, %d",
		DT_INST_BUS_LABEL(0),
		DT_INST_REG_ADDR(0));

	return 0;
}

static int mcr20a_init(const struct device *dev)
{
	struct mcr20a_context *mcr20a = dev->data;

	k_mutex_init(&mcr20a->phy_mutex);
	k_sem_init(&mcr20a->isr_sem, 0, 1);

	LOG_DBG("\nInitialize MCR20A Transceiver\n");

	if (configure_gpios(dev) != 0) {
		LOG_ERR("Configuring GPIOS failed");
		return -EIO;
	}

	if (configure_spi(dev) != 0) {
		LOG_ERR("Configuring SPI failed");
		return -EIO;
	}

	LOG_DBG("GPIO and SPI configured");

	if (power_on_and_setup(dev) != 0) {
		LOG_ERR("Configuring MCR20A failed");
		return -EIO;
	}

	k_thread_create(&mcr20a->mcr20a_rx_thread, mcr20a->mcr20a_rx_stack,
			CONFIG_IEEE802154_MCR20A_RX_STACK_SIZE,
			(k_thread_entry_t)mcr20a_thread_main,
			mcr20a, NULL, NULL, K_PRIO_COOP(2), 0, K_NO_WAIT);
	k_thread_name_set(&mcr20a->mcr20a_rx_thread, "mcr20a_rx");

	return 0;
}

static void mcr20a_iface_init(struct net_if *iface)
{
	const struct device *dev = net_if_get_device(iface);
	struct mcr20a_context *mcr20a = dev->data;
	uint8_t *mac = get_mac(dev);

	net_if_set_link_addr(iface, mac, 8, NET_LINK_IEEE802154);

	mcr20a->iface = iface;

	ieee802154_init(iface);

	LOG_DBG("done");
}

static struct mcr20a_context mcr20a_context_data;

static struct ieee802154_radio_api mcr20a_radio_api = {
	.iface_api.init	= mcr20a_iface_init,

	.get_capabilities	= mcr20a_get_capabilities,
	.cca			= mcr20a_cca,
	.set_channel		= mcr20a_set_channel,
	.filter			= mcr20a_filter,
	.set_txpower		= mcr20a_set_txpower,
	.start			= mcr20a_start,
	.stop			= mcr20a_stop,
	.tx			= mcr20a_tx,
};

#if defined(CONFIG_IEEE802154_RAW_MODE)
DEVICE_DEFINE(mcr20a, CONFIG_IEEE802154_MCR20A_DRV_NAME,
		mcr20a_init, device_pm_control_nop, &mcr20a_context_data, NULL,
		POST_KERNEL, CONFIG_IEEE802154_MCR20A_INIT_PRIO,
		&mcr20a_radio_api);
#else
NET_DEVICE_INIT(mcr20a, CONFIG_IEEE802154_MCR20A_DRV_NAME,
		mcr20a_init, device_pm_control_nop, &mcr20a_context_data, NULL,
		CONFIG_IEEE802154_MCR20A_INIT_PRIO,
		&mcr20a_radio_api, IEEE802154_L2,
		NET_L2_GET_CTX_TYPE(IEEE802154_L2),
		MCR20A_PSDU_LENGTH);
#endif
