CK HU has uploaded this change for review. ( https://review.coreboot.org/c/coreboot/+/44851 )
Change subject: soc/mediatek/mt8192: Add SPI flash controller DMA read function ......................................................................
soc/mediatek/mt8192: Add SPI flash controller DMA read function
To speed up SPI flash read, enable DMA read function.
Signed-off-by: CK Hu ck.hu@mediatek.com Change-Id: Ic1679ef7940258350feeadac50ad8ea407fd7b90 --- M src/soc/mediatek/mt8192/flash_controller.c 1 file changed, 55 insertions(+), 1 deletion(-)
git pull ssh://review.coreboot.org:29418/coreboot refs/changes/51/44851/1
diff --git a/src/soc/mediatek/mt8192/flash_controller.c b/src/soc/mediatek/mt8192/flash_controller.c index 304e4c3..0c37ae5 100644 --- a/src/soc/mediatek/mt8192/flash_controller.c +++ b/src/soc/mediatek/mt8192/flash_controller.c @@ -8,6 +8,7 @@ #include <spi-generic.h> #include <stdint.h> #include <string.h> +#include <symbols.h> #include <timer.h> #include <types.h>
@@ -91,6 +92,37 @@ return 0; }
+static int dma_read(u32 addr, u8 *buf, u32 len, uintptr_t dma_buf, + size_t dma_buf_len) +{ + struct stopwatch sw; + + assert(IS_ALIGNED((uintptr_t)addr, SFLASH_DMA_ALIGN) && + IS_ALIGNED(len, SFLASH_DMA_ALIGN) && + len <= dma_buf_len); + + /* do dma reset */ + write32(&mt8192_nor->fdma_ctl, SFLASH_DMA_SW_RESET); + write32(&mt8192_nor->fdma_ctl, SFLASH_DMA_WDLE_EN); + /* flash source address and dram dest address */ + write32(&mt8192_nor->fdma_fadr, addr); + write32(&mt8192_nor->fdma_dadr, dma_buf); + write32(&mt8192_nor->fdma_end_dadr, (dma_buf + len)); + /* start dma */ + write32(&mt8192_nor->fdma_ctl, SFLASH_DMA_TRIGGER | SFLASH_DMA_WDLE_EN); + + stopwatch_init_usecs_expire(&sw, SFLASH_POLLINGREG_US); + while ((read32(&mt8192_nor->fdma_ctl) & SFLASH_DMA_TRIGGER) != 0) { + if (stopwatch_expired(&sw)) { + printk(BIOS_WARNING, "dma read timeout!\n"); + return -1; + } + } + + memcpy(buf, (const void *)dma_buf, len); + return 0; +} + static int pio_read(u32 addr, u8 *buf, u32 len) { set_sfpaddr(addr); @@ -107,7 +139,29 @@ static int nor_read(const struct spi_flash *flash, u32 addr, size_t len, void *buf) { - if (pio_read(addr, buf, len)) + size_t done = 0; + uintptr_t dma_buf = (uintptr_t)_dma_coherent; + size_t dma_buf_len = REGION_SIZE(dma_coherent); + u32 next; + + if (!IS_ALIGNED((uintptr_t)addr, SFLASH_DMA_ALIGN)) { + next = MIN(ALIGN_UP((uintptr_t)addr, SFLASH_DMA_ALIGN) - + (uintptr_t)addr, len); + if (pio_read(addr, buf, next)) + return -1; + done += next; + } + + while (len - done >= SFLASH_DMA_ALIGN) { + next = MIN(dma_buf_len, ALIGN_DOWN(len - done, + SFLASH_DMA_ALIGN)); + if (dma_read(addr + done, buf + done, next, dma_buf, + dma_buf_len)) + return -1; + done += next; + } + next = len - done; + if (next > 0 && pio_read(addr + done, buf + done, next)) return -1;
return 0;