/* Routines for name->symbol lookups in GDB.
- Copyright (C) 2003-2019 Free Software Foundation, Inc.
+ Copyright (C) 2003-2020 Free Software Foundation, Inc.
Contributed by David Carlton <carlton@bactrian.org> and by Kealia,
Inc.
#include "dictionary.h"
#include "safe-ctype.h"
#include <unordered_map>
+#include "language.h"
/* This file implements dictionaries, which are tables that associate
symbols to names. They are represented by an opaque type 'struct
static void expand_hashtable (struct dictionary *dict);
-/* A function to convert a linked list into a vector. */
-
-static std::vector<symbol *>
-pending_to_vector (const struct pending *symbol_list)
-{
- std::vector<symbol *> symlist;
-
- for (const struct pending *list_counter = symbol_list;
- list_counter != nullptr; list_counter = list_counter->next)
- {
- for (int i = list_counter->nsyms - 1; i >= 0; --i)
- symlist.push_back (list_counter->symbol[i]);
- }
-
- return symlist;
-}
-
/* The creation functions. */
-/* A function to transition dict_create_hashed to new API. */
+/* Create a hashed dictionary of a given language. */
static struct dictionary *
-dict_create_hashed_1 (struct obstack *obstack,
- enum language language,
- const std::vector<symbol *> &symbol_list)
+dict_create_hashed (struct obstack *obstack,
+ enum language language,
+ const std::vector<symbol *> &symbol_list)
{
/* Allocate the dictionary. */
struct dictionary *retval = XOBNEW (obstack, struct dictionary);
return retval;
}
-/* See dictionary.h. */
-
-struct dictionary *
-dict_create_hashed (struct obstack *obstack,
- enum language language,
- const struct pending *symbol_list)
-{
- std::vector<symbol *> symlist = pending_to_vector (symbol_list);
-
- return dict_create_hashed_1 (obstack, language, symlist);
-}
-
-/* See dictionary.h. */
+/* Create an expandable hashed dictionary of a given language. */
-extern struct dictionary *
+static struct dictionary *
dict_create_hashed_expandable (enum language language)
{
struct dictionary *retval = XNEW (struct dictionary);
return retval;
}
-/* A function to transition dict_create_linear to new API. */
+/* Create a linear dictionary of a given language. */
static struct dictionary *
-dict_create_linear_1 (struct obstack *obstack,
- enum language language,
- const std::vector<symbol *> &symbol_list)
+dict_create_linear (struct obstack *obstack,
+ enum language language,
+ const std::vector<symbol *> &symbol_list)
{
struct dictionary *retval = XOBNEW (obstack, struct dictionary);
DICT_VECTOR (retval) = &dict_linear_vector;
return retval;
}
-/* See dictionary.h. */
+/* Create an expandable linear dictionary of a given language. */
-struct dictionary *
-dict_create_linear (struct obstack *obstack,
- enum language language,
- const struct pending *symbol_list)
-{
- std::vector<symbol *> symlist = pending_to_vector (symbol_list);
-
- return dict_create_linear_1 (obstack, language, symlist);
-}
-
-/* See dictionary.h. */
-
-struct dictionary *
+static struct dictionary *
dict_create_linear_expandable (enum language language)
{
struct dictionary *retval = XNEW (struct dictionary);
/* Free the memory used by a dictionary that's not on an obstack. (If
any.) */
-void
+static void
dict_free (struct dictionary *dict)
{
(DICT_VECTOR (dict))->free (dict);
/* Add SYM to DICT. DICT had better be expandable. */
-void
+static void
dict_add_symbol (struct dictionary *dict, struct symbol *sym)
{
(DICT_VECTOR (dict))->add_symbol (dict, sym);
}
-/* A function to transition dict_add_pending to new API. */
+/* Utility to add a list of symbols to a dictionary.
+ DICT must be an expandable dictionary. */
static void
-dict_add_pending_1 (struct dictionary *dict,
- const std::vector<symbol *> &symbol_list)
+dict_add_pending (struct dictionary *dict,
+ const std::vector<symbol *> &symbol_list)
{
/* Preserve ordering by reversing the list. */
for (auto sym = symbol_list.rbegin (); sym != symbol_list.rend (); ++sym)
dict_add_symbol (dict, *sym);
}
-/* Utility to add a list of symbols to a dictionary.
- DICT must be an expandable dictionary. */
-
-void
-dict_add_pending (struct dictionary *dict, const struct pending *symbol_list)
-{
- std::vector<symbol *> symlist = pending_to_vector (symbol_list);
-
- dict_add_pending_1 (dict, symlist);
-}
-
/* Initialize ITERATOR to point at the first symbol in DICT, and
return that first symbol, or NULL if DICT is empty. */
-struct symbol *
+static struct symbol *
dict_iterator_first (const struct dictionary *dict,
struct dict_iterator *iterator)
{
/* Advance ITERATOR, and return the next symbol, or NULL if there are
no more symbols. */
-struct symbol *
+static struct symbol *
dict_iterator_next (struct dict_iterator *iterator)
{
return (DICT_VECTOR (DICT_ITERATOR_DICT (iterator)))
->iterator_next (iterator);
}
-struct symbol *
+static struct symbol *
dict_iter_match_first (const struct dictionary *dict,
const lookup_name_info &name,
struct dict_iterator *iterator)
return (DICT_VECTOR (dict))->iter_match_first (dict, name, iterator);
}
-struct symbol *
+static struct symbol *
dict_iter_match_next (const lookup_name_info &name,
struct dict_iterator *iterator)
{
->iter_match_next (name, iterator);
}
-int
+static int
dict_size (const struct dictionary *dict)
{
return (DICT_VECTOR (dict))->size (dict);
implemented generically by means of the vtable. Typically, they're
rarely used. */
-/* Test to see if DICT is empty. */
-
-int
-dict_empty (struct dictionary *dict)
-{
- struct dict_iterator iter;
-
- return (dict_iterator_first (dict, &iter) == NULL);
-}
-
/* The functions implementing the dictionary interface. */
sym = sym->hash_next)
{
/* Warning: the order of arguments to compare matters! */
- if (matches_name (SYMBOL_SEARCH_NAME (sym), name, NULL))
+ if (matches_name (sym->search_name (), name, NULL))
break;
}
next != NULL;
next = next->hash_next)
{
- if (matches_name (SYMBOL_SEARCH_NAME (next), name, NULL))
+ if (matches_name (next->search_name (), name, NULL))
break;
}
/* We don't want to insert a symbol into a dictionary of a different
language. The two may not use the same hashing algorithm. */
- gdb_assert (SYMBOL_LANGUAGE (sym) == DICT_LANGUAGE (dict)->la_language);
+ gdb_assert (sym->language () == DICT_LANGUAGE (dict)->la_language);
- hash = search_name_hash (SYMBOL_LANGUAGE (sym), SYMBOL_SEARCH_NAME (sym));
+ hash = search_name_hash (sym->language (), sym->search_name ());
hash_index = hash % DICT_HASHED_NBUCKETS (dict);
sym->hash_next = buckets[hash_index];
buckets[hash_index] = sym;
{
sym = DICT_LINEAR_SYM (dict, i);
- if (matches_name (SYMBOL_SEARCH_NAME (sym), name, NULL))
+ if (matches_name (sym->search_name (), name, NULL))
{
retval = sym;
break;
{
std::unordered_map<enum language, std::vector<symbol *>> nsyms;
- for (const struct pending *list_counter = symbol_list;
+ for (const pending *list_counter = symbol_list;
list_counter != nullptr; list_counter = list_counter->next)
{
for (int i = list_counter->nsyms - 1; i >= 0; --i)
{
- enum language language = SYMBOL_LANGUAGE (list_counter->symbol[i]);
+ enum language language = list_counter->symbol[i]->language ();
nsyms[language].push_back (list_counter->symbol[i]);
}
}
std::vector<symbol *> symlist = pair.second;
retval->dictionaries[idx++]
- = dict_create_hashed_1 (obstack, language, symlist);
+ = dict_create_hashed (obstack, language, symlist);
}
return retval;
std::vector<symbol *> symlist = pair.second;
retval->dictionaries[idx++]
- = dict_create_linear_1 (obstack, language, symlist);
+ = dict_create_linear (obstack, language, symlist);
}
return retval;
mdict_add_symbol (struct multidictionary *mdict, struct symbol *sym)
{
struct dictionary *dict
- = find_language_dictionary (mdict, SYMBOL_LANGUAGE (sym));
+ = find_language_dictionary (mdict, sym->language ());
if (dict == nullptr)
{
/* SYM is of a new language that we haven't previously seen.
Create a new dictionary for it. */
- dict = create_new_language_dictionary (mdict, SYMBOL_LANGUAGE (sym));
+ dict = create_new_language_dictionary (mdict, sym->language ());
}
dict_add_symbol (dict, sym);
dict = create_new_language_dictionary (mdict, language);
}
- dict_add_pending_1 (dict, symlist);
+ dict_add_pending (dict, symlist);
}
}
return size;
}
-
-/* See dictionary.h. */
-
-bool
-mdict_empty (const struct multidictionary *mdict)
-{
- for (unsigned short idx = 0; idx < mdict->n_allocated_dictionaries; ++idx)
- {
- if (!dict_empty (mdict->dictionaries[idx]))
- return false;
- }
-
- return true;
-}