aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTom Tromey <tom@tromey.com>2019-03-07 04:20:19 -0700
committerTom Tromey <tom@tromey.com>2019-03-07 10:48:02 -0700
commit25629dfdb438c82f2bb711174042bb326a526aaf (patch)
treef0bd8f98faa31b5124de5963abe119507a095622
parentfe7266674110f34eacf2e9d2b308f76d33ce50ed (diff)
downloadgdb-25629dfdb438c82f2bb711174042bb326a526aaf.zip
gdb-25629dfdb438c82f2bb711174042bb326a526aaf.tar.gz
gdb-25629dfdb438c82f2bb711174042bb326a526aaf.tar.bz2
C++-ify bcache
This somewhat C++-ifies bcache. It replaces bcache_xmalloc and bcache_xfree with constructors; changes some functions into methods; and changes various structures to include a bcache directly (as opposed to a pointer to a bcache). Tested by the buildbot. gdb/ChangeLog 2019-03-07 Tom Tromey <tom@tromey.com> * symmisc.c (print_symbol_bcache_statistics): Update. (print_objfile_statistics): Update. * symfile.c (allocate_symtab): Update. * stabsread.c: Don't include bcache.h. * psymtab.h (struct psymbol_bcache): Don't declare. (class psymtab_storage) <psymbol_cache>: Now a bcache. (psymbol_bcache_init, psymbol_bcache_free) (psymbol_bcache_get_bcache): Don't declare. * psymtab.c (struct psymbol_bcache): Remove. (psymtab_storage::psymtab_storage): Update. (psymtab_storage::~psymtab_storage): Update. (psymbol_bcache_init, psymbol_bcache_free) (psymbol_bcache_get_bcache, psymbol_bcache_full): Remove. (add_psymbol_to_bcache): Update. (allocate_psymtab): Update. * objfiles.h (struct objfile_per_bfd_storage) <filename_cache, macro_cache>: No longer pointers. * objfiles.c (get_objfile_bfd_data): Don't call bcache_xmalloc. (free_objfile_per_bfd_storage): Don't call bcache_xfree. * macrotab.c (macro_bcache): Update. * macroexp.c: Don't include bcache.h. * gdbtypes.c (check_types_worklist): Update. (types_deeply_equal): Remove TRY/CATCH. Update. * elfread.c (elf_symtab_read): Update. * dwarf2read.c: Don't include bcache.h. * buildsym.c (buildsym_compunit::get_macro_table): Update. * bcache.h (bcache, bcache_full, bcache_xffree, bcache_xmalloc) (print_bcache_statistics, bcache_memory_used): Don't declare. (struct bcache): Move from bcache.c. Add constructor, destructor, methods. Rename all data members. * bcache.c (struct bcache): Move to bcache.h. (bcache::expand_hash_table): Rename from expand_hash_table. (bcache): Remove. (bcache::insert): Rename from bcache_full. (bcache::compare): Rename from bcache_compare. (bcache_xmalloc): Remove. (bcache::~bcache): Rename from bcache_xfree. (bcache::print_statistics): Rename from print_bcache_statistics. (bcache::memory_used): Rename from bcache_memory_used.
-rw-r--r--gdb/ChangeLog42
-rw-r--r--gdb/bcache.c238
-rw-r--r--gdb/bcache.h112
-rw-r--r--gdb/buildsym.c2
-rw-r--r--gdb/dwarf2read.c1
-rw-r--r--gdb/elfread.c4
-rw-r--r--gdb/gdbtypes.c31
-rw-r--r--gdb/macroexp.c1
-rw-r--r--gdb/macrotab.c2
-rw-r--r--gdb/objfiles.c4
-rw-r--r--gdb/objfiles.h4
-rw-r--r--gdb/psymtab.c68
-rw-r--r--gdb/psymtab.h11
-rw-r--r--gdb/stabsread.c1
-rw-r--r--gdb/symfile.c4
-rw-r--r--gdb/symmisc.c19
16 files changed, 228 insertions, 316 deletions
diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index 5614e78..de5e74a 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,45 @@
+2019-03-07 Tom Tromey <tom@tromey.com>
+
+ * symmisc.c (print_symbol_bcache_statistics): Update.
+ (print_objfile_statistics): Update.
+ * symfile.c (allocate_symtab): Update.
+ * stabsread.c: Don't include bcache.h.
+ * psymtab.h (struct psymbol_bcache): Don't declare.
+ (class psymtab_storage) <psymbol_cache>: Now a bcache.
+ (psymbol_bcache_init, psymbol_bcache_free)
+ (psymbol_bcache_get_bcache): Don't declare.
+ * psymtab.c (struct psymbol_bcache): Remove.
+ (psymtab_storage::psymtab_storage): Update.
+ (psymtab_storage::~psymtab_storage): Update.
+ (psymbol_bcache_init, psymbol_bcache_free)
+ (psymbol_bcache_get_bcache, psymbol_bcache_full): Remove.
+ (add_psymbol_to_bcache): Update.
+ (allocate_psymtab): Update.
+ * objfiles.h (struct objfile_per_bfd_storage) <filename_cache,
+ macro_cache>: No longer pointers.
+ * objfiles.c (get_objfile_bfd_data): Don't call bcache_xmalloc.
+ (free_objfile_per_bfd_storage): Don't call bcache_xfree.
+ * macrotab.c (macro_bcache): Update.
+ * macroexp.c: Don't include bcache.h.
+ * gdbtypes.c (check_types_worklist): Update.
+ (types_deeply_equal): Remove TRY/CATCH. Update.
+ * elfread.c (elf_symtab_read): Update.
+ * dwarf2read.c: Don't include bcache.h.
+ * buildsym.c (buildsym_compunit::get_macro_table): Update.
+ * bcache.h (bcache, bcache_full, bcache_xffree, bcache_xmalloc)
+ (print_bcache_statistics, bcache_memory_used): Don't declare.
+ (struct bcache): Move from bcache.c. Add constructor, destructor,
+ methods. Rename all data members.
+ * bcache.c (struct bcache): Move to bcache.h.
+ (bcache::expand_hash_table): Rename from expand_hash_table.
+ (bcache): Remove.
+ (bcache::insert): Rename from bcache_full.
+ (bcache::compare): Rename from bcache_compare.
+ (bcache_xmalloc): Remove.
+ (bcache::~bcache): Rename from bcache_xfree.
+ (bcache::print_statistics): Rename from print_bcache_statistics.
+ (bcache::memory_used): Rename from bcache_memory_used.
+
2019-03-07 Pedro Alves <palves@redhat.com>
* infrun.c (normal_stop): Also check for
diff --git a/gdb/bcache.c b/gdb/bcache.c
index 1430953..14a7847 100644
--- a/gdb/bcache.c
+++ b/gdb/bcache.c
@@ -49,48 +49,6 @@ struct bstring
d;
};
-
-/* The structure for a bcache itself. The bcache is initialized, in
- bcache_xmalloc(), by filling it with zeros and then setting the
- corresponding obstack's malloc() and free() methods. */
-
-struct bcache
-{
- /* All the bstrings are allocated here. */
- struct obstack cache;
-
- /* How many hash buckets we're using. */
- unsigned int num_buckets;
-
- /* Hash buckets. This table is allocated using malloc, so when we
- grow the table we can return the old table to the system. */
- struct bstring **bucket;
-
- /* Statistics. */
- unsigned long unique_count; /* number of unique strings */
- long total_count; /* total number of strings cached, including dups */
- long unique_size; /* size of unique strings, in bytes */
- long total_size; /* total number of bytes cached, including dups */
- long structure_size; /* total size of bcache, including infrastructure */
- /* Number of times that the hash table is expanded and hence
- re-built, and the corresponding number of times that a string is
- [re]hashed as part of entering it into the expanded table. The
- total number of hashes can be computed by adding TOTAL_COUNT to
- expand_hash_count. */
- unsigned long expand_count;
- unsigned long expand_hash_count;
- /* Number of times that the half-hash compare hit (compare the upper
- 16 bits of hash values) hit, but the corresponding combined
- length/data compare missed. */
- unsigned long half_hash_miss_count;
-
- /* Hash function to be used for this bcache object. */
- unsigned long (*hash_function)(const void *addr, int length);
-
- /* Compare function to be used for this bcache object. */
- int (*compare_function)(const void *, const void *, int length);
-};
-
/* The old hash function was stolen from SDBM. This is what DB 3.0
uses now, and is better than the old one. */
@@ -123,8 +81,8 @@ hash_continue (const void *addr, int length, unsigned long h)
resize our hash table. */
#define CHAIN_LENGTH_THRESHOLD (5)
-static void
-expand_hash_table (struct bcache *bcache)
+void
+bcache::expand_hash_table ()
{
/* A table of good hash table sizes. Whenever we grow, we pick the
next larger size from this table. sizes[i] is close to 1 << (i+10),
@@ -143,13 +101,13 @@ expand_hash_table (struct bcache *bcache)
/* Count the stats. Every unique item needs to be re-hashed and
re-entered. */
- bcache->expand_count++;
- bcache->expand_hash_count += bcache->unique_count;
+ m_expand_count++;
+ m_expand_hash_count += m_unique_count;
/* Find the next size. */
- new_num_buckets = bcache->num_buckets * 2;
+ new_num_buckets = m_num_buckets * 2;
for (i = 0; i < (sizeof (sizes) / sizeof (sizes[0])); i++)
- if (sizes[i] > bcache->num_buckets)
+ if (sizes[i] > m_num_buckets)
{
new_num_buckets = sizes[i];
break;
@@ -162,23 +120,21 @@ expand_hash_table (struct bcache *bcache)
new_buckets = (struct bstring **) xmalloc (new_size);
memset (new_buckets, 0, new_size);
- bcache->structure_size -= (bcache->num_buckets
- * sizeof (bcache->bucket[0]));
- bcache->structure_size += new_size;
+ m_structure_size -= m_num_buckets * sizeof (m_bucket[0]);
+ m_structure_size += new_size;
}
/* Rehash all existing strings. */
- for (i = 0; i < bcache->num_buckets; i++)
+ for (i = 0; i < m_num_buckets; i++)
{
struct bstring *s, *next;
- for (s = bcache->bucket[i]; s; s = next)
+ for (s = m_bucket[i]; s; s = next)
{
struct bstring **new_bucket;
next = s->next;
- new_bucket = &new_buckets[(bcache->hash_function (&s->d.data,
- s->length)
+ new_bucket = &new_buckets[(m_hash_function (&s->d.data, s->length)
% new_num_buckets)];
s->next = *new_bucket;
*new_bucket = s;
@@ -186,10 +142,9 @@ expand_hash_table (struct bcache *bcache)
}
/* Plug in the new table. */
- if (bcache->bucket)
- xfree (bcache->bucket);
- bcache->bucket = new_buckets;
- bcache->num_buckets = new_num_buckets;
+ xfree (m_bucket);
+ m_bucket = new_buckets;
+ m_num_buckets = new_num_buckets;
}
@@ -201,21 +156,12 @@ expand_hash_table (struct bcache *bcache)
/* Find a copy of the LENGTH bytes at ADDR in BCACHE. If BCACHE has
never seen those bytes before, add a copy of them to BCACHE. In
- either case, return a pointer to BCACHE's copy of that string. */
-const void *
-bcache (const void *addr, int length, struct bcache *cache)
-{
- return bcache_full (addr, length, cache, NULL);
-}
-
-/* Find a copy of the LENGTH bytes at ADDR in BCACHE. If BCACHE has
- never seen those bytes before, add a copy of them to BCACHE. In
either case, return a pointer to BCACHE's copy of that string. If
optional ADDED is not NULL, return 1 in case of new entry or 0 if
returning an old entry. */
const void *
-bcache_full (const void *addr, int length, struct bcache *bcache, int *added)
+bcache::insert (const void *addr, int length, int *added)
{
unsigned long full_hash;
unsigned short half_hash;
@@ -227,56 +173,56 @@ bcache_full (const void *addr, int length, struct bcache *bcache, int *added)
/* Lazily initialize the obstack. This can save quite a bit of
memory in some cases. */
- if (bcache->total_count == 0)
+ if (m_total_count == 0)
{
/* We could use obstack_specify_allocation here instead, but
gdb_obstack.h specifies the allocation/deallocation
functions. */
- obstack_init (&bcache->cache);
+ obstack_init (&m_cache);
}
/* If our average chain length is too high, expand the hash table. */
- if (bcache->unique_count >= bcache->num_buckets * CHAIN_LENGTH_THRESHOLD)
- expand_hash_table (bcache);
+ if (m_unique_count >= m_num_buckets * CHAIN_LENGTH_THRESHOLD)
+ expand_hash_table ();
- bcache->total_count++;
- bcache->total_size += length;
+ m_total_count++;
+ m_total_size += length;
- full_hash = bcache->hash_function (addr, length);
+ full_hash = m_hash_function (addr, length);
half_hash = (full_hash >> 16);
- hash_index = full_hash % bcache->num_buckets;
+ hash_index = full_hash % m_num_buckets;
- /* Search the hash bucket for a string identical to the caller's.
+ /* Search the hash m_bucket for a string identical to the caller's.
As a short-circuit first compare the upper part of each hash
values. */
- for (s = bcache->bucket[hash_index]; s; s = s->next)
+ for (s = m_bucket[hash_index]; s; s = s->next)
{
if (s->half_hash == half_hash)
{
if (s->length == length
- && bcache->compare_function (&s->d.data, addr, length))
+ && m_compare_function (&s->d.data, addr, length))
return &s->d.data;
else
- bcache->half_hash_miss_count++;
+ m_half_hash_miss_count++;
}
}
/* The user's string isn't in the list. Insert it after *ps. */
{
struct bstring *newobj
- = (struct bstring *) obstack_alloc (&bcache->cache,
+ = (struct bstring *) obstack_alloc (&m_cache,
BSTRING_SIZE (length));
memcpy (&newobj->d.data, addr, length);
newobj->length = length;
- newobj->next = bcache->bucket[hash_index];
+ newobj->next = m_bucket[hash_index];
newobj->half_hash = half_hash;
- bcache->bucket[hash_index] = newobj;
+ m_bucket[hash_index] = newobj;
- bcache->unique_count++;
- bcache->unique_size += length;
- bcache->structure_size += BSTRING_SIZE (length);
+ m_unique_count++;
+ m_unique_size += length;
+ m_structure_size += BSTRING_SIZE (length);
if (added)
*added = 1;
@@ -289,51 +235,19 @@ bcache_full (const void *addr, int length, struct bcache *bcache, int *added)
/* Compare the byte string at ADDR1 of lenght LENGHT to the
string at ADDR2. Return 1 if they are equal. */
-static int
-bcache_compare (const void *addr1, const void *addr2, int length)
+int
+bcache::compare (const void *addr1, const void *addr2, int length)
{
return memcmp (addr1, addr2, length) == 0;
}
-/* Allocating and freeing bcaches. */
-
-/* Allocated a bcache. HASH_FUNCTION and COMPARE_FUNCTION can be used
- to pass in custom hash, and compare functions to be used by this
- bcache. If HASH_FUNCTION is NULL hash() is used and if
- COMPARE_FUNCTION is NULL memcmp() is used. */
-
-struct bcache *
-bcache_xmalloc (unsigned long (*hash_function)(const void *, int length),
- int (*compare_function)(const void *,
- const void *,
- int length))
-{
- /* Allocate the bcache pre-zeroed. */
- struct bcache *b = XCNEW (struct bcache);
-
- if (hash_function)
- b->hash_function = hash_function;
- else
- b->hash_function = hash;
-
- if (compare_function)
- b->compare_function = compare_function;
- else
- b->compare_function = bcache_compare;
- return b;
-}
-
/* Free all the storage associated with BCACHE. */
-void
-bcache_xfree (struct bcache *bcache)
+bcache::~bcache ()
{
- if (bcache == NULL)
- return;
/* Only free the obstack if we actually initialized it. */
- if (bcache->total_count > 0)
- obstack_free (&bcache->cache, 0);
- xfree (bcache->bucket);
- xfree (bcache);
+ if (m_total_count > 0)
+ obstack_free (&m_cache, 0);
+ xfree (m_bucket);
}
@@ -356,7 +270,7 @@ print_percentage (int portion, int total)
BCACHE holds. Statistics are printed using `printf_filtered' and
its ilk. */
void
-print_bcache_statistics (struct bcache *c, const char *type)
+bcache::print_statistics (const char *type)
{
int occupied_buckets;
int max_chain_length;
@@ -368,15 +282,15 @@ print_bcache_statistics (struct bcache *c, const char *type)
lengths, and measure chain lengths. */
{
unsigned int b;
- int *chain_length = XCNEWVEC (int, c->num_buckets + 1);
- int *entry_size = XCNEWVEC (int, c->unique_count + 1);
+ int *chain_length = XCNEWVEC (int, m_num_buckets + 1);
+ int *entry_size = XCNEWVEC (int, m_unique_count + 1);
int stringi = 0;
occupied_buckets = 0;
- for (b = 0; b < c->num_buckets; b++)
+ for (b = 0; b < m_num_buckets; b++)
{
- struct bstring *s = c->bucket[b];
+ struct bstring *s = m_bucket[b];
chain_length[b] = 0;
@@ -386,9 +300,9 @@ print_bcache_statistics (struct bcache *c, const char *type)
while (s)
{
- gdb_assert (b < c->num_buckets);
+ gdb_assert (b < m_num_buckets);
chain_length[b]++;
- gdb_assert (stringi < c->unique_count);
+ gdb_assert (stringi < m_unique_count);
entry_size[stringi++] = s->length;
s = s->next;
}
@@ -397,25 +311,25 @@ print_bcache_statistics (struct bcache *c, const char *type)
/* To compute the median, we need the set of chain lengths
sorted. */
- qsort (chain_length, c->num_buckets, sizeof (chain_length[0]),
+ qsort (chain_length, m_num_buckets, sizeof (chain_length[0]),
compare_positive_ints);
- qsort (entry_size, c->unique_count, sizeof (entry_size[0]),
+ qsort (entry_size, m_unique_count, sizeof (entry_size[0]),
compare_positive_ints);
- if (c->num_buckets > 0)
+ if (m_num_buckets > 0)
{
- max_chain_length = chain_length[c->num_buckets - 1];
- median_chain_length = chain_length[c->num_buckets / 2];
+ max_chain_length = chain_length[m_num_buckets - 1];
+ median_chain_length = chain_length[m_num_buckets / 2];
}
else
{
max_chain_length = 0;
median_chain_length = 0;
}
- if (c->unique_count > 0)
+ if (m_unique_count > 0)
{
- max_entry_size = entry_size[c->unique_count - 1];
- median_entry_size = entry_size[c->unique_count / 2];
+ max_entry_size = entry_size[m_unique_count - 1];
+ median_entry_size = entry_size[m_unique_count / 2];
}
else
{
@@ -427,23 +341,23 @@ print_bcache_statistics (struct bcache *c, const char *type)
xfree (entry_size);
}
- printf_filtered (_(" Cached '%s' statistics:\n"), type);
- printf_filtered (_(" Total object count: %ld\n"), c->total_count);
- printf_filtered (_(" Unique object count: %lu\n"), c->unique_count);
+ printf_filtered (_(" M_Cached '%s' statistics:\n"), type);
+ printf_filtered (_(" Total object count: %ld\n"), m_total_count);
+ printf_filtered (_(" Unique object count: %lu\n"), m_unique_count);
printf_filtered (_(" Percentage of duplicates, by count: "));
- print_percentage (c->total_count - c->unique_count, c->total_count);
+ print_percentage (m_total_count - m_unique_count, m_total_count);
printf_filtered ("\n");
- printf_filtered (_(" Total object size: %ld\n"), c->total_size);
- printf_filtered (_(" Unique object size: %ld\n"), c->unique_size);
+ printf_filtered (_(" Total object size: %ld\n"), m_total_size);
+ printf_filtered (_(" Unique object size: %ld\n"), m_unique_size);
printf_filtered (_(" Percentage of duplicates, by size: "));
- print_percentage (c->total_size - c->unique_size, c->total_size);
+ print_percentage (m_total_size - m_unique_size, m_total_size);
printf_filtered ("\n");
printf_filtered (_(" Max entry size: %d\n"), max_entry_size);
printf_filtered (_(" Average entry size: "));
- if (c->unique_count > 0)
- printf_filtered ("%ld\n", c->unique_size / c->unique_count);
+ if (m_unique_count > 0)
+ printf_filtered ("%ld\n", m_unique_size / m_unique_count);
else
/* i18n: "Average entry size: (not applicable)". */
printf_filtered (_("(not applicable)\n"));
@@ -452,28 +366,28 @@ print_bcache_statistics (struct bcache *c, const char *type)
printf_filtered (_(" \
Total memory used by bcache, including overhead: %ld\n"),
- c->structure_size);
+ m_structure_size);
printf_filtered (_(" Percentage memory overhead: "));
- print_percentage (c->structure_size - c->unique_size, c->unique_size);
+ print_percentage (m_structure_size - m_unique_size, m_unique_size);
printf_filtered (_(" Net memory savings: "));
- print_percentage (c->total_size - c->structure_size, c->total_size);
+ print_percentage (m_total_size - m_structure_size, m_total_size);
printf_filtered ("\n");
printf_filtered (_(" Hash table size: %3d\n"),
- c->num_buckets);
+ m_num_buckets);
printf_filtered (_(" Hash table expands: %lu\n"),
- c->expand_count);
+ m_expand_count);
printf_filtered (_(" Hash table hashes: %lu\n"),
- c->total_count + c->expand_hash_count);
+ m_total_count + m_expand_hash_count);
printf_filtered (_(" Half hash misses: %lu\n"),
- c->half_hash_miss_count);
+ m_half_hash_miss_count);
printf_filtered (_(" Hash table population: "));
- print_percentage (occupied_buckets, c->num_buckets);
+ print_percentage (occupied_buckets, m_num_buckets);
printf_filtered (_(" Median hash chain length: %3d\n"),
median_chain_length);
printf_filtered (_(" Average hash chain length: "));
- if (c->num_buckets > 0)
- printf_filtered ("%3lu\n", c->unique_count / c->num_buckets);
+ if (m_num_buckets > 0)
+ printf_filtered ("%3lu\n", m_unique_count / m_num_buckets);
else
/* i18n: "Average hash chain length: (not applicable)". */
printf_filtered (_("(not applicable)\n"));
@@ -483,9 +397,9 @@ Total memory used by bcache, including overhead: %ld\n"),
}
int
-bcache_memory_used (struct bcache *bcache)
+bcache::memory_used ()
{
- if (bcache->total_count == 0)
+ if (m_total_count == 0)
return 0;
- return obstack_memory_used (&bcache->cache);
+ return obstack_memory_used (&m_cache);
}
diff --git a/gdb/bcache.h b/gdb/bcache.h
index aa014792..15dcc63 100644
--- a/gdb/bcache.h
+++ b/gdb/bcache.h
@@ -136,41 +136,89 @@
*/
-
-struct bcache;
-
-/* Find a copy of the LENGTH bytes at ADDR in BCACHE. If BCACHE has
- never seen those bytes before, add a copy of them to BCACHE. In
- either case, return a pointer to BCACHE's copy of that string.
- Since the cached value is ment to be read-only, return a const
- buffer. */
-extern const void *bcache (const void *addr, int length,
- struct bcache *bcache);
-
-/* Like bcache, but if ADDED is not NULL, set *ADDED to true if the
- bytes were newly added to the cache, or to false if the bytes were
- found in the cache. */
-extern const void *bcache_full (const void *addr, int length,
- struct bcache *bcache, int *added);
-
-/* Free all the storage used by BCACHE. */
-extern void bcache_xfree (struct bcache *bcache);
-
-/* Create a new bcache object. */
-extern struct bcache *bcache_xmalloc (
- unsigned long (*hash_function)(const void *, int length),
- int (*compare_function)(const void *, const void *, int length));
-
-/* Print statistics on BCACHE's memory usage and efficacity at
- eliminating duplication. TYPE should be a string describing the
- kind of data BCACHE holds. Statistics are printed using
- `printf_filtered' and its ilk. */
-extern void print_bcache_statistics (struct bcache *bcache, const char *type);
-extern int bcache_memory_used (struct bcache *bcache);
+struct bstring;
/* The hash functions */
-extern unsigned long hash(const void *addr, int length);
+extern unsigned long hash (const void *addr, int length);
extern unsigned long hash_continue (const void *addr, int length,
unsigned long h);
+struct bcache
+{
+ /* Allocate a bcache. HASH_FN and COMPARE_FN can be used to pass in
+ custom hash, and compare functions to be used by this bcache. If
+ HASH_FUNCTION is NULL hash() is used and if COMPARE_FUNCTION is
+ NULL memcmp() is used. */
+
+ explicit bcache (unsigned long (*hash_fn)(const void *,
+ int length) = nullptr,
+ int (*compare_fn)(const void *, const void *,
+ int length) = nullptr)
+ : m_hash_function (hash_fn == nullptr ? hash : hash_fn),
+ m_compare_function (compare_fn == nullptr ? compare : compare_fn)
+ {
+ }
+
+ ~bcache ();
+
+ /* Find a copy of the LENGTH bytes at ADDR in BCACHE. If BCACHE has
+ never seen those bytes before, add a copy of them to BCACHE. In
+ either case, return a pointer to BCACHE's copy of that string.
+ Since the cached value is ment to be read-only, return a const
+ buffer. If ADDED is not NULL, set *ADDED to true if the bytes
+ were newly added to the cache, or to false if the bytes were
+ found in the cache. */
+
+ const void *insert (const void *addr, int length, int *added = nullptr);
+
+ /* Print statistics on this bcache's memory usage and efficacity at
+ eliminating duplication. TYPE should be a string describing the
+ kind of data this bcache holds. Statistics are printed using
+ `printf_filtered' and its ilk. */
+ void print_statistics (const char *type);
+ int memory_used ();
+
+private:
+
+ /* All the bstrings are allocated here. */
+ struct obstack m_cache {};
+
+ /* How many hash buckets we're using. */
+ unsigned int m_num_buckets = 0;
+
+ /* Hash buckets. This table is allocated using malloc, so when we
+ grow the table we can return the old table to the system. */
+ struct bstring **m_bucket = nullptr;
+
+ /* Statistics. */
+ unsigned long m_unique_count = 0; /* number of unique strings */
+ long m_total_count = 0; /* total number of strings cached, including dups */
+ long m_unique_size = 0; /* size of unique strings, in bytes */
+ long m_total_size = 0; /* total number of bytes cached, including dups */
+ long m_structure_size = 0; /* total size of bcache, including infrastructure */
+ /* Number of times that the hash table is expanded and hence
+ re-built, and the corresponding number of times that a string is
+ [re]hashed as part of entering it into the expanded table. The
+ total number of hashes can be computed by adding TOTAL_COUNT to
+ expand_hash_count. */
+ unsigned long m_expand_count = 0;
+ unsigned long m_expand_hash_count = 0;
+ /* Number of times that the half-hash compare hit (compare the upper
+ 16 bits of hash values) hit, but the corresponding combined
+ length/data compare missed. */
+ unsigned long m_half_hash_miss_count = 0;
+
+ /* Hash function to be used for this bcache object. */
+ unsigned long (*m_hash_function)(const void *addr, int length);
+
+ /* Compare function to be used for this bcache object. */
+ int (*m_compare_function)(const void *, const void *, int length);
+
+ /* Default compare function. */
+ static int compare (const void *addr1, const void *addr2, int length);
+
+ /* Expand the hash table. */
+ void expand_hash_table ();
+};
+
#endif /* BCACHE_H */
diff --git a/gdb/buildsym.c b/gdb/buildsym.c
index bd0f25e..9a23c8f 100644
--- a/gdb/buildsym.c
+++ b/gdb/buildsym.c
@@ -122,7 +122,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->macro_cache,
m_compunit_symtab);
return m_pending_macros;
}
diff --git a/gdb/dwarf2read.c b/gdb/dwarf2read.c
index 2d6cb35..0c59dcd 100644
--- a/gdb/dwarf2read.c
+++ b/gdb/dwarf2read.c
@@ -46,7 +46,6 @@
#include "macrotab.h"
#include "language.h"
#include "complaints.h"
-#include "bcache.h"
#include "dwarf2expr.h"
#include "dwarf2loc.h"
#include "cp-support.h"
diff --git a/gdb/elfread.c b/gdb/elfread.c
index 8fc6692..55a16bb 100644
--- a/gdb/elfread.c
+++ b/gdb/elfread.c
@@ -334,8 +334,8 @@ elf_symtab_read (minimal_symbol_reader &reader,
if (sym->flags & BSF_FILE)
{
filesymname
- = (const char *) bcache (sym->name, strlen (sym->name) + 1,
- objfile->per_bfd->filename_cache);
+ = ((const char *) objfile->per_bfd->filename_cache.insert
+ (sym->name, strlen (sym->name) + 1));
}
else if (sym->flags & BSF_SECTION_SYM)
continue;
diff --git a/gdb/gdbtypes.c b/gdb/gdbtypes.c
index b5f2692..8e48587 100644
--- a/gdb/gdbtypes.c
+++ b/gdb/gdbtypes.c
@@ -3732,7 +3732,7 @@ check_types_worklist (std::vector<type_equality_entry> *worklist,
/* If the type pair has already been visited, we know it is
ok. */
- bcache_full (&entry, sizeof (entry), cache, &added);
+ cache->insert (&entry, sizeof (entry), &added);
if (!added)
continue;
@@ -3749,9 +3749,6 @@ check_types_worklist (std::vector<type_equality_entry> *worklist,
bool
types_deeply_equal (struct type *type1, struct type *type2)
{
- struct gdb_exception except = exception_none;
- bool result = false;
- struct bcache *cache;
std::vector<type_equality_entry> worklist;
gdb_assert (type1 != NULL && type2 != NULL);
@@ -3760,31 +3757,9 @@ types_deeply_equal (struct type *type1, struct type *type2)
if (type1 == type2)
return true;
- cache = bcache_xmalloc (NULL, NULL);
-
+ struct bcache cache (nullptr, nullptr);
worklist.emplace_back (type1, type2);
-
- /* check_types_worklist calls several nested helper functions, some
- of which can raise a GDB exception, so we just check and rethrow
- here. If there is a GDB exception, a comparison is not capable
- (or trusted), so exit. */
- TRY
- {
- result = check_types_worklist (&worklist, cache);
- }
- CATCH (ex, RETURN_MASK_ALL)
- {
- except = ex;
- }
- END_CATCH
-
- bcache_xfree (cache);
-
- /* Rethrow if there was a problem. */
- if (except.reason < 0)
- throw_exception (except);
-
- return result;
+ return check_types_worklist (&worklist, &cache);
}
/* Allocated status of type TYPE. Return zero if type TYPE is allocated.
diff --git a/gdb/macroexp.c b/gdb/macroexp.c
index a588cc8..33a72a7 100644
--- a/gdb/macroexp.c
+++ b/gdb/macroexp.c
@@ -19,7 +19,6 @@
#include "defs.h"
#include "gdb_obstack.h"
-#include "bcache.h"
#include "macrotab.h"
#include "macroexp.h"
#include "c-lang.h"
diff --git a/gdb/macrotab.c b/gdb/macrotab.c
index fa30616..90f2943 100644
--- a/gdb/macrotab.c
+++ b/gdb/macrotab.c
@@ -113,7 +113,7 @@ static const void *
macro_bcache (struct macro_table *t, const void *addr, int len)
{
if (t->bcache)
- return bcache (addr, len, t->bcache);
+ return t->bcache->insert (addr, len);
else
{
void *copy = xmalloc (len);
diff --git a/gdb/objfiles.c b/gdb/objfiles.c
index 34b271e..4091b42 100644
--- a/gdb/objfiles.c
+++ b/gdb/objfiles.c
@@ -157,8 +157,6 @@ get_objfile_bfd_data (struct objfile *objfile, struct bfd *abfd)
if (abfd != NULL)
storage->gdbarch = gdbarch_from_bfd (abfd);
- storage->filename_cache = bcache_xmalloc (NULL, NULL);
- storage->macro_cache = bcache_xmalloc (NULL, NULL);
storage->language_of_main = language_unknown;
}
@@ -170,8 +168,6 @@ get_objfile_bfd_data (struct objfile *objfile, struct bfd *abfd)
static void
free_objfile_per_bfd_storage (struct objfile_per_bfd_storage *storage)
{
- bcache_xfree (storage->filename_cache);
- bcache_xfree (storage->macro_cache);
if (storage->demangled_names_hash)
htab_delete (storage->demangled_names_hash);
storage->~objfile_per_bfd_storage ();
diff --git a/gdb/objfiles.h b/gdb/objfiles.h
index a10781f..c5ce9ee 100644
--- a/gdb/objfiles.h
+++ b/gdb/objfiles.h
@@ -240,11 +240,11 @@ struct objfile_per_bfd_storage
/* Byte cache for file names. */
- struct bcache *filename_cache = NULL;
+ struct bcache filename_cache;
/* Byte cache for macros. */
- struct bcache *macro_cache = NULL;
+ struct bcache macro_cache;
/* The gdbarch associated with the BFD. Note that this gdbarch is
determined solely from BFD information, without looking at target
diff --git a/gdb/psymtab.c b/gdb/psymtab.c
index 17db297..96b4fa0 100644
--- a/gdb/psymtab.c
+++ b/gdb/psymtab.c
@@ -26,7 +26,6 @@
#include "source.h"
#include "addrmap.h"
#include "gdbtypes.h"
-#include "bcache.h"
#include "ui-out.h"
#include "command.h"
#include "readline/readline.h"
@@ -38,11 +37,6 @@
#include <algorithm>
#include <set>
-struct psymbol_bcache
-{
- struct bcache *bcache;
-};
-
static struct partial_symbol *match_partial_symbol (struct objfile *,
struct partial_symtab *,
int,
@@ -67,14 +61,16 @@ static struct compunit_symtab *psymtab_to_symtab (struct objfile *objfile,
+static unsigned long psymbol_hash (const void *addr, int length);
+static int psymbol_compare (const void *addr1, const void *addr2, int length);
+
psymtab_storage::psymtab_storage ()
- : psymbol_cache (psymbol_bcache_init ())
+ : psymbol_cache (psymbol_hash, psymbol_compare)
{
}
psymtab_storage::~psymtab_storage ()
{
- psymbol_bcache_free (psymbol_cache);
}
/* See psymtab.h. */
@@ -1589,52 +1585,6 @@ psymbol_compare (const void *addr1, const void *addr2, int length)
&& sym1->name == sym2->name);
}
-/* Initialize a partial symbol bcache. */
-
-struct psymbol_bcache *
-psymbol_bcache_init (void)
-{
- struct psymbol_bcache *bcache = XCNEW (struct psymbol_bcache);
-
- bcache->bcache = bcache_xmalloc (psymbol_hash, psymbol_compare);
- return bcache;
-}
-
-/* Free a partial symbol bcache. */
-
-void
-psymbol_bcache_free (struct psymbol_bcache *bcache)
-{
- if (bcache == NULL)
- return;
-
- bcache_xfree (bcache->bcache);
- xfree (bcache);
-}
-
-/* Return the internal bcache of the psymbol_bcache BCACHE. */
-
-struct bcache *
-psymbol_bcache_get_bcache (struct psymbol_bcache *bcache)
-{
- return bcache->bcache;
-}
-
-/* Find a copy of the SYM in BCACHE. If BCACHE has never seen this
- symbol before, add a copy to BCACHE. In either case, return a pointer
- to BCACHE's copy of the symbol. If optional ADDED is not NULL, return
- 1 in case of new entry or 0 if returning an old entry. */
-
-static struct partial_symbol *
-psymbol_bcache_full (struct partial_symbol *sym,
- struct psymbol_bcache *bcache,
- int *added)
-{
- return ((struct partial_symbol *)
- bcache_full (sym, sizeof (struct partial_symbol), bcache->bcache,
- added));
-}
-
/* Helper function, initialises partial symbol structure and stashes
it into objfile's bcache. Note that our caching mechanism will
use all fields of struct partial_symbol to determine hash value of the
@@ -1664,9 +1614,9 @@ add_psymbol_to_bcache (const char *name, int namelength, int copy_name,
symbol_set_names (&psymbol, name, namelength, copy_name, objfile->per_bfd);
/* Stash the partial symbol away in the cache. */
- return psymbol_bcache_full (&psymbol,
- objfile->partial_symtabs->psymbol_cache,
- added);
+ return ((struct partial_symbol *)
+ objfile->partial_symtabs->psymbol_cache.insert
+ (&psymbol, sizeof (struct partial_symbol), added));
}
/* Helper function, adds partial symbol to the given partial symbol list. */
@@ -1741,8 +1691,8 @@ allocate_psymtab (const char *filename, struct objfile *objfile)
= objfile->partial_symtabs->allocate_psymtab ();
psymtab->filename
- = (const char *) bcache (filename, strlen (filename) + 1,
- objfile->per_bfd->filename_cache);
+ = ((const char *) objfile->per_bfd->filename_cache.insert
+ (filename, strlen (filename) + 1));
psymtab->compunit_symtab = NULL;
if (symtab_create_debug)
diff --git a/gdb/psymtab.h b/gdb/psymtab.h
index 3ee5eee..c761fa7 100644
--- a/gdb/psymtab.h
+++ b/gdb/psymtab.h
@@ -23,13 +23,10 @@
#include "gdb_obstack.h"
#include "symfile.h"
#include "common/next-iterator.h"
+#include "bcache.h"
struct partial_symbol;
-/* A bcache for partial symbols. */
-
-struct psymbol_bcache;
-
/* An instance of this class manages the partial symbol tables and
partial symbols for a given objfile.
@@ -119,7 +116,7 @@ public:
/* A byte cache where we can stash arbitrary "chunks" of bytes that
will not change. */
- struct psymbol_bcache *psymbol_cache;
+ struct bcache psymbol_cache;
/* Vectors of all partial symbols read in from file. The actual data
is stored in the objfile_obstack. */
@@ -140,10 +137,6 @@ private:
};
-extern struct psymbol_bcache *psymbol_bcache_init (void);
-extern void psymbol_bcache_free (struct psymbol_bcache *);
-extern struct bcache *psymbol_bcache_get_bcache (struct psymbol_bcache *);
-
extern const struct quick_symbol_functions psym_functions;
extern const struct quick_symbol_functions dwarf2_gdb_index_functions;
diff --git a/gdb/stabsread.c b/gdb/stabsread.c
index ac33465..3f340db 100644
--- a/gdb/stabsread.c
+++ b/gdb/stabsread.c
@@ -44,7 +44,6 @@
#include "target-float.h"
#include "cp-abi.h"
#include "cp-support.h"
-#include "bcache.h"
#include <ctype.h>
#include "stabsread.h"
diff --git a/gdb/symfile.c b/gdb/symfile.c
index 6148382..2214f16 100644
--- a/gdb/symfile.c
+++ b/gdb/symfile.c
@@ -2795,8 +2795,8 @@ allocate_symtab (struct compunit_symtab *cust, const char *filename)
= OBSTACK_ZALLOC (&objfile->objfile_obstack, struct symtab);
symtab->filename
- = (const char *) bcache (filename, strlen (filename) + 1,
- objfile->per_bfd->filename_cache);
+ = ((const char *) objfile->per_bfd->filename_cache.insert
+ (filename, strlen (filename) + 1));
symtab->fullname = NULL;
symtab->language = deduce_language_from_filename (filename);
diff --git a/gdb/symmisc.c b/gdb/symmisc.c
index bb4fdfd..cb0b5a5 100644
--- a/gdb/symmisc.c
+++ b/gdb/symmisc.c
@@ -69,13 +69,11 @@ print_symbol_bcache_statistics (void)
QUIT;
printf_filtered (_("Byte cache statistics for '%s':\n"),
objfile_name (objfile));
- print_bcache_statistics
- (psymbol_bcache_get_bcache (objfile->partial_symtabs->psymbol_cache),
- "partial symbol cache");
- print_bcache_statistics (objfile->per_bfd->macro_cache,
- "preprocessor macro cache");
- print_bcache_statistics (objfile->per_bfd->filename_cache,
- "file name cache");
+ 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");
}
}
@@ -136,12 +134,11 @@ print_objfile_statistics (void)
->storage_obstack)));
printf_filtered
(_(" Total memory used for psymbol cache: %d\n"),
- bcache_memory_used (psymbol_bcache_get_bcache
- (objfile->partial_symtabs->psymbol_cache)));
+ objfile->partial_symtabs->psymbol_cache.memory_used ());
printf_filtered (_(" Total memory used for macro cache: %d\n"),
- bcache_memory_used (objfile->per_bfd->macro_cache));
+ objfile->per_bfd->macro_cache.memory_used ());
printf_filtered (_(" Total memory used for file name cache: %d\n"),
- bcache_memory_used (objfile->per_bfd->filename_cache));
+ objfile->per_bfd->filename_cache.memory_used ());
}
}