aboutsummaryrefslogtreecommitdiff
path: root/gdb/cp-support.c
diff options
context:
space:
mode:
authorKeith Seitz <keiths@redhat.com>2014-04-14 15:47:15 -0700
committerKeith Seitz <keiths@redhat.com>2014-04-14 15:47:15 -0700
commitb50c861487bb7d71185777193a9246bac81e4f26 (patch)
tree858f9f12feaafb9ca1aa0e467b9d1149b7f60e9b /gdb/cp-support.c
parent3d567982aca11c85a7fa31f13046de3271d3afc8 (diff)
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/cp-support.c')
-rw-r--r--gdb/cp-support.c25
1 files changed, 24 insertions, 1 deletions
diff --git a/gdb/cp-support.c b/gdb/cp-support.c
index 2379b54c2b..91533e8e4e 100644
--- a/gdb/cp-support.c
+++ b/gdb/cp-support.c
@@ -35,6 +35,7 @@
#include "expression.h"
#include "value.h"
#include "cp-abi.h"
+#include "language.h"
#include "safe-ctype.h"
@@ -177,7 +178,29 @@ inspect_type (struct demangle_parse_info *info,
sym = NULL;
TRY_CATCH (except, RETURN_MASK_ALL)
{
- sym = lookup_symbol (name, 0, VAR_DOMAIN, 0);
+ /* It is not legal to have a typedef and tag name of the same
+ name in C++. However, anonymous composite types that are defined
+ with a typedef ["typedef struct {...} anonymous_struct;"] WILL
+ have symbols for a TYPE_CODE_TYPEDEF (in VAR_DOMAIN) and a
+ TYPE_CODE_STRUCT (in STRUCT_DOMAIN).
+
+ If VAR_DOMAIN is searched first, it will return the TYPEDEF symbol,
+ and this function will never output the definition of the typedef,
+ since type_print is called below with SHOW = -1. [The typedef hash
+ is never initialized/used when SHOW <= 0 -- and the finder
+ (find_typedef_for_canonicalize) will always return NULL as a result.]
+
+ Consequently, type_print will eventually keep calling this function
+ to replace the typedef (via
+ print_name_maybe_canonical/cp_canonicalize_full). This leads to
+ infinite recursion.
+
+ This can all be safely avoid by explicitly searching STRUCT_DOMAIN
+ first to find the structure definition. */
+ if (current_language->la_language == language_cplus)
+ sym = lookup_symbol (name, 0, STRUCT_DOMAIN, 0);
+ if (sym == NULL)
+ sym = lookup_symbol (name, 0, VAR_DOMAIN, NULL);
}
if (except.reason >= 0 && sym != NULL)