aboutsummaryrefslogtreecommitdiff
path: root/gcc/cp
diff options
context:
space:
mode:
authorJason Merrill <jason@redhat.com>2009-04-06 16:55:04 -0400
committerJason Merrill <jason@gcc.gnu.org>2009-04-06 16:55:04 -0400
commit463ecaca844a0a834d86b804fea9a8bed120678c (patch)
tree288125d2703e3ee1ec38844d785486bf035c7f63 /gcc/cp
parentb6837b94d9916498b79b854728187361dde113a0 (diff)
downloadgcc-463ecaca844a0a834d86b804fea9a8bed120678c.zip
gcc-463ecaca844a0a834d86b804fea9a8bed120678c.tar.gz
gcc-463ecaca844a0a834d86b804fea9a8bed120678c.tar.bz2
re PR c++/35146 (weird error in template function specialization)
PR c++/35146 * pt.c (fn_type_unification): For DEDUCE_EXACT check that the deduced template arguments give us the parameter types we're looking for. From-SVN: r145625
Diffstat (limited to 'gcc/cp')
-rw-r--r--gcc/cp/ChangeLog7
-rw-r--r--gcc/cp/pt.c24
2 files changed, 28 insertions, 3 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index 4086257..02440e5 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,10 @@
+2009-04-06 Jason Merrill <jason@redhat.com>
+
+ PR c++/35146
+ * pt.c (fn_type_unification): For DEDUCE_EXACT check that
+ the deduced template arguments give us the parameter types
+ we're looking for.
+
2009-04-05 Giovanni Bajo <giovannibajo@libero.it>
Jason Merrill <jason@redhat.com>
diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c
index 3e3d4f2..92815c0 100644
--- a/gcc/cp/pt.c
+++ b/gcc/cp/pt.c
@@ -12301,9 +12301,27 @@ fn_type_unification (tree fn,
the corresponding deduced argument values. If the
substitution results in an invalid type, as described above,
type deduction fails. */
- if (tsubst (TREE_TYPE (fn), targs, tf_none, NULL_TREE)
- == error_mark_node)
- return 1;
+ {
+ tree substed = tsubst (TREE_TYPE (fn), targs, tf_none, NULL_TREE);
+ if (substed == error_mark_node)
+ return 1;
+
+ /* If we're looking for an exact match, check that what we got
+ is indeed an exact match. It might not be if some template
+ parameters are used in non-deduced contexts. */
+ if (strict == DEDUCE_EXACT)
+ {
+ tree sarg
+ = skip_artificial_parms_for (fn, TYPE_ARG_TYPES (substed));
+ tree arg = args;
+ if (return_type)
+ sarg = tree_cons (NULL_TREE, TREE_TYPE (substed), sarg);
+ for (; arg && sarg;
+ arg = TREE_CHAIN (arg), sarg = TREE_CHAIN (sarg))
+ if (!same_type_p (TREE_VALUE (arg), TREE_VALUE (sarg)))
+ return 1;
+ }
+ }
return result;
}