diff options
author | Keith Seitz <keiths@redhat.com> | 2014-04-14 15:47:15 -0700 |
---|---|---|
committer | Keith Seitz <keiths@redhat.com> | 2014-04-14 15:47:15 -0700 |
commit | b50c861487bb7d71185777193a9246bac81e4f26 (patch) | |
tree | 858f9f12feaafb9ca1aa0e467b9d1149b7f60e9b /gdb/symtab.c | |
parent | 3d567982aca11c85a7fa31f13046de3271d3afc8 (diff) | |
download | gdb-b50c861487bb7d71185777193a9246bac81e4f26.zip gdb-b50c861487bb7d71185777193a9246bac81e4f26.tar.gz gdb-b50c861487bb7d71185777193a9246bac81e4f26.tar.bz2 |
Remove symbol_matches_domain. This fixes
PR c++/16253.
symbol_matches_domain was permitting searches for a VAR_DOMAIN
symbol to also match STRUCT_DOMAIN symbols for languages like C++
where STRUCT_DOMAIN symbols also define a typedef of the same name,
e.g., "struct foo {}" introduces a typedef of the name "foo".
Problems occur if there exists both a VAR_DOMAIN and STRUCT_DOMAIN
symbol of the same name. Then it is essentially a race between which
symbol is found first. The other symbol is obscurred.
[This is a relatively common idiom: enum e { ... } e;]
This patchset moves this "language defines a typedef" logic to
lookup_symbol[_in_language], looking first for a symbol in the given
domain and falling back to searching STRUCT_DOMAIN when/if appropriate.
2014-04-14 Keith Seitz <keiths@redhat.com>
PR c++/16253
* ada-lang.c (ada_symbol_matches_domain): Moved here and renamed
from symbol_matches_domain in symtab.c. All local callers
of symbol_matches_domain updated.
(standard_lookup): If DOMAIN is VAR_DOMAIN and no symbol is found,
search STRUCT_DOMAIN.
(ada_find_any_type_symbol): Do not search STRUCT_DOMAIN
independently. standard_lookup will do that automatically.
* cp-namespace.c (cp_lookup_symbol_nonlocal): Explain when/why
VAR_DOMAIN searches may return a STRUCT_DOMAIN match.
(cp_lookup_symbol_in_namespace): Likewise.
If no VAR_DOMAIN symbol is found, search STRUCT_DOMAIN.
(cp_lookup_symbol_exports): Explain when/why VAR_DOMAIN searches
may return a STRUCT_DOMAIN match.
(lookup_symbol_file): Search for the class name in STRUCT_DOMAIN.
* cp-support.c: Include language.h.
(inspect_type): Explicitly search STRUCT_DOMAIN before searching
VAR_DOMAIN.
* psymtab.c (match_partial_symbol): Compare the requested
domain with the symbol's domain directly.
(lookup_partial_symbol): Likewise.
* symtab.c (lookup_symbol_in_language): Explain when/why
VAR_DOMAIN searches may return a STRUCT_DOMAIN match.
If no VAR_DOMAIN symbol is found, search STRUCT_DOMAIN for
appropriate languages.
(symbol_matches_domain): Renamed `ada_symbol_matches_domain'
and moved to ada-lang.c
(lookup_block_symbol): Explain that this function only returns
symbol matching the requested DOMAIN.
Compare the requested domain with the symbol's domain directly.
(iterate_over_symbols): Compare the requested domain with the
symbol's domain directly.
* symtab.h (symbol_matches_domain): Remove.
2014-04-14 Keith Seitz <keiths@redhat.com>
PR c++/16253
* gdb.cp/var-tag.cc: New file.
* gdb.cp/var-tag.exp: New file.
* gdb.dwarf2/dw2-ada-ffffffff.exp: Set the language to C++.
* gdb.dwarf2/dw2-anon-mptr.exp: Likewise.
* gdb.dwarf2/dw2-double-set-die-type.exp: Likewise.
* gdb.dwarf2/dw2-inheritance.exp: Likewise.
Diffstat (limited to 'gdb/symtab.c')
-rw-r--r-- | gdb/symtab.c | 60 |
1 files changed, 31 insertions, 29 deletions
diff --git a/gdb/symtab.c b/gdb/symtab.c index 66d1624..15ac3d1 100644 --- a/gdb/symtab.c +++ b/gdb/symtab.c @@ -1310,7 +1310,11 @@ demangle_for_lookup (const char *name, enum language lang, NAME is a field of the current implied argument `this'. If so set *IS_A_FIELD_OF_THIS to 1, otherwise set it to zero. BLOCK_FOUND is set to the block in which NAME is found (in the case of - a field of `this', value_of_this sets BLOCK_FOUND to the proper value.) */ + a field of `this', value_of_this sets BLOCK_FOUND to the proper value.) + + If DOMAIN is VAR_DOMAIN and the language permits using tag names for + elaborated types, such as classes in C++, this function will search + STRUCT_DOMAIN if no matching is found. */ /* This function (or rather its subordinates) have a bunch of loops and it would seem to be attractive to put in some QUIT's (though I'm not really @@ -1333,6 +1337,23 @@ lookup_symbol_in_language (const char *name, const struct block *block, returnval = lookup_symbol_aux (modified_name, block, domain, lang, is_a_field_of_this); + if (returnval == NULL) + { + if (is_a_field_of_this != NULL + && is_a_field_of_this->type != NULL) + return NULL; + + /* Some languages define typedefs of a type equal to its tag name, + e.g., in C++, "struct foo { ... }" also defines a typedef for + "foo". */ + if (domain == VAR_DOMAIN + && (lang == language_cplus || lang == language_java + || lang == language_ada || lang == language_d)) + { + returnval = lookup_symbol_aux (modified_name, block, STRUCT_DOMAIN, + lang, is_a_field_of_this); + } + } do_cleanups (cleanup); return returnval; @@ -1907,27 +1928,6 @@ lookup_symbol_global (const char *name, return lookup_data.result; } -int -symbol_matches_domain (enum language symbol_language, - domain_enum symbol_domain, - domain_enum domain) -{ - /* For C++ "struct foo { ... }" also defines a typedef for "foo". - A Java class declaration also defines a typedef for the class. - Similarly, any Ada type declaration implicitly defines a typedef. */ - if (symbol_language == language_cplus - || symbol_language == language_d - || symbol_language == language_java - || symbol_language == language_ada) - { - if ((domain == VAR_DOMAIN || domain == STRUCT_DOMAIN) - && symbol_domain == STRUCT_DOMAIN) - return 1; - } - /* For all other languages, strict match is required. */ - return (symbol_domain == domain); -} - /* Look up a type named NAME in the struct_domain. The type returned must not be opaque -- i.e., must have at least one field defined. */ @@ -2050,7 +2050,12 @@ basic_lookup_transparent_type (const char *name) binary search terminates, we drop through and do a straight linear search on the symbols. Each symbol which is marked as being a ObjC/C++ symbol (language_cplus or language_objc set) has both the encoded and - non-encoded names tested for a match. */ + non-encoded names tested for a match. + + This function specifically disallows domain mismatches. If a language + defines a typedef for an elaborated type, such as classes in C++, + then this function will need to be called twice, once to search + VAR_DOMAIN and once to search STRUCT_DOMAIN. */ struct symbol * lookup_block_symbol (const struct block *block, const char *name, @@ -2065,8 +2070,7 @@ lookup_block_symbol (const struct block *block, const char *name, sym != NULL; sym = block_iter_name_next (name, &iter)) { - if (symbol_matches_domain (SYMBOL_LANGUAGE (sym), - SYMBOL_DOMAIN (sym), domain)) + if (SYMBOL_DOMAIN (sym) == domain) return sym; } return NULL; @@ -2085,8 +2089,7 @@ lookup_block_symbol (const struct block *block, const char *name, sym != NULL; sym = block_iter_name_next (name, &iter)) { - if (symbol_matches_domain (SYMBOL_LANGUAGE (sym), - SYMBOL_DOMAIN (sym), domain)) + if (SYMBOL_DOMAIN (sym) == domain) { sym_found = sym; if (!SYMBOL_IS_ARGUMENT (sym)) @@ -2120,8 +2123,7 @@ iterate_over_symbols (const struct block *block, const char *name, sym != NULL; sym = block_iter_name_next (name, &iter)) { - if (symbol_matches_domain (SYMBOL_LANGUAGE (sym), - SYMBOL_DOMAIN (sym), domain)) + if (SYMBOL_DOMAIN (sym) == domain) { if (!callback (sym, data)) return; |