[clang] [clang] Implement P2582R1: CTAD from inherited constructors (PR #98788)

Matheus Izvekov via cfe-commits cfe-commits at lists.llvm.org
Fri Sep 27 09:57:15 PDT 2024


================
@@ -10581,6 +10581,47 @@ bool clang::isBetterOverloadCandidate(
     auto *Guide1 = dyn_cast_or_null<CXXDeductionGuideDecl>(Cand1.Function);
     auto *Guide2 = dyn_cast_or_null<CXXDeductionGuideDecl>(Cand2.Function);
     if (Guide1 && Guide2) {
+      //  -- F1 and F2 are generated from class template argument deduction
+      //  for a class D, and F2 is generated from inheriting constructors
+      //  from a base class of D while F1 is not, ...
+      bool G1Inherited =
+          Guide1->getSourceDeductionGuide() &&
+          Guide1->getSourceKind() ==
+              CXXDeductionGuideDecl::SourceKind::InheritedConstructor;
+      bool G2Inherited =
+          Guide2->getSourceDeductionGuide() &&
+          Guide2->getSourceKind() ==
+              CXXDeductionGuideDecl::SourceKind::InheritedConstructor;
+      if (Guide1->isImplicit() && Guide2->isImplicit() &&
+          G1Inherited != G2Inherited) {
+        const FunctionProtoType *FPT1 =
+            Guide1->getType()->getAs<FunctionProtoType>();
+        const FunctionProtoType *FPT2 =
+            Guide2->getType()->getAs<FunctionProtoType>();
+        assert(FPT1 && FPT2);
+
+        // ... and for each explicit function argument, the parameters of F1 and
+        // F2 are either both ellipses or have the same type
+        if (FPT1->isVariadic() == FPT2->isVariadic() &&
+            FPT1->getNumParams() == FPT2->getNumParams()) {
+          bool ParamsHaveSameType = true;
+          const auto &A1 = FPT1->getParamTypes();
+          const auto &A2 = FPT2->getParamTypes();
+          for (unsigned I = 0, N = FPT1->getNumParams(); I != N; ++I) {
+            llvm::FoldingSetNodeID ID1, ID2;
+            S.Context.getCanonicalType(A1[I]).Profile(ID1);
+            S.Context.getCanonicalType(A2[I]).Profile(ID2);
+            if (ID1 != ID2) {
+              ParamsHaveSameType = false;
+              break;
+            }
----------------
mizvekov wrote:

```suggestion
            if (!S.Context.hasSameType(A1[I]), A2[I]) {
              ParamsHaveSameType = false;
              break;
            }
```
Though you can probably do better here using `llvm::all_of`.

https://github.com/llvm/llvm-project/pull/98788


More information about the cfe-commits mailing list