[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread Corentin Jabot via cfe-commits

cor3ntin wrote:

See https://github.com/llvm/llvm-project/pull/82776#issuecomment-1975871421

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread Yanzuo Liu via cfe-commits

zwuis wrote:

Thank you for your patch! Please see #82776 and ensure concerns in that PR are 
addressed in this PR.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread A. Jiang via cfe-commits


@@ -0,0 +1,35 @@
+//===--===//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//===--===//
+
+// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20
+
+#include 
+
+struct NonTrivial {
+  int x;
+  ~NonTrivial() {}
+};
+
+struct Incomplete; // expected-note {{forward declaration of 'Incomplete'}}
+
+void test_invalid_types(void* p) {
+  // expected-error@*:* {{type 'NonTrivial' is not an implicit-lifetime type, 
cannot start lifetime}}
+  std::start_lifetime_as(p);
+
+  // expected-error@*:* {{incomplete type 'Incomplete' where a complete type 
is required}}
+  std::start_lifetime_as(p);
+
+  // expected-error@*:* {{type 'void' is not an implicit-lifetime type, cannot 
start lifetime}}
+  std::start_lifetime_as(p);
+
+  // expected-error@*:* {{static_cast from 'void *' to 'void (*)()' is not 
allowed}}
+  std::start_lifetime_as(p);
+}
+
+void test_constexpr() {

frederick-vs-ja wrote:

This looks quite novel. We almost never test missing of `constexpr`.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread A. Jiang via cfe-commits


@@ -0,0 +1,35 @@
+//===--===//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//===--===//
+
+// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20
+
+#include 
+
+struct NonTrivial {
+  int x;
+  ~NonTrivial() {}
+};
+
+struct Incomplete; // expected-note {{forward declaration of 'Incomplete'}}
+
+void test_invalid_types(void* p) {

frederick-vs-ja wrote:

Perhaps we should also test invalid types for `start_lifetime_as_array`.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread A. Jiang via cfe-commits


@@ -0,0 +1,76 @@
+//===--===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===--===//
+
+// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20

frederick-vs-ja wrote:

```suggestion
// REQUIRES: std-at-least-c++23
```

Same for other tests.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread A. Jiang via cfe-commits


@@ -0,0 +1,35 @@
+//===--===//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//===--===//
+
+// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20
+
+#include 
+
+struct NonTrivial {
+  int x;
+  ~NonTrivial() {}
+};
+
+struct Incomplete; // expected-note {{forward declaration of 'Incomplete'}}
+
+void test_invalid_types(void* p) {
+  // expected-error@*:* {{type 'NonTrivial' is not an implicit-lifetime type, 
cannot start lifetime}}
+  std::start_lifetime_as(p);
+
+  // expected-error@*:* {{incomplete type 'Incomplete' where a complete type 
is required}}
+  std::start_lifetime_as(p);
+
+  // expected-error@*:* {{type 'void' is not an implicit-lifetime type, cannot 
start lifetime}}
+  std::start_lifetime_as(p);
+
+  // expected-error@*:* {{static_cast from 'void *' to 'void (*)()' is not 
allowed}}
+  std::start_lifetime_as(p);
+}
+
+void test_constexpr() {
+  // expected-error@+1 {{constexpr variable 'fail' must be initialized by a 
constant expression}}
+  constexpr auto* fail = std::start_lifetime_as((void*)nullptr);
+}

frederick-vs-ja wrote:

We conventionally have an empty line at the end of every test file.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread A. Jiang via cfe-commits


@@ -0,0 +1,76 @@
+//===--===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===--===//
+
+// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20
+
+// 
+// template T* start_lifetime_as(void* p) noexcept;
+// template const T* start_lifetime_as(const void* p) noexcept;
+// template volatile T* start_lifetime_as(volatile void* p) noexcept;
+// template const volatile T* start_lifetime_as(const volatile void* 
p) noexcept;
+
+#include 
+#include 
+#include 
+
+struct Trivial {
+  int x;
+  float y;
+};
+
+struct NestedArray {
+  int arr[3][4];
+};
+
+static_assert(noexcept(std::start_lifetime_as(std::declval(;
+static_assert(noexcept(std::start_lifetime_as(std::declval(;
+static_assert(noexcept(std::start_lifetime_as(std::declval(;
+static_assert(noexcept(std::start_lifetime_as(std::declval(;
+
+static_assert(std::is_same_v(std::declval())),
 int*>);
+static_assert(std::is_same_v(std::declval())), const int*>);
+static_assert(std::is_same_v(std::declval())), volatile int*>);
+static_assert(
+std::is_same_v(std::declval())), const volatile int*>);
+
+void test_cv_qualifiers() {
+  alignas(Trivial) unsigned char buffer[sizeof(Trivial)];
+  void* p  = buffer;
+  const void* cp   = buffer;
+  volatile void* vp= buffer;
+  const volatile void* cvp = buffer;
+
+  Trivial* ptr  = std::start_lifetime_as(p);
+  const Trivial* cptr   = std::start_lifetime_as(cp);
+  volatile Trivial* vptr= std::start_lifetime_as(vp);
+  const volatile Trivial* cvptr = std::start_lifetime_as(cvp);
+
+  assert(static_cast(ptr) == buffer);
+  assert(static_cast(cptr) == buffer);
+  assert(static_cast(vptr) == buffer);
+  assert(static_cast(cvptr) == buffer);

frederick-vs-ja wrote:

IIUC these assertions doesn't verify that `start_lifetime_as` starts lifetime 
of objects (and reuses object representations) at all.

I think we definitely want to verify the values of re-created objects.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread A. Jiang via cfe-commits


@@ -5914,3 +5914,54 @@ StringRef PredefinedSugarType::getName(Kind KD) {
   }
   llvm_unreachable("unexpected kind");
 }
+
+bool Type::isImplicitLifetimeType() const {

frederick-vs-ja wrote:

Couldn't we just reuse the logic for `__builtin_implicit_lifetime` (see 
#101807)?

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread A. Jiang via cfe-commits


@@ -71,43 +71,37 @@ class TemplateParameterList;
 class Type;
 class Attr;
 
-enum {
-  TypeAlignmentInBits = 4,
-  TypeAlignment = 1 << TypeAlignmentInBits
-};
+enum { TypeAlignmentInBits = 4, TypeAlignment = 1 << TypeAlignmentInBits };

frederick-vs-ja wrote:

Please revert formatting changes.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread Yash Verma via cfe-commits

My-Bad-2 wrote:

> Thank you for your patch! Please see #82776 and ensure concerns in that PR 
> are addressed in this PR.

Thanks for pointing me to the previous PR. It appears I'm a bit late to this 
lol. Anyways, After reading through the patch, it appears that the author 
wanted to implement `__builtin_start_lifetime` as a language extension. While 
my current PR strictly conforms to C++23 ISO guidelines.

There were concerns about TBAA. The previous implementation used the 
`__builtin_launder` path for CodeGen for both builtins. I don't think that this 
patch has to worry about TBAA as `Sema` validates that the element type (or 
base type) is implicit-lifetime and implicit-lifetime objects don't have to 
worry about vptr or vtables. Though, I'm not sure if 
`__builtin_start_lifetime_as` should be extended to support non-implicit types. 
It'll be appreciated if someone provides a second-opinion on this matter. 
Perhaps, it can be implemented as a flag in the builtin itself such that 
`std::start_lifetime_as` doesn't introduce instantiation overhead. Clang could 
handle code generation (and address TBAA concerns) internally. I'm thinking of 
something like:

```cpp
__builtin_start_lifetime_as((T*)ptr, Strict=True/False);
```

Another concern raised in the previous patch was about supporting the array 
version of start_lifetime. This patch does address this concern as `Sema` 
strips away array dimensions before checking the Base element type. #82776 
requires libc++ to type-check, library maintainers might have to write 
recursive template traits to strip away array dimensions.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread Nikolas Klauser via cfe-commits

philnik777 wrote:

Please split this into a Clang and a libc++ patch to make it easier to review.

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread Yash Verma via cfe-commits


@@ -5914,3 +5914,54 @@ StringRef PredefinedSugarType::getName(Kind KD) {
   }
   llvm_unreachable("unexpected kind");
 }
+
+bool Type::isImplicitLifetimeType() const {

My-Bad-2 wrote:

It's possible. But I think, we need to extract the logic from #101807 into 
another function/method  as it's buried deep inside `EvaluateUnaryTypeTrait()`

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread Yash Verma via cfe-commits

https://github.com/My-Bad-2 edited 
https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread via cfe-commits

llvmorg-github-actions[bot] wrote:




@llvm/pr-subscribers-libcxx

Author: Yash Verma (My-Bad-2)


Changes

This PR implements the compiler built-in and standard library interfaces for 
C++23 Explicit Lifetime Management as proposed in 
[P2590R2](https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2022/p2590r2.pdf) 
and fixed for arrays in 
[P2679R2](https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2023/p2679r2.pdf).

This PR implements a `__builtin_start_lifetime_as((T*)ptr)` builtin which is 
used by `std::start_lifetime_as(ptr)` and 
`std::start_lifetime_as_array(ptr, n)`.

I'm sorry if there are any mistakes in the pull request as this my first PR 
ever. Also, the commit timestamp is a bit messed up because I forgot to run 
`git clang-format` hook before pushing a few commits to the remote host.

---

Patch is 209.42 KiB, truncated to 20.00 KiB below, full version: 
https://github.com/llvm/llvm-project/pull/196286.diff


17 Files Affected:

- (modified) clang/include/clang/AST/TypeBase.h (+304-385) 
- (modified) clang/include/clang/Basic/Builtins.td (+6) 
- (modified) clang/include/clang/Basic/DiagnosticSemaKinds.td (+3) 
- (modified) clang/include/clang/Sema/Sema.h (+7) 
- (modified) clang/lib/AST/ExprConstant.cpp (+6) 
- (modified) clang/lib/AST/Type.cpp (+51) 
- (modified) clang/lib/CodeGen/CGBuiltin.cpp (+265-261) 
- (modified) clang/lib/Sema/SemaChecking.cpp (+463-396) 
- (added) clang/test/CodeGenCXX/builtin-start-lifetime-as.cpp (+13) 
- (added) clang/test/SemaCXX/builtin-start-lifetime-as.cpp (+56) 
- (modified) libcxx/include/CMakeLists.txt (+1) 
- (added) libcxx/include/__memory/start_lifetime_as.h (+72) 
- (modified) libcxx/include/memory (+26) 
- (modified) libcxx/include/module.modulemap.in (+1) 
- (added) libcxx/test/std/memory/start.lifetime/start_lifetime_as.pass.cpp 
(+76) 
- (added) libcxx/test/std/memory/start.lifetime/start_lifetime_as.verify.cpp 
(+35) 
- (added) 
libcxx/test/std/memory/start.lifetime/start_lifetime_as_array.pass.cpp (+47) 


``diff
diff --git a/clang/include/clang/AST/TypeBase.h 
b/clang/include/clang/AST/TypeBase.h
index b2887bcc36246..2e20cecd8ae1d 100644
--- a/clang/include/clang/AST/TypeBase.h
+++ b/clang/include/clang/AST/TypeBase.h
@@ -71,43 +71,37 @@ class TemplateParameterList;
 class Type;
 class Attr;
 
-enum {
-  TypeAlignmentInBits = 4,
-  TypeAlignment = 1 << TypeAlignmentInBits
-};
+enum { TypeAlignmentInBits = 4, TypeAlignment = 1 << TypeAlignmentInBits };
 
 namespace serialization {
-  template  class AbstractTypeReader;
-  template  class AbstractTypeWriter;
-}
+template  class AbstractTypeReader;
+template  class AbstractTypeWriter;
+} // namespace serialization
 
 } // namespace clang
 
 namespace llvm {
 
-  template 
-  struct PointerLikeTypeTraits;
-  template<>
-  struct PointerLikeTypeTraits< ::clang::Type*> {
-static inline void *getAsVoidPointer(::clang::Type *P) { return P; }
+template  struct PointerLikeTypeTraits;
+template <> struct PointerLikeTypeTraits<::clang::Type *> {
+  static inline void *getAsVoidPointer(::clang::Type *P) { return P; }
 
-static inline ::clang::Type *getFromVoidPointer(void *P) {
-  return static_cast< ::clang::Type*>(P);
-}
+  static inline ::clang::Type *getFromVoidPointer(void *P) {
+return static_cast<::clang::Type *>(P);
+  }
 
-static constexpr int NumLowBitsAvailable = clang::TypeAlignmentInBits;
-  };
+  static constexpr int NumLowBitsAvailable = clang::TypeAlignmentInBits;
+};
 
-  template<>
-  struct PointerLikeTypeTraits< ::clang::ExtQuals*> {
-static inline void *getAsVoidPointer(::clang::ExtQuals *P) { return P; }
+template <> struct PointerLikeTypeTraits<::clang::ExtQuals *> {
+  static inline void *getAsVoidPointer(::clang::ExtQuals *P) { return P; }
 
-static inline ::clang::ExtQuals *getFromVoidPointer(void *P) {
-  return static_cast< ::clang::ExtQuals*>(P);
-}
+  static inline ::clang::ExtQuals *getFromVoidPointer(void *P) {
+return static_cast<::clang::ExtQuals *>(P);
+  }
 
-static constexpr int NumLowBitsAvailable = clang::TypeAlignmentInBits;
-  };
+  static constexpr int NumLowBitsAvailable = clang::TypeAlignmentInBits;
+};
 
 } // namespace llvm
 
@@ -339,11 +333,7 @@ class Qualifiers {
 CVRMask = Const | Volatile | Restrict
   };
 
-  enum GC {
-GCNone = 0,
-Weak,
-Strong
-  };
+  enum GC { GCNone = 0, Weak, Strong };
 
   enum ObjCLifetime {
 /// There is no lifetime qualification on this type.
@@ -496,9 +486,7 @@ class Qualifiers {
 assert(!(mask & ~CVRMask) && "bitmask contains non-CVR bits");
 Mask &= ~static_cast(mask);
   }
-  void removeCVRQualifiers() {
-removeCVRQualifiers(CVRMask);
-  }
+  void removeCVRQualifiers() { removeCVRQualifiers(CVRMask); }
   void addCVRQualifiers(unsigned mask) {
 assert(!(mask & ~CVRMask) && "bitmask contains non-CVR bits");
 Mask |= mask;
@@ -509,9 +497,7 @@ class Qualifiers {
   }
 
   bool hasUnaligned() const { return Mask & UMask; }
-

[clang] [libcxx] [Clang][libc++] Implement C++23 std::start_lifetime_as (P2590R2, P2679R2) (PR #196286)

2026-05-07 Thread via cfe-commits

github-actions[bot] wrote:



Thank you for submitting a Pull Request (PR) to the LLVM Project!

This PR will be automatically labeled and the relevant teams will be notified.

If you wish to, you can add reviewers by using the "Reviewers" section on this 
page.

If this is not working for you, it is probably because you do not have write 
permissions for the repository. In which case you can instead tag reviewers by 
name in a comment by using `@` followed by their GitHub username.

If you have received no comments on your PR for a week, you can request a 
review by "ping"ing the PR by adding a comment “Ping”. The common courtesy 
"ping" rate is once a week. Please remember that you are asking for valuable 
time from other developers.

If you have further questions, they may be answered by the [LLVM GitHub User 
Guide](https://llvm.org/docs/GitHub.html).

You can also ask questions in a comment on this PR, on the [LLVM 
Discord](https://discord.com/invite/xS7Z362) or on the 
[forums](https://discourse.llvm.org/).

https://github.com/llvm/llvm-project/pull/196286
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits