diff mbox series

[v1,10/12] dmaengine: fsl-edma: move tcd into struct fsl_dma_chan

Message ID 20230526143639.1037099-11-Frank.Li@nxp.com
State Superseded
Headers show
Series [v1,01/12] dmaengine: fsl-edma: clean up EXPORT_SYMBOL_GPL in fsl-edma-common.c | expand

Commit Message

Frank Li May 26, 2023, 2:36 p.m. UTC
Relocates the tcd into the fsl_dma_chan structure. This adjustment reduces
the need to reference back to fsl_edma_engine, paving the way for EDMA V3
support.

Unified the edma_writel and edma_writew functions for accessing TCD
(Transfer Control Descriptor) registers. A new macro is added that can
automatically detect whether a 32-bit or 16-bit access should be used
based on the structure field definition. This provide better support
64-bit TCD with future v5 version.

Signed-off-by: Frank Li <Frank.Li@nxp.com>
---
 drivers/dma/fsl-edma-common.c | 38 +++++++++++++----------------------
 drivers/dma/fsl-edma-common.h | 22 +++++++++++++++++++-
 drivers/dma/fsl-edma-main.c   |  6 ++++--
 drivers/dma/mcf-edma-main.c   |  4 +++-
 4 files changed, 42 insertions(+), 28 deletions(-)

Comments

kernel test robot May 27, 2023, 11:58 a.m. UTC | #1
Hi Frank,

kernel test robot noticed the following build warnings:

[auto build test WARNING on vkoul-dmaengine/next]
[also build test WARNING on robh/for-next linus/master v6.4-rc3 next-20230525]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch#_base_tree_information]

url:    https://github.com/intel-lab-lkp/linux/commits/Frank-Li/dmaengine-fsl-edma-clean-up-EXPORT_SYMBOL_GPL-in-fsl-edma-common-c/20230526-224442
base:   https://git.kernel.org/pub/scm/linux/kernel/git/vkoul/dmaengine.git next
patch link:    https://lore.kernel.org/r/20230526143639.1037099-11-Frank.Li%40nxp.com
patch subject: [PATCH v1 10/12] dmaengine: fsl-edma: move tcd into struct fsl_dma_chan
config: i386-randconfig-s003-20230526 (https://download.01.org/0day-ci/archive/20230527/202305271951.gmRobs3a-lkp@intel.com/config)
compiler: gcc-11 (Debian 11.3.0-12) 11.3.0
reproduce:
        # apt-get install sparse
        # sparse version: v0.6.4-39-gce1a6720-dirty
        # https://github.com/intel-lab-lkp/linux/commit/913c495a6c017a70bd6d7a518a9edbd361212985
        git remote add linux-review https://github.com/intel-lab-lkp/linux
        git fetch --no-tags linux-review Frank-Li/dmaengine-fsl-edma-clean-up-EXPORT_SYMBOL_GPL-in-fsl-edma-common-c/20230526-224442
        git checkout 913c495a6c017a70bd6d7a518a9edbd361212985
        # save the config file
        mkdir build_dir && cp config build_dir/.config
        make W=1 C=1 CF='-fdiagnostic-prefix -D__CHECK_ENDIAN__' O=build_dir ARCH=i386 olddefconfig
        make W=1 C=1 CF='-fdiagnostic-prefix -D__CHECK_ENDIAN__' O=build_dir ARCH=i386 SHELL=/bin/bash drivers/dma/

If you fix the issue, kindly add following tag where applicable
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202305271951.gmRobs3a-lkp@intel.com/

sparse warnings: (new ones prefixed by >>)
   drivers/dma/fsl-edma-common.c:367:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:367:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:368:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:368:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:370:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:370:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:371:9: sparse: sparse: incorrect type in argument 2 (different base types) @@     expected unsigned short [usertype] val @@     got restricted __le16 [usertype] soff @@
   drivers/dma/fsl-edma-common.c:371:9: sparse:     expected unsigned short [usertype] val
   drivers/dma/fsl-edma-common.c:371:9: sparse:     got restricted __le16 [usertype] soff
>> drivers/dma/fsl-edma-common.c:371:9: sparse: sparse: incorrect type in argument 2 (different base types) @@     expected unsigned int [usertype] val @@     got restricted __le16 [usertype] soff @@
   drivers/dma/fsl-edma-common.c:371:9: sparse:     expected unsigned int [usertype] val
   drivers/dma/fsl-edma-common.c:371:9: sparse:     got restricted __le16 [usertype] soff
   drivers/dma/fsl-edma-common.c:373:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:373:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:374:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:374:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:376:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:376:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:377:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:377:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:378:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:378:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:380:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:380:9: sparse: sparse: cast from restricted __le32
   drivers/dma/fsl-edma-common.c:388:9: sparse: sparse: cast from restricted __le16
   drivers/dma/fsl-edma-common.c:388:9: sparse: sparse: cast from restricted __le16

vim +371 drivers/dma/fsl-edma-common.c

   353	
   354	static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan,
   355					  struct fsl_edma_hw_tcd *tcd)
   356	{
   357		u16 csr = 0;
   358	
   359		/*
   360		 * TCD parameters are stored in struct fsl_edma_hw_tcd in little
   361		 * endian format. However, we need to load the TCD registers in
   362		 * big- or little-endian obeying the eDMA engine model endian,
   363		 * and this is performed from specific edma_write functions
   364		 */
   365		edma_write_tcdreg(fsl_chan, 0, csr);
   366	
   367		edma_write_tcdreg(fsl_chan, (s32)tcd->saddr, saddr);
   368		edma_write_tcdreg(fsl_chan, (s32)tcd->daddr, daddr);
   369	
   370		edma_write_tcdreg(fsl_chan, (s16)tcd->attr, attr);
 > 371		edma_write_tcdreg(fsl_chan, tcd->soff, soff);
   372	
   373		edma_write_tcdreg(fsl_chan, (s32)tcd->nbytes, nbytes);
   374		edma_write_tcdreg(fsl_chan, (s32)tcd->slast, slast);
   375	
   376		edma_write_tcdreg(fsl_chan, (s16)tcd->citer, citer);
   377		edma_write_tcdreg(fsl_chan, (s16)tcd->biter, biter);
   378		edma_write_tcdreg(fsl_chan, (s16)tcd->doff, doff);
   379	
   380		edma_write_tcdreg(fsl_chan, (s32)tcd->dlast_sga, dlast_sga);
   381	
   382		if (fsl_chan->is_sw) {
   383			csr = le16_to_cpu(tcd->csr);
   384			csr |= EDMA_TCD_CSR_START;
   385			tcd->csr = cpu_to_le16(csr);
   386		}
   387	
   388		edma_write_tcdreg(fsl_chan, (s16)tcd->csr, csr);
   389	}
   390
diff mbox series

Patch

diff --git a/drivers/dma/fsl-edma-common.c b/drivers/dma/fsl-edma-common.c
index 659bef4a3b23..186b5c41d07f 100644
--- a/drivers/dma/fsl-edma-common.c
+++ b/drivers/dma/fsl-edma-common.c
@@ -40,8 +40,6 @@ 
 #define EDMA64_ERRH		0x28
 #define EDMA64_ERRL		0x2c
 
-#define EDMA_TCD		0x1000
-
 void fsl_edma_tx_chan_handler(struct fsl_edma_chan *fsl_chan)
 {
 	spin_lock(&fsl_chan->vchan.lock);
@@ -285,8 +283,6 @@  static size_t fsl_edma_desc_residue(struct fsl_edma_chan *fsl_chan,
 		struct virt_dma_desc *vdesc, bool in_progress)
 {
 	struct fsl_edma_desc *edesc = fsl_chan->edesc;
-	struct edma_regs *regs = &fsl_chan->edma->regs;
-	u32 ch = fsl_chan->vchan.chan.chan_id;
 	enum dma_transfer_direction dir = edesc->dirn;
 	dma_addr_t cur_addr, dma_addr;
 	size_t len, size;
@@ -301,9 +297,9 @@  static size_t fsl_edma_desc_residue(struct fsl_edma_chan *fsl_chan,
 		return len;
 
 	if (dir == DMA_MEM_TO_DEV)
-		cur_addr = edma_readl(fsl_chan->edma, &regs->tcd[ch].saddr);
+		cur_addr = edma_read_tcdreg(fsl_chan, saddr);
 	else
-		cur_addr = edma_readl(fsl_chan->edma, &regs->tcd[ch].daddr);
+		cur_addr = edma_read_tcdreg(fsl_chan, daddr);
 
 	/* figure out the finished and calculate the residue */
 	for (i = 0; i < fsl_chan->edesc->n_tcds; i++) {
@@ -358,9 +354,6 @@  enum dma_status fsl_edma_tx_status(struct dma_chan *chan,
 static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan,
 				  struct fsl_edma_hw_tcd *tcd)
 {
-	struct fsl_edma_engine *edma = fsl_chan->edma;
-	struct edma_regs *regs = &fsl_chan->edma->regs;
-	u32 ch = fsl_chan->vchan.chan.chan_id;
 	u16 csr = 0;
 
 	/*
@@ -369,23 +362,22 @@  static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan,
 	 * big- or little-endian obeying the eDMA engine model endian,
 	 * and this is performed from specific edma_write functions
 	 */
-	edma_writew(edma, 0,  &regs->tcd[ch].csr);
+	edma_write_tcdreg(fsl_chan, 0, csr);
 
-	edma_writel(edma, (s32)tcd->saddr, &regs->tcd[ch].saddr);
-	edma_writel(edma, (s32)tcd->daddr, &regs->tcd[ch].daddr);
+	edma_write_tcdreg(fsl_chan, (s32)tcd->saddr, saddr);
+	edma_write_tcdreg(fsl_chan, (s32)tcd->daddr, daddr);
 
-	edma_writew(edma, (s16)tcd->attr, &regs->tcd[ch].attr);
-	edma_writew(edma, tcd->soff, &regs->tcd[ch].soff);
+	edma_write_tcdreg(fsl_chan, (s16)tcd->attr, attr);
+	edma_write_tcdreg(fsl_chan, tcd->soff, soff);
 
-	edma_writel(edma, (s32)tcd->nbytes, &regs->tcd[ch].nbytes);
-	edma_writel(edma, (s32)tcd->slast, &regs->tcd[ch].slast);
+	edma_write_tcdreg(fsl_chan, (s32)tcd->nbytes, nbytes);
+	edma_write_tcdreg(fsl_chan, (s32)tcd->slast, slast);
 
-	edma_writew(edma, (s16)tcd->citer, &regs->tcd[ch].citer);
-	edma_writew(edma, (s16)tcd->biter, &regs->tcd[ch].biter);
-	edma_writew(edma, (s16)tcd->doff, &regs->tcd[ch].doff);
+	edma_write_tcdreg(fsl_chan, (s16)tcd->citer, citer);
+	edma_write_tcdreg(fsl_chan, (s16)tcd->biter, biter);
+	edma_write_tcdreg(fsl_chan, (s16)tcd->doff, doff);
 
-	edma_writel(edma, (s32)tcd->dlast_sga,
-			&regs->tcd[ch].dlast_sga);
+	edma_write_tcdreg(fsl_chan, (s32)tcd->dlast_sga, dlast_sga);
 
 	if (fsl_chan->is_sw) {
 		csr = le16_to_cpu(tcd->csr);
@@ -393,7 +385,7 @@  static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan,
 		tcd->csr = cpu_to_le16(csr);
 	}
 
-	edma_writew(edma, (s16)tcd->csr, &regs->tcd[ch].csr);
+	edma_write_tcdreg(fsl_chan, (s16)tcd->csr, csr);
 }
 
 static inline
@@ -745,7 +737,5 @@  void fsl_edma_setup_regs(struct fsl_edma_engine *edma)
 		edma->regs.errh = edma->membase + EDMA64_ERRH;
 		edma->regs.inth = edma->membase + EDMA64_INTH;
 	}
-
-	edma->regs.tcd = edma->membase + EDMA_TCD;
 }
 
diff --git a/drivers/dma/fsl-edma-common.h b/drivers/dma/fsl-edma-common.h
index 39b5f903ba87..0a95fd5d74f5 100644
--- a/drivers/dma/fsl-edma-common.h
+++ b/drivers/dma/fsl-edma-common.h
@@ -48,6 +48,8 @@ 
 
 #define DMAMUX_NR	2
 
+#define EDMA_TCD                0x1000
+
 #define FSL_EDMA_BUSWIDTHS	(BIT(DMA_SLAVE_BUSWIDTH_1_BYTE) | \
 				 BIT(DMA_SLAVE_BUSWIDTH_2_BYTES) | \
 				 BIT(DMA_SLAVE_BUSWIDTH_4_BYTES) | \
@@ -93,7 +95,6 @@  struct edma_regs {
 	void __iomem *intl;
 	void __iomem *errh;
 	void __iomem *errl;
-	struct fsl_edma_hw_tcd __iomem *tcd;
 };
 
 struct fsl_edma_sw_tcd {
@@ -117,6 +118,7 @@  struct fsl_edma_chan {
 	u32				dma_dev_size;
 	enum dma_data_direction		dma_dir;
 	char				chan_name[32];
+	struct fsl_edma_hw_tcd __iomem *tcd;
 };
 
 struct fsl_edma_desc {
@@ -160,6 +162,16 @@  struct fsl_edma_engine {
 	struct fsl_edma_chan	chans[];
 };
 
+#define edma_read_tcdreg(chan, __name)				\
+(sizeof(chan->tcd->__name) == sizeof(u32) ?			\
+	edma_readl(chan->edma, &chan->tcd->__name) :		\
+	edma_readw(chan->edma, &chan->tcd->__name))
+
+#define edma_write_tcdreg(chan, val, __name)			\
+(sizeof(chan->tcd->__name) == sizeof(u32) ?			\
+	edma_writel(chan->edma, val, &chan->tcd->__name) :	\
+	edma_writew(chan->edma, val, &chan->tcd->__name))
+
 /*
  * R/W functions for big- or little-endian registers:
  * The eDMA controller's endian is independent of the CPU core's endian.
@@ -174,6 +186,14 @@  static inline u32 edma_readl(struct fsl_edma_engine *edma, void __iomem *addr)
 		return ioread32(addr);
 }
 
+static inline u16 edma_readw(struct fsl_edma_engine *edma, void __iomem *addr)
+{
+	if (edma->big_endian)
+		return ioread16be(addr);
+	else
+		return ioread16(addr);
+}
+
 static inline void edma_writeb(struct fsl_edma_engine *edma,
 			       u8 val, void __iomem *addr)
 {
diff --git a/drivers/dma/fsl-edma-main.c b/drivers/dma/fsl-edma-main.c
index 722ebecdc894..8d1d0100f6e6 100644
--- a/drivers/dma/fsl-edma-main.c
+++ b/drivers/dma/fsl-edma-main.c
@@ -312,9 +312,11 @@  static int fsl_edma_probe(struct platform_device *pdev)
 		fsl_chan->idle = true;
 		fsl_chan->dma_dir = DMA_NONE;
 		fsl_chan->vchan.desc_free = fsl_edma_free_desc;
+		fsl_chan->tcd = fsl_edma->membase + EDMA_TCD
+				+ i * sizeof(struct fsl_edma_hw_tcd);
 		vchan_init(&fsl_chan->vchan, &fsl_edma->dma_dev);
 
-		edma_writew(fsl_edma, 0x0, &regs->tcd[i].csr);
+		edma_write_tcdreg(fsl_chan, 0, csr);
 		fsl_edma_chan_mux(fsl_chan, 0, false);
 	}
 
@@ -421,7 +423,7 @@  static int fsl_edma_resume_early(struct device *dev)
 	for (i = 0; i < fsl_edma->n_chans; i++) {
 		fsl_chan = &fsl_edma->chans[i];
 		fsl_chan->pm_state = RUNNING;
-		edma_writew(fsl_edma, 0x0, &regs->tcd[i].csr);
+		edma_write_tcdreg(fsl_chan, 0, csr);
 		if (fsl_chan->slave_id != 0)
 			fsl_edma_chan_mux(fsl_chan, fsl_chan->slave_id, true);
 	}
diff --git a/drivers/dma/mcf-edma-main.c b/drivers/dma/mcf-edma-main.c
index af1b0e8a3021..d79a04a03fda 100644
--- a/drivers/dma/mcf-edma-main.c
+++ b/drivers/dma/mcf-edma-main.c
@@ -200,7 +200,9 @@  static int mcf_edma_probe(struct platform_device *pdev)
 		mcf_chan->dma_dir = DMA_NONE;
 		mcf_chan->vchan.desc_free = fsl_edma_free_desc;
 		vchan_init(&mcf_chan->vchan, &mcf_edma->dma_dev);
-		iowrite32(0x0, &regs->tcd[i].csr);
+		mcf_chan->tcd = mcf_edma->membase + EDMA_TCD
+				+ i * sizeof(struct fsl_edma_hw_tcd);
+		iowrite32(0x0, &mcf_chan->tcd->csr);
 	}
 
 	iowrite32(~0, regs->inth);