X-Git-Url: https://review.openocd.org/gitweb?a=blobdiff_plain;f=src%2Fjtag%2Ftcl.c;h=153a98e1b64ebc53bf9fc02051cf08d9c7d4d740;hb=24db985f602bbe21ee4d10147937ed897f28a555;hp=5c5198e6b2d4d77aedce41b77fea6181a02cecd2;hpb=08d4411b59dd8bd0e7d8009003b71d23acbf6eee;p=openocd.git diff --git a/src/jtag/tcl.c b/src/jtag/tcl.c index 5c5198e6b2..153a98e1b6 100644 --- a/src/jtag/tcl.c +++ b/src/jtag/tcl.c @@ -23,9 +23,7 @@ * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * - * along with this program; if not, write to the * - * Free Software Foundation, Inc., * - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * + * along with this program. If not, see . * ***************************************************************************/ #ifdef HAVE_CONFIG_H @@ -44,6 +42,7 @@ #endif #include +#include "transport/transport.h" /** * @file @@ -59,8 +58,6 @@ static const Jim_Nvp nvp_jtag_tap_event[] = { { .name = NULL, .value = -1 } }; -extern struct jtag_interface *jtag_interface; - struct jtag_tap *jtag_tap_by_jim_obj(Jim_Interp *interp, Jim_Obj *o) { const char *cp = Jim_GetString(o, NULL); @@ -111,7 +108,7 @@ static int Jim_Command_drscan(Jim_Interp *interp, int argc, Jim_Obj *const *args endstate = TAP_IDLE; - script_debug(interp, "drscan", argc, args); + script_debug(interp, argc, args); /* validate arguments as numbers */ e = JIM_OK; @@ -171,7 +168,10 @@ static int Jim_Command_drscan(Jim_Interp *interp, int argc, Jim_Obj *const *args return JIM_ERR; num_fields = (argc-2)/2; - assert(num_fields > 0); + if (num_fields <= 0) { + Jim_SetResultString(interp, "drscan: no scan fields supplied", -1); + return JIM_ERR; + } fields = malloc(sizeof(struct scan_field) * num_fields); for (i = 2; i < argc; i += 2) { long bits; @@ -204,8 +204,8 @@ static int Jim_Command_drscan(Jim_Interp *interp, int argc, Jim_Obj *const *args char *str; Jim_GetLong(interp, args[i], &bits); - str = buf_to_str(fields[field_count].in_value, bits, 16); - free((void *)fields[field_count].out_value); + str = buf_to_hex_str(fields[field_count].in_value, bits); + free(fields[field_count].in_value); Jim_ListAppendElement(interp, list, Jim_NewStringObj(interp, str, strlen(str))); free(str); @@ -229,7 +229,7 @@ static int Jim_Command_pathmove(Jim_Interp *interp, int argc, Jim_Obj *const *ar return JIM_ERR; } - script_debug(interp, "pathmove", argc, args); + script_debug(interp, argc, args); int i; for (i = 0; i < argc-1; i++) { @@ -261,7 +261,7 @@ static int Jim_Command_pathmove(Jim_Interp *interp, int argc, Jim_Obj *const *ar static int Jim_Command_flush_count(Jim_Interp *interp, int argc, Jim_Obj *const *args) { - script_debug(interp, "flush_count", argc, args); + script_debug(interp, argc, args); Jim_SetResult(interp, Jim_NewIntObj(interp, jtag_get_flush_queue_count())); @@ -307,11 +307,13 @@ static const struct command_registration jtag_command_handlers_to_move[] = { enum jtag_tap_cfg_param { - JCFG_EVENT + JCFG_EVENT, + JCFG_IDCODE, }; static Jim_Nvp nvp_config_opts[] = { { .name = "-event", .value = JCFG_EVENT }, + { .name = "-idcode", .value = JCFG_IDCODE }, { .name = NULL, .value = -1 } }; @@ -404,8 +406,23 @@ static int jtag_tap_configure_cmd(Jim_GetOptInfo *goi, struct jtag_tap *tap) if (e != JIM_OK) return e; break; + case JCFG_IDCODE: + if (goi->isconfigure) { + Jim_SetResultFormatted(goi->interp, + "not settable: %s", n->name); + return JIM_ERR; + } else { + if (goi->argc != 0) { + Jim_WrongNumArgs(goi->interp, + goi->argc, goi->argv, + "NO PARAMS"); + return JIM_ERR; + } + } + Jim_SetResult(goi->interp, Jim_NewIntObj(goi->interp, tap->idcode)); + break; default: - Jim_SetResultFormatted(goi->interp, "unknown event: %s", n->name); + Jim_SetResultFormatted(goi->interp, "unknown value: %s", n->name); return JIM_ERR; } } @@ -433,20 +450,15 @@ static int jim_newtap_expected_id(Jim_Nvp *n, Jim_GetOptInfo *goi, return e; } - unsigned expected_len = sizeof(uint32_t) * pTap->expected_ids_cnt; - uint32_t *new_expected_ids = malloc(expected_len + sizeof(uint32_t)); - if (new_expected_ids == NULL) { + uint32_t *p = realloc(pTap->expected_ids, + (pTap->expected_ids_cnt + 1) * sizeof(uint32_t)); + if (!p) { Jim_SetResultFormatted(goi->interp, "no memory"); return JIM_ERR; } - memcpy(new_expected_ids, pTap->expected_ids, expected_len); - - new_expected_ids[pTap->expected_ids_cnt] = w; - - free(pTap->expected_ids); - pTap->expected_ids = new_expected_ids; - pTap->expected_ids_cnt++; + pTap->expected_ids = p; + pTap->expected_ids[pTap->expected_ids_cnt++] = w; return JIM_OK; } @@ -467,7 +479,6 @@ static int jim_newtap_ir_param(Jim_Nvp *n, Jim_GetOptInfo *goi, if (e != JIM_OK) { Jim_SetResultFormatted(goi->interp, "option: %s bad parameter", n->name); - free((void *)pTap->dotted_name); return e; } switch (n->value) { @@ -538,11 +549,13 @@ static int jim_newtap_cmd(Jim_GetOptInfo *goi) free(pTap); return JIM_ERR; } - Jim_GetOpt_String(goi, &cp, NULL); - pTap->chip = strdup(cp); - Jim_GetOpt_String(goi, &cp, NULL); - pTap->tapname = strdup(cp); + const char *tmp; + Jim_GetOpt_String(goi, &tmp, NULL); + pTap->chip = strdup(tmp); + + Jim_GetOpt_String(goi, &tmp, NULL); + pTap->tapname = strdup(tmp); /* name + dot + name + null */ x = strlen(pTap->chip) + 1 + strlen(pTap->tapname) + 1; @@ -553,8 +566,15 @@ static int jim_newtap_cmd(Jim_GetOptInfo *goi) LOG_DEBUG("Creating New Tap, Chip: %s, Tap: %s, Dotted: %s, %d params", pTap->chip, pTap->tapname, pTap->dotted_name, goi->argc); + if (!transport_is_jtag()) { + /* SWD doesn't require any JTAG tap parameters */ + pTap->enabled = true; + jtag_tap_init(pTap); + return JIM_OK; + } + /* IEEE specifies that the two LSBs of an IR scan are 01, so make - * that the default. The "-irlen" and "-irmask" options are only + * that the default. The "-ircapture" and "-irmask" options are only * needed to cope with nonstandard TAPs, or to specify more bits. */ pTap->ir_capture_mask = 0x03; @@ -564,7 +584,7 @@ static int jim_newtap_cmd(Jim_GetOptInfo *goi) e = Jim_GetOpt_Nvp(goi, opts, &n); if (e != JIM_OK) { Jim_GetOpt_NvpUnknown(goi, opts, 0); - free((void *)pTap->dotted_name); + free(cp); free(pTap); return e; } @@ -579,7 +599,7 @@ static int jim_newtap_cmd(Jim_GetOptInfo *goi) case NTAP_OPT_EXPECTED_ID: e = jim_newtap_expected_id(n, goi, pTap); if (JIM_OK != e) { - free((void *)pTap->dotted_name); + free(cp); free(pTap); return e; } @@ -589,7 +609,7 @@ static int jim_newtap_cmd(Jim_GetOptInfo *goi) case NTAP_OPT_IRCAPTURE: e = jim_newtap_ir_param(n, goi, pTap); if (JIM_OK != e) { - free((void *)pTap->dotted_name); + free(cp); free(pTap); return e; } @@ -619,6 +639,7 @@ static int jim_newtap_cmd(Jim_GetOptInfo *goi) static void jtag_tap_handle_event(struct jtag_tap *tap, enum jtag_event e) { struct jtag_tap_event_action *jteap; + int retval; for (jteap = tap->event_action; jteap != NULL; jteap = jteap->next) { if (jteap->event != e) @@ -629,7 +650,11 @@ static void jtag_tap_handle_event(struct jtag_tap *tap, enum jtag_event e) tap->dotted_name, e, nvp->name, Jim_GetString(jteap->body, NULL)); - if (Jim_EvalObj(jteap->interp, jteap->body) != JIM_OK) { + retval = Jim_EvalObj(jteap->interp, jteap->body); + if (retval == JIM_RETURN) + retval = jteap->interp->returnCode; + + if (retval != JIM_OK) { Jim_MakeErrorMessage(jteap->interp); LOG_USER("%s", Jim_GetString(Jim_GetResult(jteap->interp), NULL)); continue; @@ -664,8 +689,9 @@ static int jim_jtag_arp_init(Jim_Interp *interp, int argc, Jim_Obj *const *argv) int e = jtag_init_inner(context); if (e != ERROR_OK) { Jim_Obj *eObj = Jim_NewIntObj(goi.interp, e); + Jim_IncrRefCount(eObj); Jim_SetResultFormatted(goi.interp, "error: %#s", eObj); - Jim_FreeNewObj(goi.interp, eObj); + Jim_DecrRefCount(goi.interp, eObj); return JIM_ERR; } return JIM_OK; @@ -688,8 +714,9 @@ static int jim_jtag_arp_init_reset(Jim_Interp *interp, int argc, Jim_Obj *const if (e != ERROR_OK) { Jim_Obj *eObj = Jim_NewIntObj(goi.interp, e); + Jim_IncrRefCount(eObj); Jim_SetResultFormatted(goi.interp, "error: %#s", eObj); - Jim_FreeNewObj(goi.interp, eObj); + Jim_DecrRefCount(goi.interp, eObj); return JIM_ERR; } return JIM_OK; @@ -891,7 +918,7 @@ static const struct command_registration jtag_subcommand_handlers[] = { }, { .name = "configure", - .mode = COMMAND_EXEC, + .mode = COMMAND_ANY, .jim_handler = jim_jtag_configure, .help = "Provide a Tcl handler for the specified " "TAP event.", @@ -932,15 +959,15 @@ COMMAND_HANDLER(handle_scan_chain_command) char expected_id[12]; tap = jtag_all_taps(); - command_print(CMD_CTX, + command_print(CMD, " TapName Enabled IdCode Expected IrLen IrCap IrMask"); - command_print(CMD_CTX, + command_print(CMD, "-- ------------------- -------- ---------- ---------- ----- ----- ------"); while (tap) { uint32_t expected, expected_mask, ii; - snprintf(expected_id, sizeof expected_id, "0x%08x", + snprintf(expected_id, sizeof(expected_id), "0x%08x", (unsigned)((tap->expected_ids_cnt > 0) ? tap->expected_ids[0] : 0)); @@ -950,7 +977,7 @@ COMMAND_HANDLER(handle_scan_chain_command) expected = buf_get_u32(tap->expected, 0, tap->ir_length); expected_mask = buf_get_u32(tap->expected_mask, 0, tap->ir_length); - command_print(CMD_CTX, + command_print(CMD, "%2d %-18s %c 0x%08x %s %5d 0x%02x 0x%02x", tap->abs_chain_position, tap->dotted_name, @@ -962,12 +989,12 @@ COMMAND_HANDLER(handle_scan_chain_command) (unsigned int)(expected_mask)); for (ii = 1; ii < tap->expected_ids_cnt; ii++) { - snprintf(expected_id, sizeof expected_id, "0x%08x", + snprintf(expected_id, sizeof(expected_id), "0x%08x", (unsigned) tap->expected_ids[ii]); if (tap->ignore_version) expected_id[2] = '*'; - command_print(CMD_CTX, + command_print(CMD, " %s", expected_id); } @@ -988,7 +1015,7 @@ COMMAND_HANDLER(handle_jtag_ntrst_delay_command) jtag_set_ntrst_delay(delay); } - command_print(CMD_CTX, "jtag_ntrst_delay: %u", jtag_get_ntrst_delay()); + command_print(CMD, "jtag_ntrst_delay: %u", jtag_get_ntrst_delay()); return ERROR_OK; } @@ -1002,7 +1029,7 @@ COMMAND_HANDLER(handle_jtag_ntrst_assert_width_command) jtag_set_ntrst_assert_width(delay); } - command_print(CMD_CTX, "jtag_ntrst_assert_width: %u", jtag_get_ntrst_assert_width()); + command_print(CMD, "jtag_ntrst_assert_width: %u", jtag_get_ntrst_assert_width()); return ERROR_OK; } @@ -1027,41 +1054,13 @@ COMMAND_HANDLER(handle_jtag_rclk_command) return retval; if (cur_khz) - command_print(CMD_CTX, "RCLK not supported - fallback to %d kHz", cur_khz); + command_print(CMD, "RCLK not supported - fallback to %d kHz", cur_khz); else - command_print(CMD_CTX, "RCLK - adaptive"); + command_print(CMD, "RCLK - adaptive"); return retval; } -COMMAND_HANDLER(handle_jtag_reset_command) -{ - if (CMD_ARGC != 2) - return ERROR_COMMAND_SYNTAX_ERROR; - - int trst = -1; - if (CMD_ARGV[0][0] == '1') - trst = 1; - else if (CMD_ARGV[0][0] == '0') - trst = 0; - else - return ERROR_COMMAND_SYNTAX_ERROR; - - int srst = -1; - if (CMD_ARGV[1][0] == '1') - srst = 1; - else if (CMD_ARGV[1][0] == '0') - srst = 0; - else - return ERROR_COMMAND_SYNTAX_ERROR; - - if (adapter_init(CMD_CTX) != ERROR_OK) - return ERROR_JTAG_INIT_FAILED; - - jtag_add_reset(trst, srst); - return jtag_execute_queue(); -} - COMMAND_HANDLER(handle_runtest_command) { if (CMD_ARGC != 1) @@ -1121,32 +1120,32 @@ COMMAND_HANDLER(handle_irscan_command) return ERROR_COMMAND_SYNTAX_ERROR; } - size_t fields_len = sizeof(struct scan_field) * num_fields; - fields = malloc(fields_len); - memset(fields, 0, fields_len); + fields = calloc(num_fields, sizeof(*fields)); int retval; for (i = 0; i < num_fields; i++) { tap = jtag_tap_by_string(CMD_ARGV[i*2]); if (tap == NULL) { - int j; - for (j = 0; j < i; j++) - free((void *)fields[j].out_value); free(fields); - command_print(CMD_CTX, "Tap: %s unknown", CMD_ARGV[i*2]); + command_print(CMD, "Tap: %s unknown", CMD_ARGV[i*2]); return ERROR_FAIL; } + uint64_t value; + retval = parse_u64(CMD_ARGV[i * 2 + 1], &value); + if (ERROR_OK != retval) + goto error_return; + int field_size = tap->ir_length; fields[i].num_bits = field_size; - fields[i].out_value = malloc(DIV_ROUND_UP(field_size, 8)); - - uint32_t value; - retval = parse_u32(CMD_ARGV[i * 2 + 1], &value); - if (ERROR_OK != retval) + uint8_t *v = calloc(1, DIV_ROUND_UP(field_size, 8)); + if (!v) { + LOG_ERROR("Out of memory"); goto error_return; - void *v = (void *)fields[i].out_value; - buf_set_u32(v, 0, field_size, value); + } + + buf_set_u64(v, 0, field_size, value); + fields[i].out_value = v; fields[i].in_value = NULL; } @@ -1156,10 +1155,8 @@ COMMAND_HANDLER(handle_irscan_command) retval = jtag_execute_queue(); error_return: - for (i = 0; i < num_fields; i++) { - if (NULL != fields[i].out_value) - free((void *)fields[i].out_value); - } + for (i = 0; i < num_fields; i++) + free((void *)fields[i].out_value); free(fields); @@ -1178,7 +1175,7 @@ COMMAND_HANDLER(handle_verify_ircapture_command) } const char *status = jtag_will_verify_capture_ir() ? "enabled" : "disabled"; - command_print(CMD_CTX, "verify Capture-IR is %s", status); + command_print(CMD, "verify Capture-IR is %s", status); return ERROR_OK; } @@ -1195,7 +1192,7 @@ COMMAND_HANDLER(handle_verify_jtag_command) } const char *status = jtag_will_verify() ? "enabled" : "disabled"; - command_print(CMD_CTX, "verify jtag capture is %s", status); + command_print(CMD, "verify jtag capture is %s", status); return ERROR_OK; } @@ -1217,7 +1214,7 @@ COMMAND_HANDLER(handle_tms_sequence_command) tap_use_new_tms_table(use_new_table); } - command_print(CMD_CTX, "tms sequence is %s", + command_print(CMD, "tms sequence is %s", tap_uses_new_tms_table() ? "short" : "long"); return ERROR_OK; @@ -1250,7 +1247,7 @@ COMMAND_HANDLER(handle_wait_srst_deassert) LOG_USER("Waiting for srst assert + deassert for at most %dms", timeout_ms); int asserted_yet; - long long then = timeval_ms(); + int64_t then = timeval_ms(); while (jtag_srst_asserted(&asserted_yet) == ERROR_OK) { if ((timeval_ms() - then) > timeout_ms) { LOG_ERROR("Timed out"); @@ -1311,14 +1308,6 @@ static const struct command_registration jtag_command_handlers[] = { .help = "print current scan chain configuration", .usage = "" }, - { - .name = "jtag_reset", - .handler = handle_jtag_reset_command, - .mode = COMMAND_EXEC, - .help = "Set reset line values. Value '1' is active, " - "value '0' is inactive.", - .usage = "trst_active srst_active", - }, { .name = "runtest", .handler = handle_runtest_command, @@ -1330,7 +1319,7 @@ static const struct command_registration jtag_command_handlers[] = { .name = "irscan", .handler = handle_irscan_command, .mode = COMMAND_EXEC, - .help = "Execute Instruction Register (DR) scan. The " + .help = "Execute Instruction Register (IR) scan. The " "specified opcodes are put into each TAP's IR, " "and other TAPs are put in BYPASS.", .usage = "[tap_name instruction]* ['-endstate' state_name]",