[clang] [Sema] add cast from IncompleteArrayType to ConstantArrayType in TryReferenceListInitialization (PR #65918)

Congcong Cai via cfe-commits cfe-commits at lists.llvm.org
Thu Sep 14 18:59:31 PDT 2023


https://github.com/HerrCai0907 updated https://github.com/llvm/llvm-project/pull/65918:

>From cfedbe3fb2f2f331b3f9ee1f4f3e2fcd348797e2 Mon Sep 17 00:00:00 2001
From: Congcong Cai <congcongcai0907 at 163.com>
Date: Mon, 11 Sep 2023 09:15:41 +0800
Subject: [PATCH 1/4] [Sema] add cast from IncompleteArrayType to
 ConstantArrayType in TryReferenceListInitialization

Fixed: https://github.com/llvm/llvm-project/issues/62945
c++20 supports "Permit conversions to arrays of unknown bound".
This need additional cast from IncompleteArrayType to ConstantArrayType
in TryReferenceListInitialization
---
 clang/lib/Sema/SemaInit.cpp                       | 9 +++++++++
 clang/test/CodeGenCXX/cxx20-p0388-unbound-ary.cpp | 9 +++++++++
 2 files changed, 18 insertions(+)

diff --git a/clang/lib/Sema/SemaInit.cpp b/clang/lib/Sema/SemaInit.cpp
index 93f05e2e47285e4..966d35226eec748 100644
--- a/clang/lib/Sema/SemaInit.cpp
+++ b/clang/lib/Sema/SemaInit.cpp
@@ -4532,6 +4532,15 @@ static void TryReferenceListInitialization(Sema &S,
       if (T1Quals.hasAddressSpace())
         Sequence.AddQualificationConversionStep(
             cv1T1, DestType->isRValueReferenceType() ? VK_XValue : VK_LValue);
+      else if (S.getLangOpts().CPlusPlus20 &&
+               isa<IncompleteArrayType>(T1->getUnqualifiedDesugaredType()) &&
+               DestType->isRValueReferenceType()) {
+        // [dcl.init.list] p3.10
+        // unless T is “reference to array of unknown bound of U”, in which case
+        // the type of the prvalue is the type of x in the declaration U x[] H,
+        // where H is the initializer list.
+        Sequence.AddQualificationConversionStep(cv1T1, VK_XValue);
+      }
     } else
       Sequence.SetFailed(
           InitializationSequence::FK_NonConstLValueReferenceBindingToTemporary);
diff --git a/clang/test/CodeGenCXX/cxx20-p0388-unbound-ary.cpp b/clang/test/CodeGenCXX/cxx20-p0388-unbound-ary.cpp
index 78f35a024a54014..a29f4d720c1de4e 100644
--- a/clang/test/CodeGenCXX/cxx20-p0388-unbound-ary.cpp
+++ b/clang/test/CodeGenCXX/cxx20-p0388-unbound-ary.cpp
@@ -23,4 +23,13 @@ auto &frob2(int (&arp)[1]) {
 
   return r2;
 }
+
+// CHECK-LABEL: @_ZN3One3fooEi
+// CHECK-NEXT: entry:
+// CHECK-NEXT: ret void
+void foo(int a) {
+  auto f = [](int(&&)[]) {};
+  f({a});
+}
+
 } // namespace One

>From 0d149d1e07783d2cf7b869623c6c055b9184ce8e Mon Sep 17 00:00:00 2001
From: Congcong Cai <congcongcai0907 at 163.com>
Date: Thu, 14 Sep 2023 00:28:28 +0800
Subject: [PATCH 2/4] Update clang/lib/Sema/SemaInit.cpp

Co-authored-by: Mariya Podchishchaeva <mariya.podchishchaeva at intel.com>
---
 clang/lib/Sema/SemaInit.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/clang/lib/Sema/SemaInit.cpp b/clang/lib/Sema/SemaInit.cpp
index 966d35226eec748..d8a035b60dcb6e5 100644
--- a/clang/lib/Sema/SemaInit.cpp
+++ b/clang/lib/Sema/SemaInit.cpp
@@ -4535,7 +4535,7 @@ static void TryReferenceListInitialization(Sema &S,
       else if (S.getLangOpts().CPlusPlus20 &&
                isa<IncompleteArrayType>(T1->getUnqualifiedDesugaredType()) &&
                DestType->isRValueReferenceType()) {
-        // [dcl.init.list] p3.10
+        // C++20 [dcl.init.list]p3.10:
         // unless T is “reference to array of unknown bound of U”, in which case
         // the type of the prvalue is the type of x in the declaration U x[] H,
         // where H is the initializer list.

>From fecee704039f5c9cb964a646f0d5f27edd6101f6 Mon Sep 17 00:00:00 2001
From: Congcong Cai <congcongcai0907 at 163.com>
Date: Fri, 15 Sep 2023 09:46:52 +0800
Subject: [PATCH 3/4] fix

---
 clang/lib/Sema/SemaInit.cpp | 21 ++++++++++++---------
 1 file changed, 12 insertions(+), 9 deletions(-)

diff --git a/clang/lib/Sema/SemaInit.cpp b/clang/lib/Sema/SemaInit.cpp
index d8a035b60dcb6e5..da006e98e81b99a 100644
--- a/clang/lib/Sema/SemaInit.cpp
+++ b/clang/lib/Sema/SemaInit.cpp
@@ -18,6 +18,7 @@
 #include "clang/AST/TypeLoc.h"
 #include "clang/Basic/CharInfo.h"
 #include "clang/Basic/SourceManager.h"
+#include "clang/Basic/Specifiers.h"
 #include "clang/Basic/TargetInfo.h"
 #include "clang/Sema/Designator.h"
 #include "clang/Sema/EnterExpressionEvaluationContext.h"
@@ -4527,20 +4528,22 @@ static void TryReferenceListInitialization(Sema &S,
   if (Sequence) {
     if (DestType->isRValueReferenceType() ||
         (T1Quals.hasConst() && !T1Quals.hasVolatile())) {
+      if (S.getLangOpts().CPlusPlus20 &&
+          isa<IncompleteArrayType>(T1->getUnqualifiedDesugaredType()) &&
+          DestType->isRValueReferenceType()) {
+        // C++20 [dcl.init.list]p3.10:
+        // List-initialization of an object or reference of type T is defined as
+        // follows:
+        // ..., unless T is “reference to array of unknown bound of U”, in which
+        // case the type of the prvalue is the type of x in the declaration U
+        // x[] H, where H is the initializer list.
+        Sequence.AddQualificationConversionStep(cv1T1, clang::VK_PRValue);
+      }
       Sequence.AddReferenceBindingStep(cv1T1IgnoreAS,
                                        /*BindingTemporary=*/true);
       if (T1Quals.hasAddressSpace())
         Sequence.AddQualificationConversionStep(
             cv1T1, DestType->isRValueReferenceType() ? VK_XValue : VK_LValue);
-      else if (S.getLangOpts().CPlusPlus20 &&
-               isa<IncompleteArrayType>(T1->getUnqualifiedDesugaredType()) &&
-               DestType->isRValueReferenceType()) {
-        // C++20 [dcl.init.list]p3.10:
-        // unless T is “reference to array of unknown bound of U”, in which case
-        // the type of the prvalue is the type of x in the declaration U x[] H,
-        // where H is the initializer list.
-        Sequence.AddQualificationConversionStep(cv1T1, VK_XValue);
-      }
     } else
       Sequence.SetFailed(
           InitializationSequence::FK_NonConstLValueReferenceBindingToTemporary);

>From 70d516b7aa6c0bb9a9e6fc6165a36c3dc1ec578c Mon Sep 17 00:00:00 2001
From: Congcong Cai <congcongcai0907 at 163.com>
Date: Fri, 15 Sep 2023 09:59:14 +0800
Subject: [PATCH 4/4] add release note

---
 clang/docs/ReleaseNotes.rst | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 3cdad2f7b9f0e5a..1dd19f05d00482b 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -220,6 +220,9 @@ Bug Fixes in This Version
   an invalid conversion during method function overload resolution.
 - Fix parser crash when dealing with ill-formed objective C++ header code. Fixes
   (`#64836 <https://github.com/llvm/llvm-project/issues/64836>`_)
+- Fix crash in implicit conversions from initialize list to arrays of unknown 
+  bound for C++20. Fixes
+  (`#62945 <https://github.com/llvm/llvm-project/issues/62945>`_)
 
 Bug Fixes to Compiler Builtins
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^



More information about the cfe-commits mailing list