]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
c++: CWG 2273 and non-constructors
authorPatrick Palka <ppalka@redhat.com>
Fri, 20 Sep 2024 16:31:40 +0000 (12:31 -0400)
committerPatrick Palka <ppalka@redhat.com>
Fri, 20 Sep 2024 16:31:40 +0000 (12:31 -0400)
Our implementation of the CWG 2273 inheritedness tiebreaker seems to be
incorrectly considering all member functions introduced via using, not
just constructors.  This patch restricts the tiebreaker accordingly.

DR 2273

gcc/cp/ChangeLog:

* call.cc (joust): Restrict inheritedness tiebreaker to
constructors.

gcc/testsuite/ChangeLog:

* g++.dg/cpp1z/using1.C: Expect ambiguity for non-constructor call.
* g++.dg/overload/using5.C: Likewise.

Reviewed-by: Jason Merrill <jason@redhat.com>
gcc/cp/call.cc
gcc/testsuite/g++.dg/cpp1z/using1.C
gcc/testsuite/g++.dg/overload/using5.C

index 3f753e2d2f98292643b4e75890367ed9f33ad4a0..6229dc4526363a2dc4bd3c0d4f1e2179fcaa4eb7 100644 (file)
@@ -13350,13 +13350,10 @@ joust (struct z_candidate *cand1, struct z_candidate *cand2, bool warn,
        }
     }
 
-  /* F1 is a member of a class D, F2 is a member of a base class B of D, and
-     for all arguments the corresponding parameters of F1 and F2 have the same
-     type (CWG 2273/2277). */
-  if (DECL_P (cand1->fn) && DECL_CLASS_SCOPE_P (cand1->fn)
-      && !DECL_CONV_FN_P (cand1->fn)
-      && DECL_P (cand2->fn) && DECL_CLASS_SCOPE_P (cand2->fn)
-      && !DECL_CONV_FN_P (cand2->fn))
+  /* F1 is a constructor for a class D, F2 is a constructor for a base class B
+     of D, and for all arguments the corresponding parameters of F1 and F2 have
+     the same type (CWG 2273/2277).  */
+  if (DECL_INHERITED_CTOR (cand1->fn) || DECL_INHERITED_CTOR (cand2->fn))
     {
       tree base1 = DECL_CONTEXT (strip_inheriting_ctors (cand1->fn));
       tree base2 = DECL_CONTEXT (strip_inheriting_ctors (cand2->fn));
index 1ed939d45fd442c8377d47a6c6da3935d03522ef..d8a045255795c99ef5085d7eb4bd0a2ce5358295 100644 (file)
@@ -1,5 +1,5 @@
-// Test for hiding of used base functions when all the conversion sequences are
-// equivalent, needed to avoid a regression on inherited default ctors.
+// Test the CWG 2273 inheritedness tiebreaker doesn't apply to
+// non-constructors.
 
 struct A
 {
@@ -17,7 +17,7 @@ struct B:A
 
 int main()
 {
-  B().f(1);                    // OK, derived f hides base f for single arg
+  B().f(1);                    // { dg-error "ambiguous" }
   B().f(1,2);                  // OK, base f can still be called with two args
-  B().g(1);                    // { dg-error "" } signatures differ, ambiguous
+  B().g(1);                    // { dg-error "ambiguous" }
 }
index ad17c78a561e41f15507086d803b1e6c99c660bd..0933a9f0fac3dd647fc179cee3b086ef2cb20103 100644 (file)
@@ -24,5 +24,5 @@ struct C: B {
 int main()
 {
   C c (42);
-  c.f();
+  c.f(); // { dg-error "ambiguous" }
 }