[binutils-gdb] Disassemble blocks with non-contiguous ranges

Kevin Buettner kevinb@sourceware.org
Thu Aug 23 23:26:00 GMT 2018


https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=e94802301b37de0e75e9329a96b0e70d38e5ead9

commit e94802301b37de0e75e9329a96b0e70d38e5ead9
Author: Kevin Buettner <kevinb@redhat.com>
Date:   Thu Aug 23 16:00:49 2018 -0700

    Disassemble blocks with non-contiguous ranges
    
    This patch adds support for disassembly of blocks with non-contiguous
    ranges.  These blocks are printed as follows:
    
    (gdb) disassemble foo
    Dump of assembler code for function foo:
    Address range 0x401136 to 0x401151:
       0x0000000000401136 <+0>:     push   %rbp
       0x0000000000401137 <+1>:     mov    %rsp,%rbp
       0x000000000040113a <+4>:     callq  0x401134 <bar>
       0x000000000040113f <+9>:     mov    0x2eef(%rip),%eax        # 0x404034 <e>
       0x0000000000401145 <+15>:    test   %eax,%eax
       0x0000000000401147 <+17>:    je     0x40114e <foo+24>
       0x0000000000401149 <+19>:    callq  0x401128 <foo+4294967282>
       0x000000000040114e <+24>:    nop
       0x000000000040114f <+25>:    pop    %rbp
       0x0000000000401150 <+26>:    retq
    Address range 0x401128 to 0x401134:
       0x0000000000401128 <+-14>:   push   %rbp
       0x0000000000401129 <+-13>:   mov    %rsp,%rbp
       0x000000000040112c <+-10>:   callq  0x401126 <baz>
       0x0000000000401131 <+-5>:    nop
       0x0000000000401132 <+-4>:    pop    %rbp
       0x0000000000401133 <+-3>:    retq
    End of assembler dump.
    
    This is an actual dump from the test case that I constructed for
    this work.  The ranges are printed in the order encountered in the
    debug info. For the above example, note that the second range occupies
    lower addresses than the first range.
    
    Functions with contiguous ranges are still printed as follows:
    
    (gdb) disassemble main
    Dump of assembler code for function main:
       0x0000000000401151 <+0>:     push   %rbp
       0x0000000000401152 <+1>:     mov    %rsp,%rbp
       0x0000000000401155 <+4>:     callq  0x401136 <foo>
       0x000000000040115a <+9>:     mov    $0x0,%eax
       0x000000000040115f <+14>:    pop    %rbp
       0x0000000000401160 <+15>:    retq
    End of assembler dump.
    
    gdb/ChangeLog:
    
    	* cli/cli-cmds.c (block.h): Include.
    	(print_disassembly): Handle printing of non-contiguous blocks.
    	(disassemble_current_function): Likewise.
    	(disassemble_command): Likewise.

Diff:
---
 gdb/ChangeLog      |  4 ++++
 gdb/cli/cli-cmds.c | 43 ++++++++++++++++++++++++++++++++-----------
 2 files changed, 36 insertions(+), 11 deletions(-)

diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index 9d226c1..751b3ed 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -14,6 +14,10 @@
 	(clear_pc_function_cache): Clear cache_pc_function_block.
 	(find_pc_partial_function): Move comment to symtab.h.  Add
 	support for non-contiguous blocks.
+	* cli/cli-cmds.c (block.h): Include.
+	(print_disassembly): Handle printing of non-contiguous blocks.
+	(disassemble_current_function): Likewise.
+	(disassemble_command): Likewise.
 
 2018-08-23  Xavier Roirand  <roirand@adacore.com>
 
diff --git a/gdb/cli/cli-cmds.c b/gdb/cli/cli-cmds.c
index 5c5d6dc..4694553 100644
--- a/gdb/cli/cli-cmds.c
+++ b/gdb/cli/cli-cmds.c
@@ -38,6 +38,7 @@
 #include "tracepoint.h"
 #include "filestuff.h"
 #include "location.h"
+#include "block.h"
 
 #include "ui-out.h"
 
@@ -1091,11 +1092,15 @@ list_command (const char *arg, int from_tty)
    Perform the disassembly.
    NAME is the name of the function if known, or NULL.
    [LOW,HIGH) are the range of addresses to disassemble.
+   BLOCK is the block to disassemble; it needs to be provided
+   when non-contiguous blocks are disassembled; otherwise
+   it can be NULL.
    MIXED is non-zero to print source with the assembler.  */
 
 static void
 print_disassembly (struct gdbarch *gdbarch, const char *name,
 		   CORE_ADDR low, CORE_ADDR high,
+		   const struct block *block,
 		   gdb_disassembly_flags flags)
 {
 #if defined(TUI)
@@ -1104,14 +1109,28 @@ print_disassembly (struct gdbarch *gdbarch, const char *name,
     {
       printf_filtered ("Dump of assembler code ");
       if (name != NULL)
-        printf_filtered ("for function %s:\n", name);
-      else
-        printf_filtered ("from %s to %s:\n",
-			 paddress (gdbarch, low), paddress (gdbarch, high));
-
-      /* Dump the specified range.  */
-      gdb_disassembly (gdbarch, current_uiout, flags, -1, low, high);
+	printf_filtered ("for function %s:\n", name);
+      if (block == nullptr || BLOCK_CONTIGUOUS_P (block))
+        {
+	  if (name == NULL)
+	    printf_filtered ("from %s to %s:\n",
+			     paddress (gdbarch, low), paddress (gdbarch, high));
 
+	  /* Dump the specified range.  */
+	  gdb_disassembly (gdbarch, current_uiout, flags, -1, low, high);
+	}
+      else
+        {
+	  for (int i = 0; i < BLOCK_NRANGES (block); i++)
+	    {
+	      CORE_ADDR low = BLOCK_RANGE_START (block, i);
+	      CORE_ADDR high = BLOCK_RANGE_END (block, i);
+	      printf_filtered (_("Address range %s to %s:\n"),
+			       paddress (gdbarch, low),
+			       paddress (gdbarch, high));
+	      gdb_disassembly (gdbarch, current_uiout, flags, -1, low, high);
+	    }
+	}
       printf_filtered ("End of assembler dump.\n");
       gdb_flush (gdb_stdout);
     }
@@ -1133,11 +1152,12 @@ disassemble_current_function (gdb_disassembly_flags flags)
   struct gdbarch *gdbarch;
   CORE_ADDR low, high, pc;
   const char *name;
+  const struct block *block;
 
   frame = get_selected_frame (_("No frame selected."));
   gdbarch = get_frame_arch (frame);
   pc = get_frame_address_in_block (frame);
-  if (find_pc_partial_function (pc, &name, &low, &high) == 0)
+  if (find_pc_partial_function (pc, &name, &low, &high, &block) == 0)
     error (_("No function contains program counter for selected frame."));
 #if defined(TUI)
   /* NOTE: cagney/2003-02-13 The `tui_active' was previously
@@ -1148,7 +1168,7 @@ disassemble_current_function (gdb_disassembly_flags flags)
 #endif
   low += gdbarch_deprecated_function_start_offset (gdbarch);
 
-  print_disassembly (gdbarch, name, low, high, flags);
+  print_disassembly (gdbarch, name, low, high, block, flags);
 }
 
 /* Dump a specified section of assembly code.
@@ -1184,6 +1204,7 @@ disassemble_command (const char *arg, int from_tty)
   CORE_ADDR pc;
   gdb_disassembly_flags flags;
   const char *p;
+  const struct block *block = nullptr;
 
   p = arg;
   name = NULL;
@@ -1234,7 +1255,7 @@ disassemble_command (const char *arg, int from_tty)
   if (p[0] == '\0')
     {
       /* One argument.  */
-      if (find_pc_partial_function (pc, &name, &low, &high) == 0)
+      if (find_pc_partial_function (pc, &name, &low, &high, &block) == 0)
 	error (_("No function contains specified address."));
 #if defined(TUI)
       /* NOTE: cagney/2003-02-13 The `tui_active' was previously
@@ -1262,7 +1283,7 @@ disassemble_command (const char *arg, int from_tty)
 	high += low;
     }
 
-  print_disassembly (gdbarch, name, low, high, flags);
+  print_disassembly (gdbarch, name, low, high, block, flags);
 }
 
 static void



More information about the Gdb-cvs mailing list