X-Git-Url: https://review.openocd.org/gitweb?p=openocd.git;a=blobdiff_plain;f=src%2Ftarget%2Farmv7m.c;h=9fe705af7c92c600e5a1a7deda61fe912cd14466;hp=d0f58deecc4dccd879452e6c2b09e1fb65b19afe;hb=ff5deeeeaa4f394931e3c5ccfb4cfd33beda0743;hpb=b3bf1d12b2fdfba1c1cbee3e1afbfbb27cbd1a26 diff --git a/src/target/armv7m.c b/src/target/armv7m.c index d0f58deecc..9fe705af7c 100644 --- a/src/target/armv7m.c +++ b/src/target/armv7m.c @@ -538,7 +538,7 @@ struct reg_cache *armv7m_build_reg_cache(struct target *target) /** Sets up target as a generic ARMv7-M core */ int armv7m_init_arch_info(struct target *target, struct armv7m_common *armv7m) { - /* register arch-specific functions */ + armv7m->common_magic = ARMV7M_COMMON_MAGIC; target->arch_info = armv7m; armv7m->read_core_reg = armv7m_read_core_reg; @@ -694,13 +694,49 @@ int armv7m_blank_check_memory(struct target *target, return ERROR_OK; } +int armv7m_maybe_skip_bkpt_inst(struct target *target, bool *inst_found) +{ + struct armv7m_common *armv7m = target_to_armv7m(target); + struct reg *r = armv7m->core_cache->reg_list + 15; + bool result = false; + + + /* if we halted last time due to a bkpt instruction + * then we have to manually step over it, otherwise + * the core will break again */ + + if (target->debug_reason == DBG_REASON_BREAKPOINT) + { + uint16_t op; + uint32_t pc = buf_get_u32(r->value, 0, 32); + + pc &= ~1; + if (target_read_u16(target, pc, &op) == ERROR_OK) + { + if ((op & 0xFF00) == 0xBE00) + { + pc = buf_get_u32(r->value, 0, 32) + 2; + buf_set_u32(r->value, 0, 32, pc); + r->dirty = true; + r->valid = true; + result = true; + LOG_DEBUG("Skipping over BKPT instruction"); + } + } + } + + if (inst_found) { + *inst_found = result; + } + + return ERROR_OK; +} + /*--------------------------------------------------------------------------*/ /* * Only stuff below this line should need to verify that its target * is an ARMv7-M node. - * - * FIXME yet none of it _does_ verify target types yet! */ @@ -713,32 +749,13 @@ COMMAND_HANDLER(handle_dap_baseaddr_command) struct target *target = get_current_target(CMD_CTX); struct armv7m_common *armv7m = target_to_armv7m(target); struct swjdp_common *swjdp = &armv7m->swjdp_info; - uint32_t apsel, apselsave, baseaddr; - int retval; - apselsave = swjdp->apsel; - switch (CMD_ARGC) { - case 0: - apsel = swjdp->apsel; - break; - case 1: - COMMAND_PARSE_NUMBER(u32, CMD_ARGV[0], apsel); - break; - default: - return ERROR_COMMAND_SYNTAX_ERROR; + if (!is_armv7m(armv7m)) { + command_print(CMD_CTX, "current target isn't an ARM7-M"); + return ERROR_TARGET_INVALID; } - if (apselsave != apsel) - dap_ap_select(swjdp, apsel); - - dap_ap_read_reg_u32(swjdp, 0xF8, &baseaddr); - retval = swjdp_transaction_endcheck(swjdp); - command_print(CMD_CTX, "0x%8.8" PRIx32 "", baseaddr); - - if (apselsave != apsel) - dap_ap_select(swjdp, apselsave); - - return retval; + return CALL_COMMAND_HANDLER(dap_baseaddr_command, swjdp); } /* @@ -751,6 +768,11 @@ COMMAND_HANDLER(handle_dap_apid_command) struct armv7m_common *armv7m = target_to_armv7m(target); struct swjdp_common *swjdp = &armv7m->swjdp_info; + if (!is_armv7m(armv7m)) { + command_print(CMD_CTX, "current target isn't an ARM7-M"); + return ERROR_TARGET_INVALID; + } + return CALL_COMMAND_HANDLER(dap_apid_command, swjdp); } @@ -760,6 +782,11 @@ COMMAND_HANDLER(handle_dap_apsel_command) struct armv7m_common *armv7m = target_to_armv7m(target); struct swjdp_common *swjdp = &armv7m->swjdp_info; + if (!is_armv7m(armv7m)) { + command_print(CMD_CTX, "current target isn't an ARM7-M"); + return ERROR_TARGET_INVALID; + } + return CALL_COMMAND_HANDLER(dap_apsel_command, swjdp); } @@ -769,6 +796,11 @@ COMMAND_HANDLER(handle_dap_memaccess_command) struct armv7m_common *armv7m = target_to_armv7m(target); struct swjdp_common *swjdp = &armv7m->swjdp_info; + if (!is_armv7m(armv7m)) { + command_print(CMD_CTX, "current target isn't an ARM7-M"); + return ERROR_TARGET_INVALID; + } + return CALL_COMMAND_HANDLER(dap_memaccess_command, swjdp); } @@ -780,6 +812,11 @@ COMMAND_HANDLER(handle_dap_info_command) struct swjdp_common *swjdp = &armv7m->swjdp_info; uint32_t apsel; + if (!is_armv7m(armv7m)) { + command_print(CMD_CTX, "current target isn't an ARM7-M"); + return ERROR_TARGET_INVALID; + } + switch (CMD_ARGC) { case 0: apsel = swjdp->apsel; @@ -794,40 +831,49 @@ COMMAND_HANDLER(handle_dap_info_command) return dap_info_command(CMD_CTX, swjdp, apsel); } +/* FIXME this table should be part of generic DAP support, and + * be shared by the ARMv7-A/R and ARMv7-M support ... + */ static const struct command_registration armv7m_exec_command_handlers[] = { { .name = "info", - .handler = &handle_dap_info_command, + .handler = handle_dap_info_command, .mode = COMMAND_EXEC, - .help = "dap info for ap [num], " - "default currently selected AP", + .help = "display ROM table for MEM-AP " + "(default currently selected AP)", + .usage = "[ap_num]", }, { .name = "apsel", - .handler = &handle_dap_apsel_command, + .handler = handle_dap_apsel_command, .mode = COMMAND_EXEC, - .help = "select a different AP [num] (default 0)", + .help = "Set the currently selected AP (default 0) " + "and display the result", + .usage = "[ap_num]", }, { .name = "apid", - .handler = &handle_dap_apid_command, + .handler = handle_dap_apid_command, .mode = COMMAND_EXEC, - .help = "return id reg from AP [num], " - "default currently selected AP", + .help = "return ID register from AP " + "(default currently selected AP)", + .usage = "[ap_num]", }, { .name = "baseaddr", - .handler = &handle_dap_baseaddr_command, + .handler = handle_dap_baseaddr_command, .mode = COMMAND_EXEC, - .help = "return debug base address from AP [num], " - "default currently selected AP", + .help = "return debug base address from MEM-AP " + "(default currently selected AP)", + .usage = "[ap_num]", }, { .name = "memaccess", - .handler = &handle_dap_memaccess_command, + .handler = handle_dap_memaccess_command, .mode = COMMAND_EXEC, - .help = "set/get number of extra tck for mem-ap memory " + .help = "set/get number of extra tck for MEM-AP memory " "bus access [0-255]", + .usage = "[cycles]", }, COMMAND_REGISTRATION_DONE };