diff options
author | drath <drath@b42882b7-edfa-0310-969c-e2dbd0fdcd60> | 2007-04-16 14:58:16 +0000 |
---|---|---|
committer | drath <drath@b42882b7-edfa-0310-969c-e2dbd0fdcd60> | 2007-04-16 14:58:16 +0000 |
commit | 04dc98916d9acb57e0f5595534151a24ba4dc684 (patch) | |
tree | 3b351f19237f6d15916e392f0304506b48e74b4c /src/target/arm7_9_common.c | |
parent | c62e5b4c233d5ee0bc2066728a5b432f481ad7fe (diff) |
- explicitly disable monitor mode on ARM7/9 targets
- added "prepare_reset_halt()" to target_type_t, which allows reset_halt to be prepared before a reset is asserted, possibly preventing communication with the target
- arm7/9 devices now use a breakpoint at 0x0 or reset vector catching for debug out of reset
git-svn-id: svn://svn.berlios.de/openocd/trunk@141 b42882b7-edfa-0310-969c-e2dbd0fdcd60
Diffstat (limited to 'src/target/arm7_9_common.c')
-rw-r--r-- | src/target/arm7_9_common.c | 81 |
1 files changed, 64 insertions, 17 deletions
diff --git a/src/target/arm7_9_common.c b/src/target/arm7_9_common.c index 7a409b0f..3a7c80a1 100644 --- a/src/target/arm7_9_common.c +++ b/src/target/arm7_9_common.c @@ -725,9 +725,8 @@ int arm7_9_deassert_reset(target_t *target) /* deassert reset lines */ jtag_add_reset(0, 0); - + return ERROR_OK; - } int arm7_9_clear_halt(target_t *target) @@ -736,7 +735,8 @@ int arm7_9_clear_halt(target_t *target) arm7_9_common_t *arm7_9 = armv4_5->arch_info; reg_t *dbg_ctrl = &arm7_9->eice_cache->reg_list[EICE_DBG_CTRL]; - if (arm7_9->use_dbgrq) + /* we used DBGRQ only if we didn't come out of reset */ + if (!arm7_9->debug_entry_from_reset && arm7_9->use_dbgrq) { /* program EmbeddedICE Debug Control Register to deassert DBGRQ */ @@ -745,18 +745,29 @@ int arm7_9_clear_halt(target_t *target) } else { - /* restore registers if watchpoint unit 0 was in use - */ - if (arm7_9->wp0_used) + if (arm7_9->debug_entry_from_reset && arm7_9->has_vector_catch) { - embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_ADDR_MASK]); - embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_DATA_MASK]); - embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_MASK]); + /* if we came out of reset, and vector catch is supported, we used + * vector catch to enter debug state + * restore the register in that case + */ + embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_VEC_CATCH]); + } + else + { + /* restore registers if watchpoint unit 0 was in use + */ + if (arm7_9->wp0_used) + { + embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_ADDR_MASK]); + embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_DATA_MASK]); + embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_MASK]); + } + /* control value always has to be restored, as it was either disabled, + * or enabled with possibly different bits + */ + embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_VALUE]); } - /* control value always has to be restored, as it was either disabled, - * or enabled with possibly different bits - */ - embeddedice_store_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_VALUE]); } return ERROR_OK; @@ -831,6 +842,28 @@ int arm7_9_soft_reset_halt(struct target_s *target) return ERROR_OK; } +int arm7_9_prepare_reset_halt(target_t *target) +{ + armv4_5_common_t *armv4_5 = target->arch_info; + arm7_9_common_t *arm7_9 = armv4_5->arch_info; + + if (arm7_9->has_vector_catch) + { + /* program vector catch register to catch reset vector */ + embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_VEC_CATCH], 0x1); + } + else + { + /* program watchpoint unit to match on reset vector address */ + embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_ADDR_MASK], 0x3); + embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_DATA_MASK], 0x0); + embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_VALUE], 0x100); + embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_MASK], 0xf7); + } + + return ERROR_OK; +} + int arm7_9_halt(target_t *target) { armv4_5_common_t *armv4_5 = target->arch_info; @@ -843,17 +876,29 @@ int arm7_9_halt(target_t *target) { WARNING("target was already halted"); return ERROR_TARGET_ALREADY_HALTED; - } + } if (target->state == TARGET_UNKNOWN) { WARNING("target was in unknown state when halt was requested"); } - if ((target->state == TARGET_RESET) && (jtag_reset_config & RESET_SRST_PULLS_TRST) && (jtag_srst)) + if (target->state == TARGET_RESET) { - ERROR("can't request a halt while in reset if nSRST pulls nTRST"); - return ERROR_TARGET_FAILURE; + if ((jtag_reset_config & RESET_SRST_PULLS_TRST) && jtag_srst) + { + ERROR("can't request a halt while in reset if nSRST pulls nTRST"); + return ERROR_TARGET_FAILURE; + } + else + { + /* we came here in a reset_halt or reset_init sequence + * debug entry was already prepared in arm7_9_prepare_reset_halt() + */ + target->debug_reason = DBG_REASON_DBGRQ; + + return ERROR_OK; + } } if (arm7_9->use_dbgrq) @@ -2477,6 +2522,8 @@ int arm7_9_init_arch_info(target_t *target, arm7_9_common_t *arm7_9) arm7_9->reinit_embeddedice = 0; + arm7_9->debug_entry_from_reset = 0; + arm7_9->dcc_working_area = NULL; arm7_9->fast_memory_access = 0; |