[clang] Reapply "[Clang][Sema] placement new initializes typedef array with correct size (#83124)" (PR #89036)
via cfe-commits
cfe-commits at lists.llvm.org
Thu Apr 18 03:04:38 PDT 2024
https://github.com/mahtohappy updated https://github.com/llvm/llvm-project/pull/89036
>From 56c2b4f70735a6ef3b80cb8461a88ea51f2d02d7 Mon Sep 17 00:00:00 2001
From: mahtohappy <Happy.Kumar at Windriver.com>
Date: Tue, 16 Apr 2024 17:48:45 +0530
Subject: [PATCH 1/5] [Clang][Sema] placement new initializes typedef array
with correct size (#83124)
When in-place new-ing a local variable of an array of trivial type, the
generated code calls 'memset' with the correct size of the array,
earlier it was generating size (squared of the typedef array + size).
The cause: `typedef TYPE TArray[8]; TArray x;` The type of declarator is
Tarray[8] and in `SemaExprCXX.cpp::BuildCXXNew` we check if it's of
typedef and of constant size then we get the original type and it works
fine for non-dependent cases.
But in case of template we do `TreeTransform.h:TransformCXXNEWExpr` and
there we again check the allocated type which is TArray[8] and it stays
that way, so ArraySize=(Tarray[8] type, alloc Tarray[8*type]) so the
squared size allocation.
ArraySize gets calculated earlier in `TreeTransform.h` so that
`if(!ArraySize)` condition was failing.
fix: I changed that condition to `if(ArraySize)`.
Fixes #41441
---
clang/docs/ReleaseNotes.rst | 2 ++
clang/lib/Sema/TreeTransform.h | 14 ++++++++++++-
.../instantiate-new-placement-size.cpp | 20 +++++++++++++++++++
3 files changed, 35 insertions(+), 1 deletion(-)
create mode 100644 clang/test/SemaCXX/instantiate-new-placement-size.cpp
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 96ad92b540b47f..636d76f1836759 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -534,6 +534,8 @@ Bug Fixes to C++ Support
Fixes (#GH70604), (#GH79754), (#GH84163), (#GH84425), (#GH86054), (#GH86398), and (#GH86399).
- Fix a crash when deducing ``auto`` from an invalid dereference (#GH88329).
- Fix a crash in requires expression with templated base class member function. Fixes (#GH84020).
+- placement new initializes typedef array with correct size
+ (`#GH41441 <https://github.com/llvm/llvm-project/issues/41441>`_)
Bug Fixes to AST Handling
^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h
index eb05783a6219dc..0c7fdb357235e1 100644
--- a/clang/lib/Sema/TreeTransform.h
+++ b/clang/lib/Sema/TreeTransform.h
@@ -12864,6 +12864,19 @@ TreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) {
ArraySize = NewArraySize.get();
}
+ // Per C++0x [expr.new]p5, the type being constructed may be a
+ // typedef of an array type.
+ QualType AllocType = AllocTypeInfo->getType();
+ if (ArraySize) {
+ if (const ConstantArrayType *Array =
+ SemaRef.Context.getAsConstantArrayType(AllocType)) {
+ ArraySize = IntegerLiteral::Create(SemaRef.Context, Array->getSize(),
+ SemaRef.Context.getSizeType(),
+ E->getBeginLoc());
+ AllocType = Array->getElementType();
+ }
+ }
+
// Transform the placement arguments (if any).
bool ArgumentChanged = false;
SmallVector<Expr*, 8> PlacementArgs;
@@ -12925,7 +12938,6 @@ TreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) {
return E;
}
- QualType AllocType = AllocTypeInfo->getType();
if (!ArraySize) {
// If no array size was specified, but the new expression was
// instantiated with an array type (e.g., "new T" where T is
diff --git a/clang/test/SemaCXX/instantiate-new-placement-size.cpp b/clang/test/SemaCXX/instantiate-new-placement-size.cpp
new file mode 100644
index 00000000000000..7a29d3dee8491e
--- /dev/null
+++ b/clang/test/SemaCXX/instantiate-new-placement-size.cpp
@@ -0,0 +1,20 @@
+// RUN: %clang -S -fno-discard-value-names -emit-llvm -o - %s | FileCheck %s
+// Issue no: 41441
+#include <new>
+
+// CHECK: call void @llvm.memset.p0.i64(ptr align 1 %x, i8 0, i64 8, i1 false)
+// CHECK: call void @llvm.memset.p0.i64(ptr align 16 %x, i8 0, i64 32, i1 false)
+template <typename TYPE>
+void f()
+{
+ typedef TYPE TArray[8];
+
+ TArray x;
+ new(&x) TArray();
+}
+
+int main()
+{
+ f<char>();
+ f<int>();
+}
>From bdd7f66e560f60d1f0027b04ad12989b2f786df3 Mon Sep 17 00:00:00 2001
From: mahtohappy <Happy.Kumar at Windriver.com>
Date: Wed, 17 Apr 2024 00:12:14 +0530
Subject: [PATCH 2/5] [Clang][Sema] placement new initializes typedef array
with correct size (#88902)
Build Failure Fix
Fixes build failures due to #83124
---
.../{instantiate-new-placement-size.cpp => PR41441.cpp} | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
rename clang/test/SemaCXX/{instantiate-new-placement-size.cpp => PR41441.cpp} (75%)
diff --git a/clang/test/SemaCXX/instantiate-new-placement-size.cpp b/clang/test/SemaCXX/PR41441.cpp
similarity index 75%
rename from clang/test/SemaCXX/instantiate-new-placement-size.cpp
rename to clang/test/SemaCXX/PR41441.cpp
index 7a29d3dee8491e..0b012b33fce343 100644
--- a/clang/test/SemaCXX/instantiate-new-placement-size.cpp
+++ b/clang/test/SemaCXX/PR41441.cpp
@@ -1,5 +1,5 @@
-// RUN: %clang -S -fno-discard-value-names -emit-llvm -o - %s | FileCheck %s
-// Issue no: 41441
+// RUN: %clang --target=x86_64-pc-linux -S -fno-discard-value-names -emit-llvm -o - %s | FileCheck %s
+
#include <new>
// CHECK: call void @llvm.memset.p0.i64(ptr align 1 %x, i8 0, i64 8, i1 false)
>From 71f00c3bf2b6f0047d51332843490de08c097490 Mon Sep 17 00:00:00 2001
From: erichkeane <ekeane at nvidia.com>
Date: Tue, 16 Apr 2024 12:12:25 -0700
Subject: [PATCH 3/5] Fix test from #83124 and #88902
This just replaces an '#include<new>' with a declaration of array
placement new.
---
clang/test/SemaCXX/PR41441.cpp | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/clang/test/SemaCXX/PR41441.cpp b/clang/test/SemaCXX/PR41441.cpp
index 0b012b33fce343..d0f2917e52f211 100644
--- a/clang/test/SemaCXX/PR41441.cpp
+++ b/clang/test/SemaCXX/PR41441.cpp
@@ -1,6 +1,9 @@
// RUN: %clang --target=x86_64-pc-linux -S -fno-discard-value-names -emit-llvm -o - %s | FileCheck %s
-#include <new>
+namespace std {
+ using size_t = decltype(sizeof(int));
+};
+void* operator new[](std::size_t, void*) noexcept;
// CHECK: call void @llvm.memset.p0.i64(ptr align 1 %x, i8 0, i64 8, i1 false)
// CHECK: call void @llvm.memset.p0.i64(ptr align 16 %x, i8 0, i64 32, i1 false)
>From c64cd9db1c2a754e8343607cc604a9588ebdbf3d Mon Sep 17 00:00:00 2001
From: mahtohappy <Happy.Kumar at windriver.com>
Date: Wed, 17 Apr 2024 03:10:34 -0700
Subject: [PATCH 4/5] [Clang][Sema] placement new initializes typedef array
with correct size
Fixing test documentation build failure
---
clang/docs/ReleaseNotes.rst | 3 +--
1 file changed, 1 insertion(+), 2 deletions(-)
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 636d76f1836759..ca4de4289c433f 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -534,8 +534,7 @@ Bug Fixes to C++ Support
Fixes (#GH70604), (#GH79754), (#GH84163), (#GH84425), (#GH86054), (#GH86398), and (#GH86399).
- Fix a crash when deducing ``auto`` from an invalid dereference (#GH88329).
- Fix a crash in requires expression with templated base class member function. Fixes (#GH84020).
-- placement new initializes typedef array with correct size
- (`#GH41441 <https://github.com/llvm/llvm-project/issues/41441>`_)
+- Fix placement new initializes typedef array with correct size. Fixes (#GH41441).
Bug Fixes to AST Handling
^^^^^^^^^^^^^^^^^^^^^^^^^
>From 1a73ca6ea3ec1ca5f2676c8c162fd697faacfd07 Mon Sep 17 00:00:00 2001
From: mahtohappy <Happy.Kumar at windriver.com>
Date: Thu, 18 Apr 2024 03:00:25 -0700
Subject: [PATCH 5/5] Reapply "[Clang][Sema] placement new initializes typedef
array with correct size
fixing the regression test failure
---
clang/docs/ReleaseNotes.rst | 4 ++++
clang/lib/Sema/TreeTransform.h | 2 +-
2 files changed, 5 insertions(+), 1 deletion(-)
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index ca4de4289c433f..b03f40c2479127 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -364,6 +364,8 @@ Improvements to Clang's diagnostics
- Clang now uses the correct type-parameter-key (``class`` or ``typename``) when printing
template template parameter declarations.
+- Clang now diagnoses requires expressions with explicit object parameters.
+
Improvements to Clang's time-trace
----------------------------------
@@ -534,6 +536,8 @@ Bug Fixes to C++ Support
Fixes (#GH70604), (#GH79754), (#GH84163), (#GH84425), (#GH86054), (#GH86398), and (#GH86399).
- Fix a crash when deducing ``auto`` from an invalid dereference (#GH88329).
- Fix a crash in requires expression with templated base class member function. Fixes (#GH84020).
+- Fix a crash caused by defined struct in a type alias template when the structure
+ has fields with dependent type. Fixes (#GH75221).
- Fix placement new initializes typedef array with correct size. Fixes (#GH41441).
Bug Fixes to AST Handling
diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h
index 0c7fdb357235e1..4e088baf696eac 100644
--- a/clang/lib/Sema/TreeTransform.h
+++ b/clang/lib/Sema/TreeTransform.h
@@ -12867,7 +12867,7 @@ TreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) {
// Per C++0x [expr.new]p5, the type being constructed may be a
// typedef of an array type.
QualType AllocType = AllocTypeInfo->getType();
- if (ArraySize) {
+ if (ArraySize && E->isTypeDependent()) {
if (const ConstantArrayType *Array =
SemaRef.Context.getAsConstantArrayType(AllocType)) {
ArraySize = IntegerLiteral::Create(SemaRef.Context, Array->getSize(),
More information about the cfe-commits
mailing list