aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/arm/mach-omap2/gpmc.c11
-rw-r--r--arch/arm/plat-omap/include/plat/gpmc.h5
-rw-r--r--drivers/mtd/nand/omap2.c22
3 files changed, 25 insertions, 13 deletions
diff --git a/arch/arm/mach-omap2/gpmc.c b/arch/arm/mach-omap2/gpmc.c
index 382dea83e4f0..674174365f78 100644
--- a/arch/arm/mach-omap2/gpmc.c
+++ b/arch/arm/mach-omap2/gpmc.c
@@ -60,7 +60,6 @@
60#define GPMC_CHUNK_SHIFT 24 /* 16 MB */ 60#define GPMC_CHUNK_SHIFT 24 /* 16 MB */
61#define GPMC_SECTION_SHIFT 28 /* 128 MB */ 61#define GPMC_SECTION_SHIFT 28 /* 128 MB */
62 62
63#define PREFETCH_FIFOTHRESHOLD (0x40 << 8)
64#define CS_NUM_SHIFT 24 63#define CS_NUM_SHIFT 24
65#define ENABLE_PREFETCH (0x1 << 7) 64#define ENABLE_PREFETCH (0x1 << 7)
66#define DMA_MPU_MODE 2 65#define DMA_MPU_MODE 2
@@ -606,15 +605,19 @@ EXPORT_SYMBOL(gpmc_nand_write);
606/** 605/**
607 * gpmc_prefetch_enable - configures and starts prefetch transfer 606 * gpmc_prefetch_enable - configures and starts prefetch transfer
608 * @cs: cs (chip select) number 607 * @cs: cs (chip select) number
608 * @fifo_th: fifo threshold to be used for read/ write
609 * @dma_mode: dma mode enable (1) or disable (0) 609 * @dma_mode: dma mode enable (1) or disable (0)
610 * @u32_count: number of bytes to be transferred 610 * @u32_count: number of bytes to be transferred
611 * @is_write: prefetch read(0) or write post(1) mode 611 * @is_write: prefetch read(0) or write post(1) mode
612 */ 612 */
613int gpmc_prefetch_enable(int cs, int dma_mode, 613int gpmc_prefetch_enable(int cs, int fifo_th, int dma_mode,
614 unsigned int u32_count, int is_write) 614 unsigned int u32_count, int is_write)
615{ 615{
616 616
617 if (!(gpmc_read_reg(GPMC_PREFETCH_CONTROL))) { 617 if (fifo_th > PREFETCH_FIFOTHRESHOLD_MAX) {
618 pr_err("gpmc: fifo threshold is not supported\n");
619 return -1;
620 } else if (!(gpmc_read_reg(GPMC_PREFETCH_CONTROL))) {
618 /* Set the amount of bytes to be prefetched */ 621 /* Set the amount of bytes to be prefetched */
619 gpmc_write_reg(GPMC_PREFETCH_CONFIG2, u32_count); 622 gpmc_write_reg(GPMC_PREFETCH_CONFIG2, u32_count);
620 623
@@ -622,7 +625,7 @@ int gpmc_prefetch_enable(int cs, int dma_mode,
622 * enable the engine. Set which cs is has requested for. 625 * enable the engine. Set which cs is has requested for.
623 */ 626 */
624 gpmc_write_reg(GPMC_PREFETCH_CONFIG1, ((cs << CS_NUM_SHIFT) | 627 gpmc_write_reg(GPMC_PREFETCH_CONFIG1, ((cs << CS_NUM_SHIFT) |
625 PREFETCH_FIFOTHRESHOLD | 628 PREFETCH_FIFOTHRESHOLD(fifo_th) |
626 ENABLE_PREFETCH | 629 ENABLE_PREFETCH |
627 (dma_mode << DMA_MPU_MODE) | 630 (dma_mode << DMA_MPU_MODE) |
628 (0x1 & is_write))); 631 (0x1 & is_write)));
diff --git a/arch/arm/plat-omap/include/plat/gpmc.h b/arch/arm/plat-omap/include/plat/gpmc.h
index 9c060da0a873..a2434639063d 100644
--- a/arch/arm/plat-omap/include/plat/gpmc.h
+++ b/arch/arm/plat-omap/include/plat/gpmc.h
@@ -83,6 +83,9 @@
83#define GPMC_IRQ_FIFOEVENTENABLE 0x01 83#define GPMC_IRQ_FIFOEVENTENABLE 0x01
84#define GPMC_IRQ_COUNT_EVENT 0x02 84#define GPMC_IRQ_COUNT_EVENT 0x02
85 85
86#define PREFETCH_FIFOTHRESHOLD_MAX 0x40
87#define PREFETCH_FIFOTHRESHOLD(val) ((val) << 8)
88
86/* 89/*
87 * Note that all values in this struct are in nanoseconds except sync_clk 90 * Note that all values in this struct are in nanoseconds except sync_clk
88 * (which is in picoseconds), while the register values are in gpmc_fck cycles. 91 * (which is in picoseconds), while the register values are in gpmc_fck cycles.
@@ -134,7 +137,7 @@ extern int gpmc_cs_request(int cs, unsigned long size, unsigned long *base);
134extern void gpmc_cs_free(int cs); 137extern void gpmc_cs_free(int cs);
135extern int gpmc_cs_set_reserved(int cs, int reserved); 138extern int gpmc_cs_set_reserved(int cs, int reserved);
136extern int gpmc_cs_reserved(int cs); 139extern int gpmc_cs_reserved(int cs);
137extern int gpmc_prefetch_enable(int cs, int dma_mode, 140extern int gpmc_prefetch_enable(int cs, int fifo_th, int dma_mode,
138 unsigned int u32_count, int is_write); 141 unsigned int u32_count, int is_write);
139extern int gpmc_prefetch_reset(int cs); 142extern int gpmc_prefetch_reset(int cs);
140extern void omap3_gpmc_save_context(void); 143extern void omap3_gpmc_save_context(void);
diff --git a/drivers/mtd/nand/omap2.c b/drivers/mtd/nand/omap2.c
index fbe841467175..f1648fd5924a 100644
--- a/drivers/mtd/nand/omap2.c
+++ b/drivers/mtd/nand/omap2.c
@@ -244,7 +244,8 @@ static void omap_read_buf_pref(struct mtd_info *mtd, u_char *buf, int len)
244 } 244 }
245 245
246 /* configure and start prefetch transfer */ 246 /* configure and start prefetch transfer */
247 ret = gpmc_prefetch_enable(info->gpmc_cs, 0x0, len, 0x0); 247 ret = gpmc_prefetch_enable(info->gpmc_cs,
248 PREFETCH_FIFOTHRESHOLD_MAX, 0x0, len, 0x0);
248 if (ret) { 249 if (ret) {
249 /* PFPW engine is busy, use cpu copy method */ 250 /* PFPW engine is busy, use cpu copy method */
250 if (info->nand.options & NAND_BUSWIDTH_16) 251 if (info->nand.options & NAND_BUSWIDTH_16)
@@ -289,7 +290,8 @@ static void omap_write_buf_pref(struct mtd_info *mtd,
289 } 290 }
290 291
291 /* configure and start prefetch transfer */ 292 /* configure and start prefetch transfer */
292 ret = gpmc_prefetch_enable(info->gpmc_cs, 0x0, len, 0x1); 293 ret = gpmc_prefetch_enable(info->gpmc_cs,
294 PREFETCH_FIFOTHRESHOLD_MAX, 0x0, len, 0x1);
293 if (ret) { 295 if (ret) {
294 /* PFPW engine is busy, use cpu copy method */ 296 /* PFPW engine is busy, use cpu copy method */
295 if (info->nand.options & NAND_BUSWIDTH_16) 297 if (info->nand.options & NAND_BUSWIDTH_16)
@@ -345,8 +347,9 @@ static inline int omap_nand_dma_transfer(struct mtd_info *mtd, void *addr,
345 int ret; 347 int ret;
346 unsigned long tim, limit; 348 unsigned long tim, limit;
347 349
348 /* The fifo depth is 64 bytes. We have a sync at each frame and frame 350 /* The fifo depth is 64 bytes max.
349 * length is 64 bytes. 351 * But configure the FIFO-threahold to 32 to get a sync at each frame
352 * and frame length is 32 bytes.
350 */ 353 */
351 int buf_len = len >> 6; 354 int buf_len = len >> 6;
352 355
@@ -387,7 +390,8 @@ static inline int omap_nand_dma_transfer(struct mtd_info *mtd, void *addr,
387 OMAP24XX_DMA_GPMC, OMAP_DMA_SRC_SYNC); 390 OMAP24XX_DMA_GPMC, OMAP_DMA_SRC_SYNC);
388 } 391 }
389 /* configure and start prefetch transfer */ 392 /* configure and start prefetch transfer */
390 ret = gpmc_prefetch_enable(info->gpmc_cs, 0x1, len, is_write); 393 ret = gpmc_prefetch_enable(info->gpmc_cs,
394 PREFETCH_FIFOTHRESHOLD_MAX, 0x1, len, is_write);
391 if (ret) 395 if (ret)
392 /* PFPW engine is busy, use cpu copy method */ 396 /* PFPW engine is busy, use cpu copy method */
393 goto out_copy; 397 goto out_copy;
@@ -522,7 +526,8 @@ static void omap_read_buf_irq_pref(struct mtd_info *mtd, u_char *buf, int len)
522 init_completion(&info->comp); 526 init_completion(&info->comp);
523 527
524 /* configure and start prefetch transfer */ 528 /* configure and start prefetch transfer */
525 ret = gpmc_prefetch_enable(info->gpmc_cs, 0x0, len, 0x0); 529 ret = gpmc_prefetch_enable(info->gpmc_cs,
530 PREFETCH_FIFOTHRESHOLD_MAX/2, 0x0, len, 0x0);
526 if (ret) 531 if (ret)
527 /* PFPW engine is busy, use cpu copy method */ 532 /* PFPW engine is busy, use cpu copy method */
528 goto out_copy; 533 goto out_copy;
@@ -569,8 +574,9 @@ static void omap_write_buf_irq_pref(struct mtd_info *mtd,
569 info->buf = (u_char *) buf; 574 info->buf = (u_char *) buf;
570 init_completion(&info->comp); 575 init_completion(&info->comp);
571 576
572 /* configure and start prefetch transfer */ 577 /* configure and start prefetch transfer : size=24 */
573 ret = gpmc_prefetch_enable(info->gpmc_cs, 0x0, len, 0x1); 578 ret = gpmc_prefetch_enable(info->gpmc_cs,
579 (PREFETCH_FIFOTHRESHOLD_MAX * 3) / 8, 0x0, len, 0x1);
574 if (ret) 580 if (ret)
575 /* PFPW engine is busy, use cpu copy method */ 581 /* PFPW engine is busy, use cpu copy method */
576 goto out_copy; 582 goto out_copy;