All of lore.kernel.org
 help / color / mirror / Atom feed
* [U-Boot] [PATCH 1/3] sf: ops: Add spi_flash_copy_mmap function
@ 2014-07-11 20:53 Tom Rini
  2014-07-11 20:53 ` [U-Boot] [PATCH 2/3] dma: Add TI EDMA driver Tom Rini
  2014-07-11 20:53 ` [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL Tom Rini
  0 siblings, 2 replies; 8+ messages in thread
From: Tom Rini @ 2014-07-11 20:53 UTC (permalink / raw)
  To: u-boot

When doing a memory mapped copy we may have DMA available and thus need
to have this copy abstracted so that the driver can do it, rather than a
simple memcpy.

Cc: Jagannadha Sutradharudu Teki <jaganna@xilinx.com>
Signed-off-by: Tom Rini <trini@ti.com>
---
 drivers/mtd/spi/sf_ops.c |    8 +++++++-
 include/spi.h            |    3 +++
 2 files changed, 10 insertions(+), 1 deletion(-)

diff --git a/drivers/mtd/spi/sf_ops.c b/drivers/mtd/spi/sf_ops.c
index ef91b92..2c7b890 100644
--- a/drivers/mtd/spi/sf_ops.c
+++ b/drivers/mtd/spi/sf_ops.c
@@ -14,6 +14,7 @@
 #include <spi.h>
 #include <spi_flash.h>
 #include <watchdog.h>
+#include <linux/compiler.h>
 
 #include "sf_internal.h"
 
@@ -359,6 +360,11 @@ int spi_flash_read_common(struct spi_flash *flash, const u8 *cmd,
 	return ret;
 }
 
+void __weak spi_flash_copy_mmap(void *data, void *offset, size_t len)
+{
+	memcpy(data, offset, len);
+}
+
 int spi_flash_cmd_read_ops(struct spi_flash *flash, u32 offset,
 		size_t len, void *data)
 {
@@ -375,7 +381,7 @@ int spi_flash_cmd_read_ops(struct spi_flash *flash, u32 offset,
 			return ret;
 		}
 		spi_xfer(flash->spi, 0, NULL, NULL, SPI_XFER_MMAP);
-		memcpy(data, flash->memory_map + offset, len);
+		spi_flash_copy_mmap(data, flash->memory_map + offset, len);
 		spi_xfer(flash->spi, 0, NULL, NULL, SPI_XFER_MMAP_END);
 		spi_release_bus(flash->spi);
 		return 0;
diff --git a/include/spi.h b/include/spi.h
index ffd6647..eecb9ad 100644
--- a/include/spi.h
+++ b/include/spi.h
@@ -220,6 +220,9 @@ int spi_set_wordlen(struct spi_slave *slave, unsigned int wordlen);
 int  spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout,
 		void *din, unsigned long flags);
 
+/* Copy memory mapped data */
+void spi_flash_copy_mmap(void *data, void *offset, size_t len);
+
 /**
  * Determine if a SPI chipselect is valid.
  * This function is provided by the board if the low-level SPI driver
-- 
1.7.9.5

^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [U-Boot] [PATCH 2/3] dma: Add TI EDMA driver
  2014-07-11 20:53 [U-Boot] [PATCH 1/3] sf: ops: Add spi_flash_copy_mmap function Tom Rini
@ 2014-07-11 20:53 ` Tom Rini
  2014-07-11 20:53 ` [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL Tom Rini
  1 sibling, 0 replies; 8+ messages in thread
From: Tom Rini @ 2014-07-11 20:53 UTC (permalink / raw)
  To: u-boot

From: Vinothkumar Rajendran <vinothr@ti.com>

Add a driver for the EDMA (EDMA3) IP block.  Provide an API to initialize
edma, program PaRAM, set register, enable and disable the interrupts,
map channel to eventq and enble and disable event triggers.

Signed-off-by: vinothkumar <a0131713@ti.com>
Signed-off-by: Tom Rini <trini@ti.com>
---
 arch/arm/cpu/armv7/omap5/hw_data.c     |    2 +
 arch/arm/cpu/armv7/omap5/prcm-regs.c   |    4 +
 arch/arm/include/asm/arch-omap5/edma.h |   46 +++++++
 arch/arm/include/asm/omap_common.h     |    4 +
 drivers/dma/Makefile                   |    1 +
 drivers/dma/ti_edma.c                  |  225 ++++++++++++++++++++++++++++++++
 drivers/dma/ti_edma.h                  |  117 +++++++++++++++++
 include/configs/dra7xx_evm.h           |    4 +
 8 files changed, 403 insertions(+)
 create mode 100644 arch/arm/include/asm/arch-omap5/edma.h
 create mode 100644 drivers/dma/ti_edma.c
 create mode 100644 drivers/dma/ti_edma.h

diff --git a/arch/arm/cpu/armv7/omap5/hw_data.c b/arch/arm/cpu/armv7/omap5/hw_data.c
index 4baca11..a349525 100644
--- a/arch/arm/cpu/armv7/omap5/hw_data.c
+++ b/arch/arm/cpu/armv7/omap5/hw_data.c
@@ -499,6 +499,8 @@ void enable_basic_uboot_clocks(void)
 
 	u32 const clk_modules_hw_auto_essential[] = {
 		(*prcm)->cm_l3init_hsusbtll_clkctrl,
+		(*prcm)->cm_l3main1_tptc1_clkctrl,
+		(*prcm)->cm_l3main1_tptc2_clkctrl,
 		0
 	};
 
diff --git a/arch/arm/cpu/armv7/omap5/prcm-regs.c b/arch/arm/cpu/armv7/omap5/prcm-regs.c
index ff08ef4..edda406 100644
--- a/arch/arm/cpu/armv7/omap5/prcm-regs.c
+++ b/arch/arm/cpu/armv7/omap5/prcm-regs.c
@@ -975,4 +975,8 @@ struct prcm_regs const dra7xx_prcm = {
 
 	.prm_abbldo_mpu_setup			= 0x4AE07DDC,
 	.prm_abbldo_mpu_ctrl			= 0x4AE07DE0,
+
+	/*l3main1 edma*/
+	.cm_l3main1_tptc1_clkctrl		= 0x4a008778,
+	.cm_l3main1_tptc2_clkctrl		= 0x4a008780,
 };
diff --git a/arch/arm/include/asm/arch-omap5/edma.h b/arch/arm/include/asm/arch-omap5/edma.h
new file mode 100644
index 0000000..4483e84
--- /dev/null
+++ b/arch/arm/include/asm/arch-omap5/edma.h
@@ -0,0 +1,46 @@
+/*
+ * hw_edma_tpcc.h - register-level header file for EDMA_TPCC
+ *
+ * Copyright (C) 2014, Texas Instruments, Incorporated
+ *
+ * SPDX-License-Identifier:	GPL-2.0+
+ */
+
+
+#ifndef HW_EDMA_TPCC_H_
+#define HW_EDMA_TPCC_H_
+
+/* Register Definitions */
+
+#define EDMA_TPCC_DCHMAPN(n)		(0x100 + (n * 4))
+#define EDMA_TPCC_DMAQNUMN(n)		(0x240 + (n * 4))
+#define EDMA_TPCC_QDMAQNUM		(0x260)
+#define EDMA_TPCC_EMCR			(0x308)
+#define EDMA_TPCC_EMCRH			(0x30c)
+#define EDMA_TPCC_QEMCR			(0x314)
+#define EDMA_TPCC_CCERRCLR		(0x31c)
+#define EDMA_TPCC_DRAEM(n)		(0x340 + (n * 8))
+#define EDMA_TPCC_DRAEHM(n)		(0x344 + (n * 8))
+#define EDMA_TPCC_QRAEN(n)		(0x380 + (n * 4))
+#define EDMA_TPCC_IESRH_RN(n)		(0x2064 + (n * 512))
+#define EDMA_TPCC_ESR_RN(n)		(0x2010 + (n * 512))
+#define EDMA_TPCC_ICRH_RN(n)		(0x2074 + (n * 512))
+#define EDMA_TPCC_IESR_RN(n)		(0x2060 + (n * 512))
+#define EDMA_TPCC_SECR_RN(n)		(0x2040 + (n * 512))
+#define EDMA_TPCC_EESR_RN(n)		(0x2030 + (n * 512))
+#define EDMA_TPCC_SECRH_RN(n)		(0x2044 + (n * 512))
+#define EDMA_TPCC_EESRH_RN(n)		(0x2034 + (n * 512))
+#define EDMA_TPCC_ICR_RN(n)		(0x2070 + (n * 512))
+#define EDMA_TPCC_IPR_RN(n)		(0x2068 + (n * 512))
+#define EDMA_TPCC_ESRH_RN(n)		(0x2014 + (n * 512))
+#define EDMA_TPCC_OPT(n)		(0x4000 + (n * 32))
+
+/* Field Definition Macros */
+#define EDMA_TPCC_DCHMAPN_SHIFT		(5)
+#define EDMA_TPCC_DMAQNUMN_SHIFT	(3)
+#define EDMA_TPCC_OPT_TCC_SHIFT		(12)
+#define EDMA_TPCC_OPT_TCC_MASK		(0x0003f000)
+#define EDMA_TPCC_OPT_TCINTEN_MASK	(0x00100000)
+#define EDMA_TPCC_OPT_SYNCDIM_MASK	(0x00000004)
+
+#endif
diff --git a/arch/arm/include/asm/omap_common.h b/arch/arm/include/asm/omap_common.h
index d1344ee..969a541 100644
--- a/arch/arm/include/asm/omap_common.h
+++ b/arch/arm/include/asm/omap_common.h
@@ -344,6 +344,10 @@ struct prcm_regs {
 	/* GMAC Clk Ctrl */
 	u32 cm_gmac_gmac_clkctrl;
 	u32 cm_gmac_clkstctrl;
+
+	/*l3main1 edma*/
+	u32 cm_l3main1_tptc1_clkctrl;
+	u32 cm_l3main1_tptc2_clkctrl;
 };
 
 struct omap_sys_ctrl_regs {
diff --git a/drivers/dma/Makefile b/drivers/dma/Makefile
index 8b2821b..4ac6170 100644
--- a/drivers/dma/Makefile
+++ b/drivers/dma/Makefile
@@ -9,3 +9,4 @@ obj-$(CONFIG_FSLDMAFEC) += MCD_tasksInit.o MCD_dmaApi.o MCD_tasks.o
 obj-$(CONFIG_APBH_DMA) += apbh_dma.o
 obj-$(CONFIG_FSL_DMA) += fsl_dma.o
 obj-$(CONFIG_OMAP3_DMA) += omap3_dma.o
+obj-$(CONFIG_TI_EDMA) += ti_edma.o
diff --git a/drivers/dma/ti_edma.c b/drivers/dma/ti_edma.c
new file mode 100644
index 0000000..e874b55
--- /dev/null
+++ b/drivers/dma/ti_edma.c
@@ -0,0 +1,225 @@
+/*
+ * TI edma driver
+ *
+ * Copyright (C) 2014, Texas Instruments, Incorporated
+ *
+ * SPDX-License-Identifier:	GPL-2.0+
+ *
+ * Support for the EDMA (sometimes referred to as EDMA3) controller found
+ * in a number of TI parts.  This implementation does not support QDMA nor
+ * channels above 32.  We also only support region 0.  We only support manual
+ * triggering of DMA events as well.
+ */
+
+#include <common.h>
+#include <stdbool.h>
+#include <asm/types.h>
+#include <asm/io.h>
+#include <asm/arch/edma.h>
+#include "ti_edma.h"
+
+#define EDMA_BASE_ADDR     0x43300000
+
+static u32 base_add = EDMA_BASE_ADDR;
+
+/**
+ * @brief EDMA Initialization
+ *
+ * This function initializes the EDMA Driver Clears the error specific
+ * registers (EMCR/EMCRh, CCERRCLR) and initialize the Queue Number Registers
+ *
+ * @param  que_num	Event Queue Number to which the channel will be mapped
+ *			(valid only for the Master Channel (DMA/QDMA) request).
+ *
+ * @return None
+ *
+ * @note We only support region 0 (of the two that exist) and the Event Queue
+ * used is either (0 or 1). There are only four shadow regions and only two
+ * event Queues.
+ */
+void edma_init(u32 que_num)
+{
+	int i;
+	u32 addr;
+
+	/* Clear the Event miss Registers */
+	writel(EDMA_SET_ALL_BITS,(base_add + EDMA_TPCC_EMCR));
+	writel(EDMA_SET_ALL_BITS,(base_add + EDMA_TPCC_EMCRH));
+
+	/* Clear CCERR register */
+	writel(EDMA_SET_ALL_BITS,(base_add + EDMA_TPCC_CCERRCLR));
+
+	/* FOR TYPE EDMA*/
+	/* Enable the DMA (0 - 32) channels in the DRAE and DRAEH register */
+	writel(EDMA_SET_ALL_BITS,(base_add + EDMA_TPCC_DRAEM(0)));
+
+	for (i = 0; i < 32; i++)
+		/* All events are one to one mapped with the channels */
+		writel(i << EDMA_TPCC_DCHMAPN_SHIFT,
+				base_add + EDMA_TPCC_DCHMAPN(i));
+
+	/* Initialize the DMA Queue Number Registers */
+	for (i = 0; i < (SOC_EDMA_NUM_DMACH / 2); i++) {
+		addr = base_add;
+		addr += EDMA_TPCC_DMAQNUMN(i >> EDMA_TPCC_DMAQNUMN_SHIFT);
+		writel(readl(addr) & EDMACC_DMAQNUM_CLR(i), addr);
+		writel(readl(addr) | EDMACC_DMAQNUM_SET(i, que_num), addr);
+	}
+}
+
+/**
+ * @brief  Map channel to Event Queue
+ *
+ * This API maps DMA/QDMA channels to the Event Queue.  QDMA channels are
+ * not supported.
+ *
+ * @param  base_add    Memory address of the EDMA instance used.
+ *
+ * @param  ch_num      Allocated channel number.
+ *
+ * @param  evt_qnum    Event Queue Number to which the channel
+ *                    will be mapped (valid only for the
+ *                    Master Channel (DMA/QDMA) request).
+ *
+ * @return  None
+ */
+static void edma_mapch_to_evtq(u32 ch_num, u32 evt_qnum)
+{
+	u32 addr = base_add;
+
+	addr += EDMA_TPCC_DMAQNUMN((ch_num) >> EDMA_TPCC_DMAQNUMN_SHIFT);
+
+	/* Associate DMA Channel to Event Queue */
+	writel(readl(addr) & EDMACC_DMAQNUM_CLR(ch_num), addr);
+	writel(readl(addr) | EDMACC_DMAQNUM_SET((ch_num), evt_qnum), addr);
+}
+
+/**
+ * @brief Request a DMA/QDMA/Link channel.
+ *
+ * Each channel (DMA/QDMA/Link) must be requested  before initiating a DMA
+ * transfer on that channel.
+ *
+ * This API is used to allocate a logical channel (DMA/QDMA/Link) along with
+ * the associated resources. For DMA and QDMA channels, TCC and PaRAM Set are
+ * also allocated along with the requested channel.
+ *
+ * User can request a specific logical channel by passing the channel number
+ * in 'ch_num'.
+ *
+ * For DMA/QDMA channels, after allocating all the EDMA resources, this API
+ * sets the TCC field of the OPT PaRAM Word with the allocated TCC. It also
+ * sets the event queue for the channel allocated. The event queue needs to
+ * be specified by the user.
+ *
+ * For DMA channel, it also sets the DCHMAP register.
+ *
+ * @param  ch_num                    This is the channel number requested for a
+ *                                  particular event.
+ *
+ * @param  tcc_num                   The channel number on which the
+ *                                  completion/error interrupt is generated.
+ *                                  Not used if user requested for a Link
+ *                                  channel.
+ *
+ * @param  evt_qnum                  Event Queue Number to which the channel
+ *                                  will be mapped (valid only for the
+ *                                  Master Channel (DMA/QDMA) request).
+ *
+ * @return  true if parameters are valid, else false
+ */
+bool edma_request_channel(u32 ch_num, u32 tcc_num, u32 evt_qnum)
+{
+	bool ret_val = false;
+
+	if (ch_num < (SOC_EDMA_NUM_DMACH / 2)) {
+		/*
+		 * Enable the DMA channel in the enabled in the shadow region
+		 * specific register
+		 */
+		writel(readl(base_add + EDMA_TPCC_DRAEM(0)) | (0x01 << ch_num),
+				base_add + EDMA_TPCC_DRAEM(0));
+
+		edma_mapch_to_evtq(ch_num, evt_qnum);
+		/* Interrupt channel nums are < 32 */
+		if (tcc_num < (SOC_EDMA_NUM_DMACH / 2)) {
+			/* Enable the Event Interrupt */
+			writel(readl(base_add + EDMA_TPCC_IESR_RN(0)) |
+					(0x01 << ch_num),
+					base_add + EDMA_TPCC_IESR_RN(0));
+			ret_val = true;
+		}
+
+		writel(readl(base_add + EDMA_TPCC_OPT(ch_num))&
+				EDMACC_OPT_TCC_CLR, base_add +
+				EDMA_TPCC_OPT(ch_num));
+		writel(readl(base_add + EDMA_TPCC_OPT(ch_num)) |
+				EDMACC_OPT_TCC_SET(ch_num), base_add +
+				EDMA_TPCC_OPT(ch_num));
+	}
+
+	return ret_val;
+}
+
+/**
+ * @brief Copy the user specified PaRAM Set onto the PaRAM Set associated with
+ * the logical channel (DMA/Link).
+ *
+ * This API takes a PaRAM Set as input and copies it onto the actual PaRAM Set
+ * associated with the logical channel. OPT field of the PaRAM Set is written
+ * first and the CCNT field is written last.
+ *
+ * @param param_id	PaRAMset ID whose parameter set has to be updated
+ *
+ * @param new_param	Parameter RAM set to be copied onto existing PaRAM.
+ *
+ */
+void edma_set_param(u32 param_id, struct edma_param_entry *new_param)
+{
+	struct edma_param_entry *dest;
+
+	dest = (struct edma_param_entry *)(base_add + EDMA_TPCC_OPT(param_id));
+
+	memcpy(dest, new_param, sizeof(struct edma_param_entry));
+}
+
+/**
+ * @brief Start EDMA transfer on the specified channel.
+ *
+ * In manual triggered mode, CPU manually triggers a transfer by writing a 1
+ * in the Event Set Register ESR. This API writes to the ESR to start the
+ * transfer.
+ *
+ * @param  ch_num	Channel being used to enable transfer.
+ *
+ * @return true or false depending on a valid channel number being passed
+ *
+ */
+bool edma_enable_transfer(u32 ch_num)
+{
+	/* Only the first half of the channels are supported. */
+	if (ch_num < (SOC_EDMA_NUM_DMACH / 2)) {
+		/* (ESR) - set corresponding bit to set a event */
+		writel(readl(base_add + EDMA_TPCC_ESR_RN(0)) |
+				(0x01 << ch_num),
+				base_add + EDMA_TPCC_ESR_RN(0));
+		return true;
+	}
+	return false;
+}
+
+/**
+ * @brief This function returns interrupts status of those events which is less
+ * than 32.
+ *
+ * @return Status of the Interrupt Pending Register
+ */
+u32 edma_get_intr_status(void)
+{
+	return readl(base_add + EDMA_TPCC_IPR_RN(0));
+}
+
+void edma_clr_intr(u32 value)
+{
+	writel((1 << value), base_add + EDMA_TPCC_ICR_RN(0));
+}
diff --git a/drivers/dma/ti_edma.h b/drivers/dma/ti_edma.h
new file mode 100644
index 0000000..073a5a0
--- /dev/null
+++ b/drivers/dma/ti_edma.h
@@ -0,0 +1,117 @@
+/*
+ * TI edma driver
+ *
+ * Copyright (C) 2014, Texas Instruments, Incorporated
+ *
+ * SPDX-License-Identifier:	GPL-2.0+
+ */
+#include <linux/compiler.h>
+
+/** DMAQNUM bits Clear */
+#define EDMACC_DMAQNUM_CLR(ch_num)	( ~ (0x7 << (((ch_num) % 8) \
+						* 4)))
+/** DMAQNUM bits Set */
+#define EDMACC_DMAQNUM_SET(ch_num,que_num)	((0x7 & (que_num)) << \
+							(((ch_num) % 8) * 4))
+
+/** OPT-TCC bitfield Clear */
+#define EDMACC_OPT_TCC_CLR		(~EDMA_TPCC_OPT_TCC_MASK)
+
+/** OPT-TCC bitfield Set */
+#define EDMACC_OPT_TCC_SET(tcc)	(((EDMA_TPCC_OPT_TCC_MASK >> \
+						EDMA_TPCC_OPT_TCC_SHIFT) & \
+						(tcc)) << \
+						EDMA_TPCC_OPT_TCC_SHIFT)
+
+#define EDMA_SET_ALL_BITS		(0xFFFFFFFF)
+
+#define EDMA_TRIG_MODE_MANUAL			(0)
+
+/*
+ * Number of PaRAM Entry fields
+ * OPT, SRC, A_B_CNT, DST, SRC_DST_BIDX, LINK_BCNTRLD, SRC_DST_CIDX
+ * and CCNT
+ */
+#define EDMACC_PARAM_ENTRY_FIELDS		(0x8)
+
+#define SOC_EDMA_NUM_DMACH		64
+#define SOC_EDMA_NUM_QDMACH		8
+
+/**
+ * @brief EDMA Parameter RAM Set in User Configurable format
+ *
+ * This is a mapping of the EDMA PaRAM set provided to the user
+ * for ease of modification of the individual fields
+ */
+struct edma_param_entry {
+	/** OPT field of PaRAM Set */
+	u32 opt;
+
+	/**
+	 * @brief Starting byte address of Source
+	 * For FIFO mode, src_addr must be a 256-bit aligned address.
+	 */
+	u32 src_addr;
+
+	/**
+	 * @brief Number of bytes in each Array (ACNT)
+	 */
+	u16 a_cnt;
+
+	/**
+	 * @brief Number of Arrays in each Frame (BCNT)
+	 */
+	u16 b_cnt;
+
+	/**
+	 * @brief Starting byte address of destination
+	 * For FIFO mode, dest_addr must be a 256-bit aligned address.
+	 * i.e. 5 LSBs should be 0.
+	 */
+	u32 dest_addr;
+
+	/**
+	 * @brief Index between consec. arrays of a Source Frame (SRCBIDX)
+	 */
+	s16 src_bidx;
+
+	/**
+	 * @brief Index between consec. arrays of a Destination Frame (DSTBIDX)
+	 */
+	s16 dest_bidx;
+
+	/**
+	 * @brief Address for linking (AutoReloading of a PaRAM Set)
+	 * This must point to a valid aligned 32-byte PaRAM set
+	 * A value of 0xFFFF means no linking
+	 */
+	u16 link_addr;
+
+	/**
+	 * @brief Reload value of the numArrInFrame (BCNT)
+	 * Relevant only for A-sync transfers
+	 */
+	u16 b_cnt_reload;
+
+	/**
+	 * @brief Index between consecutive frames of a Source Block (SRCCIDX)
+	 */
+	s16 src_cidx;
+
+	/**
+	 * @brief Index between consecutive frames of a Dest Block (DSTCIDX)
+	 */
+	s16 dest_cidx;
+
+	/**
+	 * @brief Number of Frames in a block (CCNT)
+	 */
+	u16 c_cnt;
+} __packed;
+
+void edma_init(u32 que_num);
+bool edma_request_channel(u32 ch_num, u32 tcc_num, u32 evt_qnum);
+void edma_set_param(u32 param_id, struct edma_param_entry* new_param);
+bool edma_enable_transfer(u32 ch_num);
+u32 edma_get_intr_status(void);
+void edma_clr_intr(u32 value);
diff --git a/include/configs/dra7xx_evm.h b/include/configs/dra7xx_evm.h
index 8d0a0eb..f86ec38 100644
--- a/include/configs/dra7xx_evm.h
+++ b/include/configs/dra7xx_evm.h
@@ -113,6 +113,10 @@
 
 /* SPI SPL */
 #define CONFIG_SPL_SPI_SUPPORT
+#define CONFIG_SPL_DMA_SUPPORT
+#ifdef CONFIG_SPL_BUILD
+#define CONFIG_TI_EDMA
+#endif
 #define CONFIG_SPL_SPI_LOAD
 #define CONFIG_SPL_SPI_FLASH_SUPPORT
 #define CONFIG_SPL_SPI_BUS             0
-- 
1.7.9.5

^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL
  2014-07-11 20:53 [U-Boot] [PATCH 1/3] sf: ops: Add spi_flash_copy_mmap function Tom Rini
  2014-07-11 20:53 ` [U-Boot] [PATCH 2/3] dma: Add TI EDMA driver Tom Rini
@ 2014-07-11 20:53 ` Tom Rini
  2014-07-12 13:12   ` Jagan Teki
  1 sibling, 1 reply; 8+ messages in thread
From: Tom Rini @ 2014-07-11 20:53 UTC (permalink / raw)
  To: u-boot

From: Vinothkumar Rajendran <vinothr@ti.com>

By default QSPI data through-put in memory mapped mode is ~2.4MB/sec @
48MHz. Added edma memory copy functionality in spi flash driver to
improve the data through put to 5.1MB/Sec.

Signed-off-by: Vinothkumar Rajendran <vinothr@ti.com>
Signed-off-by: Tom Rini <trini@ti.com>
---
 arch/arm/cpu/armv7/omap-common/boot-common.c |    5 ++
 arch/arm/cpu/armv7/omap5/hw_data.c           |    5 +-
 drivers/spi/ti_qspi.c                        |   71 ++++++++++++++++++++++++++
 3 files changed, 79 insertions(+), 2 deletions(-)

diff --git a/arch/arm/cpu/armv7/omap-common/boot-common.c b/arch/arm/cpu/armv7/omap-common/boot-common.c
index 3033564..636f5d6 100644
--- a/arch/arm/cpu/armv7/omap-common/boot-common.c
+++ b/arch/arm/cpu/armv7/omap-common/boot-common.c
@@ -14,6 +14,7 @@
 #include <asm/arch/omap.h>
 #include <asm/arch/mmc_host_def.h>
 #include <asm/arch/sys_proto.h>
+#include "../../../../../drivers/dma/ti_edma.h"
 #include <watchdog.h>
 
 DECLARE_GLOBAL_DATA_PTR;
@@ -93,6 +94,10 @@ u32 spl_boot_mode(void)
 
 void spl_board_init(void)
 {
+#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
+	edma_init(0);
+	edma_request_channel(1,1,0);
+#endif
 #ifdef CONFIG_SPL_NAND_SUPPORT
 	gpmc_init();
 #endif
diff --git a/arch/arm/cpu/armv7/omap5/hw_data.c b/arch/arm/cpu/armv7/omap5/hw_data.c
index a349525..7ee101a 100644
--- a/arch/arm/cpu/armv7/omap5/hw_data.c
+++ b/arch/arm/cpu/armv7/omap5/hw_data.c
@@ -418,6 +418,7 @@ void enable_basic_clocks(void)
 #ifdef CONFIG_DRIVER_TI_CPSW
 		(*prcm)->cm_gmac_clkstctrl,
 #endif
+		(*prcm)->cm_l3_1_clkstctrl,
 		0
 	};
 
@@ -434,6 +435,8 @@ void enable_basic_clocks(void)
 		(*prcm)->cm_l4per_gpio6_clkctrl,
 		(*prcm)->cm_l4per_gpio7_clkctrl,
 		(*prcm)->cm_l4per_gpio8_clkctrl,
+		(*prcm)->cm_l3main1_tptc1_clkctrl,
+		(*prcm)->cm_l3main1_tptc2_clkctrl,
 		0
 	};
 
@@ -499,8 +502,6 @@ void enable_basic_uboot_clocks(void)
 
 	u32 const clk_modules_hw_auto_essential[] = {
 		(*prcm)->cm_l3init_hsusbtll_clkctrl,
-		(*prcm)->cm_l3main1_tptc1_clkctrl,
-		(*prcm)->cm_l3main1_tptc2_clkctrl,
 		0
 	};
 
diff --git a/drivers/spi/ti_qspi.c b/drivers/spi/ti_qspi.c
index fd7fea8..f2ba75b 100644
--- a/drivers/spi/ti_qspi.c
+++ b/drivers/spi/ti_qspi.c
@@ -13,6 +13,8 @@
 #include <spi.h>
 #include <asm/gpio.h>
 #include <asm/omap_gpio.h>
+#include <asm/arch/edma.h>
+#include "../dma/ti_edma.h"
 
 /* ti qpsi register bit masks */
 #define QSPI_TIMEOUT                    2000000
@@ -340,3 +342,72 @@ int spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout,
 
 	return 0;
 }
+
+#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
+void spi_flash_copy_mmap(void *data, void *offset, size_t len)
+{
+	struct edma_param_entry edma_param;
+	int           b_cnt_value = 1;
+	int           rem_bytes  = 0;
+	int           a_cnt_value = len;
+	unsigned int          addr      = (unsigned int) (data);
+	unsigned int          max_acnt  = 0x7FFFU;
+	unsigned int edma_ch_num = 1;
+
+	if (len > max_acnt)
+	{
+		b_cnt_value = (len / max_acnt);
+		rem_bytes  = (len % max_acnt);
+		a_cnt_value = max_acnt;
+	}
+
+	/* Compute QSPI address and size */
+	edma_param.opt      = 0;
+	edma_param.src_addr  = ((unsigned int) offset);
+	edma_param.dest_addr = addr;
+	edma_param.a_cnt     = a_cnt_value;
+	edma_param.b_cnt     = b_cnt_value;
+	edma_param.c_cnt     = 1;
+	edma_param.src_bidx  = a_cnt_value;
+	edma_param.dest_bidx = a_cnt_value;
+	edma_param.src_cidx  = 0;
+	edma_param.dest_cidx = 0;
+	edma_param.link_addr = 0xFFFF;
+	edma_param.opt     |=
+		(EDMA_TPCC_OPT_TCINTEN_MASK |
+		 ((edma_ch_num <<
+		   EDMA_TPCC_OPT_TCC_SHIFT) &
+		  EDMA_TPCC_OPT_TCC_MASK) | EDMA_TPCC_OPT_SYNCDIM_MASK);
+
+	edma_set_param(edma_ch_num, &edma_param);
+	edma_enable_transfer(edma_ch_num);
+
+	while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
+	edma_clr_intr(edma_ch_num);
+	if (rem_bytes != 0)
+	{
+		/* Compute QSPI address and size */
+		edma_param.opt     = 0;
+		edma_param.src_addr =
+			(b_cnt_value * max_acnt) + ((unsigned int) offset);
+		edma_param.dest_addr = (addr + (max_acnt * b_cnt_value));
+		edma_param.a_cnt     = rem_bytes;
+		edma_param.b_cnt     = 1;
+		edma_param.c_cnt     = 1;
+		edma_param.src_bidx  = rem_bytes;
+		edma_param.dest_bidx = rem_bytes;
+		edma_param.src_cidx  = 0;
+		edma_param.dest_cidx = 0;
+		edma_param.link_addr = 0xFFFF;
+		edma_param.opt     |=
+			(EDMA_TPCC_OPT_TCINTEN_MASK |
+			 ((edma_ch_num << EDMA_TPCC_OPT_TCC_SHIFT) & EDMA_TPCC_OPT_TCC_MASK));
+		edma_set_param(edma_ch_num, &edma_param);
+		edma_enable_transfer(edma_ch_num);
+
+		while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
+		edma_clr_intr(edma_ch_num);
+	}
+	*((unsigned int *) offset) += len;
+}
+#endif
-- 
1.7.9.5

^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL
  2014-07-11 20:53 ` [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL Tom Rini
@ 2014-07-12 13:12   ` Jagan Teki
  2014-07-14 20:37     ` Tom Rini
  0 siblings, 1 reply; 8+ messages in thread
From: Jagan Teki @ 2014-07-12 13:12 UTC (permalink / raw)
  To: u-boot

On Sat, Jul 12, 2014 at 2:23 AM, Tom Rini <trini@ti.com> wrote:
> From: Vinothkumar Rajendran <vinothr@ti.com>
>
> By default QSPI data through-put in memory mapped mode is ~2.4MB/sec @
> 48MHz. Added edma memory copy functionality in spi flash driver to
> improve the data through put to 5.1MB/Sec.
>
> Signed-off-by: Vinothkumar Rajendran <vinothr@ti.com>
> Signed-off-by: Tom Rini <trini@ti.com>
> ---
>  arch/arm/cpu/armv7/omap-common/boot-common.c |    5 ++
>  arch/arm/cpu/armv7/omap5/hw_data.c           |    5 +-
>  drivers/spi/ti_qspi.c                        |   71 ++++++++++++++++++++++++++
>  3 files changed, 79 insertions(+), 2 deletions(-)
>
> diff --git a/arch/arm/cpu/armv7/omap-common/boot-common.c b/arch/arm/cpu/armv7/omap-common/boot-common.c
> index 3033564..636f5d6 100644
> --- a/arch/arm/cpu/armv7/omap-common/boot-common.c
> +++ b/arch/arm/cpu/armv7/omap-common/boot-common.c
> @@ -14,6 +14,7 @@
>  #include <asm/arch/omap.h>
>  #include <asm/arch/mmc_host_def.h>
>  #include <asm/arch/sys_proto.h>
> +#include "../../../../../drivers/dma/ti_edma.h"
>  #include <watchdog.h>
>
>  DECLARE_GLOBAL_DATA_PTR;
> @@ -93,6 +94,10 @@ u32 spl_boot_mode(void)
>
>  void spl_board_init(void)
>  {
> +#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
> +       edma_init(0);
> +       edma_request_channel(1,1,0);
> +#endif
>  #ifdef CONFIG_SPL_NAND_SUPPORT
>         gpmc_init();
>  #endif
> diff --git a/arch/arm/cpu/armv7/omap5/hw_data.c b/arch/arm/cpu/armv7/omap5/hw_data.c
> index a349525..7ee101a 100644
> --- a/arch/arm/cpu/armv7/omap5/hw_data.c
> +++ b/arch/arm/cpu/armv7/omap5/hw_data.c
> @@ -418,6 +418,7 @@ void enable_basic_clocks(void)
>  #ifdef CONFIG_DRIVER_TI_CPSW
>                 (*prcm)->cm_gmac_clkstctrl,
>  #endif
> +               (*prcm)->cm_l3_1_clkstctrl,
>                 0
>         };
>
> @@ -434,6 +435,8 @@ void enable_basic_clocks(void)
>                 (*prcm)->cm_l4per_gpio6_clkctrl,
>                 (*prcm)->cm_l4per_gpio7_clkctrl,
>                 (*prcm)->cm_l4per_gpio8_clkctrl,
> +               (*prcm)->cm_l3main1_tptc1_clkctrl,
> +               (*prcm)->cm_l3main1_tptc2_clkctrl,
>                 0
>         };
>
> @@ -499,8 +502,6 @@ void enable_basic_uboot_clocks(void)
>
>         u32 const clk_modules_hw_auto_essential[] = {
>                 (*prcm)->cm_l3init_hsusbtll_clkctrl,
> -               (*prcm)->cm_l3main1_tptc1_clkctrl,
> -               (*prcm)->cm_l3main1_tptc2_clkctrl,
>                 0
>         };
>
> diff --git a/drivers/spi/ti_qspi.c b/drivers/spi/ti_qspi.c
> index fd7fea8..f2ba75b 100644
> --- a/drivers/spi/ti_qspi.c
> +++ b/drivers/spi/ti_qspi.c
> @@ -13,6 +13,8 @@
>  #include <spi.h>
>  #include <asm/gpio.h>
>  #include <asm/omap_gpio.h>
> +#include <asm/arch/edma.h>
> +#include "../dma/ti_edma.h"

This looks odd to me - header inclusion, as .h in drivers even.

>
>  /* ti qpsi register bit masks */
>  #define QSPI_TIMEOUT                    2000000
> @@ -340,3 +342,72 @@ int spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout,
>
>         return 0;
>  }
> +
> +#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
> +void spi_flash_copy_mmap(void *data, void *offset, size_t len)
> +{
> +       struct edma_param_entry edma_param;
> +       int           b_cnt_value = 1;
> +       int           rem_bytes  = 0;
> +       int           a_cnt_value = len;
> +       unsigned int          addr      = (unsigned int) (data);
> +       unsigned int          max_acnt  = 0x7FFFU;
> +       unsigned int edma_ch_num = 1;
> +
> +       if (len > max_acnt)
> +       {
> +               b_cnt_value = (len / max_acnt);
> +               rem_bytes  = (len % max_acnt);
> +               a_cnt_value = max_acnt;
> +       }
> +
> +       /* Compute QSPI address and size */
> +       edma_param.opt      = 0;
> +       edma_param.src_addr  = ((unsigned int) offset);
> +       edma_param.dest_addr = addr;
> +       edma_param.a_cnt     = a_cnt_value;
> +       edma_param.b_cnt     = b_cnt_value;
> +       edma_param.c_cnt     = 1;
> +       edma_param.src_bidx  = a_cnt_value;
> +       edma_param.dest_bidx = a_cnt_value;
> +       edma_param.src_cidx  = 0;
> +       edma_param.dest_cidx = 0;
> +       edma_param.link_addr = 0xFFFF;
> +       edma_param.opt     |=
> +               (EDMA_TPCC_OPT_TCINTEN_MASK |
> +                ((edma_ch_num <<
> +                  EDMA_TPCC_OPT_TCC_SHIFT) &
> +                 EDMA_TPCC_OPT_TCC_MASK) | EDMA_TPCC_OPT_SYNCDIM_MASK);
> +
> +       edma_set_param(edma_ch_num, &edma_param);
> +       edma_enable_transfer(edma_ch_num);
> +
> +       while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> +       edma_clr_intr(edma_ch_num);
> +       if (rem_bytes != 0)
> +       {
> +               /* Compute QSPI address and size */
> +               edma_param.opt     = 0;
> +               edma_param.src_addr =
> +                       (b_cnt_value * max_acnt) + ((unsigned int) offset);
> +               edma_param.dest_addr = (addr + (max_acnt * b_cnt_value));
> +               edma_param.a_cnt     = rem_bytes;
> +               edma_param.b_cnt     = 1;
> +               edma_param.c_cnt     = 1;
> +               edma_param.src_bidx  = rem_bytes;
> +               edma_param.dest_bidx = rem_bytes;
> +               edma_param.src_cidx  = 0;
> +               edma_param.dest_cidx = 0;
> +               edma_param.link_addr = 0xFFFF;
> +               edma_param.opt     |=
> +                       (EDMA_TPCC_OPT_TCINTEN_MASK |
> +                        ((edma_ch_num << EDMA_TPCC_OPT_TCC_SHIFT) & EDMA_TPCC_OPT_TCC_MASK));
> +               edma_set_param(edma_ch_num, &edma_param);
> +               edma_enable_transfer(edma_ch_num);
> +
> +               while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> +               edma_clr_intr(edma_ch_num);
> +       }
> +       *((unsigned int *) offset) += len;
> +}
> +#endif

I'm some how !OK with this memory or flash change in spi driver.
Any better approach to move this - may be in DMA driver itself and
picking up the
memory attributes from sf layer.

I'm not much clear about this now, but will come back again.

thanks!
-- 
Jagan.

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL
  2014-07-12 13:12   ` Jagan Teki
@ 2014-07-14 20:37     ` Tom Rini
  2015-01-16 16:00       ` Tom Rini
  2015-04-22 11:15       ` Jagan Teki
  0 siblings, 2 replies; 8+ messages in thread
From: Tom Rini @ 2014-07-14 20:37 UTC (permalink / raw)
  To: u-boot

On Sat, Jul 12, 2014 at 06:42:31PM +0530, Jagan Teki wrote:
> On Sat, Jul 12, 2014 at 2:23 AM, Tom Rini <trini@ti.com> wrote:
> > From: Vinothkumar Rajendran <vinothr@ti.com>
> >
> > By default QSPI data through-put in memory mapped mode is ~2.4MB/sec @
> > 48MHz. Added edma memory copy functionality in spi flash driver to
> > improve the data through put to 5.1MB/Sec.
[snip]
> > +#include <asm/arch/edma.h>
> > +#include "../dma/ti_edma.h"
> 
> This looks odd to me - header inclusion, as .h in drivers even.

I could shove this under arch/arm/include/asm/ti-common I suppose.

> >
> >  /* ti qpsi register bit masks */
> >  #define QSPI_TIMEOUT                    2000000
> > @@ -340,3 +342,72 @@ int spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout,
> >
> >         return 0;
> >  }
> > +
> > +#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
> > +void spi_flash_copy_mmap(void *data, void *offset, size_t len)
> > +{
> > +       struct edma_param_entry edma_param;
> > +       int           b_cnt_value = 1;
> > +       int           rem_bytes  = 0;
> > +       int           a_cnt_value = len;
> > +       unsigned int          addr      = (unsigned int) (data);
> > +       unsigned int          max_acnt  = 0x7FFFU;
> > +       unsigned int edma_ch_num = 1;
> > +
> > +       if (len > max_acnt)
> > +       {
> > +               b_cnt_value = (len / max_acnt);
> > +               rem_bytes  = (len % max_acnt);
> > +               a_cnt_value = max_acnt;
> > +       }
> > +
> > +       /* Compute QSPI address and size */
> > +       edma_param.opt      = 0;
> > +       edma_param.src_addr  = ((unsigned int) offset);
> > +       edma_param.dest_addr = addr;
> > +       edma_param.a_cnt     = a_cnt_value;
> > +       edma_param.b_cnt     = b_cnt_value;
> > +       edma_param.c_cnt     = 1;
> > +       edma_param.src_bidx  = a_cnt_value;
> > +       edma_param.dest_bidx = a_cnt_value;
> > +       edma_param.src_cidx  = 0;
> > +       edma_param.dest_cidx = 0;
> > +       edma_param.link_addr = 0xFFFF;
> > +       edma_param.opt     |=
> > +               (EDMA_TPCC_OPT_TCINTEN_MASK |
> > +                ((edma_ch_num <<
> > +                  EDMA_TPCC_OPT_TCC_SHIFT) &
> > +                 EDMA_TPCC_OPT_TCC_MASK) | EDMA_TPCC_OPT_SYNCDIM_MASK);
> > +
> > +       edma_set_param(edma_ch_num, &edma_param);
> > +       edma_enable_transfer(edma_ch_num);
> > +
> > +       while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> > +       edma_clr_intr(edma_ch_num);
> > +       if (rem_bytes != 0)
> > +       {
> > +               /* Compute QSPI address and size */
> > +               edma_param.opt     = 0;
> > +               edma_param.src_addr =
> > +                       (b_cnt_value * max_acnt) + ((unsigned int) offset);
> > +               edma_param.dest_addr = (addr + (max_acnt * b_cnt_value));
> > +               edma_param.a_cnt     = rem_bytes;
> > +               edma_param.b_cnt     = 1;
> > +               edma_param.c_cnt     = 1;
> > +               edma_param.src_bidx  = rem_bytes;
> > +               edma_param.dest_bidx = rem_bytes;
> > +               edma_param.src_cidx  = 0;
> > +               edma_param.dest_cidx = 0;
> > +               edma_param.link_addr = 0xFFFF;
> > +               edma_param.opt     |=
> > +                       (EDMA_TPCC_OPT_TCINTEN_MASK |
> > +                        ((edma_ch_num << EDMA_TPCC_OPT_TCC_SHIFT) & EDMA_TPCC_OPT_TCC_MASK));
> > +               edma_set_param(edma_ch_num, &edma_param);
> > +               edma_enable_transfer(edma_ch_num);
> > +
> > +               while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> > +               edma_clr_intr(edma_ch_num);
> > +       }
> > +       *((unsigned int *) offset) += len;
> > +}
> > +#endif
> 
> I'm some how !OK with this memory or flash change in spi driver.
> Any better approach to move this - may be in DMA driver itself and
> picking up the
> memory attributes from sf layer.
> 
> I'm not much clear about this now, but will come back again.

Well, are you happy with how drivers/spi/mxs_spi.c works (search around
on mxs_dma)?  I can re-jigger things along those lines I suppose.

-- 
Tom
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 836 bytes
Desc: Digital signature
URL: <http://lists.denx.de/pipermail/u-boot/attachments/20140714/a800cdd6/attachment.pgp>

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL
  2014-07-14 20:37     ` Tom Rini
@ 2015-01-16 16:00       ` Tom Rini
  2015-04-22 11:15       ` Jagan Teki
  1 sibling, 0 replies; 8+ messages in thread
From: Tom Rini @ 2015-01-16 16:00 UTC (permalink / raw)
  To: u-boot

On Mon, Jul 14, 2014 at 04:37:36PM -0400, Tom Rini wrote:
> On Sat, Jul 12, 2014 at 06:42:31PM +0530, Jagan Teki wrote:
> > On Sat, Jul 12, 2014 at 2:23 AM, Tom Rini <trini@ti.com> wrote:
> > > From: Vinothkumar Rajendran <vinothr@ti.com>
> > >
> > > By default QSPI data through-put in memory mapped mode is ~2.4MB/sec @
> > > 48MHz. Added edma memory copy functionality in spi flash driver to
> > > improve the data through put to 5.1MB/Sec.
> [snip]
> > > +#include <asm/arch/edma.h>
> > > +#include "../dma/ti_edma.h"
> > 
> > This looks odd to me - header inclusion, as .h in drivers even.
> 
> I could shove this under arch/arm/include/asm/ti-common I suppose.
> 
> > >
> > >  /* ti qpsi register bit masks */
> > >  #define QSPI_TIMEOUT                    2000000
> > > @@ -340,3 +342,72 @@ int spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout,
> > >
> > >         return 0;
> > >  }
> > > +
> > > +#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
> > > +void spi_flash_copy_mmap(void *data, void *offset, size_t len)
> > > +{
> > > +       struct edma_param_entry edma_param;
> > > +       int           b_cnt_value = 1;
> > > +       int           rem_bytes  = 0;
> > > +       int           a_cnt_value = len;
> > > +       unsigned int          addr      = (unsigned int) (data);
> > > +       unsigned int          max_acnt  = 0x7FFFU;
> > > +       unsigned int edma_ch_num = 1;
> > > +
> > > +       if (len > max_acnt)
> > > +       {
> > > +               b_cnt_value = (len / max_acnt);
> > > +               rem_bytes  = (len % max_acnt);
> > > +               a_cnt_value = max_acnt;
> > > +       }
> > > +
> > > +       /* Compute QSPI address and size */
> > > +       edma_param.opt      = 0;
> > > +       edma_param.src_addr  = ((unsigned int) offset);
> > > +       edma_param.dest_addr = addr;
> > > +       edma_param.a_cnt     = a_cnt_value;
> > > +       edma_param.b_cnt     = b_cnt_value;
> > > +       edma_param.c_cnt     = 1;
> > > +       edma_param.src_bidx  = a_cnt_value;
> > > +       edma_param.dest_bidx = a_cnt_value;
> > > +       edma_param.src_cidx  = 0;
> > > +       edma_param.dest_cidx = 0;
> > > +       edma_param.link_addr = 0xFFFF;
> > > +       edma_param.opt     |=
> > > +               (EDMA_TPCC_OPT_TCINTEN_MASK |
> > > +                ((edma_ch_num <<
> > > +                  EDMA_TPCC_OPT_TCC_SHIFT) &
> > > +                 EDMA_TPCC_OPT_TCC_MASK) | EDMA_TPCC_OPT_SYNCDIM_MASK);
> > > +
> > > +       edma_set_param(edma_ch_num, &edma_param);
> > > +       edma_enable_transfer(edma_ch_num);
> > > +
> > > +       while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> > > +       edma_clr_intr(edma_ch_num);
> > > +       if (rem_bytes != 0)
> > > +       {
> > > +               /* Compute QSPI address and size */
> > > +               edma_param.opt     = 0;
> > > +               edma_param.src_addr =
> > > +                       (b_cnt_value * max_acnt) + ((unsigned int) offset);
> > > +               edma_param.dest_addr = (addr + (max_acnt * b_cnt_value));
> > > +               edma_param.a_cnt     = rem_bytes;
> > > +               edma_param.b_cnt     = 1;
> > > +               edma_param.c_cnt     = 1;
> > > +               edma_param.src_bidx  = rem_bytes;
> > > +               edma_param.dest_bidx = rem_bytes;
> > > +               edma_param.src_cidx  = 0;
> > > +               edma_param.dest_cidx = 0;
> > > +               edma_param.link_addr = 0xFFFF;
> > > +               edma_param.opt     |=
> > > +                       (EDMA_TPCC_OPT_TCINTEN_MASK |
> > > +                        ((edma_ch_num << EDMA_TPCC_OPT_TCC_SHIFT) & EDMA_TPCC_OPT_TCC_MASK));
> > > +               edma_set_param(edma_ch_num, &edma_param);
> > > +               edma_enable_transfer(edma_ch_num);
> > > +
> > > +               while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> > > +               edma_clr_intr(edma_ch_num);
> > > +       }
> > > +       *((unsigned int *) offset) += len;
> > > +}
> > > +#endif
> > 
> > I'm some how !OK with this memory or flash change in spi driver.
> > Any better approach to move this - may be in DMA driver itself and
> > picking up the
> > memory attributes from sf layer.
> > 
> > I'm not much clear about this now, but will come back again.
> 
> Well, are you happy with how drivers/spi/mxs_spi.c works (search around
> on mxs_dma)?  I can re-jigger things along those lines I suppose.

Ping?  Thanks!

-- 
Tom
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 836 bytes
Desc: Digital signature
URL: <http://lists.denx.de/pipermail/u-boot/attachments/20150116/2ef03682/attachment.pgp>

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL
  2014-07-14 20:37     ` Tom Rini
  2015-01-16 16:00       ` Tom Rini
@ 2015-04-22 11:15       ` Jagan Teki
  2015-04-22 14:25         ` Tom Rini
  1 sibling, 1 reply; 8+ messages in thread
From: Jagan Teki @ 2015-04-22 11:15 UTC (permalink / raw)
  To: u-boot

On 15 July 2014 at 02:07, Tom Rini <trini@ti.com> wrote:
> On Sat, Jul 12, 2014 at 06:42:31PM +0530, Jagan Teki wrote:
>> On Sat, Jul 12, 2014 at 2:23 AM, Tom Rini <trini@ti.com> wrote:
>> > From: Vinothkumar Rajendran <vinothr@ti.com>
>> >
>> > By default QSPI data through-put in memory mapped mode is ~2.4MB/sec @
>> > 48MHz. Added edma memory copy functionality in spi flash driver to
>> > improve the data through put to 5.1MB/Sec.
> [snip]
>> > +#include <asm/arch/edma.h>
>> > +#include "../dma/ti_edma.h"
>>
>> This looks odd to me - header inclusion, as .h in drivers even.
>
> I could shove this under arch/arm/include/asm/ti-common I suppose.

Any changes in code logic or updates?

>
>> >
>> >  /* ti qpsi register bit masks */
>> >  #define QSPI_TIMEOUT                    2000000
>> > @@ -340,3 +342,72 @@ int spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout,
>> >
>> >         return 0;
>> >  }
>> > +
>> > +#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
>> > +void spi_flash_copy_mmap(void *data, void *offset, size_t len)
>> > +{
>> > +       struct edma_param_entry edma_param;
>> > +       int           b_cnt_value = 1;
>> > +       int           rem_bytes  = 0;
>> > +       int           a_cnt_value = len;
>> > +       unsigned int          addr      = (unsigned int) (data);
>> > +       unsigned int          max_acnt  = 0x7FFFU;
>> > +       unsigned int edma_ch_num = 1;
>> > +
>> > +       if (len > max_acnt)
>> > +       {
>> > +               b_cnt_value = (len / max_acnt);
>> > +               rem_bytes  = (len % max_acnt);
>> > +               a_cnt_value = max_acnt;
>> > +       }
>> > +
>> > +       /* Compute QSPI address and size */
>> > +       edma_param.opt      = 0;
>> > +       edma_param.src_addr  = ((unsigned int) offset);
>> > +       edma_param.dest_addr = addr;
>> > +       edma_param.a_cnt     = a_cnt_value;
>> > +       edma_param.b_cnt     = b_cnt_value;
>> > +       edma_param.c_cnt     = 1;
>> > +       edma_param.src_bidx  = a_cnt_value;
>> > +       edma_param.dest_bidx = a_cnt_value;
>> > +       edma_param.src_cidx  = 0;
>> > +       edma_param.dest_cidx = 0;
>> > +       edma_param.link_addr = 0xFFFF;
>> > +       edma_param.opt     |=
>> > +               (EDMA_TPCC_OPT_TCINTEN_MASK |
>> > +                ((edma_ch_num <<
>> > +                  EDMA_TPCC_OPT_TCC_SHIFT) &
>> > +                 EDMA_TPCC_OPT_TCC_MASK) | EDMA_TPCC_OPT_SYNCDIM_MASK);
>> > +
>> > +       edma_set_param(edma_ch_num, &edma_param);
>> > +       edma_enable_transfer(edma_ch_num);
>> > +
>> > +       while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
>> > +       edma_clr_intr(edma_ch_num);
>> > +       if (rem_bytes != 0)
>> > +       {
>> > +               /* Compute QSPI address and size */
>> > +               edma_param.opt     = 0;
>> > +               edma_param.src_addr =
>> > +                       (b_cnt_value * max_acnt) + ((unsigned int) offset);
>> > +               edma_param.dest_addr = (addr + (max_acnt * b_cnt_value));
>> > +               edma_param.a_cnt     = rem_bytes;
>> > +               edma_param.b_cnt     = 1;
>> > +               edma_param.c_cnt     = 1;
>> > +               edma_param.src_bidx  = rem_bytes;
>> > +               edma_param.dest_bidx = rem_bytes;
>> > +               edma_param.src_cidx  = 0;
>> > +               edma_param.dest_cidx = 0;
>> > +               edma_param.link_addr = 0xFFFF;
>> > +               edma_param.opt     |=
>> > +                       (EDMA_TPCC_OPT_TCINTEN_MASK |
>> > +                        ((edma_ch_num << EDMA_TPCC_OPT_TCC_SHIFT) & EDMA_TPCC_OPT_TCC_MASK));
>> > +               edma_set_param(edma_ch_num, &edma_param);
>> > +               edma_enable_transfer(edma_ch_num);
>> > +
>> > +               while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
>> > +               edma_clr_intr(edma_ch_num);
>> > +       }
>> > +       *((unsigned int *) offset) += len;
>> > +}
>> > +#endif
>>
>> I'm some how !OK with this memory or flash change in spi driver.
>> Any better approach to move this - may be in DMA driver itself and
>> picking up the
>> memory attributes from sf layer.
>>
>> I'm not much clear about this now, but will come back again.
>
> Well, are you happy with how drivers/spi/mxs_spi.c works (search around
> on mxs_dma)?  I can re-jigger things along those lines I suppose.

thanks!
-- 
Jagan.

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL
  2015-04-22 11:15       ` Jagan Teki
@ 2015-04-22 14:25         ` Tom Rini
  0 siblings, 0 replies; 8+ messages in thread
From: Tom Rini @ 2015-04-22 14:25 UTC (permalink / raw)
  To: u-boot

On Wed, Apr 22, 2015 at 04:45:05PM +0530, Jagan Teki wrote:
> On 15 July 2014 at 02:07, Tom Rini <trini@ti.com> wrote:
> > On Sat, Jul 12, 2014 at 06:42:31PM +0530, Jagan Teki wrote:
> >> On Sat, Jul 12, 2014 at 2:23 AM, Tom Rini <trini@ti.com> wrote:
> >> > From: Vinothkumar Rajendran <vinothr@ti.com>
> >> >
> >> > By default QSPI data through-put in memory mapped mode is ~2.4MB/sec @
> >> > 48MHz. Added edma memory copy functionality in spi flash driver to
> >> > improve the data through put to 5.1MB/Sec.
> > [snip]
> >> > +#include <asm/arch/edma.h>
> >> > +#include "../dma/ti_edma.h"
> >>
> >> This looks odd to me - header inclusion, as .h in drivers even.
> >
> > I could shove this under arch/arm/include/asm/ti-common I suppose.
> 
> Any changes in code logic or updates?

Since I posted? No, I was waiting for your reply :)

> >> >  /* ti qpsi register bit masks */
> >> >  #define QSPI_TIMEOUT                    2000000
> >> > @@ -340,3 +342,72 @@ int spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout,
> >> >
> >> >         return 0;
> >> >  }
> >> > +
> >> > +#if defined(CONFIG_SPL_DMA_SUPPORT) && defined(CONFIG_TI_EDMA)
> >> > +void spi_flash_copy_mmap(void *data, void *offset, size_t len)
> >> > +{
> >> > +       struct edma_param_entry edma_param;
> >> > +       int           b_cnt_value = 1;
> >> > +       int           rem_bytes  = 0;
> >> > +       int           a_cnt_value = len;
> >> > +       unsigned int          addr      = (unsigned int) (data);
> >> > +       unsigned int          max_acnt  = 0x7FFFU;
> >> > +       unsigned int edma_ch_num = 1;
> >> > +
> >> > +       if (len > max_acnt)
> >> > +       {
> >> > +               b_cnt_value = (len / max_acnt);
> >> > +               rem_bytes  = (len % max_acnt);
> >> > +               a_cnt_value = max_acnt;
> >> > +       }
> >> > +
> >> > +       /* Compute QSPI address and size */
> >> > +       edma_param.opt      = 0;
> >> > +       edma_param.src_addr  = ((unsigned int) offset);
> >> > +       edma_param.dest_addr = addr;
> >> > +       edma_param.a_cnt     = a_cnt_value;
> >> > +       edma_param.b_cnt     = b_cnt_value;
> >> > +       edma_param.c_cnt     = 1;
> >> > +       edma_param.src_bidx  = a_cnt_value;
> >> > +       edma_param.dest_bidx = a_cnt_value;
> >> > +       edma_param.src_cidx  = 0;
> >> > +       edma_param.dest_cidx = 0;
> >> > +       edma_param.link_addr = 0xFFFF;
> >> > +       edma_param.opt     |=
> >> > +               (EDMA_TPCC_OPT_TCINTEN_MASK |
> >> > +                ((edma_ch_num <<
> >> > +                  EDMA_TPCC_OPT_TCC_SHIFT) &
> >> > +                 EDMA_TPCC_OPT_TCC_MASK) | EDMA_TPCC_OPT_SYNCDIM_MASK);
> >> > +
> >> > +       edma_set_param(edma_ch_num, &edma_param);
> >> > +       edma_enable_transfer(edma_ch_num);
> >> > +
> >> > +       while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> >> > +       edma_clr_intr(edma_ch_num);
> >> > +       if (rem_bytes != 0)
> >> > +       {
> >> > +               /* Compute QSPI address and size */
> >> > +               edma_param.opt     = 0;
> >> > +               edma_param.src_addr =
> >> > +                       (b_cnt_value * max_acnt) + ((unsigned int) offset);
> >> > +               edma_param.dest_addr = (addr + (max_acnt * b_cnt_value));
> >> > +               edma_param.a_cnt     = rem_bytes;
> >> > +               edma_param.b_cnt     = 1;
> >> > +               edma_param.c_cnt     = 1;
> >> > +               edma_param.src_bidx  = rem_bytes;
> >> > +               edma_param.dest_bidx = rem_bytes;
> >> > +               edma_param.src_cidx  = 0;
> >> > +               edma_param.dest_cidx = 0;
> >> > +               edma_param.link_addr = 0xFFFF;
> >> > +               edma_param.opt     |=
> >> > +                       (EDMA_TPCC_OPT_TCINTEN_MASK |
> >> > +                        ((edma_ch_num << EDMA_TPCC_OPT_TCC_SHIFT) & EDMA_TPCC_OPT_TCC_MASK));
> >> > +               edma_set_param(edma_ch_num, &edma_param);
> >> > +               edma_enable_transfer(edma_ch_num);
> >> > +
> >> > +               while (!(edma_get_intr_status() & (1 << edma_ch_num))) ;
> >> > +               edma_clr_intr(edma_ch_num);
> >> > +       }
> >> > +       *((unsigned int *) offset) += len;
> >> > +}
> >> > +#endif
> >>
> >> I'm some how !OK with this memory or flash change in spi driver.
> >> Any better approach to move this - may be in DMA driver itself and
> >> picking up the
> >> memory attributes from sf layer.
> >>
> >> I'm not much clear about this now, but will come back again.
> >
> > Well, are you happy with how drivers/spi/mxs_spi.c works (search around
> > on mxs_dma)?  I can re-jigger things along those lines I suppose.
> 
> thanks!

So you're happy with how mxs_spi.c does DMA then?  I'll pencil in some
time to rework this code using that driver as a model then, thanks.

-- 
Tom
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 836 bytes
Desc: Digital signature
URL: <http://lists.denx.de/pipermail/u-boot/attachments/20150422/5f7c831a/attachment.sig>

^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, other threads:[~2015-04-22 14:25 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2014-07-11 20:53 [U-Boot] [PATCH 1/3] sf: ops: Add spi_flash_copy_mmap function Tom Rini
2014-07-11 20:53 ` [U-Boot] [PATCH 2/3] dma: Add TI EDMA driver Tom Rini
2014-07-11 20:53 ` [U-Boot] [PATCH 3/3] sf: ti_qspi: Enable EDMA for reads in SPL Tom Rini
2014-07-12 13:12   ` Jagan Teki
2014-07-14 20:37     ` Tom Rini
2015-01-16 16:00       ` Tom Rini
2015-04-22 11:15       ` Jagan Teki
2015-04-22 14:25         ` Tom Rini

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.