/*
 * drivers/dma/fsl-edma3-v3.c
 *
 * Copyright 2017-2018 NXP .
 *
 * Driver for the Freescale eDMA engine v3. This driver based on fsl-edma3.c
 * but changed to meet the IP change on i.MX8QM: every dma channel is specific
 * to hardware. For example, channel 14 for LPUART1 receive request and channel
 * 13 for transmit requesst. The eDMA block can be found on i.MX8QM
 *
 * This program is free software; you can redistribute  it and/or modify it
 * under  the terms of  the GNU General  Public License as published by the
 * Free Software Foundation;  either version 2 of the  License, or (at your
 * option) any later version.
 */

#include <linux/init.h>
#include <linux/module.h>
#include <linux/interrupt.h>
#include <linux/clk.h>
#include <linux/dma-mapping.h>
#include <linux/dmapool.h>
#include <linux/slab.h>
#include <linux/spinlock.h>
#include <linux/of.h>
#include <linux/of_device.h>
#include <linux/of_address.h>
#include <linux/of_irq.h>
#include <linux/of_dma.h>

#include "virt-dma.h"

#define EDMA_CH_CSR			0x00
#define EDMA_CH_ES			0x04
#define EDMA_CH_INT			0x08
#define EDMA_CH_SBR			0x0C
#define EDMA_CH_PRI			0x10
#define EDMA_TCD_SADDR			0x20
#define EDMA_TCD_SOFF			0x24
#define EDMA_TCD_ATTR			0x26
#define EDMA_TCD_NBYTES			0x28
#define EDMA_TCD_SLAST			0x2C
#define EDMA_TCD_DADDR			0x30
#define EDMA_TCD_DOFF			0x34
#define EDMA_TCD_CITER_ELINK		0x36
#define EDMA_TCD_CITER			0x36
#define EDMA_TCD_DLAST_SGA		0x38
#define EDMA_TCD_CSR			0x3C
#define EDMA_TCD_BITER_ELINK		0x3E
#define EDMA_TCD_BITER			0x3E

#define EDMA_CH_SBR_RD		BIT(22)
#define EDMA_CH_SBR_WR		BIT(21)
#define EDMA_CH_CSR_ERQ		BIT(0)
#define EDMA_CH_CSR_EARQ	BIT(1)
#define EDMA_CH_CSR_EEI		BIT(2)
#define EDMA_CH_CSR_DONE	BIT(30)
#define EDMA_CH_CSR_ACTIVE	BIT(31)

#define EDMA_TCD_ATTR_DSIZE(x)		(((x) & 0x0007))
#define EDMA_TCD_ATTR_DMOD(x)		(((x) & 0x001F) << 3)
#define EDMA_TCD_ATTR_SSIZE(x)		(((x) & 0x0007) << 8)
#define EDMA_TCD_ATTR_SMOD(x)		(((x) & 0x001F) << 11)
#define EDMA_TCD_ATTR_SSIZE_8BIT	(0x0000)
#define EDMA_TCD_ATTR_SSIZE_16BIT	(0x0100)
#define EDMA_TCD_ATTR_SSIZE_32BIT	(0x0200)
#define EDMA_TCD_ATTR_SSIZE_64BIT	(0x0300)
#define EDMA_TCD_ATTR_SSIZE_16BYTE	(0x0400)
#define EDMA_TCD_ATTR_SSIZE_32BYTE	(0x0500)
#define EDMA_TCD_ATTR_SSIZE_64BYTE	(0x0600)
#define EDMA_TCD_ATTR_DSIZE_8BIT	(0x0000)
#define EDMA_TCD_ATTR_DSIZE_16BIT	(0x0001)
#define EDMA_TCD_ATTR_DSIZE_32BIT	(0x0002)
#define EDMA_TCD_ATTR_DSIZE_64BIT	(0x0003)
#define EDMA_TCD_ATTR_DSIZE_16BYTE	(0x0004)
#define EDMA_TCD_ATTR_DSIZE_32BYTE	(0x0005)
#define EDMA_TCD_ATTR_DSIZE_64BYTE	(0x0006)

#define EDMA_TCD_SOFF_SOFF(x)		(x)
#define EDMA_TCD_NBYTES_NBYTES(x)	(x)
#define EDMA_TCD_NBYTES_MLOFF(x)	(x << 10)
#define EDMA_TCD_NBYTES_DMLOE		(1 << 30)
#define EDMA_TCD_NBYTES_SMLOE		(1 << 31)
#define EDMA_TCD_SLAST_SLAST(x)		(x)
#define EDMA_TCD_DADDR_DADDR(x)		(x)
#define EDMA_TCD_CITER_CITER(x)		((x) & 0x7FFF)
#define EDMA_TCD_DOFF_DOFF(x)		(x)
#define EDMA_TCD_DLAST_SGA_DLAST_SGA(x)	(x)
#define EDMA_TCD_BITER_BITER(x)		((x) & 0x7FFF)

#define EDMA_TCD_CSR_START		BIT(0)
#define EDMA_TCD_CSR_INT_MAJOR		BIT(1)
#define EDMA_TCD_CSR_INT_HALF		BIT(2)
#define EDMA_TCD_CSR_D_REQ		BIT(3)
#define EDMA_TCD_CSR_E_SG		BIT(4)
#define EDMA_TCD_CSR_E_LINK		BIT(5)
#define EDMA_TCD_CSR_ACTIVE		BIT(6)
#define EDMA_TCD_CSR_DONE		BIT(7)

#define FSL_EDMA_BUSWIDTHS	(BIT(DMA_SLAVE_BUSWIDTH_1_BYTE) | \
				BIT(DMA_SLAVE_BUSWIDTH_2_BYTES) | \
				BIT(DMA_SLAVE_BUSWIDTH_4_BYTES) | \
				BIT(DMA_SLAVE_BUSWIDTH_8_BYTES) | \
				BIT(DMA_SLAVE_BUSWIDTH_16_BYTES))

#define ARGS_RX				BIT(0)
#define ARGS_REMOTE			BIT(1)
#define ARGS_DFIFO			BIT(2)

/* channel name template define in dts */
#define CHAN_PREFIX			"edma0-chan"
#define CHAN_POSFIX			"-tx"

enum fsl_edma3_pm_state {
	RUNNING = 0,
	SUSPENDED,
};

struct fsl_edma3_hw_tcd {
	__le32	saddr;
	__le16	soff;
	__le16	attr;
	__le32	nbytes;
	__le32	slast;
	__le32	daddr;
	__le16	doff;
	__le16	citer;
	__le32	dlast_sga;
	__le16	csr;
	__le16	biter;
};

struct fsl_edma3_sw_tcd {
	dma_addr_t			ptcd;
	struct fsl_edma3_hw_tcd		*vtcd;
};

struct fsl_edma3_slave_config {
	enum dma_transfer_direction	dir;
	enum dma_slave_buswidth		addr_width;
	u32				dev_addr;
	u32				dev2_addr; /* source addr for dev2dev */
	u32				burst;
	u32				attr;
};

struct fsl_edma3_chan {
	struct virt_dma_chan		vchan;
	enum dma_status			status;
	enum fsl_edma3_pm_state		pm_state;
	bool				idle;
	struct fsl_edma3_engine		*edma3;
	struct fsl_edma3_desc		*edesc;
	struct fsl_edma3_slave_config	fsc;
	void __iomem			*membase;
	int				txirq;
	int				hw_chanid;
	int				priority;
	int				is_rxchan;
	int				is_remote;
	int				is_dfifo;
	struct dma_pool			*tcd_pool;
	u32				chn_real_count;
	char				txirq_name[32];
};

struct fsl_edma3_desc {
	struct virt_dma_desc		vdesc;
	struct fsl_edma3_chan		*echan;
	bool				iscyclic;
	unsigned int			n_tcds;
	struct fsl_edma3_sw_tcd		tcd[];
};

struct fsl_edma3_reg_save {
	u32 csr;
	u32 sbr;
};

struct fsl_edma3_engine {
	struct dma_device	dma_dev;
	struct mutex		fsl_edma3_mutex;
	u32			n_chans;
	int			errirq;
	#define MAX_CHAN_NUM	32
	struct fsl_edma3_reg_save edma_regs[MAX_CHAN_NUM];
	bool			swap;	/* remote/local swapped on Audio edma */
	struct fsl_edma3_chan	chans[];
};

static struct fsl_edma3_chan *to_fsl_edma3_chan(struct dma_chan *chan)
{
	return container_of(chan, struct fsl_edma3_chan, vchan.chan);
}

static struct fsl_edma3_desc *to_fsl_edma3_desc(struct virt_dma_desc *vd)
{
	return container_of(vd, struct fsl_edma3_desc, vdesc);
}

static void fsl_edma3_enable_request(struct fsl_edma3_chan *fsl_chan)
{
	void __iomem *addr = fsl_chan->membase;
	u32 val;

	val = readl(addr + EDMA_CH_SBR);
	/* Remote/local swapped wrongly on iMX8 QM Audio edma */
	if (fsl_chan->edma3->swap) {
		if (!fsl_chan->is_rxchan)
			val |= EDMA_CH_SBR_RD;
		else
			val |= EDMA_CH_SBR_WR;
	} else {
		if (fsl_chan->is_rxchan)
			val |= EDMA_CH_SBR_RD;
		else
			val |= EDMA_CH_SBR_WR;
	}

	if (fsl_chan->is_remote)
		val &= ~(EDMA_CH_SBR_RD | EDMA_CH_SBR_WR);

	writel(val, addr + EDMA_CH_SBR);

	val = readl(addr + EDMA_CH_CSR);

	val |= EDMA_CH_CSR_ERQ;
	writel(val, addr + EDMA_CH_CSR);
}

static void fsl_edma3_disable_request(struct fsl_edma3_chan *fsl_chan)
{
	void __iomem *addr = fsl_chan->membase;
	u32 val = readl(addr + EDMA_CH_CSR);

	val &= ~EDMA_CH_CSR_ERQ;
	writel(val, addr + EDMA_CH_CSR);
}

static unsigned int fsl_edma3_get_tcd_attr(enum dma_slave_buswidth addr_width)
{
	switch (addr_width) {
	case 1:
		return EDMA_TCD_ATTR_SSIZE_8BIT | EDMA_TCD_ATTR_DSIZE_8BIT;
	case 2:
		return EDMA_TCD_ATTR_SSIZE_16BIT | EDMA_TCD_ATTR_DSIZE_16BIT;
	case 4:
		return EDMA_TCD_ATTR_SSIZE_32BIT | EDMA_TCD_ATTR_DSIZE_32BIT;
	case 8:
		return EDMA_TCD_ATTR_SSIZE_64BIT | EDMA_TCD_ATTR_DSIZE_64BIT;
	case 16:
		return EDMA_TCD_ATTR_SSIZE_16BYTE | EDMA_TCD_ATTR_DSIZE_16BYTE;
	case 32:
		return EDMA_TCD_ATTR_SSIZE_32BYTE | EDMA_TCD_ATTR_DSIZE_32BYTE;
	case 64:
		return EDMA_TCD_ATTR_SSIZE_64BYTE | EDMA_TCD_ATTR_DSIZE_64BYTE;
	default:
		return EDMA_TCD_ATTR_SSIZE_32BIT | EDMA_TCD_ATTR_DSIZE_32BIT;
	}
}

static void fsl_edma3_free_desc(struct virt_dma_desc *vdesc)
{
	struct fsl_edma3_desc *fsl_desc;
	int i;

	fsl_desc = to_fsl_edma3_desc(vdesc);
	for (i = 0; i < fsl_desc->n_tcds; i++)
		dma_pool_free(fsl_desc->echan->tcd_pool, fsl_desc->tcd[i].vtcd,
			      fsl_desc->tcd[i].ptcd);
	kfree(fsl_desc);
}

static int fsl_edma3_terminate_all(struct dma_chan *chan)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	unsigned long flags;
	LIST_HEAD(head);

	spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
	fsl_edma3_disable_request(fsl_chan);
	fsl_chan->edesc = NULL;
	fsl_chan->idle = true;
	vchan_get_all_descriptors(&fsl_chan->vchan, &head);
	spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
	vchan_dma_desc_free_list(&fsl_chan->vchan, &head);
	return 0;
}

static int fsl_edma3_pause(struct dma_chan *chan)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	unsigned long flags;

	spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
	if (fsl_chan->edesc) {
		fsl_edma3_disable_request(fsl_chan);
		fsl_chan->status = DMA_PAUSED;
		fsl_chan->idle = true;
	}
	spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
	return 0;
}

static int fsl_edma3_resume(struct dma_chan *chan)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	unsigned long flags;

	spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
	if (fsl_chan->edesc) {
		fsl_edma3_enable_request(fsl_chan);
		fsl_chan->status = DMA_IN_PROGRESS;
		fsl_chan->idle = false;
	}
	spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
	return 0;
}

static int fsl_edma3_slave_config(struct dma_chan *chan,
				 struct dma_slave_config *cfg)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);

	fsl_chan->fsc.dir = cfg->direction;
	if (cfg->direction == DMA_DEV_TO_MEM) {
		fsl_chan->fsc.dev_addr = cfg->src_addr;
		fsl_chan->fsc.addr_width = cfg->src_addr_width;
		fsl_chan->fsc.burst = cfg->src_maxburst;
		fsl_chan->fsc.attr = fsl_edma3_get_tcd_attr
					(cfg->src_addr_width);
	} else if (cfg->direction == DMA_MEM_TO_DEV) {
		fsl_chan->fsc.dev_addr = cfg->dst_addr;
		fsl_chan->fsc.addr_width = cfg->dst_addr_width;
		fsl_chan->fsc.burst = cfg->dst_maxburst;
		fsl_chan->fsc.attr = fsl_edma3_get_tcd_attr
					(cfg->dst_addr_width);
	} else if (cfg->direction == DMA_DEV_TO_DEV) {
		fsl_chan->fsc.dev2_addr = cfg->src_addr;
		fsl_chan->fsc.dev_addr = cfg->dst_addr;
		fsl_chan->fsc.addr_width = cfg->dst_addr_width;
		fsl_chan->fsc.burst = cfg->dst_maxburst;
		fsl_chan->fsc.attr = fsl_edma3_get_tcd_attr
					(cfg->dst_addr_width);
	} else {
			return -EINVAL;
	}
	return 0;
}

static size_t fsl_edma3_desc_residue(struct fsl_edma3_chan *fsl_chan,
		struct virt_dma_desc *vdesc, bool in_progress)
{
	struct fsl_edma3_desc *edesc = fsl_chan->edesc;
	void __iomem *addr = fsl_chan->membase;
	enum dma_transfer_direction dir = fsl_chan->fsc.dir;
	dma_addr_t cur_addr, dma_addr;
	size_t len, size;
	int i;

	/* calculate the total size in this desc */
	for (len = i = 0; i < fsl_chan->edesc->n_tcds; i++)
		len += le32_to_cpu(edesc->tcd[i].vtcd->nbytes)
			* le16_to_cpu(edesc->tcd[i].vtcd->biter);

	if (!in_progress)
		return len;

	if (dir == DMA_MEM_TO_DEV)
		cur_addr = readl(addr + EDMA_TCD_SADDR);
	else
		cur_addr = readl(addr + EDMA_TCD_DADDR);

	/* figure out the finished and calculate the residue */
	for (i = 0; i < fsl_chan->edesc->n_tcds; i++) {
		size = le32_to_cpu(edesc->tcd[i].vtcd->nbytes)
			* le16_to_cpu(edesc->tcd[i].vtcd->biter);
		if (dir == DMA_MEM_TO_DEV)
			dma_addr = le32_to_cpu(edesc->tcd[i].vtcd->saddr);
		else
			dma_addr = le32_to_cpu(edesc->tcd[i].vtcd->daddr);

		len -= size;
		if (cur_addr >= dma_addr && cur_addr < dma_addr + size) {
			len += dma_addr + size - cur_addr;
			break;
		}
	}

	return len;
}

static enum dma_status fsl_edma3_tx_status(struct dma_chan *chan,
		dma_cookie_t cookie, struct dma_tx_state *txstate)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	struct virt_dma_desc *vdesc;
	enum dma_status status;
	unsigned long flags;

	status = dma_cookie_status(chan, cookie, txstate);
	if (status == DMA_COMPLETE) {
		spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
		txstate->residue = fsl_chan->chn_real_count;
		spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
		return status;
	}

	if (!txstate)
		return fsl_chan->status;

	spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
	vdesc = vchan_find_desc(&fsl_chan->vchan, cookie);
	if (fsl_chan->edesc && cookie == fsl_chan->edesc->vdesc.tx.cookie)
		txstate->residue = fsl_edma3_desc_residue(fsl_chan, vdesc,
								true);
	else if (vdesc)
		txstate->residue = fsl_edma3_desc_residue(fsl_chan, vdesc,
								false);
	else
		txstate->residue = 0;

	spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);

	return fsl_chan->status;
}

static void fsl_edma3_set_tcd_regs(struct fsl_edma3_chan *fsl_chan,
				  struct fsl_edma3_hw_tcd *tcd)
{
	void __iomem *addr = fsl_chan->membase;
	/*
	 * TCD parameters are stored in struct fsl_edma3_hw_tcd in little
	 * endian format. However, we need to load the TCD registers in
	 * big- or little-endian obeying the eDMA engine model endian.
	 */
	writew(0, addr + EDMA_TCD_CSR);
	writel(le32_to_cpu(tcd->saddr), addr + EDMA_TCD_SADDR);
	writel(le32_to_cpu(tcd->daddr), addr + EDMA_TCD_DADDR);

	writew(le16_to_cpu(tcd->attr), addr + EDMA_TCD_ATTR);
	writew(le16_to_cpu(tcd->soff), addr + EDMA_TCD_SOFF);

	writel(le32_to_cpu(tcd->nbytes), addr + EDMA_TCD_NBYTES);
	writel(le32_to_cpu(tcd->slast), addr + EDMA_TCD_SLAST);

	writew(le16_to_cpu(tcd->citer), addr + EDMA_TCD_CITER);
	writew(le16_to_cpu(tcd->biter), addr + EDMA_TCD_BITER);
	writew(le16_to_cpu(tcd->doff), addr + EDMA_TCD_DOFF);

	writel(le32_to_cpu(tcd->dlast_sga), addr + EDMA_TCD_DLAST_SGA);

	/* Must clear CHa_CSR[DONE] bit before enable TCDa_CSR[ESG] */
	writel(readl(addr + EDMA_CH_CSR), addr + EDMA_CH_CSR);

	writew(le16_to_cpu(tcd->csr), addr + EDMA_TCD_CSR);
}

static inline
void fsl_edma3_fill_tcd(struct fsl_edma3_chan *fsl_chan,
			struct fsl_edma3_hw_tcd *tcd, u32 src, u32 dst,
			u16 attr, u16 soff, u32 nbytes, u32 slast, u16 citer,
			u16 biter, u16 doff, u32 dlast_sga, bool major_int,
			bool disable_req, bool enable_sg)
{
	u16 csr = 0;

	/*
	 * eDMA hardware SGs require the TCDs to be stored in little
	 * endian format irrespective of the register endian model.
	 * So we put the value in little endian in memory, waiting
	 * for fsl_edma3_set_tcd_regs doing the swap.
	 */
	tcd->saddr = cpu_to_le32(src);
	tcd->daddr = cpu_to_le32(dst);

	tcd->attr = cpu_to_le16(attr);

	tcd->soff = cpu_to_le16(EDMA_TCD_SOFF_SOFF(soff));

	if (fsl_chan->is_dfifo) {
		/* set mloff as -8 */
		nbytes |= EDMA_TCD_NBYTES_MLOFF(-8);
		/* enable DMLOE/SMLOE */
		if (fsl_chan->fsc.dir == DMA_MEM_TO_DEV) {
			nbytes |= EDMA_TCD_NBYTES_DMLOE;
			nbytes &= ~EDMA_TCD_NBYTES_SMLOE;
		} else {
			nbytes |= EDMA_TCD_NBYTES_SMLOE;
			nbytes &= ~EDMA_TCD_NBYTES_DMLOE;
		}
	}

	tcd->nbytes = cpu_to_le32(EDMA_TCD_NBYTES_NBYTES(nbytes));
	tcd->slast = cpu_to_le32(EDMA_TCD_SLAST_SLAST(slast));

	tcd->citer = cpu_to_le16(EDMA_TCD_CITER_CITER(citer));
	tcd->doff = cpu_to_le16(EDMA_TCD_DOFF_DOFF(doff));

	tcd->dlast_sga = cpu_to_le32(EDMA_TCD_DLAST_SGA_DLAST_SGA(dlast_sga));

	tcd->biter = cpu_to_le16(EDMA_TCD_BITER_BITER(biter));
	if (major_int)
		csr |= EDMA_TCD_CSR_INT_MAJOR;

	if (disable_req)
		csr |= EDMA_TCD_CSR_D_REQ;

	if (enable_sg)
		csr |= EDMA_TCD_CSR_E_SG;

	if (fsl_chan->is_rxchan)
		csr |= EDMA_TCD_CSR_ACTIVE;

	tcd->csr = cpu_to_le16(csr);
}

static struct fsl_edma3_desc *fsl_edma3_alloc_desc(struct fsl_edma3_chan
						*fsl_chan, int sg_len)
{
	struct fsl_edma3_desc *fsl_desc;
	int i;

	fsl_desc = kzalloc(sizeof(*fsl_desc) + sizeof(struct fsl_edma3_sw_tcd)
				* sg_len, GFP_ATOMIC);
	if (!fsl_desc)
		return NULL;

	fsl_desc->echan = fsl_chan;
	fsl_desc->n_tcds = sg_len;
	for (i = 0; i < sg_len; i++) {
		fsl_desc->tcd[i].vtcd = dma_pool_alloc(fsl_chan->tcd_pool,
					GFP_ATOMIC, &fsl_desc->tcd[i].ptcd);
		if (!fsl_desc->tcd[i].vtcd)
			goto err;
	}
	return fsl_desc;

err:
	while (--i >= 0)
		dma_pool_free(fsl_chan->tcd_pool, fsl_desc->tcd[i].vtcd,
				fsl_desc->tcd[i].ptcd);
	kfree(fsl_desc);
	return NULL;
}

static struct dma_async_tx_descriptor *fsl_edma3_prep_dma_cyclic(
		struct dma_chan *chan, dma_addr_t dma_addr, size_t buf_len,
		size_t period_len, enum dma_transfer_direction direction,
		unsigned long flags)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	struct fsl_edma3_desc *fsl_desc;
	dma_addr_t dma_buf_next;
	int sg_len, i;
	u32 src_addr, dst_addr, last_sg, nbytes;
	u16 soff, doff, iter;

	sg_len = buf_len / period_len;
	fsl_desc = fsl_edma3_alloc_desc(fsl_chan, sg_len);
	if (!fsl_desc)
		return NULL;
	fsl_desc->iscyclic = true;

	dma_buf_next = dma_addr;
	nbytes = fsl_chan->fsc.addr_width * fsl_chan->fsc.burst;
	iter = period_len / nbytes;

	for (i = 0; i < sg_len; i++) {
		if (dma_buf_next >= dma_addr + buf_len)
			dma_buf_next = dma_addr;

		/* get next sg's physical address */
		last_sg = fsl_desc->tcd[(i + 1) % sg_len].ptcd;

		if (fsl_chan->fsc.dir == DMA_MEM_TO_DEV) {
			src_addr = dma_buf_next;
			dst_addr = fsl_chan->fsc.dev_addr;
			soff = fsl_chan->fsc.addr_width;
			if (fsl_chan->is_dfifo)
				doff = 4;
			else
				doff = 0;
		} else if (fsl_chan->fsc.dir == DMA_DEV_TO_MEM) {
			src_addr = fsl_chan->fsc.dev_addr;
			dst_addr = dma_buf_next;
			if (fsl_chan->is_dfifo)
				soff = 4;
			else
				soff = 0;
			doff = fsl_chan->fsc.addr_width;
		} else {
			/* DMA_DEV_TO_DEV */
			src_addr = fsl_chan->fsc.dev2_addr;
			dst_addr = fsl_chan->fsc.dev_addr;
			soff = 0;
			doff = 0;
		}

		fsl_edma3_fill_tcd(fsl_chan, fsl_desc->tcd[i].vtcd, src_addr,
				dst_addr, fsl_chan->fsc.attr, soff, nbytes, 0,
				iter, iter, doff, last_sg, true, false, true);
		dma_buf_next += period_len;
	}

	return vchan_tx_prep(&fsl_chan->vchan, &fsl_desc->vdesc, flags);
}

static struct dma_async_tx_descriptor *fsl_edma3_prep_slave_sg(
		struct dma_chan *chan, struct scatterlist *sgl,
		unsigned int sg_len, enum dma_transfer_direction direction,
		unsigned long flags, void *context)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	struct fsl_edma3_desc *fsl_desc;
	struct scatterlist *sg;
	u32 src_addr, dst_addr, last_sg, nbytes;
	u16 soff, doff, iter;
	int i;

	if (!is_slave_direction(fsl_chan->fsc.dir))
		return NULL;

	fsl_desc = fsl_edma3_alloc_desc(fsl_chan, sg_len);
	if (!fsl_desc)
		return NULL;
	fsl_desc->iscyclic = false;

	nbytes = fsl_chan->fsc.addr_width * fsl_chan->fsc.burst;
	for_each_sg(sgl, sg, sg_len, i) {
		/* get next sg's physical address */
		last_sg = fsl_desc->tcd[(i + 1) % sg_len].ptcd;

		if (fsl_chan->fsc.dir == DMA_MEM_TO_DEV) {
			src_addr = sg_dma_address(sg);
			dst_addr = fsl_chan->fsc.dev_addr;
			soff = fsl_chan->fsc.addr_width;
			doff = 0;
		} else if (fsl_chan->fsc.dir == DMA_DEV_TO_MEM) {
			src_addr = fsl_chan->fsc.dev_addr;
			dst_addr = sg_dma_address(sg);
			soff = 0;
			doff = fsl_chan->fsc.addr_width;
		} else {
			/* DMA_DEV_TO_DEV */
			src_addr = fsl_chan->fsc.dev2_addr;
			dst_addr = fsl_chan->fsc.dev_addr;
			soff = 0;
			doff = 0;
		}

		iter = sg_dma_len(sg) / nbytes;
		if (i < sg_len - 1) {
			last_sg = fsl_desc->tcd[(i + 1)].ptcd;
			fsl_edma3_fill_tcd(fsl_chan, fsl_desc->tcd[i].vtcd,
					src_addr, dst_addr, fsl_chan->fsc.attr,
					soff, nbytes, 0, iter, iter, doff,
					last_sg, false, false, true);
		} else {
			last_sg = 0;
			fsl_edma3_fill_tcd(fsl_chan, fsl_desc->tcd[i].vtcd,
					src_addr, dst_addr, fsl_chan->fsc.attr,
					soff, nbytes, 0, iter, iter, doff,
					last_sg, true, true, false);
		}
	}

	return vchan_tx_prep(&fsl_chan->vchan, &fsl_desc->vdesc, flags);
}

static void fsl_edma3_xfer_desc(struct fsl_edma3_chan *fsl_chan)
{
	struct virt_dma_desc *vdesc;

	vdesc = vchan_next_desc(&fsl_chan->vchan);
	if (!vdesc)
		return;
	fsl_chan->edesc = to_fsl_edma3_desc(vdesc);
	fsl_edma3_set_tcd_regs(fsl_chan, fsl_chan->edesc->tcd[0].vtcd);
	fsl_edma3_enable_request(fsl_chan);
	fsl_chan->status = DMA_IN_PROGRESS;
	fsl_chan->idle = false;
}

static size_t fsl_edma3_desc_residue(struct fsl_edma3_chan *fsl_chan,
		struct virt_dma_desc *vdesc, bool in_progress);

static void fsl_edma3_get_realcnt(struct fsl_edma3_chan *fsl_chan)
{
	fsl_chan->chn_real_count = fsl_edma3_desc_residue(fsl_chan, NULL, true);
}

static irqreturn_t fsl_edma3_tx_handler(int irq, void *dev_id)
{
	struct fsl_edma3_chan *fsl_chan = dev_id;
	unsigned int intr;
	void __iomem *base_addr;

	base_addr = fsl_chan->membase;

	intr = readl(base_addr + EDMA_CH_INT);
	if (!intr)
		return IRQ_NONE;

	writel(1, base_addr + EDMA_CH_INT);

	spin_lock(&fsl_chan->vchan.lock);

	/* Ignore this interrupt since channel has been disabled already */
	if (!fsl_chan->edesc)
		goto irq_handled;

	if (!fsl_chan->edesc->iscyclic) {
		fsl_edma3_get_realcnt(fsl_chan);
		list_del(&fsl_chan->edesc->vdesc.node);
		vchan_cookie_complete(&fsl_chan->edesc->vdesc);
		fsl_chan->edesc = NULL;
		fsl_chan->status = DMA_COMPLETE;
		fsl_chan->idle = true;
	} else {
		vchan_cyclic_callback(&fsl_chan->edesc->vdesc);
	}

	if (!fsl_chan->edesc)
		fsl_edma3_xfer_desc(fsl_chan);
irq_handled:
	spin_unlock(&fsl_chan->vchan.lock);

	return IRQ_HANDLED;
}

static void fsl_edma3_issue_pending(struct dma_chan *chan)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	unsigned long flags;

	spin_lock_irqsave(&fsl_chan->vchan.lock, flags);

	if (unlikely(fsl_chan->pm_state != RUNNING)) {
		spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
		/* cannot submit due to suspend */
		return;
	}

	if (vchan_issue_pending(&fsl_chan->vchan) && !fsl_chan->edesc)
		fsl_edma3_xfer_desc(fsl_chan);

	spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
}

static struct dma_chan *fsl_edma3_xlate(struct of_phandle_args *dma_spec,
		struct of_dma *ofdma)
{
	struct fsl_edma3_engine *fsl_edma3 = ofdma->of_dma_data;
	struct dma_chan *chan, *_chan;
	struct fsl_edma3_chan *fsl_chan;

	if (dma_spec->args_count != 3)
		return NULL;

	mutex_lock(&fsl_edma3->fsl_edma3_mutex);
	list_for_each_entry_safe(chan, _chan, &fsl_edma3->dma_dev.channels,
					device_node) {
		if (chan->client_count)
			continue;

		fsl_chan = to_fsl_edma3_chan(chan);
		if (fsl_chan->hw_chanid == dma_spec->args[0]) {
			chan = dma_get_slave_channel(chan);
			chan->device->privatecnt++;
			fsl_chan->priority = dma_spec->args[1];
			fsl_chan->is_rxchan = dma_spec->args[2] & ARGS_RX;
			fsl_chan->is_remote = dma_spec->args[2] & ARGS_REMOTE;
			fsl_chan->is_dfifo = dma_spec->args[2] & ARGS_DFIFO;
			mutex_unlock(&fsl_edma3->fsl_edma3_mutex);
			return chan;
		}
	}
	mutex_unlock(&fsl_edma3->fsl_edma3_mutex);
	return NULL;
}

static int fsl_edma3_alloc_chan_resources(struct dma_chan *chan)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);

	fsl_chan->tcd_pool = dma_pool_create("tcd_pool", chan->device->dev,
				sizeof(struct fsl_edma3_hw_tcd),
				32, 0);
	return 0;
}

static void fsl_edma3_free_chan_resources(struct dma_chan *chan)
{
	struct fsl_edma3_chan *fsl_chan = to_fsl_edma3_chan(chan);
	unsigned long flags;
	LIST_HEAD(head);

	spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
	fsl_edma3_disable_request(fsl_chan);
	fsl_chan->edesc = NULL;
	vchan_get_all_descriptors(&fsl_chan->vchan, &head);
	spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);

	vchan_dma_desc_free_list(&fsl_chan->vchan, &head);
	dma_pool_destroy(fsl_chan->tcd_pool);
	fsl_chan->tcd_pool = NULL;
}

static int fsl_edma3_probe(struct platform_device *pdev)
{
	struct device_node *np = pdev->dev.of_node;
	struct fsl_edma3_engine *fsl_edma3;
	struct fsl_edma3_chan *fsl_chan;
	struct resource *res;
	int len, chans;
	int ret, i;
	unsigned long irqflag = 0;

	ret = of_property_read_u32(np, "dma-channels", &chans);
	if (ret) {
		dev_err(&pdev->dev, "Can't get dma-channels.\n");
		return ret;
	}

	len = sizeof(*fsl_edma3) + sizeof(*fsl_chan) * chans;
	fsl_edma3 = devm_kzalloc(&pdev->dev, len, GFP_KERNEL);
	if (!fsl_edma3)
		return -ENOMEM;

	/* Audio edma rx/tx channel shared interrupt */
	if (of_property_read_bool(np, "shared-interrupt"))
		irqflag = IRQF_SHARED;

	fsl_edma3->swap = of_device_is_compatible(np, "fsl,imx8qm-adma");
	fsl_edma3->n_chans = chans;

	INIT_LIST_HEAD(&fsl_edma3->dma_dev.channels);
	for (i = 0; i < fsl_edma3->n_chans; i++) {
		struct fsl_edma3_chan *fsl_chan = &fsl_edma3->chans[i];
		const char *txirq_name = fsl_chan->txirq_name;
		char chanid[3], id_len = 0;
		char *p = chanid;
		unsigned long val;

		fsl_chan->edma3 = fsl_edma3;
		fsl_chan->pm_state = RUNNING;
		fsl_chan->idle = true;
		/* Get per channel membase */
		res = platform_get_resource(pdev, IORESOURCE_MEM, i);
		fsl_chan->membase = devm_ioremap_resource(&pdev->dev, res);
		if (IS_ERR(fsl_chan->membase))
			return PTR_ERR(fsl_chan->membase);

		/* Get the hardware chanel id by the channel membase
		 * channel0:0x10000, channel1:0x20000... total 32 channels
		 */
		fsl_chan->hw_chanid = (res->start >> 16) & 0x1f;

		ret = of_property_read_string_index(np, "interrupt-names", i,
							&txirq_name);
		if (ret) {
			dev_err(&pdev->dev, "read interrupt-names fail.\n");
			return ret;
		}
		/* Get channel id length from dts, one-digit or double-digit */
		id_len = strlen(txirq_name) - strlen(CHAN_PREFIX) -
			 strlen(CHAN_POSFIX);
		if (id_len > 2) {
			dev_err(&pdev->dev, "%s is edmaX-chanX-tx in dts?\n",
				res->name);
			return -EINVAL;
		}
		/* Grab channel id from txirq_name */
		strncpy(p, txirq_name + strlen(CHAN_PREFIX), id_len);
		*(p + id_len) = '\0';

		/* check if the channel id match well with hw_chanid */
		ret = kstrtoul(chanid, 0, &val);
		if (ret || val != fsl_chan->hw_chanid) {
			dev_err(&pdev->dev, "%s,wrong id?\n", txirq_name);
			return -EINVAL;
		}

		/* request channel irq */
		fsl_chan->txirq = platform_get_irq_byname(pdev, txirq_name);
		if (fsl_chan->txirq < 0) {
			dev_err(&pdev->dev, "Can't get %s irq.\n", txirq_name);
			return fsl_chan->txirq;
		}

		ret = devm_request_irq(&pdev->dev, fsl_chan->txirq,
				fsl_edma3_tx_handler, irqflag, txirq_name,
				fsl_chan);
		if (ret) {
			dev_err(&pdev->dev, "Can't register %s IRQ.\n",
				txirq_name);
			return ret;
		}

		fsl_chan->vchan.desc_free = fsl_edma3_free_desc;
		vchan_init(&fsl_chan->vchan, &fsl_edma3->dma_dev);
	}

	mutex_init(&fsl_edma3->fsl_edma3_mutex);

	dma_cap_set(DMA_PRIVATE, fsl_edma3->dma_dev.cap_mask);
	dma_cap_set(DMA_SLAVE, fsl_edma3->dma_dev.cap_mask);
	dma_cap_set(DMA_CYCLIC, fsl_edma3->dma_dev.cap_mask);

	fsl_edma3->dma_dev.dev = &pdev->dev;
	fsl_edma3->dma_dev.device_alloc_chan_resources
		= fsl_edma3_alloc_chan_resources;
	fsl_edma3->dma_dev.device_free_chan_resources
		= fsl_edma3_free_chan_resources;
	fsl_edma3->dma_dev.device_tx_status = fsl_edma3_tx_status;
	fsl_edma3->dma_dev.device_prep_slave_sg = fsl_edma3_prep_slave_sg;
	fsl_edma3->dma_dev.device_prep_dma_cyclic = fsl_edma3_prep_dma_cyclic;
	fsl_edma3->dma_dev.device_config = fsl_edma3_slave_config;
	fsl_edma3->dma_dev.device_pause = fsl_edma3_pause;
	fsl_edma3->dma_dev.device_resume = fsl_edma3_resume;
	fsl_edma3->dma_dev.device_terminate_all = fsl_edma3_terminate_all;
	fsl_edma3->dma_dev.device_issue_pending = fsl_edma3_issue_pending;

	fsl_edma3->dma_dev.src_addr_widths = FSL_EDMA_BUSWIDTHS;
	fsl_edma3->dma_dev.dst_addr_widths = FSL_EDMA_BUSWIDTHS;
	fsl_edma3->dma_dev.directions = BIT(DMA_DEV_TO_MEM) |
					BIT(DMA_MEM_TO_DEV) |
					BIT(DMA_DEV_TO_DEV);

	platform_set_drvdata(pdev, fsl_edma3);

	ret = dma_async_device_register(&fsl_edma3->dma_dev);
	if (ret) {
		dev_err(&pdev->dev, "Can't register Freescale eDMA engine.\n");
		return ret;
	}

	ret = of_dma_controller_register(np, fsl_edma3_xlate, fsl_edma3);
	if (ret) {
		dev_err(&pdev->dev, "Can't register Freescale eDMA of_dma.\n");
		dma_async_device_unregister(&fsl_edma3->dma_dev);
		return ret;
	}

	return 0;
}

static int fsl_edma3_remove(struct platform_device *pdev)
{
	struct device_node *np = pdev->dev.of_node;
	struct fsl_edma3_engine *fsl_edma3 = platform_get_drvdata(pdev);

	of_dma_controller_free(np);
	dma_async_device_unregister(&fsl_edma3->dma_dev);

	return 0;
}

static int fsl_edma3_suspend_late(struct device *dev)
{
	struct fsl_edma3_engine *fsl_edma = dev_get_drvdata(dev);
	struct fsl_edma3_chan *fsl_chan;
	unsigned long flags;
	void __iomem *addr;
	int i;

	for (i = 0; i < fsl_edma->n_chans; i++) {
		fsl_chan = &fsl_edma->chans[i];
		addr = fsl_chan->membase;

		spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
		fsl_edma->edma_regs[i].csr = readl(addr + EDMA_CH_CSR);
		fsl_edma->edma_regs[i].sbr = readl(addr + EDMA_CH_SBR);
		/* Make sure chan is idle or will force disable. */
		if (unlikely(!fsl_chan->idle)) {
			dev_warn(dev, "WARN: There is non-idle channel.");
			fsl_edma3_disable_request(fsl_chan);
		}
		fsl_chan->pm_state = SUSPENDED;
		spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
	}

	return 0;
}

static int fsl_edma3_resume_early(struct device *dev)
{
	struct fsl_edma3_engine *fsl_edma = dev_get_drvdata(dev);
	struct fsl_edma3_chan *fsl_chan;
	void __iomem *addr;
	unsigned long flags;
	int i;

	for (i = 0; i < fsl_edma->n_chans; i++) {
		fsl_chan = &fsl_edma->chans[i];
		addr = fsl_chan->membase;

		spin_lock_irqsave(&fsl_chan->vchan.lock, flags);
		writel(fsl_edma->edma_regs[i].csr, addr + EDMA_CH_CSR);
		writel(fsl_edma->edma_regs[i].sbr, addr + EDMA_CH_SBR);
		/* restore tcd if this channel not terminated before suspend */
		if (fsl_chan->edesc)
			fsl_edma3_set_tcd_regs(fsl_chan,
						fsl_chan->edesc->tcd[0].vtcd);
		fsl_chan->pm_state = RUNNING;
		spin_unlock_irqrestore(&fsl_chan->vchan.lock, flags);
	}

	return 0;
}

static const struct dev_pm_ops fsl_edma3_pm_ops = {
	.suspend_late   = fsl_edma3_suspend_late,
	.resume_early   = fsl_edma3_resume_early,
};

static const struct of_device_id fsl_edma3_dt_ids[] = {
	{ .compatible = "fsl,imx8qm-edma", },
	{ .compatible = "fsl,imx8qm-adma", },
	{ /* sentinel */ }
};
MODULE_DEVICE_TABLE(of, fsl_edma3_dt_ids);

static struct platform_driver fsl_edma3_driver = {
	.driver		= {
		.name	= "fsl-edma-v3",
		.of_match_table = fsl_edma3_dt_ids,
		.pm     = &fsl_edma3_pm_ops,
	},
	.probe          = fsl_edma3_probe,
	.remove		= fsl_edma3_remove,
};

static int __init fsl_edma3_init(void)
{
	return platform_driver_register(&fsl_edma3_driver);
}
subsys_initcall(fsl_edma3_init);

static void __exit fsl_edma3_exit(void)
{
	platform_driver_unregister(&fsl_edma3_driver);
}
module_exit(fsl_edma3_exit);

MODULE_ALIAS("platform:fsl-edma3");
MODULE_DESCRIPTION("Freescale eDMA-V3 engine driver");
MODULE_LICENSE("GPL v2");
