arm_adi_v5: add dap apreg command for AP register read/write
authorTomas Vanek <vanekt@fbl.cz>
Fri, 24 Apr 2015 05:33:50 +0000 (07:33 +0200)
committerAndreas Fritiofson <andreas.fritiofson@gmail.com>
Sun, 17 Jul 2016 22:30:09 +0000 (23:30 +0100)
A developer tool: Direct access to AP registers can be useful
for handling vendor specific AP like Freescale Kinetis MDM or Atmel SMAP.

Change-Id: Ie2c7160fc6b2e398513eb23e1e52cbb52b88d9bd
Signed-off-by: Tomas Vanek <vanekt@fbl.cz>
Reviewed-on: http://openocd.zylin.com/2777
Reviewed-by: Andreas Fritiofson <andreas.fritiofson@gmail.com>
Tested-by: jenkins
doc/openocd.texi
src/target/arm_adi_v5.c

index 1d517213d8c3ab5e49e1a02c64bf77e61e88e10e..983ce3ca94eb5fddc38aafa09231f811af49ff28 100644 (file)
@@ -7836,6 +7836,12 @@ Displays ID register from AP @var{num},
 defaulting to the currently selected AP.
 @end deffn
 
+@deffn Command {dap apreg} ap_num reg [value]
+Displays content of a register @var{reg} from AP @var{ap_num}
+or set a new value @var{value}.
+@var{reg} is byte address of a word register, 0, 4, 8 ... 0xfc.
+@end deffn
+
 @deffn Command {dap apsel} [num]
 Select AP @var{num}, defaulting to 0.
 @end deffn
index eb3392bf7d8e290adb6aee6c1eed981e3e7ad83f..f58afdc0a9f84d8864fbba101154e3586c6cd90d 100644 (file)
@@ -1556,6 +1556,45 @@ COMMAND_HANDLER(dap_apid_command)
        return retval;
 }
 
+COMMAND_HANDLER(dap_apreg_command)
+{
+       struct target *target = get_current_target(CMD_CTX);
+       struct arm *arm = target_to_arm(target);
+       struct adiv5_dap *dap = arm->dap;
+
+       uint32_t apsel, reg, value;
+       int retval;
+
+       if (CMD_ARGC < 2 || CMD_ARGC > 3)
+               return ERROR_COMMAND_SYNTAX_ERROR;
+
+       COMMAND_PARSE_NUMBER(u32, CMD_ARGV[0], apsel);
+       /* AP address is in bits 31:24 of DP_SELECT */
+       if (apsel >= 256)
+               return ERROR_COMMAND_SYNTAX_ERROR;
+
+       COMMAND_PARSE_NUMBER(u32, CMD_ARGV[1], reg);
+       if (reg >= 256 || (reg & 3))
+               return ERROR_COMMAND_SYNTAX_ERROR;
+
+       if (CMD_ARGC == 3) {
+               COMMAND_PARSE_NUMBER(u32, CMD_ARGV[2], value);
+               retval = dap_queue_ap_write(dap_ap(dap, apsel), reg, value);
+       } else {
+               retval = dap_queue_ap_read(dap_ap(dap, apsel), reg, &value);
+       }
+       if (retval == ERROR_OK)
+               retval = dap_run(dap);
+
+       if (retval != ERROR_OK)
+               return retval;
+
+       if (CMD_ARGC == 2)
+               command_print(CMD_CTX, "0x%08" PRIx32, value);
+
+       return retval;
+}
+
 COMMAND_HANDLER(dap_ti_be_32_quirks_command)
 {
        struct target *target = get_current_target(CMD_CTX);
@@ -1615,6 +1654,14 @@ static const struct command_registration dap_commands[] = {
                        "(default currently selected AP)",
                .usage = "[ap_num]",
        },
+       {
+               .name = "apreg",
+               .handler = dap_apreg_command,
+               .mode = COMMAND_EXEC,
+               .help = "read/write a register from AP "
+                       "(reg is byte address of a word register, like 0 4 8...)",
+               .usage = "ap_num reg [value]",
+       },
        {
                .name = "baseaddr",
                .handler = dap_baseaddr_command,