Provide an "armv7a disassemble" command.  Current omissions include
VFP (except as coprocessor instructions), Neon, and various Thumb2
opcodes that are not available in ARMv7-M processors.
---
 doc/openocd.texi    |   17 +++++++++
 src/target/armv7a.c |   86 ++++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 103 insertions(+)

--- a/doc/openocd.texi
+++ b/doc/openocd.texi
@@ -5105,6 +5105,23 @@ Displays the number of extra tck for mem
 If @var{value} is defined, first assigns that.
 @end deffn
 
+...@subsection ARMv7-A specific commands
+...@cindex ARMv7-A
+
+...@deffn Command {armv7a disassemble} address [count [...@option{thumb}]]
+...@cindex disassemble
+Disassembles @var{count} instructions starting at @var{address}.
+If @var{count} is not specified, a single instruction is disassembled.
+If @option{thumb} is specified, or the low bit of the address is set,
+Thumb2 (mixed 16/32-bit) instructions are used;
+else ARM (32-bit) instructions are used.
+With a handful of exceptions, ThumbEE instructions are the same as Thumb2;
+ThumbEE disassembly currently has no explicit support.
+(Processors may also support the Jazelle state, but
+those instructions are not currently understood by OpenOCD.)
+...@end deffn
+
+
 @subsection Cortex-M3 specific commands
 @cindex Cortex-M3
 
--- a/src/target/armv7a.c
+++ b/src/target/armv7a.c
@@ -23,6 +23,7 @@
 #include "replacements.h"
 
 #include "armv7a.h"
+#include "arm_disassembler.h"
 
 #include "target.h"
 #include "register.h"
@@ -269,9 +270,86 @@ static int handle_dap_info_command(struc
        return dap_info_command(cmd_ctx, swjdp, apsel);
 }
 
+static int
+handle_armv7a_disassemble_command(struct command_context_s *cmd_ctx,
+               char *cmd, char **args, int argc)
+{
+       target_t *target = get_current_target(cmd_ctx);
+       armv4_5_common_t *armv4_5 = target->arch_info;
+       int thumb = 0;
+       int count = 1;
+       uint32_t address;
+       int i;
+
+       if (armv4_5->common_magic != ARMV4_5_COMMON_MAGIC) {
+               command_print(cmd_ctx, "current target isn't an ARM target");
+               return ERROR_OK;
+       }
+
+       /* REVISIT:  eventually support ThumbEE disassembly too;
+        * some opcodes work differently.
+        */
+
+       switch (argc) {
+       case 3:
+               if (strcmp(args[2], "thumb") != 0)
+                       goto usage;
+               thumb = 1;
+               /* FALL THROUGH */
+       case 2:
+               count = strtoul(args[1], NULL, 0);
+               /* FALL THROUGH */
+       case 1:
+               address = strtoul(args[0], NULL, 0);
+               if (address & 0x01) {
+                       if (!thumb) {
+                               command_print(cmd_ctx, "Disassemble as Thumb");
+                               thumb = 1;
+                       }
+                       address &= ~1;
+               }
+               break;
+       default:
+usage:
+               command_print(cmd_ctx,
+                       "usage: armv4_5 disassemble <address> [<count> 
['thumb']]");
+               return ERROR_OK;
+       }
+
+       for (i = 0; i < count; i++) {
+               arm_instruction_t cur_instruction;
+               int retval;
+
+               if (thumb) {
+                       retval = thumb2_opcode(target, address, 
&cur_instruction);
+                       if (retval != ERROR_OK)
+                               return retval;
+
+                       address += cur_instruction.instruction_size;
+               } else {
+                       uint32_t opcode;
+
+                       retval = target_read_u32(target, address, &opcode);
+                       if (retval != ERROR_OK)
+                               return retval;
+
+                       retval = arm_evaluate_opcode(opcode, address,
+                                       &cur_instruction);
+                       if (retval != ERROR_OK)
+                               return retval;
+
+                       address += 4;
+               }
+               command_print(cmd_ctx, "%s", cur_instruction.text);
+       }
+
+       return ERROR_OK;
+}
+
 int armv7a_register_commands(struct command_context_s *cmd_ctx)
 {
        command_t *arm_adi_v5_dap_cmd;
+       command_t *armv7a_cmd;
 
        arm_adi_v5_dap_cmd = register_command(cmd_ctx, NULL, "dap",
                        NULL, COMMAND_ANY,
@@ -297,5 +375,13 @@ int armv7a_register_commands(struct comm
                        "set/get number of extra tck for mem-ap memory "
                        "bus access [0-255]");
 
+       armv7a_cmd = register_command(cmd_ctx, NULL, "armv7a",
+                       NULL, COMMAND_ANY,
+                       "ARMv7-A specific commands");
+
+       register_command(cmd_ctx, armv7a_cmd, "disassemble",
+                       handle_armv7a_disassemble_command, COMMAND_EXEC,
+                       "disassemble instructions <address> [<count> 
['thumb']]");
+
        return ERROR_OK;
 }
Provide an "armv7a disassemble" command.  Current omissions include
VFP (except as coprocessor instructions), Neon, and various Thumb2
opcodes that are not available in ARMv7-M processors.
---
 doc/openocd.texi    |   17 +++++++++
 src/target/armv7a.c |   86 ++++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 103 insertions(+)

--- a/doc/openocd.texi
+++ b/doc/openocd.texi
@@ -5105,6 +5105,23 @@ Displays the number of extra tck for mem
 If @var{value} is defined, first assigns that.
 @end deffn
 
+...@subsection ARMv7-A specific commands
+...@cindex ARMv7-A
+
+...@deffn Command {armv7a disassemble} address [count [...@option{thumb}]]
+...@cindex disassemble
+Disassembles @var{count} instructions starting at @var{address}.
+If @var{count} is not specified, a single instruction is disassembled.
+If @option{thumb} is specified, or the low bit of the address is set,
+Thumb2 (mixed 16/32-bit) instructions are used;
+else ARM (32-bit) instructions are used.
+With a handful of exceptions, ThumbEE instructions are the same as Thumb2;
+ThumbEE disassembly currently has no explicit support.
+(Processors may also support the Jazelle state, but
+those instructions are not currently understood by OpenOCD.)
+...@end deffn
+
+
 @subsection Cortex-M3 specific commands
 @cindex Cortex-M3
 
--- a/src/target/armv7a.c
+++ b/src/target/armv7a.c
@@ -23,6 +23,7 @@
 #include "replacements.h"
 
 #include "armv7a.h"
+#include "arm_disassembler.h"
 
 #include "target.h"
 #include "register.h"
@@ -269,9 +270,86 @@ static int handle_dap_info_command(struc
 	return dap_info_command(cmd_ctx, swjdp, apsel);
 }
 
+static int
+handle_armv7a_disassemble_command(struct command_context_s *cmd_ctx,
+		char *cmd, char **args, int argc)
+{
+	target_t *target = get_current_target(cmd_ctx);
+	armv4_5_common_t *armv4_5 = target->arch_info;
+	int thumb = 0;
+	int count = 1;
+	uint32_t address;
+	int i;
+
+	if (armv4_5->common_magic != ARMV4_5_COMMON_MAGIC) {
+		command_print(cmd_ctx, "current target isn't an ARM target");
+		return ERROR_OK;
+	}
+
+	/* REVISIT:  eventually support ThumbEE disassembly too;
+	 * some opcodes work differently.
+	 */
+
+	switch (argc) {
+	case 3:
+		if (strcmp(args[2], "thumb") != 0)
+			goto usage;
+		thumb = 1;
+		/* FALL THROUGH */
+	case 2:
+		count = strtoul(args[1], NULL, 0);
+		/* FALL THROUGH */
+	case 1:
+		address = strtoul(args[0], NULL, 0);
+		if (address & 0x01) {
+			if (!thumb) {
+				command_print(cmd_ctx, "Disassemble as Thumb");
+				thumb = 1;
+			}
+			address &= ~1;
+		}
+		break;
+	default:
+usage:
+		command_print(cmd_ctx,
+			"usage: armv4_5 disassemble <address> [<count> ['thumb']]");
+		return ERROR_OK;
+	}
+
+	for (i = 0; i < count; i++) {
+		arm_instruction_t cur_instruction;
+		int retval;
+
+		if (thumb) {
+			retval = thumb2_opcode(target, address, &cur_instruction);
+			if (retval != ERROR_OK)
+				return retval;
+
+			address += cur_instruction.instruction_size;
+		} else {
+			uint32_t opcode;
+
+			retval = target_read_u32(target, address, &opcode);
+			if (retval != ERROR_OK)
+				return retval;
+
+			retval = arm_evaluate_opcode(opcode, address,
+					&cur_instruction);
+			if (retval != ERROR_OK)
+				return retval;
+
+			address += 4;
+		}
+		command_print(cmd_ctx, "%s", cur_instruction.text);
+	}
+
+	return ERROR_OK;
+}
+
 int armv7a_register_commands(struct command_context_s *cmd_ctx)
 {
 	command_t *arm_adi_v5_dap_cmd;
+	command_t *armv7a_cmd;
 
 	arm_adi_v5_dap_cmd = register_command(cmd_ctx, NULL, "dap",
 			NULL, COMMAND_ANY,
@@ -297,5 +375,13 @@ int armv7a_register_commands(struct comm
 			"set/get number of extra tck for mem-ap memory "
 			"bus access [0-255]");
 
+	armv7a_cmd = register_command(cmd_ctx, NULL, "armv7a",
+			NULL, COMMAND_ANY,
+			"ARMv7-A specific commands");
+
+	register_command(cmd_ctx, armv7a_cmd, "disassemble",
+			handle_armv7a_disassemble_command, COMMAND_EXEC,
+			"disassemble instructions <address> [<count> ['thumb']]");
+
 	return ERROR_OK;
 }
_______________________________________________
Openocd-development mailing list
Openocd-development@lists.berlios.de
https://lists.berlios.de/mailman/listinfo/openocd-development

Reply via email to