diff options
Diffstat (limited to 'util')
-rw-r--r-- | util/uut/main.c | 120 | ||||
-rw-r--r-- | util/uut/opr.c | 36 | ||||
-rw-r--r-- | util/uut/opr.h | 1 |
3 files changed, 144 insertions, 13 deletions
diff --git a/util/uut/main.c b/util/uut/main.c index cde439ba17..ff3a3066fd 100644 --- a/util/uut/main.c +++ b/util/uut/main.c @@ -14,6 +14,7 @@ #include <sys/stat.h> #include "com_port.h" +#include "compile_time_macros.h" #include "main.h" #include "misc_util.h" #include "opr.h" @@ -44,6 +45,12 @@ #define FIRMWARE_START_ADDR 0x10090000 /* Divide the ec firmware image into 4K byte */ #define FIRMWARE_SEGMENT 0x1000 +/* Register address for chip ID */ +#define NPCX_SRID_CR 0x400C101C +/* Register address for device ID */ +#define NPCX_DEVICE_ID_CR 0x400C1022 +#define NPCX_FLASH_BASE_ADDR 0x64000000 + /*--------------------------------------------------------------------------- * Global variables *--------------------------------------------------------------------------- @@ -69,7 +76,50 @@ static uint32_t baudrate; static uint32_t dev_num; static uint32_t flash_offset; static bool auto_mode; +static bool read_flash_flag; + +struct npcx_chip_info { + uint8_t device_id; + uint8_t chip_id; + uint32_t flash_size; +}; +const static struct npcx_chip_info chip_info[] = { + { + /* NPCX796FA */ + .device_id = 0x21, + .chip_id = 0x06, + .flash_size = 1024 * 1024, + }, + + { + /* NPCX796FB */ + .device_id = 0x21, + .chip_id = 0x07, + .flash_size = 1024 * 1024, + }, + + { + /* NPCX797WB */ + .device_id = 0x24, + .chip_id = 0x07, + .flash_size = 1024 * 1024, + }, + + { + /* NPCX796FC */ + .device_id = 0x29, + .chip_id = 0x07, + .flash_size = 512 * 1024, + }, + + { + /* NPCX797WC */ + .device_id = 0x2C, + .chip_id = 0x07, + .flash_size = 512 * 1024, + }, +}; /*--------------------------------------------------------------------------- * Functions prototypes *--------------------------------------------------------------------------- @@ -198,6 +248,29 @@ static bool image_auto_write(uint32_t offset, uint8_t *buffer, return true; } +static bool get_flash_size(uint32_t *flash_size) +{ + uint8_t dev_id, chip_id, i; + + if (opr_read_chunk(&dev_id, NPCX_DEVICE_ID_CR, 1) != true) + return false; + + if (opr_read_chunk(&chip_id, NPCX_SRID_CR, 1) != true) + return false; + + for (i = 0; i < ARRAY_SIZE(chip_info); i++) { + if (chip_info[i].device_id == dev_id && + chip_info[i].chip_id == chip_id) { + *flash_size = chip_info[i].flash_size; + return true; + } + } + printf("Unknown NPCX device ID:0x%02x chip ID:0x%02x\n", + dev_id, chip_id); + + return false; +} + /*--------------------------------------------------------------------------- * Function: read_input_file * @@ -269,6 +342,7 @@ int main(int argc, char *argv[]) verbose = true; console = false; auto_mode = false; + read_flash_flag = false; param_parse_cmd_line(argc, argv); @@ -328,6 +402,20 @@ int main(int argc, char *argv[]) exit_uart_app(-1); } + if (read_flash_flag) { + uint32_t flash_size; + + if (get_flash_size(&flash_size)) { + printf("Read %d bytes from flash...\n", flash_size); + opr_read_mem(file_name, NPCX_FLASH_BASE_ADDR, + flash_size); + exit_uart_app(EC_OK); + } + + printf("Fail to read the flash size\n"); + exit_uart_app(-1); + } + param_check_opr_num(opr_name); /* Write buffer data to chosen address */ @@ -397,22 +485,23 @@ int main(int argc, char *argv[]) */ static const struct option long_opts[] = { - {"version", 0, 0, 'v'}, - {"help", 0, 0, 'h'}, - {"quiet", 0, 0, 'q'}, - {"console", 0, 0, 'c'}, - {"auto", 0, 0, 'A'}, - {"baudrate", 1, 0, 'b'}, - {"opr", 1, 0, 'o'}, - {"port", 1, 0, 'p'}, - {"file", 1, 0, 'f'}, - {"addr", 1, 0, 'a'}, - {"size", 1, 0, 's'}, - {"offset", 1, 0, 'O'}, + {"version", 0, 0, 'v'}, + {"help", 0, 0, 'h'}, + {"quiet", 0, 0, 'q'}, + {"console", 0, 0, 'c'}, + {"auto", 0, 0, 'A'}, + {"read-flash", 0, 0, 'r'}, + {"baudrate", 1, 0, 'b'}, + {"opr", 1, 0, 'o'}, + {"port", 1, 0, 'p'}, + {"file", 1, 0, 'f'}, + {"addr", 1, 0, 'a'}, + {"size", 1, 0, 's'}, + {"offset", 1, 0, 'O'}, {NULL, 0, 0, 0} }; -static char *short_opts = "vhqcAb:o:p:f:a:s:O:?"; +static char *short_opts = "vhqcArb:o:p:f:a:s:O:?"; static void param_parse_cmd_line(int argc, char *argv[]) { @@ -439,6 +528,9 @@ static void param_parse_cmd_line(int argc, char *argv[]) case 'A': auto_mode = true; break; + case 'r': + read_flash_flag = true; + break; case 'b': if (sscanf(optarg, "%du", &baudrate) == 0) exit(EC_BAUDRATE_ERR); @@ -585,6 +677,8 @@ static void tool_usage(void) printf(" -A, --auto - Enable auto mode. (default is off)\n"); printf(" -O, --offset <num> - With --auto, assign the offset of"); printf(" flash where the image to be written.\n"); + printf(" -r, --read-flash - With --file=<file>, Read the whole" + " flash content and write it to <file>.\n"); printf("\n"); printf("Operation specific switches:\n"); printf(" -o, --opr <name> - Operation number (see list below)\n"); diff --git a/util/uut/opr.c b/util/uut/opr.c index 27f4c3463d..81a711cf75 100644 --- a/util/uut/opr.c +++ b/util/uut/opr.c @@ -156,6 +156,42 @@ bool opr_write_chunk(uint8_t *buffer, uint32_t addr, uint32_t size) wr_cmd_buf.cmd, &wr_cmd_buf.cmd_size); return opr_send_cmds(&wr_cmd_buf, 1); } + +/*---------------------------------------------------------------------------- + * Function: opr_read_chunk + * + * Parameters: + * buffer - Data read buffer. + * addr - Memory address to read from. + * size - Data size to read. + * Returns: true if successful, false in the case of an error. + * Side effects: + * Description: + * Read data from RAM, starting from the given address (addr). + * Data size is limited to the max chunk size (256 bytes). + *--------------------------------------------------------------------------- + */ +bool opr_read_chunk(uint8_t *buffer, uint32_t addr, uint32_t size) +{ + struct command_node rd_cmd_buf; + + if (size > MAX_RW_DATA_SIZE) { + display_color_msg(FAIL, + "ERROR: Block cannot exceed %d\n", MAX_RW_DATA_SIZE); + return false; + } + + cmd_create_read(addr, ((uint8_t)size - 1), + rd_cmd_buf.cmd, &rd_cmd_buf.cmd_size); + rd_cmd_buf.resp_size = size + 3; + if (opr_send_cmds(&rd_cmd_buf, 1)) { + if (resp_buf[0] == (uint8_t)(UFPP_READ_CMD)) { + memcpy(buffer, &resp_buf[1], size); + return true; + } + } + return false; +} /*---------------------------------------------------------------------------- * Function: opr_write_mem * diff --git a/util/uut/opr.h b/util/uut/opr.h index f3d630ceb4..3b166f0c7e 100644 --- a/util/uut/opr.h +++ b/util/uut/opr.h @@ -49,6 +49,7 @@ void opr_usage(void); bool opr_close_port(void); bool opr_open_port(const char *port_name, struct comport_fields port_cfg); bool opr_write_chunk(uint8_t *buffer, uint32_t addr, uint32_t size); +bool opr_read_chunk(uint8_t *buffer, uint32_t addr, uint32_t size); void opr_write_mem(uint8_t *buffer, uint32_t addr, uint32_t size); void opr_read_mem(char *output, uint32_t addr, uint32_t size); void opr_execute_exit(uint32_t addr); |