A small further tweak: let's try lookup first and when we do create a
new decl, stash it in local_specializations.
Tested x86_64-pc-linux-gnu, applying to trunk.
commit 92a208c9176551243e305e779c7aaa730cace8f5
Author: Jason Merrill <ja...@redhat.com>
Date: Tue Jun 3 10:09:23 2014 -0400
PR c++/60992
* pt.c (tsubst_copy) [VAR_DECL]: Try lookup first. Add a new
variable to local_specializations.
diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c
index d267a5c..8858908 100644
--- a/gcc/cp/pt.c
+++ b/gcc/cp/pt.c
@@ -12730,14 +12730,19 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
r = retrieve_local_specialization (t);
if (r == NULL_TREE)
{
- if (DECL_ANON_UNION_VAR_P (t))
+ /* First try name lookup to find the instantiation. */
+ r = lookup_name (DECL_NAME (t));
+ if (r)
{
- /* Just use name lookup to find a member alias for an
- anonymous union, but then add it to the hash table. */
- r = lookup_name (DECL_NAME (t));
- gcc_assert (DECL_ANON_UNION_VAR_P (r));
- register_local_specialization (r, t);
+ /* Make sure that the one we found is the one we want. */
+ tree ctx = tsubst (DECL_CONTEXT (t), args,
+ complain, in_decl);
+ if (ctx != DECL_CONTEXT (r))
+ r = NULL_TREE;
}
+
+ if (r)
+ /* OK */;
else
{
/* This can happen for a variable used in a
@@ -12771,10 +12776,12 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
else if (decl_constant_var_p (r))
/* A use of a local constant decays to its value.
FIXME update for core DR 696. */
- return integral_constant_value (r);
+ r = integral_constant_value (r);
}
- return r;
}
+ /* Remember this for subsequent uses. */
+ if (local_specializations)
+ register_local_specialization (r, t);
}
}
else