summaryrefslogtreecommitdiff
path: root/util
diff options
context:
space:
mode:
authorDino Li <Dino.Li@ite.com.tw>2020-08-27 18:06:05 +0800
committerCommit Bot <commit-bot@chromium.org>2020-09-03 00:33:43 +0000
commitd031c14214cb1e2a229a909e946b5b36ff91afee (patch)
tree30f888d7a23f280175bb10b8e4898d9566e8d991 /util
parent147803fd0f6785692c215e49d31b948ac871acb5 (diff)
downloadchrome-ec-d031c14214cb1e2a229a909e946b5b36ff91afee.tar.gz
iteflash: speed up flash read
To save time, this patch removes unnecessary i2c transactions in reading (verifying) flash. BUG=none BRANCH=none TEST=Read 512k bytes without/with this patch: ======without patch / with patch============= servo v2 : 36s / 14s ( 22s reduced) servo micro: 2m:13s / 1m:04s (1m:09s reduced) c2d2 : 81s / 23s ( 58s reduced) Change-Id: I9dc05e107eaf004c4c2017de9ffe9aa97a0d9c68 Signed-off-by: Dino Li <Dino.Li@ite.com.tw> Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2379368 Reviewed-by: Jett Rink <jettrink@chromium.org> Commit-Queue: Jett Rink <jettrink@chromium.org>
Diffstat (limited to 'util')
-rw-r--r--util/iteflash.c51
1 files changed, 31 insertions, 20 deletions
diff --git a/util/iteflash.c b/util/iteflash.c
index b2c4161f1f..36e45c2012 100644
--- a/util/iteflash.c
+++ b/util/iteflash.c
@@ -1135,13 +1135,34 @@ static void draw_spinner(uint32_t remaining, uint32_t size)
windex %= sizeof(wheel);
}
+/* Note: this function must be called in follow mode */
+static int spi_send_cmd_fast_read(struct common_hnd *chnd, uint32_t addr)
+{
+ int ret = 0;
+ uint8_t cmd = 0x9;
+
+ /* Fast Read command */
+ ret = spi_flash_command_short(chnd, SPI_CMD_FAST_READ, "fast read");
+ /* Send address */
+ ret |= i2c_write_byte(chnd, 0x08, ((addr >> 16) & 0xff)); /* addr_h */
+ ret |= i2c_write_byte(chnd, 0x08, ((addr >> 8) & 0xff)); /* addr_m */
+ ret |= i2c_write_byte(chnd, 0x08, (addr & 0xff)); /* addr_l */
+ /* fake byte */
+ ret |= i2c_write_byte(chnd, 0x08, 0x00);
+ /* use i2c block read command */
+ ret |= i2c_byte_transfer(chnd, I2C_CMD_ADDR, &cmd, 1, 1);
+ if (ret < 0)
+ fprintf(stderr, "Send fast read command failed\n");
+
+ return ret;
+}
+
static int command_read_pages(struct common_hnd *chnd, uint32_t address,
uint32_t size, uint8_t *buffer)
{
int res = -EIO;
uint32_t remaining = size;
int cnt;
- uint8_t addr_H, addr_M;
if (address & 0xFF) {
fprintf(stderr, "page read requested at non-page boundary: "
@@ -1152,30 +1173,14 @@ static int command_read_pages(struct common_hnd *chnd, uint32_t address,
if (spi_flash_follow_mode(chnd, "fast read") < 0)
goto failed_read;
- while (remaining) {
- uint8_t cmd = 0x9;
+ if (spi_send_cmd_fast_read(chnd, address) < 0)
+ goto failed_read;
+ while (remaining) {
cnt = (remaining > PAGE_SIZE) ? PAGE_SIZE : remaining;
- addr_H = (address >> 16) & 0xFF;
- addr_M = (address >> 8) & 0xFF;
-
draw_spinner(remaining, size);
- /* Fast Read command */
- if (spi_flash_command_short(chnd, SPI_CMD_FAST_READ,
- "fast read") < 0)
- goto failed_read;
- res = i2c_write_byte(chnd, 0x08, addr_H);
- res += i2c_write_byte(chnd, 0x08, addr_M);
- res += i2c_write_byte(chnd, 0x08, 0x00); /* addr_L */
- res += i2c_write_byte(chnd, 0x08, 0x00);
- if (res < 0) {
- fprintf(stderr, "page address set failed\n");
- goto failed_read;
- }
-
/* read page data */
- res = i2c_byte_transfer(chnd, I2C_CMD_ADDR, &cmd, 1, 1);
res = i2c_byte_transfer(chnd, I2C_BLOCK_ADDR, buffer, 0, cnt);
if (res < 0) {
fprintf(stderr, "page data read failed\n");
@@ -1185,6 +1190,12 @@ static int command_read_pages(struct common_hnd *chnd, uint32_t address,
address += cnt;
remaining -= cnt;
buffer += cnt;
+
+ /* We need to resend fast read command at 256KB boundary. */
+ if (!(address % 0x40000) && remaining) {
+ if (spi_send_cmd_fast_read(chnd, address) < 0)
+ goto failed_read;
+ }
}
/* No error so far */
res = size;