]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
c++: only strip conversions for deduction [PR118632]
authorJason Merrill <jason@redhat.com>
Mon, 27 Jan 2025 17:04:13 +0000 (12:04 -0500)
committerJason Merrill <jason@redhat.com>
Mon, 27 Jan 2025 23:01:56 +0000 (18:01 -0500)
In r15-2761 I changed unify to always strip IMPLICIT_CONV_EXPR from PARM.
In this testcase that leads to comparing nullptr to (int*)0, and failing
because they aren't the same.  Let's only strip conversions if we're
actually going to try to deduce template arguments.

While we're at it, let's move this after the early exits.

And with this adjustment we can remove the workaround for mangle57.C.

PR c++/118632

gcc/cp/ChangeLog:

* pt.cc (unify): Only strip conversion if deducible_expression.

gcc/testsuite/ChangeLog:

* g++.dg/cpp0x/nontype7.C: New test.

gcc/cp/pt.cc
gcc/testsuite/g++.dg/cpp0x/nontype7.C [new file with mode: 0644]

index d4a6e2e0675fdd46b9661fb984523d9a7bf94945..2811afed0071c253083bf67b0b5da2f0ba21491f 100644 (file)
@@ -25099,15 +25099,6 @@ unify (tree tparms, tree targs, tree parm, tree arg, int strict,
                             ? tf_warning_or_error
                             : tf_none);
 
-  /* I don't think this will do the right thing with respect to types.
-     But the only case I've seen it in so far has been array bounds, where
-     signedness is the only information lost, and I think that will be
-     okay.  VIEW_CONVERT_EXPR can appear with class NTTP, thanks to
-     finish_id_expression_1, and are also OK.  */
-  while (CONVERT_EXPR_P (parm) || TREE_CODE (parm) == VIEW_CONVERT_EXPR
-        || TREE_CODE (parm) == IMPLICIT_CONV_EXPR)
-    parm = TREE_OPERAND (parm, 0);
-
   if (arg == error_mark_node)
     return unify_invalid (explain_p);
   if (arg == unknown_type_node
@@ -25119,11 +25110,16 @@ unify (tree tparms, tree targs, tree parm, tree arg, int strict,
   if (parm == any_targ_node || arg == any_targ_node)
     return unify_success (explain_p);
 
-  /* Stripping IMPLICIT_CONV_EXPR above can produce this mismatch
-     (g++.dg/abi/mangle57.C).  */
-  if (TREE_CODE (parm) == FUNCTION_DECL
-      && TREE_CODE (arg) == ADDR_EXPR)
-    arg = TREE_OPERAND (arg, 0);
+  /* Strip conversions that will interfere with NTTP deduction.
+     I don't think this will do the right thing with respect to types.
+     But the only case I've seen it in so far has been array bounds, where
+     signedness is the only information lost, and I think that will be
+     okay.  VIEW_CONVERT_EXPR can appear with class NTTP, thanks to
+     finish_id_expression_1, and are also OK.  */
+  if (deducible_expression (parm))
+    while (CONVERT_EXPR_P (parm) || TREE_CODE (parm) == VIEW_CONVERT_EXPR
+          || TREE_CODE (parm) == IMPLICIT_CONV_EXPR)
+      parm = TREE_OPERAND (parm, 0);
 
   /* If PARM uses template parameters, then we can't bail out here,
      even if ARG == PARM, since we won't record unifications for the
diff --git a/gcc/testsuite/g++.dg/cpp0x/nontype7.C b/gcc/testsuite/g++.dg/cpp0x/nontype7.C
new file mode 100644 (file)
index 0000000..30c1d39
--- /dev/null
@@ -0,0 +1,13 @@
+// PR c++/118632
+// { dg-do compile { target c++11 } }
+
+template<class T, T* = nullptr>
+class Matrix {};
+
+template<class T>
+void operator*(Matrix<T>, int);
+
+int main() {
+  Matrix<int> m;
+  m * 42;
+}