This is the mail archive of the gdb-patches@sourceware.org mailing list for the GDB project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[5/5] reimplement 'set print vtbl on'


I noticed that 'set print vtbl on' doesn't seem to do anything with code
generated by a modern GCC.  I think "modern" includes anything starting
with GCC 3.0 -- which by now is rather ancient.

It is hard to tell what this command was really supposed to do.  There
are no tests for it and the documentation is light.  Basically, though,
it seems to boil down to looking up the vtable's minsym and printing
that when printing the vtable pointer.

This seemed to be more easily done at a single point in cp-valprint.

The result looks like (test case virtfunc2.cc):

    (gdb) set print vtbl on
    (gdb) set print pretty on
    (gdb) p o
    $1 = {
      <interface> = {
        _vptr.interface = 0x4008c0 <vtable for Obj+32>
      }, <No data fields>}

I am not sure but this change may break printing with code compiled with
versions of GCC before 3.0.  I think that doesn't matter, but I'd
appreciate other input; for example if you still use GCC 2.95, speak up.

Tom

        * cp-valprint.c (cp_is_vtbl_ptr_type, cp_is_vtbl_member): Remove.
        (cp_print_value_fields): Handle vtable printing.
        * c-valprint.c (c_val_print) <TYPE_CODE_ARRAY>: Remove
        vtable-printing code.
        <TYPE_CODE_PTR>: Likewise.
        <TYPE_CODE_STRUCT>: Likewise.
        * c-lang.h (cp_is_vtbl_ptr_type, cp_is_vtbl_member): Remove.
    gdb/testsuite
        * gdb.cp/virtfunc2.exp: Add 'set vtbl print on' test.

>From 3a20de256825e2047d2fb1b7d1aed08497756d7a Mon Sep 17 00:00:00 2001
From: Tom Tromey <tromey@redhat.com>
Date: Tue, 28 Feb 2012 07:37:56 -0700
Subject: [PATCH 5/5] 	* cp-valprint.c (cp_is_vtbl_ptr_type,
 cp_is_vtbl_member): Remove. 	(cp_print_value_fields):
 Handle vtable printing. 	* c-valprint.c
 (c_val_print) <TYPE_CODE_ARRAY>: Remove 
 vtable-printing code. 	<TYPE_CODE_PTR>: Likewise. 
 <TYPE_CODE_STRUCT>: Likewise. 	* c-lang.h
 (cp_is_vtbl_ptr_type, cp_is_vtbl_member): Remove.
 gdb/testsuite 	* gdb.cp/virtfunc2.exp: Add 'set vtbl
 print on' test.

---
 gdb/c-lang.h                       |    4 --
 gdb/c-valprint.c                   |  103 ++---------------------------------
 gdb/cp-valprint.c                  |   60 ++++-----------------
 gdb/testsuite/gdb.cp/virtfunc2.exp |    2 +
 4 files changed, 19 insertions(+), 150 deletions(-)

diff --git a/gdb/c-lang.h b/gdb/c-lang.h
index e8c632f..5901b48 100644
--- a/gdb/c-lang.h
+++ b/gdb/c-lang.h
@@ -131,10 +131,6 @@ extern void cp_print_value_fields_rtti (struct type *,
 					const struct value_print_options *,
 					struct type **, int);
 
-extern int cp_is_vtbl_ptr_type (struct type *);
-
-extern int cp_is_vtbl_member (struct type *);
-
 /* These are in c-valprint.c.  */
 
 extern int c_textual_element_type (struct type *, char);
diff --git a/gdb/c-valprint.c b/gdb/c-valprint.c
index 0054dc0..9627bf9 100644
--- a/gdb/c-valprint.c
+++ b/gdb/c-valprint.c
@@ -192,19 +192,7 @@ c_val_print (struct type *type, const gdb_byte *valaddr,
 	  else
 	    {
 	      fprintf_filtered (stream, "{");
-	      /* If this is a virtual function table, print the 0th
-	         entry specially, and the rest of the members
-	         normally.  */
-	      if (cp_is_vtbl_ptr_type (elttype))
-		{
-		  i = 1;
-		  fprintf_filtered (stream, _("%d vtable entries"),
-				    len - 1);
-		}
-	      else
-		{
-		  i = 0;
-		}
+	      i = 0;
 	      val_print_array_elements (type, valaddr, embedded_offset,
 					address, stream,
 					recurse, original_value, options, i);
@@ -238,19 +226,6 @@ c_val_print (struct type *type, const gdb_byte *valaddr,
 				      original_value, options, 0, stream);
 	  break;
 	}
-      if (options->vtblprint && cp_is_vtbl_ptr_type (type))
-	{
-	  /* Print the unmangled name if desired.  */
-	  /* Print vtable entry - we only get here if we ARE using
-	     -fvtable_thunks.  (Otherwise, look under
-	     TYPE_CODE_STRUCT.)  */
-	  CORE_ADDR addr
-	    = extract_typed_address (valaddr + embedded_offset, type);
-
-	  print_function_pointer_address (gdbarch, addr, stream,
-					  options->addressprint);
-	  break;
-	}
       unresolved_elttype = TYPE_TARGET_TYPE (type);
       elttype = check_typedef (unresolved_elttype);
 	{
@@ -281,53 +256,6 @@ c_val_print (struct type *type, const gdb_byte *valaddr,
 				    addr, -1,
 				    stream, options);
 	    }
-	  else if (cp_is_vtbl_member (type))
-	    {
-	      /* Print vtbl's nicely.  */
-	      CORE_ADDR vt_address = unpack_pointer (type,
-						     valaddr
-						     + embedded_offset);
-
-	      struct minimal_symbol *msymbol =
-	      lookup_minimal_symbol_by_pc (vt_address);
-	      if ((msymbol != NULL)
-		  && (vt_address == SYMBOL_VALUE_ADDRESS (msymbol)))
-		{
-		  fputs_filtered (" <", stream);
-		  fputs_filtered (SYMBOL_PRINT_NAME (msymbol), stream);
-		  fputs_filtered (">", stream);
-		}
-	      if (vt_address && options->vtblprint)
-		{
-		  struct value *vt_val;
-		  struct symbol *wsym = (struct symbol *) NULL;
-		  struct type *wtype;
-		  struct block *block = (struct block *) NULL;
-		  int is_this_fld;
-
-		  if (msymbol != NULL)
-		    wsym = lookup_symbol (SYMBOL_LINKAGE_NAME (msymbol),
-					  block, VAR_DOMAIN,
-					  &is_this_fld);
-
-		  if (wsym)
-		    {
-		      wtype = SYMBOL_TYPE (wsym);
-		    }
-		  else
-		    {
-		      wtype = unresolved_elttype;
-		    }
-		  vt_val = value_at (wtype, vt_address);
-		  common_val_print (vt_val, stream, recurse + 1,
-				    options, current_language);
-		  if (options->pretty)
-		    {
-		      fprintf_filtered (stream, "\n");
-		      print_spaces_filtered (2 + 2 * recurse, stream);
-		    }
-		}
-	    }
 
 	  /* Return number of characters printed, including the
 	     terminating '\0' if we reached the end.  val_print_string
@@ -384,30 +312,11 @@ c_val_print (struct type *type, const gdb_byte *valaddr,
 	}
       /* Fall through.  */
     case TYPE_CODE_STRUCT:
-      /*FIXME: Abstract this away.  */
-      if (options->vtblprint && cp_is_vtbl_ptr_type (type))
-	{
-	  /* Print the unmangled name if desired.  */
-	  /* Print vtable entry - we only get here if NOT using
-	     -fvtable_thunks.  (Otherwise, look under
-	     TYPE_CODE_PTR.)  */
-	  int offset = (embedded_offset
-			+ TYPE_FIELD_BITPOS (type,
-					     VTBL_FNADDR_OFFSET) / 8);
-	  struct type *field_type = TYPE_FIELD_TYPE (type,
-						     VTBL_FNADDR_OFFSET);
-	  CORE_ADDR addr
-	    = extract_typed_address (valaddr + offset, field_type);
-
-	  print_function_pointer_address (gdbarch, addr, stream,
-					  options->addressprint);
-	}
-      else
-	cp_print_value_fields_rtti (type, valaddr,
-				    embedded_offset, address,
-				    stream, recurse,
-				    original_value, options,
-				    NULL, 0);
+      cp_print_value_fields_rtti (type, valaddr,
+				  embedded_offset, address,
+				  stream, recurse,
+				  original_value, options,
+				  NULL, 0);
       break;
 
     case TYPE_CODE_ENUM:
diff --git a/gdb/cp-valprint.c b/gdb/cp-valprint.c
index 1697006..d679af1 100644
--- a/gdb/cp-valprint.c
+++ b/gdb/cp-valprint.c
@@ -92,55 +92,6 @@ static void cp_print_value (struct type *, struct type *,
 /* GCC versions after 2.4.5 use this.  */
 const char vtbl_ptr_name[] = "__vtbl_ptr_type";
 
-/* Return truth value for assertion that TYPE is of the type
-   "pointer to virtual function".  */
-
-int
-cp_is_vtbl_ptr_type (struct type *type)
-{
-  const char *typename = type_name_no_tag (type);
-
-  return (typename != NULL && !strcmp (typename, vtbl_ptr_name));
-}
-
-/* Return truth value for the assertion that TYPE is of the type
-   "pointer to virtual function table".  */
-
-int
-cp_is_vtbl_member (struct type *type)
-{
-  /* With older versions of g++, the vtbl field pointed to an array of
-     structures.  Nowadays it points directly to the structure.  */
-  if (TYPE_CODE (type) == TYPE_CODE_PTR)
-    {
-      type = TYPE_TARGET_TYPE (type);
-      if (TYPE_CODE (type) == TYPE_CODE_ARRAY)
-	{
-	  type = TYPE_TARGET_TYPE (type);
-	  if (TYPE_CODE (type) == TYPE_CODE_STRUCT    /* if not using thunks */
-	      || TYPE_CODE (type) == TYPE_CODE_PTR)   /* if using thunks */
-	    {
-	      /* Virtual functions tables are full of pointers
-	         to virtual functions.  */
-	      return cp_is_vtbl_ptr_type (type);
-	    }
-	}
-      else if (TYPE_CODE (type) == TYPE_CODE_STRUCT)  /* if not using thunks */
-	{
-	  return cp_is_vtbl_ptr_type (type);
-	}
-      else if (TYPE_CODE (type) == TYPE_CODE_PTR)     /* if using thunks */
-	{
-	  /* The type name of the thunk pointer is NULL when using
-	     dwarf2.  We could test for a pointer to a function, but
-	     there is no type info for the virtual table either, so it
-	     wont help.  */
-	  return cp_is_vtbl_ptr_type (type);
-	}
-    }
-  return 0;
-}
-
 /* Mutually recursive subroutines of cp_print_value and c_val_print to
    print out a structure's fields: cp_print_value_fields and
    cp_print_value.
@@ -358,6 +309,17 @@ cp_print_value_fields (struct type *type, struct type *real_type,
 					   v, stream, recurse + 1,
 					   options);
 		}
+	      else if (options->vtblprint && i == TYPE_VPTR_FIELDNO (type))
+		{
+		  CORE_ADDR addr
+		    = extract_typed_address (valaddr + offset
+					     + TYPE_FIELD_BITSIZE (type, i) / 8,
+					     TYPE_FIELD_TYPE (type, i));
+
+		  print_function_pointer_address (get_type_arch (type),
+						  addr, stream,
+						  options->addressprint);
+		}
 	      else
 		{
 		  struct value_print_options opts = *options;
diff --git a/gdb/testsuite/gdb.cp/virtfunc2.exp b/gdb/testsuite/gdb.cp/virtfunc2.exp
index 0039692..bd66485 100644
--- a/gdb/testsuite/gdb.cp/virtfunc2.exp
+++ b/gdb/testsuite/gdb.cp/virtfunc2.exp
@@ -53,6 +53,8 @@ gdb_test "print o2.do_print()"  "\\$\[0-9\]+ = 123456"
 gdb_test "print o2.do_print2()"  "\\$\[0-9\]+ = 654321"
 gdb_test "print o2.do_print3()"  "\\$\[0-9\]+ = 111111"
 
+gdb_test_no_output "set print vtbl on"
+gdb_test "print o" " = {<interface> = {.*_vptr.interface = $hex <vtable for Obj.*>}, <No data fields>}"
 
 gdb_exit
 return 0
-- 
1.7.7.6


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]