Commit 7fcb9343 by Nathan Sidwell

c++: Expr pack expansion equality [pr94454]

We were not comparing expression pack expansions correctly. We could
consider distinct expansions equal and creating two, apparently equal,
specializations that would sometimes collide.  cp_tree_operand_length
says a pack has 1 operand (for mangling), whereas it actually has 3,
but only two of which are significant for equality.  We must special
case that in cp_tree_equal.  That new code matches the hasher and the
type_pack_expansion case in structural_comp_types.

	* tree.c (cp_tree_equal): [TEMPLATE_ID_EXPR, default] Refactor.
	[EXPR_PACK_EXPANSION]: Add.
parent aa576f2a
2020-04-20 Nathan Sidwell <nathan@acm.org> 2020-04-20 Nathan Sidwell <nathan@acm.org>
PR 94454 - Expr pack expansion equality
* tree.c (cp_tree_equal): [TEMPLATE_ID_EXPR, default] Refactor.
[EXPR_PACK_EXPANSION]: Add.
PR c++/94454 Template Argument Hashing PR c++/94454 Template Argument Hashing
* pt.c (iterative_hash_template_arg): Strip nodes as * pt.c (iterative_hash_template_arg): Strip nodes as
template_args_equal does. template_args_equal does.
......
...@@ -3771,8 +3771,11 @@ cp_tree_equal (tree t1, tree t2) ...@@ -3771,8 +3771,11 @@ cp_tree_equal (tree t1, tree t2)
TREE_TYPE (TEMPLATE_PARM_DECL (t2)))); TREE_TYPE (TEMPLATE_PARM_DECL (t2))));
case TEMPLATE_ID_EXPR: case TEMPLATE_ID_EXPR:
return (cp_tree_equal (TREE_OPERAND (t1, 0), TREE_OPERAND (t2, 0)) if (!cp_tree_equal (TREE_OPERAND (t1, 0), TREE_OPERAND (t2, 0)))
&& cp_tree_equal (TREE_OPERAND (t1, 1), TREE_OPERAND (t2, 1))); return false;
if (!comp_template_args (TREE_OPERAND (t1, 1), TREE_OPERAND (t2, 1)))
return false;
return true;
case CONSTRAINT_INFO: case CONSTRAINT_INFO:
return cp_tree_equal (CI_ASSOCIATED_CONSTRAINTS (t1), return cp_tree_equal (CI_ASSOCIATED_CONSTRAINTS (t1),
...@@ -3902,6 +3905,15 @@ cp_tree_equal (tree t1, tree t2) ...@@ -3902,6 +3905,15 @@ cp_tree_equal (tree t1, tree t2)
return true; return true;
} }
case EXPR_PACK_EXPANSION:
if (!cp_tree_equal (PACK_EXPANSION_PATTERN (t1),
PACK_EXPANSION_PATTERN (t2)))
return false;
if (!comp_template_args (PACK_EXPANSION_EXTRA_ARGS (t1),
PACK_EXPANSION_EXTRA_ARGS (t2)))
return false;
return true;
default: default:
break; break;
} }
...@@ -3916,14 +3928,12 @@ cp_tree_equal (tree t1, tree t2) ...@@ -3916,14 +3928,12 @@ cp_tree_equal (tree t1, tree t2)
case tcc_reference: case tcc_reference:
case tcc_statement: case tcc_statement:
{ {
int i, n; int n = cp_tree_operand_length (t1);
n = cp_tree_operand_length (t1);
if (TREE_CODE_CLASS (code1) == tcc_vl_exp if (TREE_CODE_CLASS (code1) == tcc_vl_exp
&& n != TREE_OPERAND_LENGTH (t2)) && n != TREE_OPERAND_LENGTH (t2))
return false; return false;
for (i = 0; i < n; ++i) for (int i = 0; i < n; ++i)
if (!cp_tree_equal (TREE_OPERAND (t1, i), TREE_OPERAND (t2, i))) if (!cp_tree_equal (TREE_OPERAND (t1, i), TREE_OPERAND (t2, i)))
return false; return false;
...@@ -3932,9 +3942,11 @@ cp_tree_equal (tree t1, tree t2) ...@@ -3932,9 +3942,11 @@ cp_tree_equal (tree t1, tree t2)
case tcc_type: case tcc_type:
return same_type_p (t1, t2); return same_type_p (t1, t2);
default: default:
gcc_unreachable (); gcc_unreachable ();
} }
/* We can get here with --disable-checking. */ /* We can get here with --disable-checking. */
return false; return false;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment