Introduce objfile::intern
authorTom Tromey <tom@tromey.com>
Wed, 4 Mar 2020 23:34:49 +0000 (16:34 -0700)
committerTom Tromey <tom@tromey.com>
Wed, 4 Mar 2020 23:34:49 +0000 (16:34 -0700)
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-03-04  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
gdb/buildsym.c
gdb/dwarf2/read.c
gdb/elfread.c
gdb/objfiles.h
gdb/psymtab.c
gdb/symfile.c
gdb/symmisc.c

index a8c0027001e6d50a93d50d802d6b67babcf06c57..22e500c1b3cfbec68450bdf38fc22bccfa98bc5b 100644 (file)
@@ -1,3 +1,26 @@
+2020-03-04  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.
+
 2020-03-04  Tom Tromey  <tom@tromey.com>
 
        * jit.c (bfd_open_from_target_memory): Make "target" const.
index 4965b552b32ffe52fd469dd179a3a1ab92aad3f5..84cb44277a4a4a9984cefcd6386d0fc9218eb4f8 100644 (file)
@@ -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;
 }
index 07cee58c1f013e4e196abd6143652d986597cdf6..3556908cf5a48330d94e611c24b9296e2f7a38b5 100644 (file)
@@ -1447,7 +1447,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 *);
 
@@ -9098,8 +9098,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;
@@ -10225,14 +10224,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;
        }
@@ -10352,7 +10350,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;
 }
@@ -11678,8 +11676,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;
@@ -11874,8 +11871,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,
@@ -17993,8 +17989,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;
            }
@@ -18319,9 +18314,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;
        }
@@ -18401,7 +18394,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);
        }
     }
 
@@ -21714,7 +21707,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)
     {
@@ -21723,7 +21716,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);
        }
     }
 
@@ -21797,10 +21790,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.
@@ -21820,9 +21810,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);
index d842d5b573dd5ed67634d8545f3bcf92002fc905..42c4e77785f36f5c6aa1ec118dc1e45298a30da5 100644 (file)
@@ -355,11 +355,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
index b71a8a9edb8e199ec4492a790b49165bf99b0383..a568fa4bcdac82cdaf7415755b7ecbca6a3bcbf1 100644 (file)
@@ -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).
index fd7fc8feff2a436b19e7ea4a62f7ffc4f62bbc51..69176dbee47b4013095f60e5502d6eb4a974555d 100644 (file)
@@ -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)
     {
index 01c3f5af126e55b436cb83463ff8d87be5bdaf79..3b63887ce1bda3e3df08936a9eefe2912af0c26f 100644 (file)
@@ -2783,9 +2783,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);
 
index a6a7e728c4a0c16b72894762b9e3fc182cba5a12..1d7c3816670b3dfe15c7a448dca952254913b513 100644 (file)
@@ -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 ());
     }
 }