This is the mail archive of the gdb@sources.redhat.com 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]

Re: A hack for DW_FORM_ref_addr


On Thu, Jul 31, 2003 at 02:22:19PM -0400, Daniel Jacobowitz wrote:
> On Thu, Jul 31, 2003 at 09:16:19AM -0700, H. J. Lu wrote:
> > On Wed, Jul 30, 2003 at 10:16:53PM -0700, H. J. Lu wrote:
> > > > > 
> > > > > While waiting for your new DWARF reader, I will see how my hack
> > > > > goes :-(.
> > > > 
> > > > Since the die table is hashed by offset (isn't it?), presumably very
> > > > badly.
> > > 
> > > It is OK for different compilation units within the same .debug_info
> > > section.
> > > 
> > > 
> > 
> > FYI, this is the hack I am going to try.
> 
> It may be safe, but it's unacceptable.  Take a look at the memory usage
> requirements for -readnow, if libc.so.6 has debugging information. 
> You've just eaten probably 200MB of RAM.
> 

FYI, this is my updated hack.


H.J.
---
2003-07-31  H.J. Lu  <hongjiu.lu@intel.com>

	* dwarf2read.c (die_info_list): New structure.
	(need_preserve_die_ref_table): New.
	(dwarf2_build_psymtabs_hard): Read in all compilation units.
	Free die list die reference table is not needed.
	(read_comp_unit): Reset die reference table if it is not needed
	or abfd is changed
	(read_attribute_value): Set need_preserve_die_ref_table to 1
	for DW_FORM_ref_addr.

--- gdb/dwarf2read.c.ref_addr	2003-07-31 12:59:31.000000000 -0700
+++ gdb/dwarf2read.c	2003-07-31 14:03:10.000000000 -0700
@@ -325,6 +325,12 @@ struct die_info
     struct type *type;		/* Cached type information */
   };
 
+struct die_info_list
+{
+  struct die_info *dies;
+  struct die_info_list *next; 
+};
+
 /* Attributes have a name and a value */
 struct attribute
   {
@@ -376,6 +382,7 @@ struct dwarf_block
 #endif
 
 static struct die_info *die_ref_table[REF_HASH_SIZE];
+static int need_preserve_die_ref_table = -1;
 
 /* Obstack for allocating temporary storage used during symbol reading.  */
 static struct obstack dwarf2_tmp_obstack;
@@ -1195,6 +1202,8 @@ dwarf2_build_psymtabs_hard (struct objfi
   struct partial_symtab *pst;
   struct cleanup *back_to;
   CORE_ADDR lowpc, highpc;
+  struct die_info *dies;
+  struct die_info_list *dies_list_head, *dies_list_p;
 
   info_ptr = dwarf_info_buffer;
   abbrev_ptr = dwarf_abbrev_buffer;
@@ -1230,6 +1239,13 @@ dwarf2_build_psymtabs_hard (struct objfi
   obstack_init (&dwarf2_tmp_obstack);
   back_to = make_cleanup (dwarf2_free_tmp_obstack, NULL);
 
+  need_preserve_die_ref_table = -1;
+  dies_list_head
+    = (struct die_info_list *) xmalloc (sizeof (struct die_info_list));
+  dies_list_head->dies = NULL;
+  dies_list_head->next = NULL;
+  dies_list_p = dies_list_head;
+
   /* Since the objects we're extracting from dwarf_info_buffer vary in
      length, only the individual functions to extract them (like
      read_comp_unit_head and read_partial_die) can really know whether
@@ -1280,6 +1296,18 @@ dwarf2_build_psymtabs_hard (struct objfi
       dwarf2_read_abbrevs (abfd, &cu_header);
       make_cleanup (dwarf2_empty_abbrev_table, cu_header.dwarf2_abbrevs);
 
+      dies = read_comp_unit (info_ptr, abfd, &cu_header);
+      if (dies_list_p->dies != NULL)
+	{
+	  struct die_info_list *p = (struct die_info_list *)
+	    xmalloc (sizeof (struct die_info_list));
+
+	  p->next = NULL;
+	  dies_list_p->next = p;
+	  dies_list_p = p;
+	}
+      dies_list_p->dies = dies;
+
       /* Read the compilation unit die */
       info_ptr = read_partial_die (&comp_unit_die, abfd, info_ptr,
 				   &cu_header);
@@ -1349,6 +1377,22 @@ dwarf2_build_psymtabs_hard (struct objfi
       info_ptr = beg_of_comp_unit + cu_header.length 
                                   + cu_header.initial_length_size;
     }
+
+  if (need_preserve_die_ref_table != 1)
+    {
+      struct die_info_list *next;
+
+      for (dies_list_p = dies_list_head; dies_list_p != NULL;
+	   dies_list_p = next)
+	{
+	  next = dies_list_p->next;
+	  make_cleanup_free_die_list (dies_list_p->dies);
+	  free (dies_list_p);
+	}
+
+      need_preserve_die_ref_table = 0;
+    }
+
   do_cleanups (back_to);
 }
 
@@ -3653,10 +3697,18 @@ read_comp_unit (char *info_ptr, bfd *abf
   struct die_info *first_die, *last_die, *die;
   char *cur_ptr;
   int nesting_level;
+  static bfd *bfd_die_ref_table;
 
-  /* Reset die reference table; we are
-     building new ones now.  */
-  dwarf2_empty_hash_tables ();
+  if (!bfd_die_ref_table)
+    bfd_die_ref_table = abfd;
+
+  if (need_preserve_die_ref_table == 0
+      || bfd_die_ref_table != abfd)
+    {
+      bfd_die_ref_table = abfd;
+      /* Reset die reference table; we are building new ones now.  */
+      dwarf2_empty_hash_tables ();
+    }
 
   cur_ptr = info_ptr;
   nesting_level = 0;
@@ -4080,8 +4132,9 @@ read_attribute_value (struct attribute *
   attr->form = form;
   switch (form)
     {
-    case DW_FORM_addr:
     case DW_FORM_ref_addr:
+      need_preserve_die_ref_table = 1;
+    case DW_FORM_addr:
       DW_ADDR (attr) = read_address (abfd, info_ptr, cu_header, &bytes_read);
       info_ptr += bytes_read;
       break;


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