public inbox for gdb-patches@sourceware.org
 help / color / mirror / Atom feed
* [PATCH] Introduce objfile::intern
@ 2020-02-24  2:58 Tom Tromey
  2020-03-04 23:47 ` Tom Tromey
  0 siblings, 1 reply; 3+ messages in thread
From: Tom Tromey @ 2020-02-24  2:58 UTC (permalink / raw)
  To: gdb-patches; +Cc: Tom Tromey

This introduces a string cache on the per-BFD object, replacing the
macro and filename caches.  Both of these caches just store strings,
so this consolidation by itself saves a little memory (about the size
of a bcache per objfile).

Then this patch switches some allocations on the objfile obstack to
use this bcache instead.  This saves more space; and turns out to be a
bit faster as well.

Here are the before and after "maint time" + "maint space" results of
"file ./gdb":

    Command execution time: 4.664021 (cpu), 4.728518 (wall)
    Space used: 39190528 (+29212672 for this command)

    Command execution time: 4.216209 (cpu), 4.107023 (wall)
    Space used: 36667392 (+26689536 for this command)

The main interface to the string cache is a new pair of overloaded
methods, objfile::intern.

gdb/ChangeLog
2020-02-23  Tom Tromey  <tom@tromey.com>

	* symmisc.c (print_symbol_bcache_statistics)
	(print_objfile_statistics): Update.
	* symfile.c (allocate_symtab): Use intern.
	* psymtab.c (partial_symtab::partial_symtab): Use intern.
	* objfiles.h (struct objfile_per_bfd_storage) <filename_cache,
	macro_cache>: Remove.
	<string_cache>: New member.
	(struct objfile) <intern>: New methods.
	* elfread.c (elf_symtab_read): Use intern.
	* dwarf2/read.c (fixup_go_packaging): Intern package name.
	(dwarf2_compute_name, dwarf2_physname)
	(create_dwo_unit_in_dwp_v1, create_dwo_unit_in_dwp_v2): Intern
	names.
	(guess_partial_die_structure_name): Update.
	(partial_die_info::fixup): Intern name.
	(dwarf2_canonicalize_name): Change parameter to objfile.  Intern
	name.
	(dwarf2_name): Intern name.  Update.
	* buildsym.c (buildsym_compunit::get_macro_table): Use
	string_cache.
---
 gdb/ChangeLog     | 23 +++++++++++++++++++++++
 gdb/buildsym.c    |  2 +-
 gdb/dwarf2/read.c | 43 ++++++++++++++++---------------------------
 gdb/elfread.c     |  6 +-----
 gdb/objfiles.h    | 24 ++++++++++++++++++------
 gdb/psymtab.c     |  4 +---
 gdb/symfile.c     |  4 +---
 gdb/symmisc.c     | 10 +++-------
 8 files changed, 64 insertions(+), 52 deletions(-)

diff --git a/gdb/buildsym.c b/gdb/buildsym.c
index 4965b552b32..84cb44277a4 100644
--- a/gdb/buildsym.c
+++ b/gdb/buildsym.c
@@ -120,7 +120,7 @@ buildsym_compunit::get_macro_table ()
 {
   if (m_pending_macros == nullptr)
     m_pending_macros = new_macro_table (&m_objfile->per_bfd->storage_obstack,
-					&m_objfile->per_bfd->macro_cache,
+					&m_objfile->per_bfd->string_cache,
 					m_compunit_symtab);
   return m_pending_macros;
 }
diff --git a/gdb/dwarf2/read.c b/gdb/dwarf2/read.c
index 46d510eb274..fe54680eb1d 100644
--- a/gdb/dwarf2/read.c
+++ b/gdb/dwarf2/read.c
@@ -1449,7 +1449,7 @@ static const gdb_byte *read_full_die (const struct die_reader_specs *,
 static void process_die (struct die_info *, struct dwarf2_cu *);
 
 static const char *dwarf2_canonicalize_name (const char *, struct dwarf2_cu *,
-					     struct obstack *);
+					     struct objfile *);
 
 static const char *dwarf2_name (struct die_info *die, struct dwarf2_cu *);
 
@@ -9056,8 +9056,7 @@ fixup_go_packaging (struct dwarf2_cu *cu)
   if (package_name != NULL)
     {
       struct objfile *objfile = cu->per_cu->dwarf2_per_objfile->objfile;
-      const char *saved_package_name
-	= obstack_strdup (&objfile->per_bfd->storage_obstack, package_name.get ());
+      const char *saved_package_name = objfile->intern (package_name.get ());
       struct type *type = init_type (objfile, TYPE_CODE_MODULE, 0,
 				     saved_package_name);
       struct symbol *sym;
@@ -10183,14 +10182,13 @@ dwarf2_compute_name (const char *name,
 	  if (cu->language == language_cplus)
 	    canonical_name
 	      = dwarf2_canonicalize_name (intermediate_name.c_str (), cu,
-					  &objfile->per_bfd->storage_obstack);
+					  objfile);
 
 	  /* If we only computed INTERMEDIATE_NAME, or if
 	     INTERMEDIATE_NAME is already canonical, then we need to
-	     copy it to the appropriate obstack.  */
+	     intern it.  */
 	  if (canonical_name == NULL || canonical_name == intermediate_name.c_str ())
-	    name = obstack_strdup (&objfile->per_bfd->storage_obstack,
-				   intermediate_name);
+	    name = objfile->intern (intermediate_name);
 	  else
 	    name = canonical_name;
 	}
@@ -10310,7 +10308,7 @@ dwarf2_physname (const char *name, struct die_info *die, struct dwarf2_cu *cu)
     retval = canon;
 
   if (need_copy)
-    retval = obstack_strdup (&objfile->per_bfd->storage_obstack, retval);
+    retval = objfile->intern (retval);
 
   return retval;
 }
@@ -11636,8 +11634,7 @@ create_dwo_unit_in_dwp_v1 (struct dwarf2_per_objfile *dwarf2_per_objfile,
 			      virtual_dwo_name.c_str ());
 	}
       dwo_file = new struct dwo_file;
-      dwo_file->dwo_name = obstack_strdup (&objfile->objfile_obstack,
-					   virtual_dwo_name);
+      dwo_file->dwo_name = objfile->intern (virtual_dwo_name);
       dwo_file->comp_dir = comp_dir;
       dwo_file->sections.abbrev = sections.abbrev;
       dwo_file->sections.line = sections.line;
@@ -11832,8 +11829,7 @@ create_dwo_unit_in_dwp_v2 (struct dwarf2_per_objfile *dwarf2_per_objfile,
 			      virtual_dwo_name.c_str ());
 	}
       dwo_file = new struct dwo_file;
-      dwo_file->dwo_name = obstack_strdup (&objfile->objfile_obstack,
-					   virtual_dwo_name);
+      dwo_file->dwo_name = objfile->intern (virtual_dwo_name);
       dwo_file->comp_dir = comp_dir;
       dwo_file->sections.abbrev =
 	create_dwp_v2_section (dwarf2_per_objfile, &dwp_file->sections.abbrev,
@@ -17953,8 +17949,7 @@ partial_die_info::read (const struct die_reader_specs *reader,
 		struct objfile *objfile = dwarf2_per_objfile->objfile;
 
 		name
-		  = dwarf2_canonicalize_name (DW_STRING (&attr), cu,
-					      &objfile->per_bfd->storage_obstack);
+		  = dwarf2_canonicalize_name (DW_STRING (&attr), cu, objfile);
 	      }
 	      break;
 	    }
@@ -18279,9 +18274,7 @@ guess_partial_die_structure_name (struct partial_die_info *struct_pdi,
 	  if (actual_class_name != NULL)
 	    {
 	      struct objfile *objfile = cu->per_cu->dwarf2_per_objfile->objfile;
-	      struct_pdi->name
-		= obstack_strdup (&objfile->per_bfd->storage_obstack,
-				  actual_class_name.get ());
+	      struct_pdi->name = objfile->intern (actual_class_name.get ());
 	    }
 	  break;
 	}
@@ -18361,7 +18354,7 @@ partial_die_info::fixup (struct dwarf2_cu *cu)
 	    base = demangled.get ();
 
 	  struct objfile *objfile = cu->per_cu->dwarf2_per_objfile->objfile;
-	  name = obstack_strdup (&objfile->per_bfd->storage_obstack, base);
+	  name = objfile->intern (base);
 	}
     }
 
@@ -21678,7 +21671,7 @@ sibling_die (struct die_info *die)
 
 static const char *
 dwarf2_canonicalize_name (const char *name, struct dwarf2_cu *cu,
-			  struct obstack *obstack)
+			  struct objfile *objfile)
 {
   if (name && cu->language == language_cplus)
     {
@@ -21687,7 +21680,7 @@ dwarf2_canonicalize_name (const char *name, struct dwarf2_cu *cu,
       if (!canon_name.empty ())
 	{
 	  if (canon_name != name)
-	    name = obstack_strdup (obstack, canon_name);
+	    name = objfile->intern (canon_name);
 	}
     }
 
@@ -21761,10 +21754,7 @@ dwarf2_name (struct die_info *die, struct dwarf2_cu *cu)
 
 	      const char *base;
 
-	      /* FIXME: we already did this for the partial symbol... */
-	      DW_STRING (attr)
-		= obstack_strdup (&objfile->per_bfd->storage_obstack,
-				  demangled.get ());
+	      DW_STRING (attr) = objfile->intern (demangled.get ());
 	      DW_STRING_IS_CANONICAL (attr) = 1;
 
 	      /* Strip any leading namespaces/classes, keep only the base name.
@@ -21784,9 +21774,8 @@ dwarf2_name (struct die_info *die, struct dwarf2_cu *cu)
 
   if (!DW_STRING_IS_CANONICAL (attr))
     {
-      DW_STRING (attr)
-	= dwarf2_canonicalize_name (DW_STRING (attr), cu,
-				    &objfile->per_bfd->storage_obstack);
+      DW_STRING (attr) = dwarf2_canonicalize_name (DW_STRING (attr), cu,
+						   objfile);
       DW_STRING_IS_CANONICAL (attr) = 1;
     }
   return DW_STRING (attr);
diff --git a/gdb/elfread.c b/gdb/elfread.c
index 453bca527e9..710ecbf6e17 100644
--- a/gdb/elfread.c
+++ b/gdb/elfread.c
@@ -353,11 +353,7 @@ elf_symtab_read (minimal_symbol_reader &reader,
       if (type == ST_DYNAMIC && !stripped)
 	continue;
       if (sym->flags & BSF_FILE)
-	{
-	  filesymname
-	    = ((const char *) objfile->per_bfd->filename_cache.insert
-	       (sym->name, strlen (sym->name) + 1));
-	}
+	filesymname = objfile->intern (sym->name);
       else if (sym->flags & BSF_SECTION_SYM)
 	continue;
       else if (sym->flags & (BSF_GLOBAL | BSF_LOCAL | BSF_WEAK
diff --git a/gdb/objfiles.h b/gdb/objfiles.h
index b71a8a9edb8..a568fa4bcda 100644
--- a/gdb/objfiles.h
+++ b/gdb/objfiles.h
@@ -275,13 +275,9 @@ struct objfile_per_bfd_storage
 
   auto_obstack storage_obstack;
 
-  /* Byte cache for file names.  */
+  /* String cache.  */
 
-  gdb::bcache filename_cache;
-
-  /* Byte cache for macros.  */
-
-  gdb::bcache macro_cache;
+  gdb::bcache string_cache;
 
   /* The gdbarch associated with the BFD.  Note that this gdbarch is
      determined solely from BFD information, without looking at target
@@ -533,6 +529,22 @@ public:
     return section_offsets[SECT_OFF_DATA (this)];
   }
 
+  /* Intern STRING and return the unique copy.  The copy has the same
+     lifetime as the per-BFD object.  */
+  const char *intern (const char *str)
+  {
+    return (const char *) per_bfd->string_cache.insert (str, strlen (str) + 1);
+  }
+
+  /* Intern STRING and return the unique copy.  The copy has the same
+     lifetime as the per-BFD object.  */
+  const char *intern (const std::string &str)
+  {
+    return (const char *) per_bfd->string_cache.insert (str.c_str (),
+							str.size () + 1);
+  }
+
+
   /* The object file's original name as specified by the user,
      made absolute, and tilde-expanded.  However, it is not canonicalized
      (i.e., it has not been passed through gdb_realpath).
diff --git a/gdb/psymtab.c b/gdb/psymtab.c
index fd7fc8feff2..69176dbee47 100644
--- a/gdb/psymtab.c
+++ b/gdb/psymtab.c
@@ -1656,9 +1656,7 @@ partial_symtab::partial_symtab (const char *filename_, struct objfile *objfile)
 {
   objfile->partial_symtabs->install_psymtab (this);
 
-  filename
-    = ((const char *) objfile->per_bfd->filename_cache.insert
-       (filename_, strlen (filename_) + 1));
+  filename = objfile->intern (filename_);
 
   if (symtab_create_debug)
     {
diff --git a/gdb/symfile.c b/gdb/symfile.c
index f7bada75f35..dc423f0344a 100644
--- a/gdb/symfile.c
+++ b/gdb/symfile.c
@@ -2778,9 +2778,7 @@ allocate_symtab (struct compunit_symtab *cust, const char *filename)
   struct symtab *symtab
     = OBSTACK_ZALLOC (&objfile->objfile_obstack, struct symtab);
 
-  symtab->filename
-    = ((const char *) objfile->per_bfd->filename_cache.insert
-       (filename, strlen (filename) + 1));
+  symtab->filename = objfile->intern (filename);
   symtab->fullname = NULL;
   symtab->language = deduce_language_from_filename (filename);
 
diff --git a/gdb/symmisc.c b/gdb/symmisc.c
index a6a7e728c4a..1d7c3816670 100644
--- a/gdb/symmisc.c
+++ b/gdb/symmisc.c
@@ -71,9 +71,7 @@ print_symbol_bcache_statistics (void)
 			 objfile_name (objfile));
 	objfile->partial_symtabs->psymbol_cache.print_statistics
 	  ("partial symbol cache");
-	objfile->per_bfd->macro_cache.print_statistics
-	  ("preprocessor macro cache");
-	objfile->per_bfd->filename_cache.print_statistics ("file name cache");
+	objfile->per_bfd->string_cache.print_statistics ("string cache");
       }
 }
 
@@ -135,10 +133,8 @@ print_objfile_statistics (void)
       printf_filtered
 	(_("  Total memory used for psymbol cache: %d\n"),
 	 objfile->partial_symtabs->psymbol_cache.memory_used ());
-      printf_filtered (_("  Total memory used for macro cache: %d\n"),
-		       objfile->per_bfd->macro_cache.memory_used ());
-      printf_filtered (_("  Total memory used for file name cache: %d\n"),
-		       objfile->per_bfd->filename_cache.memory_used ());
+      printf_filtered (_("  Total memory used for string cache: %d\n"),
+		       objfile->per_bfd->string_cache.memory_used ());
     }
 }
 
-- 
2.17.2

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: [PATCH] Introduce objfile::intern
  2020-02-24  2:58 [PATCH] Introduce objfile::intern Tom Tromey
@ 2020-03-04 23:47 ` Tom Tromey
  2020-03-05  9:10   ` [committed][gdb/testsuite] Update maint.exp for string cache Tom de Vries
  0 siblings, 1 reply; 3+ messages in thread
From: Tom Tromey @ 2020-03-04 23:47 UTC (permalink / raw)
  To: Tom Tromey; +Cc: gdb-patches

>>>>> "Tom" == Tom Tromey <tom@tromey.com> writes:

Tom> This introduces a string cache on the per-BFD object, replacing the
Tom> macro and filename caches.  Both of these caches just store strings,
Tom> so this consolidation by itself saves a little memory (about the size
Tom> of a bcache per objfile).

I'm checking this in now.

Tom

^ permalink raw reply	[flat|nested] 3+ messages in thread

* [committed][gdb/testsuite] Update maint.exp for string cache
  2020-03-04 23:47 ` Tom Tromey
@ 2020-03-05  9:10   ` Tom de Vries
  0 siblings, 0 replies; 3+ messages in thread
From: Tom de Vries @ 2020-03-05  9:10 UTC (permalink / raw)
  To: Tom Tromey; +Cc: gdb-patches

[-- Attachment #1: Type: text/plain, Size: 529 bytes --]

[ was: Re: [PATCH] Introduce objfile::intern ]
On 05-03-2020 00:47, Tom Tromey wrote:
>>>>>> "Tom" == Tom Tromey <tom@tromey.com> writes:
> 
> Tom> This introduces a string cache on the per-BFD object, replacing the
> Tom> macro and filename caches.  Both of these caches just store strings,
> Tom> so this consolidation by itself saves a little memory (about the size
> Tom> of a bcache per objfile).
> 
> I'm checking this in now.

This caused a regression in gdb.base/maint.exp, fixed by committed patch
below.

Thanks,
- Tom

[-- Attachment #2: 0001-gdb-testsuite-Update-maint.exp-for-string-cache.patch --]
[-- Type: text/x-patch, Size: 2482 bytes --]

[gdb/testsuite] Update maint.exp for string cache

When running gdb.base/maint.exp, I see:
...
FAIL: gdb.base/maint.exp: maint print statistics
...

This is due to commit be1e3d3eab "Introduce objfile::intern", which replaces
the macro and filename caches with a string cache.

Update maint.exp accordingly.

Tested on x86_64-linux.

gdb/testsuite/ChangeLog:

2020-03-05  Tom de Vries  <tdevries@suse.de>

	* gdb.base/maint.exp: Update "main print statistics" expected output.

---
 gdb/testsuite/gdb.base/maint.exp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/gdb/testsuite/gdb.base/maint.exp b/gdb/testsuite/gdb.base/maint.exp
index fe25e0fc61..f6eeb98a20 100644
--- a/gdb/testsuite/gdb.base/maint.exp
+++ b/gdb/testsuite/gdb.base/maint.exp
@@ -200,7 +200,7 @@ if [istarget "*-*-cygwin*"] {
 
 send_gdb "maint print statistics\n"
 gdb_expect  {
-    -re "Statistics for\[^\n\r\]*maint\[^\n\r\]*:\r\n  Number of \"minimal\" symbols read: $decimal\r\n(  Number of \"partial\" symbols read: $decimal\r\n)?  Number of \"full\" symbols read: $decimal\r\n  Number of \"types\" defined: $decimal\r\n(  Number of psym tables \\(not yet expanded\\): $decimal\r\n)?(  Number of read CUs: $decimal\r\n  Number of unread CUs: $decimal\r\n)?  Number of symbol tables: $decimal\r\n  Number of symbol tables with line tables: $decimal\r\n  Number of symbol tables with blockvectors: $decimal\r\n  Total memory used for objfile obstack: $decimal\r\n  Total memory used for BFD obstack: $decimal\r\n  Total memory used for psymbol cache: $decimal\r\n  Total memory used for macro cache: $decimal\r\n  Total memory used for file name cache: $decimal\r\n" {
+    -re "Statistics for\[^\n\r\]*maint\[^\n\r\]*:\r\n  Number of \"minimal\" symbols read: $decimal\r\n(  Number of \"partial\" symbols read: $decimal\r\n)?  Number of \"full\" symbols read: $decimal\r\n  Number of \"types\" defined: $decimal\r\n(  Number of psym tables \\(not yet expanded\\): $decimal\r\n)?(  Number of read CUs: $decimal\r\n  Number of unread CUs: $decimal\r\n)?  Number of symbol tables: $decimal\r\n  Number of symbol tables with line tables: $decimal\r\n  Number of symbol tables with blockvectors: $decimal\r\n  Total memory used for objfile obstack: $decimal\r\n  Total memory used for BFD obstack: $decimal\r\n  Total memory used for psymbol cache: $decimal\r\n  Total memory used for string cache: $decimal\r\n" {
 	gdb_expect {
 	    -re "$gdb_prompt $" {
 		pass "maint print statistics"

^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2020-03-05  9:10 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-02-24  2:58 [PATCH] Introduce objfile::intern Tom Tromey
2020-03-04 23:47 ` Tom Tromey
2020-03-05  9:10   ` [committed][gdb/testsuite] Update maint.exp for string cache Tom de Vries

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).