This is an automated email from Gerrit.

Evgeniy Didin (di...@synopsys.com) just uploaded a new patch set to Gerrit, 
which you can find at http://openocd.zylin.com/5643

-- gerrit

commit 34dc544245e722ebd5d2fa948412004f4e2a5a52
Author: Evgeniy Didin <di...@synopsys.com>
Date:   Wed Mar 18 16:12:04 2020 +0300

    target/arc: Add initial stepping functions
    
    Change-Id: I84845f2ec6f1cff975990f0a495165a02de33227
    Signed-off-by: Evgeniy Didin <di...@synopsys.com>

diff --git a/src/target/arc.c b/src/target/arc.c
index 8991f37..844e6e0 100644
--- a/src/target/arc.c
+++ b/src/target/arc.c
@@ -1494,6 +1494,107 @@ static int arc_remove_breakpoint(struct target *target,
        return ERROR_OK;
 }
 
+/* Helper function which swiches core to single_step mode by
+ * doing aux r/w operations.  */
+int arc_config_step(struct target *target, int enable_step)
+{
+       uint32_t value;
+
+       struct arc_common *arc = target_to_arc(target);
+
+       /* enable core debug step mode */
+       if (enable_step) {
+               CHECK_RETVAL(arc_jtag_read_aux_reg_one(&arc->jtag_info, 
AUX_STATUS32_REG,
+                       &value));
+               value &= ~SET_CORE_AE_BIT; /* clear the AE bit */
+               CHECK_RETVAL(arc_jtag_write_aux_reg_one(&arc->jtag_info, 
AUX_STATUS32_REG,
+                       value));
+               LOG_DEBUG(" [status32:0x%08" PRIx32 "]", value);
+
+               /* Doing read-modify-write, because DEBUG might contain 
manually set
+                * bits like UB or ED, which should be preserved.  */
+               CHECK_RETVAL(arc_jtag_read_aux_reg_one(&arc->jtag_info,
+                                       AUX_DEBUG_REG, &value));
+               value |= SET_CORE_SINGLE_INSTR_STEP; /* set the IS bit */
+               CHECK_RETVAL(arc_jtag_write_aux_reg_one(&arc->jtag_info, 
AUX_DEBUG_REG,
+                       value));
+               LOG_DEBUG("core debug step mode enabled [debug-reg:0x%08" 
PRIx32 "]", value);
+
+       } else {        /* disable core debug step mode */
+               CHECK_RETVAL(arc_jtag_read_aux_reg_one(&arc->jtag_info, 
AUX_DEBUG_REG,
+                       &value));
+               value &= ~SET_CORE_SINGLE_INSTR_STEP; /* clear the IS bit */
+               CHECK_RETVAL(arc_jtag_write_aux_reg_one(&arc->jtag_info, 
AUX_DEBUG_REG,
+                       value));
+               LOG_DEBUG("core debug step mode disabled");
+       }
+
+       return ERROR_OK;
+}
+
+int arc_step(struct target *target, int current, target_addr_t address,
+       int handle_breakpoints)
+{
+       /* get pointers to arch-specific information */
+       struct arc_common *arc = target_to_arc(target);
+       struct breakpoint *breakpoint = NULL;
+       struct reg *pc = 
&(arc->core_and_aux_cache->reg_list[arc->pc_index_in_cache]);
+
+       if (target->state != TARGET_HALTED) {
+               LOG_WARNING("target not halted");
+               return ERROR_TARGET_NOT_HALTED;
+       }
+
+       /* current = 1: continue on current pc, otherwise continue at <address> 
*/
+       if (!current) {
+               buf_set_u32(pc->value, 0, 32, address);
+               pc->dirty = 1;
+               pc->valid = 1;
+       }
+
+       LOG_DEBUG("Target steps one instruction from PC=0x%" PRIx32,
+               buf_get_u32(pc->value, 0, 32));
+
+       /* the front-end may request us not to handle breakpoints */
+       if (handle_breakpoints) {
+               breakpoint = breakpoint_find(target, buf_get_u32(pc->value, 0, 
32));
+               if (breakpoint)
+                       CHECK_RETVAL(arc_unset_breakpoint(target, breakpoint));
+       }
+
+       /* restore context */
+       CHECK_RETVAL(arc_restore_context(target));
+
+       target->debug_reason = DBG_REASON_SINGLESTEP;
+
+       CHECK_RETVAL(target_call_event_callbacks(target, TARGET_EVENT_RESUMED));
+
+       /* disable interrupts while stepping */
+       CHECK_RETVAL(arc_enable_interrupts(target, 0));
+
+       /* do a single step */
+       CHECK_RETVAL(arc_config_step(target, 1));
+
+       /* make sure we done our step */
+       alive_sleep(1);
+
+       /* registers are now invalid */
+       register_cache_invalidate(arc->core_and_aux_cache);
+
+       if (breakpoint)
+               CHECK_RETVAL(arc_set_breakpoint(target, breakpoint));
+
+       LOG_DEBUG("target stepped ");
+
+       target->state = TARGET_HALTED;
+
+       /* Saving context */
+       CHECK_RETVAL(arc_debug_entry(target));
+       CHECK_RETVAL(target_call_event_callbacks(target, TARGET_EVENT_HALTED));
+
+       return ERROR_OK;
+}
+
 /* ARC v2 target */
 struct target_type arcv2_target = {
        .name = "arcv2",
@@ -1508,7 +1609,7 @@ struct target_type arcv2_target = {
 
        .halt = arc_halt,
        .resume = arc_resume,
-       .step = NULL,
+       .step = arc_step,
 
        .assert_reset = arc_assert_reset,
        .deassert_reset = arc_deassert_reset,
diff --git a/src/target/arc.h b/src/target/arc.h
index 0ce6d9c..defa3fa 100644
--- a/src/target/arc.h
+++ b/src/target/arc.h
@@ -33,9 +33,14 @@
 #define AUX_PC_REG                      0x6
 #define AUX_STATUS32_REG                0xA
 
+
 #define SET_CORE_FORCE_HALT             BIT(1)
 #define SET_CORE_HALT_BIT               BIT(0)      /* STATUS32[0] = H field */
-#define SET_CORE_ENABLE_INTERRUPTS                     BIT(31)
+#define SET_CORE_ENABLE_INTERRUPTS      BIT(31)
+/* STATUS32[5] or AE bit indicates if the processor is in exception state */
+#define SET_CORE_AE_BIT                 BIT(5)
+/* Single instruction step bit in Debug register */
+#define SET_CORE_SINGLE_INSTR_STEP      BIT(11)
 
 #define AUX_STATUS32_REG_HALT_BIT       BIT(0)
 #define AUX_STATUS32_REG_IE_BIT         BIT(31)    /* STATUS32[31] = IE field 
*/

-- 


_______________________________________________
OpenOCD-devel mailing list
OpenOCD-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/openocd-devel

Reply via email to