spi: Add progress percentage and write speed to `sf update`

Output a progress update only at most 10 times per second, to avoid
saturating (and waiting on) the console. Make the summary line
to fit on a single line. Make sure that cursor sits at the end of
each update line instead of the beginning.

Sample output:

SF: Detected W25Q32 with page size 4 KiB, total 4 MiB
Update SPI
1331200 bytes written, 2863104 bytes skipped in 21.912s, speed 199728 B/s

time: 21.919 seconds, 21919 ticks
Skipping verify

Signed-off-by: Simon Glass <sjg@chromium.org>
Signed-off-by: James Miller <jamesmiller@chromium.org>
Signed-off-by: Taylor Hutt <thutt@chromium.org>
[trini: Drop 'const' from bytes_per_second()]
Signed-off-by: Tom Rini <trini@ti.com>
master
James Miller 12 years ago committed by Tom Rini
parent 095728803e
commit a683c288d4
  1. 41
      common/cmd_sf.c

@ -67,6 +67,23 @@ static int sf_parse_len_arg(char *arg, ulong *len)
return 1;
}
/**
* This function takes a byte length and a delta unit of time to compute the
* approximate bytes per second
*
* @param len amount of bytes currently processed
* @param start_ms start time of processing in ms
* @return bytes per second if OK, 0 on error
*/
static ulong bytes_per_second(unsigned int len, ulong start_ms)
{
/* less accurate but avoids overflow */
if (len >= ((unsigned int) -1) / 1024)
return len / (max(get_timer(start_ms) / 1024, 1));
else
return 1024 * len / max(get_timer(start_ms), 1);
}
static int do_spi_flash_probe(int argc, char * const argv[])
{
unsigned int bus = CONFIG_SF_DEFAULT_BUS;
@ -167,11 +184,26 @@ static int spi_flash_update(struct spi_flash *flash, u32 offset,
const char *end = buf + len;
size_t todo; /* number of bytes to do in this pass */
size_t skipped = 0; /* statistics */
const ulong start_time = get_timer(0);
size_t scale = 1;
const char *start_buf = buf;
ulong delta;
if (end - buf >= 200)
scale = (end - buf) / 100;
cmp_buf = malloc(flash->sector_size);
if (cmp_buf) {
ulong last_update = get_timer(0);
for (; buf < end && !err_oper; buf += todo, offset += todo) {
todo = min(end - buf, flash->sector_size);
if (get_timer(last_update) > 100) {
printf(" \rUpdating, %zu%% %lu B/s",
100 - (end - buf) / scale,
bytes_per_second(buf - start_buf,
start_time));
last_update = get_timer(0);
}
err_oper = spi_flash_update_block(flash, offset, todo,
buf, cmp_buf, &skipped);
}
@ -179,12 +211,17 @@ static int spi_flash_update(struct spi_flash *flash, u32 offset,
err_oper = "malloc";
}
free(cmp_buf);
putc('\r');
if (err_oper) {
printf("SPI flash failed in %s step\n", err_oper);
return 1;
}
printf("%zu bytes written, %zu bytes skipped\n", len - skipped,
skipped);
delta = get_timer(start_time);
printf("%zu bytes written, %zu bytes skipped", len - skipped,
skipped);
printf(" in %ld.%lds, speed %ld B/s\n",
delta / 1000, delta % 1000, bytes_per_second(len, start_time));
return 0;
}

Loading…
Cancel
Save