static void parse_cfg_cmd(struct ubl_header *ublhdr, int32_t cmd, char *token, char *name, int lineno, int fld, int dcd_len) { static int cmd_ver_first = ~0; switch (cmd) { case CMD_BOOT_MODE: ublhdr->magic = get_table_entry_id(ublimage_bootops, "ublimage special boot mode", token); if (ublhdr->magic == -1) { fprintf(stderr, "Error: %s[%d] -Invalid boot mode" "(%s)\n", name, lineno, token); exit(EXIT_FAILURE); } ublhdr->magic += UBL_MAGIC_BASE; if (unlikely(cmd_ver_first != 1)) cmd_ver_first = 0; break; case CMD_ENTRY: ublhdr->entry = get_cfg_value(token, name, lineno); break; case CMD_PAGE: ublhdr->pages = get_cfg_value(token, name, lineno); break; case CMD_ST_BLOCK: ublhdr->block = get_cfg_value(token, name, lineno); break; case CMD_ST_PAGE: ublhdr->page = get_cfg_value(token, name, lineno); break; case CMD_LD_ADDR: ublhdr->pll_m = get_cfg_value(token, name, lineno); break; } }
static void parse_cfg_fld(struct imx_header *imxhdr, int32_t *cmd, char *token, char *name, int lineno, int fld, int *dcd_len) { int value; switch (fld) { case CFG_COMMAND: *cmd = get_table_entry_id(imximage_cmds, "imximage commands", token); if (*cmd < 0) { fprintf(stderr, "Error: %s[%d] - Invalid command" "(%s)\n", name, lineno, token); exit(EXIT_FAILURE); } break; case CFG_REG_SIZE: parse_cfg_cmd(imxhdr, *cmd, token, name, lineno, fld, *dcd_len); break; case CFG_REG_ADDRESS: case CFG_REG_VALUE: switch(*cmd) { case CMD_WRITE_DATA: case CMD_WRITE_CLR_BIT: case CMD_WRITE_SET_BIT: case CMD_CHECK_BITS_SET: case CMD_CHECK_BITS_CLR: value = get_cfg_value(token, name, lineno); if (set_dcd_param) (*set_dcd_param)(imxhdr, *dcd_len, *cmd); (*set_dcd_val)(imxhdr, name, lineno, fld, value, *dcd_len); if (fld == CFG_REG_VALUE) { (*dcd_len)++; if (*dcd_len > max_dcd_entries) { fprintf(stderr, "Error: %s[%d] -" "DCD table exceeds maximum size(%d)\n", name, lineno, max_dcd_entries); exit(EXIT_FAILURE); } } break; case CMD_PLUGIN: value = get_cfg_value(token, name, lineno); imximage_iram_free_start = value; break; default: break; } break; default: break; } }
static void parse_cfg_fld(struct ubl_header *ublhdr, int32_t *cmd, char *token, char *name, int lineno, int fld, int *dcd_len) { switch (fld) { case CFG_COMMAND: *cmd = get_table_entry_id(ublimage_cmds, "ublimage commands", token); if (*cmd < 0) { fprintf(stderr, "Error: %s[%d] - Invalid command" "(%s)\n", name, lineno, token); exit(EXIT_FAILURE); } break; case CFG_REG_VALUE: parse_cfg_cmd(ublhdr, *cmd, token, name, lineno, fld, *dcd_len); break; default: break; } }
static uint32_t imximage_parse_cfg_file(struct imx_header *imxhdr, char *name) { FILE *fd = NULL; char *line = NULL; char *token, *saveptr1, *saveptr2; int lineno = 0; int fld, value; size_t len; int dcd_len = 0; dcd_t *dcd = &imxhdr->dcd_table; int32_t cmd; fd = fopen(name, "r"); if (fd == 0) { fprintf(stderr, "Error: %s - Can't open DCD file\n", name); exit(EXIT_FAILURE); } /* Very simple parsing, line starting with # are comments * and are dropped */ while ((getline(&line, &len, fd)) > 0) { lineno++; token = strtok_r(line, "\r\n", &saveptr1); if (token == NULL) continue; /* Check inside the single line */ for (fld = CFG_COMMAND, cmd = CMD_INVALID, line = token; ; line = NULL, fld++) { token = strtok_r(line, " \t", &saveptr2); if (token == NULL) break; /* Drop all text starting with '#' as comments */ if (token[0] == '#') break; /* parse all fields in a single line */ switch (fld) { case CFG_COMMAND: cmd = get_table_entry_id(imximage_cmds, "imximage commands", token); if (cmd < 0) { fprintf(stderr, "Error: %s[%d] - " "Invalid command (%s)\n", name, lineno, token); exit(EXIT_FAILURE); } break; case CFG_REG_SIZE: switch (cmd) { case CMD_BOOT_FROM: /* Get flash header offset */ imxhdr->flash_offset = get_table_entry_id( imximage_bootops, "imximage boot option", token); if (imxhdr->flash_offset == -1) { fprintf(stderr, "Error: %s[%d] -" "Invalid boot device" "(%s)\n", name, lineno, token); exit(EXIT_FAILURE); } break; case CMD_DATA: value = get_cfg_value(token, name, lineno); /* Byte, halfword, word */ if ((value != 1) && (value != 2) && (value != 4)) { fprintf(stderr, "Error: %s[%d] - " "Invalid register size " "(%d)\n", name, lineno, value); exit(EXIT_FAILURE); } dcd->addr_data[dcd_len].type = value; break; } case CFG_REG_ADDRESS: if (cmd == CMD_DATA) dcd->addr_data[dcd_len].addr = get_cfg_value(token, name, lineno); break; case CFG_REG_VALUE: if (cmd == CMD_DATA) { dcd->addr_data[dcd_len].value = get_cfg_value(token, name, lineno); dcd_len++; } break; } } if (dcd_len > MAX_HW_CFG_SIZE) { fprintf(stderr, "Error: %s[%d] -" "DCD table exceeds maximum size(%d)\n", name, lineno, MAX_HW_CFG_SIZE); } } dcd->preamble.barker = DCD_BARKER; dcd->preamble.length = dcd_len * sizeof(dcd_type_addr_data_t); fclose(fd); return dcd_len; }
int genimg_get_comp_id(const char *name) { return (get_table_entry_id(uimage_comp, "Compression", name)); }
int genimg_get_type_id(const char *name) { return (get_table_entry_id(uimage_type, "Image", name)); }
int genimg_get_arch_id(const char *name) { return (get_table_entry_id(uimage_arch, "CPU", name)); }
int genimg_get_os_id(const char *name) { return (get_table_entry_id(uimage_os, "OS", name)); }
/* * this function sets the kwbimage header by- * 1. Abstracting input command line arguments data * 2. parses the kwbimage configuration file and update extebded header data * 3. calculates header, extended header and image checksums */ static void kwdimage_set_ext_header (struct kwb_header *kwbhdr, char* name) { bhr_t *mhdr = &kwbhdr->kwb_hdr; extbhr_t *exthdr = &kwbhdr->kwb_exthdr; FILE *fd = NULL; int j; char *line = NULL; char * token, *saveptr1, *saveptr2; size_t len = 0; enum kwbimage_cmd cmd; fname = name; /* set dram register offset */ exthdr->dramregsoffs = (intptr_t)&exthdr->rcfg - (intptr_t)mhdr; if ((fd = fopen (name, "r")) == 0) { printf ("Error:%s - Can't open\n", fname); exit (EXIT_FAILURE); } /* Simple kwimage.cfg file parser */ lineno=0; while ((getline (&line, &len, fd)) > 0) { lineno++; token = strtok_r (line, "\r\n", &saveptr1); /* drop all lines with zero tokens (= empty lines) */ if (token == NULL) continue; for (j = 0, cmd = CMD_INVALID, line = token; ; line = NULL) { token = strtok_r (line, " \t", &saveptr2); if (token == NULL) break; /* Drop all text starting with '#' as comments */ if (token[0] == '#') break; /* Process rest as valid config command line */ switch (j) { case CFG_COMMAND: cmd = get_table_entry_id (kwbimage_cmds, "Kwbimage command", token); if (cmd == CMD_INVALID) goto INVL_CMD; break; case CFG_DATA0: kwbimage_check_cfgdata (token, cmd, kwbhdr); break; case CFG_DATA1: if (cmd != CMD_DATA) goto INVL_CMD; if (datacmd_cnt > KWBIMAGE_MAX_CONFIG ) { printf ("Error:%s[%d] - Found more " "than max(%zd) allowed " "data configurations\n", fname, lineno, KWBIMAGE_MAX_CONFIG); exit (EXIT_FAILURE); } else{ exthdr->rcfg[datacmd_cnt].rdata = check_get_hexval (token); datacmd_cnt++; } break; default: goto INVL_CMD; } j++; } } if (line) free (line); fclose (fd); return; /* * Invalid Command error reporring * * command CMD_DATA needs three strings on a line * whereas other commands need only two. * * if more than two/three (as per command type) are observed, * then error will be reported */ INVL_CMD: printf ("Error:%s[%d] - Invalid command\n", fname, lineno); exit (EXIT_FAILURE); }
static void kwbimage_check_cfgdata (char *token, enum kwbimage_cmd cmdsw, struct kwb_header *kwbhdr) { bhr_t *mhdr = &kwbhdr->kwb_hdr; extbhr_t *exthdr = &kwbhdr->kwb_exthdr; int i; switch (cmdsw) { case CMD_BOOT_FROM: i = get_table_entry_id (kwbimage_bootops, "Kwbimage boot option", token); if (i < 0) goto INVL_DATA; mhdr->blockid = i; printf ("Preparing kirkwood boot image to boot " "from %s\n", token); break; case CMD_NAND_ECC_MODE: i = get_table_entry_id (kwbimage_eccmodes, "NAND ecc mode", token); if (i < 0) goto INVL_DATA; mhdr->nandeccmode = i; printf ("Nand ECC mode = %s\n", token); break; case CMD_NAND_PAGE_SIZE: mhdr->nandpagesize = (uint16_t) check_get_hexval (token); printf ("Nand page size = 0x%x\n", mhdr->nandpagesize); break; case CMD_SATA_PIO_MODE: mhdr->satapiomode = (uint8_t) check_get_hexval (token); printf ("Sata PIO mode = 0x%x\n", mhdr->satapiomode); break; case CMD_DDR_INIT_DELAY: mhdr->ddrinitdelay = (uint16_t) check_get_hexval (token); printf ("DDR init delay = %d msec\n", mhdr->ddrinitdelay); break; case CMD_DATA: exthdr->rcfg[datacmd_cnt].raddr = check_get_hexval (token); break; case CMD_INVALID: goto INVL_DATA; default: goto INVL_DATA; } return; INVL_DATA: printf ("Error:%s[%d] - Invalid data\n", fname, lineno); exit (EXIT_FAILURE); }
static void parse_cfg_cmd(struct imx_header *imxhdr, int32_t cmd, char *token, char *name, int lineno, int fld, int dcd_len) { int value; static int cmd_ver_first = ~0; switch (cmd) { case CMD_IMAGE_VERSION: imximage_version = get_cfg_value(token, name, lineno); if (cmd_ver_first == 0) { fprintf(stderr, "Error: %s[%d] - IMAGE_VERSION " "command need be the first before other " "valid command in the file\n", name, lineno); exit(EXIT_FAILURE); } cmd_ver_first = 1; set_hdr_func(); break; case CMD_BOOT_FROM: imximage_ivt_offset = get_table_entry_id(imximage_boot_offset, "imximage boot option", token); if (imximage_ivt_offset == -1) { fprintf(stderr, "Error: %s[%d] -Invalid boot device" "(%s)\n", name, lineno, token); exit(EXIT_FAILURE); } imximage_init_loadsize = get_table_entry_id(imximage_boot_loadsize, "imximage boot option", token); if (imximage_init_loadsize == -1) { fprintf(stderr, "Error: %s[%d] -Invalid boot device(%s)\n", name, lineno, token); exit(EXIT_FAILURE); } /* * The SOC loads from the storage starting at address 0 * then ensures that the load size contains the offset */ if (imximage_init_loadsize < imximage_ivt_offset) imximage_init_loadsize = imximage_ivt_offset; if (unlikely(cmd_ver_first != 1)) cmd_ver_first = 0; break; case CMD_BOOT_OFFSET: imximage_ivt_offset = get_cfg_value(token, name, lineno); if (unlikely(cmd_ver_first != 1)) cmd_ver_first = 0; break; case CMD_WRITE_DATA: case CMD_WRITE_CLR_BIT: case CMD_WRITE_SET_BIT: case CMD_CHECK_BITS_SET: case CMD_CHECK_BITS_CLR: value = get_cfg_value(token, name, lineno); if (set_dcd_param) (*set_dcd_param)(imxhdr, dcd_len, cmd); (*set_dcd_val)(imxhdr, name, lineno, fld, value, dcd_len); if (unlikely(cmd_ver_first != 1)) cmd_ver_first = 0; break; case CMD_CSF: if (imximage_version != 2) { fprintf(stderr, "Error: %s[%d] - CSF only supported for VERSION 2(%s)\n", name, lineno, token); exit(EXIT_FAILURE); } imximage_csf_size = get_cfg_value(token, name, lineno); if (unlikely(cmd_ver_first != 1)) cmd_ver_first = 0; break; case CMD_PLUGIN: plugin_image = 1; copy_plugin_code(imxhdr, token); break; } }
static void parse_cfg_cmd(image_t *param_stack, int32_t cmd, char *token, char *name, int lineno) { switch (cmd) { case CMD_BOOT_FROM: sector_size = get_table_entry_id(imx8image_sector_size, "imximage boot option", token); if (!strncmp("emmc_fastboot", token, 13)) emmc_fastboot = true; break; case CMD_FUSE_VERSION: fuse_version = (uint8_t)(strtoll(token, NULL, 0) & 0xFF); break; case CMD_SW_VERSION: sw_version = (uint8_t)(strtoll(token, NULL, 0) & 0xFFFF); break; case CMD_FILEOFF: param_stack[p_idx].option = FILEOFF; param_stack[p_idx++].dst = (uint32_t)strtoll(token, NULL, 0); break; case CMD_MSG_BLOCK: param_stack[p_idx].option = MSG_BLOCK; param_stack[p_idx].filename = token; break; case CMD_FLAG: param_stack[p_idx].option = FLAG; param_stack[p_idx++].entry = (uint32_t)strtoll(token, NULL, 0); break; case CMD_APPEND: param_stack[p_idx].option = APPEND; param_stack[p_idx++].filename = token; break; case CMD_PARTITION: param_stack[p_idx].option = PARTITION; param_stack[p_idx++].entry = (uint32_t)strtoll(token, NULL, 0); break; case CMD_SOC_TYPE: if (!strncmp(token, "IMX8QX", 6)) { soc = QX; } else if (!strncmp(token, "IMX8QM", 6)) { soc = QM; } else { fprintf(stderr, "Unknown CMD_SOC_TYPE"); exit(EXIT_FAILURE); } break; case CMD_IMAGE: case CMD_DATA: core_type = get_table_entry_id(imx8image_core_entries, "imx8image core entries", token); if (core_type < 0) { fprintf(stderr, "Wrong IMAGE core_type %s\n", token); exit(EXIT_FAILURE); } break; default: break; } }
static void parse_cfg_fld(image_t *param_stack, int32_t *cmd, char *token, char *name, int lineno, int fld) { switch (fld) { case CFG_COMMAND: *cmd = get_table_entry_id(imx8image_cmds, "imx8image cmds", token); if (*cmd < 0) { fprintf(stderr, "Error: %s[%d] - Invalid command (%s)\n", name, lineno, token); exit(EXIT_FAILURE); } if (*cmd == CMD_CONTAINER) { fprintf(stdout, "New Container: \t%d\n", ++container); param_stack[p_idx++].option = NEW_CONTAINER; } break; case CFG_CORE_TYPE: parse_cfg_cmd(param_stack, *cmd, token, name, lineno); break; case CFG_IMAGE_NAME: if (*cmd == CMD_MSG_BLOCK) { if (!strncmp(token, "fuse", 4)) { param_stack[p_idx].ext = SC_R_OTP; } else if (!strncmp(token, "debug", 5)) { param_stack[p_idx].ext = SC_R_DEBUG; } else if (!strncmp(token, "field", 5)) { param_stack[p_idx].ext = SC_R_ROM_0; } else { fprintf(stderr, "MSG type not found %s\n", token); exit(EXIT_FAILURE); } break; } switch (core_type) { case CFG_SCU: param_stack[p_idx].option = SCFW; param_stack[p_idx++].filename = token; break; case CFG_M40: param_stack[p_idx].option = M40; param_stack[p_idx].ext = 0; param_stack[p_idx].filename = token; break; case CFG_M41: param_stack[p_idx].option = M41; param_stack[p_idx].ext = 1; param_stack[p_idx].filename = token; break; case CFG_A35: param_stack[p_idx].ext = CORE_CA35; param_stack[p_idx].option = (*cmd == CMD_DATA) ? DATA : AP; param_stack[p_idx].filename = token; break; case CFG_A53: param_stack[p_idx].ext = CORE_CA53; param_stack[p_idx].option = (*cmd == CMD_DATA) ? DATA : AP; param_stack[p_idx].filename = token; break; case CFG_A72: param_stack[p_idx].ext = CORE_CA72; param_stack[p_idx].option = (*cmd == CMD_DATA) ? DATA : AP; param_stack[p_idx].filename = token; break; } break; case CFG_LOAD_ADDR: if (*cmd == CMD_MSG_BLOCK) { param_stack[p_idx++].entry = (uint32_t)strtoll(token, NULL, 0); break; } switch (core_type) { case CFG_SCU: break; case CFG_M40: case CFG_M41: case CFG_A35: case CFG_A53: case CFG_A72: param_stack[p_idx++].entry = (uint32_t)strtoll(token, NULL, 0); break; } default: break; } }