// SPDX-License-Identifier: GPL-2.0+
/*
 * Xilinx SPI driver
 *
 * Supports 8 bit SPI transfers only, with or w/o FIFO
 *
 * Based on bfin_spi.c, by way of altera_spi.c
 * Copyright (c) 2015 Jagan Teki <jteki@openedev.com>
 * Copyright (c) 2012 Stephan Linz <linz@li-pro.net>
 * Copyright (c) 2010 Graeme Smecher <graeme.smecher@mail.mcgill.ca>
 * Copyright (c) 2010 Thomas Chou <thomas@wytron.com.tw>
 * Copyright (c) 2005-2008 Analog Devices Inc.
 */

#include <config.h>
#include <common.h>
#include <dm.h>
#include <errno.h>
#include <log.h>
#include <malloc.h>
#include <spi.h>
#include <spi-mem.h>
#include <asm/io.h>
#include <wait_bit.h>
#include <linux/bitops.h>

/*
 * [0]: http://www.xilinx.com/support/documentation
 *
 * Xilinx SPI Register Definitions
 * [1]:	[0]/ip_documentation/xps_spi.pdf
 *	page 8, Register Descriptions
 * [2]:	[0]/ip_documentation/axi_spi_ds742.pdf
 *	page 7, Register Overview Table
 */

/* SPI Control Register (spicr), [1] p9, [2] p8 */
#define SPICR_LSB_FIRST		BIT(9)
#define SPICR_MASTER_INHIBIT	BIT(8)
#define SPICR_MANUAL_SS		BIT(7)
#define SPICR_RXFIFO_RESEST	BIT(6)
#define SPICR_TXFIFO_RESEST	BIT(5)
#define SPICR_CPHA		BIT(4)
#define SPICR_CPOL		BIT(3)
#define SPICR_MASTER_MODE	BIT(2)
#define SPICR_SPE		BIT(1)
#define SPICR_LOOP		BIT(0)

/* SPI Status Register (spisr), [1] p11, [2] p10 */
#define SPISR_SLAVE_MODE_SELECT	BIT(5)
#define SPISR_MODF		BIT(4)
#define SPISR_TX_FULL		BIT(3)
#define SPISR_TX_EMPTY		BIT(2)
#define SPISR_RX_FULL		BIT(1)
#define SPISR_RX_EMPTY		BIT(0)

/* SPI Data Transmit Register (spidtr), [1] p12, [2] p12 */
#define SPIDTR_8BIT_MASK	GENMASK(7, 0)
#define SPIDTR_16BIT_MASK	GENMASK(15, 0)
#define SPIDTR_32BIT_MASK	GENMASK(31, 0)

/* SPI Data Receive Register (spidrr), [1] p12, [2] p12 */
#define SPIDRR_8BIT_MASK	GENMASK(7, 0)
#define SPIDRR_16BIT_MASK	GENMASK(15, 0)
#define SPIDRR_32BIT_MASK	GENMASK(31, 0)

/* SPI Slave Select Register (spissr), [1] p13, [2] p13 */
#define SPISSR_MASK(cs)		(1 << (cs))
#define SPISSR_ACT(cs)		~SPISSR_MASK(cs)
#define SPISSR_OFF		~0UL

/* SPI Software Reset Register (ssr) */
#define SPISSR_RESET_VALUE	0x0a

#define XILSPI_MAX_XFER_BITS	8
#define XILSPI_SPICR_DFLT_ON	(SPICR_MANUAL_SS | SPICR_MASTER_MODE | \
				SPICR_SPE | SPICR_MASTER_INHIBIT)
#define XILSPI_SPICR_DFLT_OFF	(SPICR_MASTER_INHIBIT | SPICR_MANUAL_SS)

#define XILINX_SPI_IDLE_VAL	GENMASK(7, 0)

#define XILINX_SPISR_TIMEOUT	10000 /* in milliseconds */

/* xilinx spi register set */
struct xilinx_spi_regs {
	u32 __space0__[7];
	u32 dgier;	/* Device Global Interrupt Enable Register (DGIER) */
	u32 ipisr;	/* IP Interrupt Status Register (IPISR) */
	u32 __space1__;
	u32 ipier;	/* IP Interrupt Enable Register (IPIER) */
	u32 __space2__[5];
	u32 srr;	/* Softare Reset Register (SRR) */
	u32 __space3__[7];
	u32 spicr;	/* SPI Control Register (SPICR) */
	u32 spisr;	/* SPI Status Register (SPISR) */
	u32 spidtr;	/* SPI Data Transmit Register (SPIDTR) */
	u32 spidrr;	/* SPI Data Receive Register (SPIDRR) */
	u32 spissr;	/* SPI Slave Select Register (SPISSR) */
	u32 spitfor;	/* SPI Transmit FIFO Occupancy Register (SPITFOR) */
	u32 spirfor;	/* SPI Receive FIFO Occupancy Register (SPIRFOR) */
};

/* xilinx spi priv */
struct xilinx_spi_priv {
	struct xilinx_spi_regs *regs;
	unsigned int freq;
	unsigned int mode;
	unsigned int fifo_depth;
	u8 startup;
};

static int xilinx_spi_probe(struct udevice *bus)
{
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs;

	regs = priv->regs = (struct xilinx_spi_regs *)dev_read_addr(bus);
	priv->fifo_depth = dev_read_u32_default(bus, "fifo-size", 0);

	writel(SPISSR_RESET_VALUE, &regs->srr);

	/*
	 * Reset RX & TX FIFO
	 * Enable Manual Slave Select Assertion,
	 * Set SPI controller into master mode, and enable it
	 */
	writel(SPICR_RXFIFO_RESEST | SPICR_TXFIFO_RESEST |
	       SPICR_MANUAL_SS | SPICR_MASTER_MODE | SPICR_SPE,
	       &regs->spicr);

	return 0;
}

static void spi_cs_activate(struct udevice *dev, uint cs)
{
	struct udevice *bus = dev_get_parent(dev);
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;

	writel(SPISSR_ACT(cs), &regs->spissr);
}

static void spi_cs_deactivate(struct udevice *dev)
{
	struct udevice *bus = dev_get_parent(dev);
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;
	u32 reg;

	reg = readl(&regs->spicr) | SPICR_RXFIFO_RESEST | SPICR_TXFIFO_RESEST;
	writel(reg, &regs->spicr);
	writel(SPISSR_OFF, &regs->spissr);
}

static int xilinx_spi_claim_bus(struct udevice *dev)
{
	struct udevice *bus = dev_get_parent(dev);
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;

	writel(SPISSR_OFF, &regs->spissr);
	writel(XILSPI_SPICR_DFLT_ON, &regs->spicr);

	return 0;
}

static int xilinx_spi_release_bus(struct udevice *dev)
{
	struct udevice *bus = dev_get_parent(dev);
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;

	writel(SPISSR_OFF, &regs->spissr);
	writel(XILSPI_SPICR_DFLT_OFF, &regs->spicr);

	return 0;
}

static u32 xilinx_spi_fill_txfifo(struct udevice *bus, const u8 *txp,
				  u32 txbytes)
{
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;
	unsigned char d;
	u32 i = 0;

	while (txbytes && !(readl(&regs->spisr) & SPISR_TX_FULL) &&
	       i < priv->fifo_depth) {
		d = txp ? *txp++ : XILINX_SPI_IDLE_VAL;
		debug("spi_xfer: tx:%x ", d);
		/* write out and wait for processing (receive data) */
		writel(d & SPIDTR_8BIT_MASK, &regs->spidtr);
		txbytes--;
		i++;
	}

	return i;
}

static u32 xilinx_spi_read_rxfifo(struct udevice *bus, u8 *rxp, u32 rxbytes)
{
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;
	unsigned char d;
	unsigned int i = 0;

	while (rxbytes && !(readl(&regs->spisr) & SPISR_RX_EMPTY)) {
		d = readl(&regs->spidrr) & SPIDRR_8BIT_MASK;
		if (rxp)
			*rxp++ = d;
		debug("spi_xfer: rx:%x\n", d);
		rxbytes--;
		i++;
	}
	debug("Rx_done\n");

	return i;
}

static int start_transfer(struct spi_slave *spi, const void *dout, void *din, u32 len)
{
	struct udevice *bus = spi->dev->parent;
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;
	u32 count, txbytes, rxbytes;
	int reg, ret;
	const unsigned char *txp = (const unsigned char *)dout;
	unsigned char *rxp = (unsigned char *)din;

	txbytes = len;
	rxbytes = len;
	while (txbytes || rxbytes) {
		/* Disable master transaction */
		reg = readl(&regs->spicr) | SPICR_MASTER_INHIBIT;
		writel(reg, &regs->spicr);
		count = xilinx_spi_fill_txfifo(bus, txp, txbytes);
		/* Enable master transaction */
		reg = readl(&regs->spicr) & ~SPICR_MASTER_INHIBIT;
		writel(reg, &regs->spicr);
		txbytes -= count;
		if (txp)
			txp += count;

		ret = wait_for_bit_le32(&regs->spisr, SPISR_TX_EMPTY, true,
					XILINX_SPISR_TIMEOUT, false);
		if (ret < 0) {
			printf("XILSPI error: Xfer timeout\n");
			return ret;
		}

		reg = readl(&regs->spicr) | SPICR_MASTER_INHIBIT;
		writel(reg, &regs->spicr);
		count = xilinx_spi_read_rxfifo(bus, rxp, rxbytes);
		rxbytes -= count;
		if (rxp)
			rxp += count;
	}

	return 0;
}

static void xilinx_spi_startup_block(struct spi_slave *spi)
{
	struct dm_spi_slave_plat *slave_plat =
				dev_get_parent_plat(spi->dev);
	unsigned char txp;
	unsigned char rxp[8];

	/*
	 * Perform a dummy read as a work around for
	 * the startup block issue.
	 */
	spi_cs_activate(spi->dev, slave_plat->cs);
	txp = 0x9f;
	start_transfer(spi, (void *)&txp, NULL, 1);

	start_transfer(spi, NULL, (void *)rxp, 6);

	spi_cs_deactivate(spi->dev);
}

static int xilinx_spi_mem_exec_op(struct spi_slave *spi,
				  const struct spi_mem_op *op)
{
	struct dm_spi_slave_plat *slave_plat =
				dev_get_parent_plat(spi->dev);
	static u32 startup;
	u32 dummy_len, ret;

	/*
	 * This is the work around for the startup block issue in
	 * the spi controller. SPI clock is passing through STARTUP
	 * block to FLASH. STARTUP block don't provide clock as soon
	 * as QSPI provides command. So first command fails.
	 */
	if (!startup) {
		xilinx_spi_startup_block(spi);
		startup++;
	}

	spi_cs_activate(spi->dev, slave_plat->cs);

	if (op->cmd.opcode) {
		ret = start_transfer(spi, (void *)&op->cmd.opcode, NULL, 1);
		if (ret)
			goto done;
	}
	if (op->addr.nbytes) {
		int i;
		u8 addr_buf[4];

		for (i = 0; i < op->addr.nbytes; i++)
			addr_buf[i] = op->addr.val >>
			(8 * (op->addr.nbytes - i - 1));

		ret = start_transfer(spi, (void *)addr_buf, NULL,
				     op->addr.nbytes);
		if (ret)
			goto done;
	}
	if (op->dummy.nbytes) {
		dummy_len = (op->dummy.nbytes * op->data.buswidth) /
			     op->dummy.buswidth;

		ret = start_transfer(spi, NULL, NULL, dummy_len);
		if (ret)
			goto done;
	}
	if (op->data.nbytes) {
		if (op->data.dir == SPI_MEM_DATA_IN) {
			ret = start_transfer(spi, NULL,
					     op->data.buf.in, op->data.nbytes);
		} else {
			ret = start_transfer(spi, op->data.buf.out,
					     NULL, op->data.nbytes);
		}
		if (ret)
			goto done;
	}
done:
	spi_cs_deactivate(spi->dev);

	return ret;
}

static int xilinx_qspi_check_buswidth(struct spi_slave *slave, u8 width)
{
	u32 mode = slave->mode;

	switch (width) {
	case 1:
		return 0;
	case 2:
		if (mode & SPI_RX_DUAL)
			return 0;
		break;
	case 4:
		if (mode & SPI_RX_QUAD)
			return 0;
		break;
	}

	return -EOPNOTSUPP;
}

bool xilinx_qspi_mem_exec_op(struct spi_slave *slave,
			     const struct spi_mem_op *op)
{
	if (xilinx_qspi_check_buswidth(slave, op->cmd.buswidth))
		return false;

	if (op->addr.nbytes &&
	    xilinx_qspi_check_buswidth(slave, op->addr.buswidth))
		return false;

	if (op->dummy.nbytes &&
	    xilinx_qspi_check_buswidth(slave, op->dummy.buswidth))
		return false;

	if (op->data.dir != SPI_MEM_NO_DATA &&
	    xilinx_qspi_check_buswidth(slave, op->data.buswidth))
		return false;

	return true;
}

static int xilinx_spi_set_speed(struct udevice *bus, uint speed)
{
	struct xilinx_spi_priv *priv = dev_get_priv(bus);

	priv->freq = speed;

	debug("%s: regs=%p, speed=%d\n", __func__, priv->regs, priv->freq);

	return 0;
}

static int xilinx_spi_set_mode(struct udevice *bus, uint mode)
{
	struct xilinx_spi_priv *priv = dev_get_priv(bus);
	struct xilinx_spi_regs *regs = priv->regs;
	u32 spicr;

	spicr = readl(&regs->spicr);
	if (mode & SPI_LSB_FIRST)
		spicr |= SPICR_LSB_FIRST;
	if (mode & SPI_CPHA)
		spicr |= SPICR_CPHA;
	if (mode & SPI_CPOL)
		spicr |= SPICR_CPOL;
	if (mode & SPI_LOOP)
		spicr |= SPICR_LOOP;

	writel(spicr, &regs->spicr);
	priv->mode = mode;

	debug("%s: regs=%p, mode=%d\n", __func__, priv->regs, priv->mode);

	return 0;
}

static const struct spi_controller_mem_ops xilinx_spi_mem_ops = {
	.exec_op = xilinx_spi_mem_exec_op,
	.supports_op = xilinx_qspi_mem_exec_op,
};

static const struct dm_spi_ops xilinx_spi_ops = {
	.claim_bus	= xilinx_spi_claim_bus,
	.release_bus	= xilinx_spi_release_bus,
	.set_speed	= xilinx_spi_set_speed,
	.set_mode	= xilinx_spi_set_mode,
	.mem_ops	= &xilinx_spi_mem_ops,
};

static const struct udevice_id xilinx_spi_ids[] = {
	{ .compatible = "xlnx,xps-spi-2.00.a" },
	{ .compatible = "xlnx,xps-spi-2.00.b" },
	{ }
};

U_BOOT_DRIVER(xilinx_spi) = {
	.name	= "xilinx_spi",
	.id	= UCLASS_SPI,
	.of_match = xilinx_spi_ids,
	.ops	= &xilinx_spi_ops,
	.priv_auto	= sizeof(struct xilinx_spi_priv),
	.probe	= xilinx_spi_probe,
};
