+
+ return retval;
+}
+
+static int handle_flash_fill_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
+{
+ int err = ERROR_OK, retval;
+ uint32_t address;
+ uint32_t pattern;
+ uint32_t count;
+ uint8_t chunk[1024];
+ uint8_t readback[1024];
+ uint32_t wrote = 0;
+ uint32_t cur_size = 0;
+ uint32_t chunk_count;
+ char *duration_text;
+ duration_t duration;
+ target_t *target = get_current_target(cmd_ctx);
+ uint32_t i;
+ uint32_t wordsize;
+
+ if (argc != 3)
+ {
+ return ERROR_COMMAND_SYNTAX_ERROR;
+ }
+
+ address = strtoul(args[0], NULL, 0);
+ pattern = strtoul(args[1], NULL, 0);
+ count = strtoul(args[2], NULL, 0);
+
+ if (count == 0)
+ return ERROR_OK;
+
+ switch (cmd[4])
+ {
+ case 'w':
+ wordsize = 4;
+ break;
+ case 'h':
+ wordsize = 2;
+ break;
+ case 'b':
+ wordsize = 1;
+ break;
+ default:
+ return ERROR_COMMAND_SYNTAX_ERROR;
+ }
+
+ chunk_count = MIN(count, (1024 / wordsize));
+ switch (wordsize)
+ {
+ case 4:
+ for (i = 0; i < chunk_count; i++)
+ {
+ target_buffer_set_u32(target, chunk + i * wordsize, pattern);
+ }
+ break;
+ case 2:
+ for (i = 0; i < chunk_count; i++)
+ {
+ target_buffer_set_u16(target, chunk + i * wordsize, pattern);
+ }
+ break;
+ case 1:
+ memset(chunk, pattern, chunk_count);
+ break;
+ default:
+ LOG_ERROR("BUG: can't happen");
+ exit(-1);
+ }
+
+ duration_start_measure(&duration);
+
+ for (wrote = 0; wrote < (count*wordsize); wrote += cur_size)
+ {
+ cur_size = MIN((count*wordsize - wrote), sizeof(chunk));
+ flash_bank_t *bank;
+ bank = get_flash_bank_by_addr(target, address);
+ if (bank == NULL)
+ {
+ return ERROR_FAIL;
+ }
+ err = flash_driver_write(bank, chunk, address - bank->base + wrote, cur_size);
+ if (err != ERROR_OK)
+ return err;
+
+ err = target_read_buffer(target, address + wrote, cur_size, readback);
+ if (err != ERROR_OK)
+ return err;
+
+ unsigned i;
+ for (i = 0; i < cur_size; i++)
+ {
+ if (readback[i]!=chunk[i])
+ {
+ LOG_ERROR("Verfication error address 0x%08" PRIx32 ", read back 0x%02x, expected 0x%02x",
+ address + wrote + i, readback[i], chunk[i]);
+ return ERROR_FAIL;
+ }
+ }
+
+ }
+
+ if ((retval = duration_stop_measure(&duration, &duration_text)) != ERROR_OK)
+ {
+ return retval;
+ }
+
+ if (err == ERROR_OK)
+ {
+ float speed;
+ speed = wrote / 1024.0;
+ speed/=((float)duration.duration.tv_sec + ((float)duration.duration.tv_usec / 1000000.0));
+ command_print(cmd_ctx,
+ "wrote %" PRId32 " bytes to 0x%8.8" PRIx32 " in %s (%f kb/s)",
+ count*wordsize,
+ address,
+ duration_text,
+ speed);
+ }
+ free(duration_text);