Cortex A/R : Allow interrupt disable during single-step 76/2876/4
authorEvan Hunter <ehunter@broadcom.com>
Fri, 17 Jul 2015 11:41:12 +0000 (12:41 +0100)
committerFreddie Chopin <freddie.chopin@gmail.com>
Sat, 7 Nov 2015 20:36:13 +0000 (20:36 +0000)
Example usage:
cortex_a maskisr on
cortex_a maskisr off
cortex_r maskisr on
cortex_r maskisr off

Change-Id: I799288d9b848a06f561ba29ec1eb8e5eeace5685
Signed-off-by: Evan Hunter <ehunter@broadcom.com>
Reviewed-on: http://openocd.zylin.com/2876
Tested-by: jenkins
Reviewed-by: Matthias Welwarsky <matthias@welwarsky.de>
Reviewed-by: Freddie Chopin <freddie.chopin@gmail.com>
doc/openocd.texi
src/target/cortex_a.c
src/target/cortex_a.h

index eb4bd4eeefce2a571508253e0f060a8c8cb18d22..76c9766c15bd350949b429d972638d243b0f6d3b 100644 (file)
@@ -7615,6 +7615,10 @@ Initialize core debug
 Enables debug by unlocking the Software Lock and clearing sticky powerdown indications
 @end deffn
 
+@deffn Command {cortex_r maskisr} [@option{on}|@option{off}]
+Selects whether interrupts will be processed when single stepping
+@end deffn
+
 
 @subsection ARMv7-M specific commands
 @cindex tracing
index 207fb811627bd80317045233e03af1150dd8b79a..39a79ddff53bf35526a66949163ed9bbbd85d021 100644 (file)
@@ -1323,9 +1323,33 @@ static int cortex_a_post_debug_entry(struct target *target)
        return ERROR_OK;
 }
 
+int cortex_a_set_dscr_bits(struct target *target, unsigned long bit_mask, unsigned long value)
+{
+       struct armv7a_common *armv7a = target_to_armv7a(target);
+       struct adiv5_dap *swjdp = armv7a->arm.dap;
+       uint32_t dscr;
+
+       /* Read DSCR */
+       int retval = mem_ap_sel_read_atomic_u32(swjdp, armv7a->debug_ap,
+                       armv7a->debug_base + CPUDBG_DSCR, &dscr);
+       if (ERROR_OK != retval)
+               return retval;
+
+       /* clear bitfield */
+       dscr &= ~bit_mask;
+       /* put new value */
+       dscr |= value & bit_mask;
+
+       /* write new DSCR */
+       retval = mem_ap_sel_write_atomic_u32(swjdp, armv7a->debug_ap,
+                       armv7a->debug_base + CPUDBG_DSCR, dscr);
+       return retval;
+}
+
 static int cortex_a_step(struct target *target, int current, uint32_t address,
        int handle_breakpoints)
 {
+       struct cortex_a_common *cortex_a = target_to_cortex_a(target);
        struct armv7a_common *armv7a = target_to_armv7a(target);
        struct arm *arm = &armv7a->arm;
        struct breakpoint *breakpoint = NULL;
@@ -1363,6 +1387,13 @@ static int cortex_a_step(struct target *target, int current, uint32_t address,
        stepbreakpoint.type = BKPT_HARD;
        stepbreakpoint.set = 0;
 
+       /* Disable interrupts during single step if requested */
+       if (cortex_a->isrmasking_mode == CORTEX_A_ISRMASK_ON) {
+               retval = cortex_a_set_dscr_bits(target, DSCR_INT_DIS, DSCR_INT_DIS);
+               if (ERROR_OK != retval)
+                       return retval;
+       }
+
        /* Break on IVA mismatch */
        cortex_a_set_breakpoint(target, &stepbreakpoint, 0x04);
 
@@ -1385,6 +1416,14 @@ static int cortex_a_step(struct target *target, int current, uint32_t address,
 
        cortex_a_unset_breakpoint(target, &stepbreakpoint);
 
+       /* Re-enable interrupts if they were disabled */
+       if (cortex_a->isrmasking_mode == CORTEX_A_ISRMASK_ON) {
+               retval = cortex_a_set_dscr_bits(target, DSCR_INT_DIS, 0);
+               if (ERROR_OK != retval)
+                       return retval;
+       }
+
+
        target->debug_reason = DBG_REASON_BREAKPOINT;
 
        if (breakpoint)
@@ -3193,6 +3232,37 @@ COMMAND_HANDLER(cortex_a_handle_smp_gdb_command)
        return ERROR_OK;
 }
 
+COMMAND_HANDLER(handle_cortex_a_mask_interrupts_command)
+{
+       struct target *target = get_current_target(CMD_CTX);
+       struct cortex_a_common *cortex_a = target_to_cortex_a(target);
+
+       static const Jim_Nvp nvp_maskisr_modes[] = {
+               { .name = "off", .value = CORTEX_A_ISRMASK_OFF },
+               { .name = "on", .value = CORTEX_A_ISRMASK_ON },
+               { .name = NULL, .value = -1 },
+       };
+       const Jim_Nvp *n;
+
+       if (target->state != TARGET_HALTED) {
+               command_print(CMD_CTX, "target must be stopped for \"%s\" command", CMD_NAME);
+               return ERROR_OK;
+       }
+
+       if (CMD_ARGC > 0) {
+               n = Jim_Nvp_name2value_simple(nvp_maskisr_modes, CMD_ARGV[0]);
+               if (n->name == NULL)
+                       return ERROR_COMMAND_SYNTAX_ERROR;
+               cortex_a->isrmasking_mode = n->value;
+
+       }
+
+       n = Jim_Nvp_value2name_simple(nvp_maskisr_modes, cortex_a->isrmasking_mode);
+       command_print(CMD_CTX, "cortex_a interrupt mask %s", n->name);
+
+       return ERROR_OK;
+}
+
 static const struct command_registration cortex_a_exec_command_handlers[] = {
        {
                .name = "cache_info",
@@ -3227,6 +3297,13 @@ static const struct command_registration cortex_a_exec_command_handlers[] = {
                .help = "display/fix current core played to gdb",
                .usage = "",
        },
+       {
+               .name = "maskisr",
+               .handler = handle_cortex_a_mask_interrupts_command,
+               .mode = COMMAND_EXEC,
+               .help = "mask cortex_a interrupts",
+               .usage = "['on'|'off']",
+       },
 
 
        COMMAND_REGISTRATION_DONE
@@ -3306,6 +3383,13 @@ static const struct command_registration cortex_r4_exec_command_handlers[] = {
                .help = "Initialize core debug",
                .usage = "",
        },
+       {
+               .name = "maskisr",
+               .handler = handle_cortex_a_mask_interrupts_command,
+               .mode = COMMAND_EXEC,
+               .help = "mask cortex_r4 interrupts",
+               .usage = "['on'|'off']",
+       },
 
        COMMAND_REGISTRATION_DONE
 };
index ebf79b88c745fba4d244d025ca9d365e58d65431..e124a9e07ccaadb6998177d4b1f05a91ab8bd823 100644 (file)
 
 #define CORTEX_A_PADDRDBG_CPU_SHIFT 13
 
+enum cortex_a_isrmasking_mode {
+       CORTEX_A_ISRMASK_OFF,
+       CORTEX_A_ISRMASK_ON,
+};
+
 struct cortex_a_brp {
        int used;
        int type;
@@ -91,6 +96,8 @@ struct cortex_a_common {
        uint32_t ttypr;
        uint32_t didr;
 
+       enum cortex_a_isrmasking_mode isrmasking_mode;
+
        struct armv7a_common armv7a_common;
 
 };

Linking to existing account procedure

If you already have an account and want to add another login method you MUST first sign in with your existing account and then change URL to read https://review.openocd.org/login/?link to get to this page again but this time it'll work for linking. Thank you.

SSH host keys fingerprints

1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=..              |
|+o..   .         |
|*.o   . .        |
|+B . . .         |
|Bo. = o S        |
|Oo.+ + =         |
|oB=.* = . o      |
| =+=.+   + E     |
|. .=o   . o      |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)