Micron Nor flash don't support read operation after send write command. As below,
flash_write_cmd(info, sector, offset, AMD_CMD_WRITE_TO_BUFFER); cnt = len >> shift; flash_write_cmd(info, sector, offset, cnt - 1); switch (info->portwidth) { case FLASH_CFI_8BIT: while (cnt-- > 0) { flash_write8(flash_read8(src), dst); src += 1, dst += 1; } break; If the src address locate in NOR flash, flash_read operation will be failed. So, read out the data to DRAM before send write command operation. --- drivers/mtd/cfi_flash.c | 70 +++++++++++++++++++++++++++++++---------------- 1 file changed, 46 insertions(+), 24 deletions(-) diff --git a/drivers/mtd/cfi_flash.c b/drivers/mtd/cfi_flash.c index a389cd1..0f532c0 100644 --- a/drivers/mtd/cfi_flash.c +++ b/drivers/mtd/cfi_flash.c @@ -25,6 +25,8 @@ #include <environment.h> #include <mtd/cfi_flash.h> #include <watchdog.h> +#include <malloc.h> +#include <asm-generic/errno.h> /* * This file implements a Common Flash Interface (CFI) driver for @@ -855,6 +857,8 @@ static int flash_write_cfibuffer (flash_info_t * info, ulong dest, uchar * cp, int cnt; int retcode; void *src = cp; + void *src2; + void *src2_bak; void *dst = (void *)dest; void *dst2 = dst; int flag = 1; @@ -880,29 +884,45 @@ static int flash_write_cfibuffer (flash_info_t * info, ulong dest, uchar * cp, goto out_unmap; } + src2 = malloc(len); + if(!src2) + { + free(src2); + return -ENOMEM; + } + + src2_bak = src2; cnt = len >> shift; while ((cnt-- > 0) && (flag == 1)) { switch (info->portwidth) { case FLASH_CFI_8BIT: - flag = ((flash_read8(dst2) & flash_read8(src)) == - flash_read8(src)); + *(u8 *)src2 = flash_read8(src); + flag = ((flash_read8(dst2) & *(u8 *)src2) == + *(u8 *)src2); src += 1, dst2 += 1; + src2 +=1; break; case FLASH_CFI_16BIT: - flag = ((flash_read16(dst2) & flash_read16(src)) == - flash_read16(src)); + *(u16 *)src2 = flash_read16(src); + flag = ((flash_read16(dst2) & *(u16 *)src2) == + *(u16 *)src2); src += 2, dst2 += 2; + src2 += 2; break; case FLASH_CFI_32BIT: - flag = ((flash_read32(dst2) & flash_read32(src)) == - flash_read32(src)); + *(u32 *)src2 = flash_read32(src); + flag = ((flash_read32(dst2) & *(u32 *)src2) == + *(u32 *)src2); src += 4, dst2 += 4; + src2 += 4; break; case FLASH_CFI_64BIT: - flag = ((flash_read64(dst2) & flash_read64(src)) == - flash_read64(src)); + *(u64 *)src2 = flash_read64(src); + flag = ((flash_read64(dst2) & *(u64 *)src2) == + *(u64 *)src2); src += 8, dst2 += 8; + src2 += 8; break; } } @@ -912,6 +932,7 @@ static int flash_write_cfibuffer (flash_info_t * info, ulong dest, uchar * cp, } src = cp; + src2 = src2_bak; sector = find_sector (info, dest); switch (info->vendor) { @@ -934,20 +955,20 @@ static int flash_write_cfibuffer (flash_info_t * info, ulong dest, uchar * cp, while (cnt-- > 0) { switch (info->portwidth) { case FLASH_CFI_8BIT: - flash_write8(flash_read8(src), dst); - src += 1, dst += 1; + flash_write8(*(u8 *)src2, dst); + src2 += 1, dst += 1; break; case FLASH_CFI_16BIT: - flash_write16(flash_read16(src), dst); - src += 2, dst += 2; + flash_write16(*(u16 *)src2, dst); + src2 += 2, dst += 2; break; case FLASH_CFI_32BIT: - flash_write32(flash_read32(src), dst); - src += 4, dst += 4; + flash_write32(*(u32 *)src2, dst); + src2 += 4, dst += 4; break; case FLASH_CFI_64BIT: - flash_write64(flash_read64(src), dst); - src += 8, dst += 8; + flash_write64(*(u64 *)src2, dst); + src2 += 8, dst += 8; break; default: retcode = ERR_INVAL; @@ -977,26 +998,26 @@ static int flash_write_cfibuffer (flash_info_t * info, ulong dest, uchar * cp, switch (info->portwidth) { case FLASH_CFI_8BIT: while (cnt-- > 0) { - flash_write8(flash_read8(src), dst); - src += 1, dst += 1; + flash_write8(*(u8 *)src2, dst); + src2 += 1, dst += 1; } break; case FLASH_CFI_16BIT: while (cnt-- > 0) { - flash_write16(flash_read16(src), dst); - src += 2, dst += 2; + flash_write16(*(u16 *)src2, dst); + src2 += 2, dst += 2; } break; case FLASH_CFI_32BIT: while (cnt-- > 0) { - flash_write32(flash_read32(src), dst); - src += 4, dst += 4; + flash_write32(*(u32 *)src2, dst); + src2 += 4, dst += 4; } break; case FLASH_CFI_64BIT: while (cnt-- > 0) { - flash_write64(flash_read64(src), dst); - src += 8, dst += 8; + flash_write64(*(u64 *)src2, dst); + src2 += 8, dst += 8; } break; default: @@ -1023,6 +1044,7 @@ static int flash_write_cfibuffer (flash_info_t * info, ulong dest, uchar * cp, } out_unmap: + free(src2_bak); return retcode; } #endif /* CONFIG_SYS_FLASH_USE_BUFFER_WRITE */ -- 1.7.9.5 Best Regards, Qi Wang EBU APAC SE Tel: 86-021-38997158 Mobile: 86-15201958202 Email: qiw...@micron.com Address: No 601 Fasai Rd, Pudong, Shanghai, China, 200131 _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de http://lists.denx.de/mailman/listinfo/u-boot