[libcxx-commits] [libcxx] [libc++][pstl] Implement LWG3552: Parallel specialized memory algorithms should require forward iterators (PR #228462)
via libcxx-commits
libcxx-commits at lists.llvm.org
Sat Oct 3 10:45:37 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-libcxx
Author: Michael G. Kazakov (mikekazakov)
<details>
<summary>Changes</summary>
This PR changes these parallel functions to no longer support input iterators and instead to require at least forward iterators, according to https://cplusplus.github.io/LWG/issue3552:
- `std::uninitialized_copy`
- `std::uninitialized_copy_n`
- `std::uninitialized_move`
- `std::uninitialized_move_n`
Fixes #<!-- -->104357
---
Patch is 27.71 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/228462.diff
10 Files Affected:
- (modified) libcxx/docs/Status/Cxx23Issues.csv (+1-1)
- (modified) libcxx/include/__memory/pstl.h (+24-24)
- (modified) libcxx/include/__pstl/backend_fwd.h (+12-12)
- (modified) libcxx/include/__pstl/backends/default.h (+12-12)
- (modified) libcxx/include/__pstl/cpu_algos/uninitialized_algorithms.h (+12-12)
- (modified) libcxx/test/libcxx/algorithms/pstl.iterator-requirements.verify.cpp (+5-7)
- (modified) libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/pstl.uninitialized_copy.pass.cpp (+7-7)
- (modified) libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/pstl.uninitialized_copy_n.pass.cpp (+7-7)
- (modified) libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.move/pstl.uninitialized_move.pass.cpp (+7-7)
- (modified) libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.move/pstl.uninitialized_move_n.pass.cpp (+7-7)
``````````diff
diff --git a/libcxx/docs/Status/Cxx23Issues.csv b/libcxx/docs/Status/Cxx23Issues.csv
index 68420a74f4878c..58ea67732f808f 100644
--- a/libcxx/docs/Status/Cxx23Issues.csv
+++ b/libcxx/docs/Status/Cxx23Issues.csv
@@ -93,7 +93,7 @@
"`LWG3548 <https://wg21.link/LWG3548>`__","``shared_ptr`` construction from ``unique_ptr`` should move (not copy) the deleter","2021-06 (Virtual)","|Complete|","15","`#104354 <https://github.com/llvm/llvm-project/issues/104354>`__",""
"`LWG3549 <https://wg21.link/LWG3549>`__","``view_interface`` is overspecified to derive from ``view_base``","2021-06 (Virtual)","|Complete|","14","`#104355 <https://github.com/llvm/llvm-project/issues/104355>`__",""
"`LWG3551 <https://wg21.link/LWG3551>`__","``borrowed_{iterator,subrange}_t`` are overspecified","2021-06 (Virtual)","|Nothing To Do|","","`#104356 <https://github.com/llvm/llvm-project/issues/104356>`__",""
-"`LWG3552 <https://wg21.link/LWG3552>`__","Parallel specialized memory algorithms should require forward iterators","2021-06 (Virtual)","","","`#104357 <https://github.com/llvm/llvm-project/issues/104357>`__",""
+"`LWG3552 <https://wg21.link/LWG3552>`__","Parallel specialized memory algorithms should require forward iterators","2021-06 (Virtual)","|Complete|","24","`#104357 <https://github.com/llvm/llvm-project/issues/104357>`__",""
"`LWG3553 <https://wg21.link/LWG3553>`__","Useless constraint in ``split_view::outer-iterator::value_type::begin()``","2021-06 (Virtual)","","","`#104358 <https://github.com/llvm/llvm-project/issues/104358>`__",""
"`LWG3555 <https://wg21.link/LWG3555>`__","``{transform,elements}_view::iterator::iterator_concept`` should consider const-qualification of the underlying range","2021-06 (Virtual)","","","`#104359 <https://github.com/llvm/llvm-project/issues/104359>`__",""
"","","","","","",""
diff --git a/libcxx/include/__memory/pstl.h b/libcxx/include/__memory/pstl.h
index 6c1fd6f10ee230..7dbc9fdcb51d4d 100644
--- a/libcxx/include/__memory/pstl.h
+++ b/libcxx/include/__memory/pstl.h
@@ -84,29 +84,29 @@ uninitialized_default_construct_n(_ExecutionPolicy&& __policy, _ForwardIterator
}
template <class _ExecutionPolicy,
- class _InputIterator,
- class _ForwardIterator,
+ class _ForwardIterator1,
+ class _ForwardIterator2,
class _RawPolicy = __remove_cvref_t<_ExecutionPolicy>,
enable_if_t<is_execution_policy_v<_RawPolicy>, int> = 0>
-_LIBCPP_HIDE_FROM_ABI _ForwardIterator uninitialized_copy(
- _ExecutionPolicy&& __policy, _InputIterator __first, _InputIterator __last, _ForwardIterator __result) {
- _LIBCPP_REQUIRE_CPP17_INPUT_ITERATOR(_InputIterator, "uninitialized_copy requires InputIterators");
- _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator, "uninitialized_copy requires ForwardIterators");
+_LIBCPP_HIDE_FROM_ABI _ForwardIterator2 uninitialized_copy(
+ _ExecutionPolicy&& __policy, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result) {
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator1, "uninitialized_copy requires ForwardIterators");
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator2, "uninitialized_copy requires ForwardIterators");
using _Implementation = __pstl::__dispatch<__pstl::__uninitialized_copy, __pstl::__current_configuration, _RawPolicy>;
return __pstl::__handle_exception<_Implementation>(
std::forward<_ExecutionPolicy>(__policy), std::move(__first), std::move(__last), std::move(__result));
}
template <class _ExecutionPolicy,
- class _InputIterator,
+ class _ForwardIterator1,
class _Size,
- class _ForwardIterator,
+ class _ForwardIterator2,
class _RawPolicy = __remove_cvref_t<_ExecutionPolicy>,
enable_if_t<is_execution_policy_v<_RawPolicy>, int> = 0>
-_LIBCPP_HIDE_FROM_ABI _ForwardIterator
-uninitialized_copy_n(_ExecutionPolicy&& __policy, _InputIterator __first, _Size __n, _ForwardIterator __result) {
- _LIBCPP_REQUIRE_CPP17_INPUT_ITERATOR(_InputIterator, "uninitialized_copy_n requires InputIterators");
- _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator, "uninitialized_copy_n requires ForwardIterators");
+_LIBCPP_HIDE_FROM_ABI _ForwardIterator2
+uninitialized_copy_n(_ExecutionPolicy&& __policy, _ForwardIterator1 __first, _Size __n, _ForwardIterator2 __result) {
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator1, "uninitialized_copy_n requires ForwardIterators");
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator2, "uninitialized_copy_n requires ForwardIterators");
using _Implementation =
__pstl::__dispatch<__pstl::__uninitialized_copy_n, __pstl::__current_configuration, _RawPolicy>;
return __pstl::__handle_exception<_Implementation>(
@@ -168,29 +168,29 @@ uninitialized_fill_n(_ExecutionPolicy&& __policy, _ForwardIterator __first, _Siz
}
template <class _ExecutionPolicy,
- class _InputIterator,
- class _ForwardIterator,
+ class _ForwardIterator1,
+ class _ForwardIterator2,
class _RawPolicy = __remove_cvref_t<_ExecutionPolicy>,
enable_if_t<is_execution_policy_v<_RawPolicy>, int> = 0>
-_LIBCPP_HIDE_FROM_ABI _ForwardIterator uninitialized_move(
- _ExecutionPolicy&& __policy, _InputIterator __first, _InputIterator __last, _ForwardIterator __result) {
- _LIBCPP_REQUIRE_CPP17_INPUT_ITERATOR(_InputIterator, "uninitialized_move requires InputIterators");
- _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator, "uninitialized_move requires ForwardIterators");
+_LIBCPP_HIDE_FROM_ABI _ForwardIterator2 uninitialized_move(
+ _ExecutionPolicy&& __policy, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result) {
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator1, "uninitialized_move requires ForwardIterators");
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator2, "uninitialized_move requires ForwardIterators");
using _Implementation = __pstl::__dispatch<__pstl::__uninitialized_move, __pstl::__current_configuration, _RawPolicy>;
return __pstl::__handle_exception<_Implementation>(
std::forward<_ExecutionPolicy>(__policy), std::move(__first), std::move(__last), std::move(__result));
}
template <class _ExecutionPolicy,
- class _InputIterator,
+ class _ForwardIterator1,
class _Size,
- class _ForwardIterator,
+ class _ForwardIterator2,
class _RawPolicy = __remove_cvref_t<_ExecutionPolicy>,
enable_if_t<is_execution_policy_v<_RawPolicy>, int> = 0>
-_LIBCPP_HIDE_FROM_ABI pair<_InputIterator, _ForwardIterator>
-uninitialized_move_n(_ExecutionPolicy&& __policy, _InputIterator __first, _Size __n, _ForwardIterator __result) {
- _LIBCPP_REQUIRE_CPP17_INPUT_ITERATOR(_InputIterator, "uninitialized_move_n requires InputIterators");
- _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator, "uninitialized_move_n requires ForwardIterators");
+_LIBCPP_HIDE_FROM_ABI pair<_ForwardIterator1, _ForwardIterator2>
+uninitialized_move_n(_ExecutionPolicy&& __policy, _ForwardIterator1 __first, _Size __n, _ForwardIterator2 __result) {
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator1, "uninitialized_move_n requires ForwardIterators");
+ _LIBCPP_REQUIRE_CPP17_FORWARD_ITERATOR(_ForwardIterator2, "uninitialized_move_n requires ForwardIterators");
using _Implementation =
__pstl::__dispatch<__pstl::__uninitialized_move_n, __pstl::__current_configuration, _RawPolicy>;
return __pstl::__handle_exception<_Implementation>(
diff --git a/libcxx/include/__pstl/backend_fwd.h b/libcxx/include/__pstl/backend_fwd.h
index a5b83f977b7098..2665209887944f 100644
--- a/libcxx/include/__pstl/backend_fwd.h
+++ b/libcxx/include/__pstl/backend_fwd.h
@@ -439,16 +439,16 @@ struct __destroy_n;
template <class _Backend, class _ExecutionPolicy>
struct __uninitialized_copy;
-// template <class _Policy, class _InputIterator, class _ForwardIterator>
-// optional<_ForwardIterator>
-// operator()(_Policy&& __policy, _InputIterator __first, _InputIterator __last, _ForwardIterator __result) const
+// template <class _Policy, class _ForwardIterator1, class _ForwardIterator2>
+// optional<_ForwardIterator2>
+// operator()(_Policy&& __policy, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result) const
// noexcept;
template <class _Backend, class _ExecutionPolicy>
struct __uninitialized_copy_n;
-// template <class _Policy, class _InputIterator, class _Size, class _ForwardIterator>
-// optional<_ForwardIterator>
-// operator()(_Policy&& __policy, _InputIterator __first, _Size __n, _ForwardIterator __result) const
+// template <class _Policy, class _ForwardIterator1, class _Size, class _ForwardIterator2>
+// optional<_ForwardIterator2>
+// operator()(_Policy&& __policy, _ForwardIterator1 __first, _Size __n, _ForwardIterator2 __result) const
// noexcept;
template <class _Backend, class _ExecutionPolicy>
@@ -465,16 +465,16 @@ struct __uninitialized_default_construct_n;
template <class _Backend, class _ExecutionPolicy>
struct __uninitialized_move;
-// template <class _Policy, class _InputIterator, class _ForwardIterator>
-// optional<_ForwardIterator>
-// operator()(_Policy&& __policy, _InputIterator __first, _InputIterator __last, _ForwardIterator __result) const
+// template <class _Policy, class _ForwardIterator1, class _ForwardIterator2>
+// optional<_ForwardIterator2>
+// operator()(_Policy&& __policy, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result) const
// noexcept;
template <class _Backend, class _ExecutionPolicy>
struct __uninitialized_move_n;
-// template <class _Policy, class _InputIterator, class _Size, class _ForwardIterator>
-// optional<pair<_InputIterator, _ForwardIterator>>
-// operator()(_Policy&& __policy, _InputIterator __first, _Size __n, _ForwardIterator __result) const
+// template <class _Policy, class _ForwardIterator1, class _Size, class _ForwardIterator2>
+// optional<pair<_ForwardIterator1, _ForwardIterator2>>
+// operator()(_Policy&& __policy, _ForwardIterator1 __first, _Size __n, _ForwardIterator2 __result) const
// noexcept;
template <class _Backend, class _ExecutionPolicy>
diff --git a/libcxx/include/__pstl/backends/default.h b/libcxx/include/__pstl/backends/default.h
index 648c2e10d033fc..61f5b0c342baac 100644
--- a/libcxx/include/__pstl/backends/default.h
+++ b/libcxx/include/__pstl/backends/default.h
@@ -925,13 +925,13 @@ struct __adjacent_difference<__default_backend_tag, _ExecutionPolicy> {
template <class _ExecutionPolicy>
struct __uninitialized_copy_n<__default_backend_tag, _ExecutionPolicy> {
- template <class _Policy, class _InputIterator, class _Size, class _ForwardIterator>
- optional<_ForwardIterator>
- operator()(_Policy&& __policy, _InputIterator __first, _Size __n, _ForwardIterator __result) const noexcept {
- if constexpr (__has_random_access_iterator_category_or_concept<_InputIterator>::value &&
- __has_random_access_iterator_category_or_concept<_ForwardIterator>::value) {
+ template <class _Policy, class _ForwardIterator1, class _Size, class _ForwardIterator2>
+ optional<_ForwardIterator2>
+ operator()(_Policy&& __policy, _ForwardIterator1 __first, _Size __n, _ForwardIterator2 __result) const noexcept {
+ if constexpr (__has_random_access_iterator_category_or_concept<_ForwardIterator1>::value &&
+ __has_random_access_iterator_category_or_concept<_ForwardIterator2>::value) {
using _UninitializedCopy = __dispatch<__uninitialized_copy, __current_configuration, _ExecutionPolicy>;
- _InputIterator __last = __first + __n;
+ _ForwardIterator1 __last = __first + __n;
return _UninitializedCopy()(__policy, std::move(__first), std::move(__last), std::move(__result));
} else {
return std::uninitialized_copy_n(std::move(__first), __n, std::move(__result));
@@ -945,13 +945,13 @@ struct __uninitialized_copy_n<__default_backend_tag, _ExecutionPolicy> {
template <class _ExecutionPolicy>
struct __uninitialized_move_n<__default_backend_tag, _ExecutionPolicy> {
- template <class _Policy, class _InputIterator, class _Size, class _ForwardIterator>
- optional<pair<_InputIterator, _ForwardIterator>>
- operator()(_Policy&& __policy, _InputIterator __first, _Size __n, _ForwardIterator __result) const noexcept {
- if constexpr (__has_random_access_iterator_category_or_concept<_InputIterator>::value &&
- __has_random_access_iterator_category_or_concept<_ForwardIterator>::value) {
+ template <class _Policy, class _ForwardIterator1, class _Size, class _ForwardIterator2>
+ optional<pair<_ForwardIterator1, _ForwardIterator2>>
+ operator()(_Policy&& __policy, _ForwardIterator1 __first, _Size __n, _ForwardIterator2 __result) const noexcept {
+ if constexpr (__has_random_access_iterator_category_or_concept<_ForwardIterator1>::value &&
+ __has_random_access_iterator_category_or_concept<_ForwardIterator2>::value) {
using _UninitializedMove = __dispatch<__uninitialized_move, __current_configuration, _ExecutionPolicy>;
- _InputIterator __last = __first + __n;
+ _ForwardIterator1 __last = __first + __n;
auto __res = _UninitializedMove()(__policy, std::move(__first), __last, std::move(__result));
if (!__res)
return nullopt; // Failed to run the parallel algorithm, propagate the failure
diff --git a/libcxx/include/__pstl/cpu_algos/uninitialized_algorithms.h b/libcxx/include/__pstl/cpu_algos/uninitialized_algorithms.h
index 861868c6ae6fab..c68e22a76758cc 100644
--- a/libcxx/include/__pstl/cpu_algos/uninitialized_algorithms.h
+++ b/libcxx/include/__pstl/cpu_algos/uninitialized_algorithms.h
@@ -36,17 +36,17 @@ namespace __pstl {
template <class _Backend, class _RawExecutionPolicy>
struct __cpu_parallel_uninitialized_copy {
- template <class _Policy, class _InputIterator, class _ForwardIterator>
- _LIBCPP_HIDE_FROM_ABI optional<_ForwardIterator>
- operator()(_Policy&&, _InputIterator __first, _InputIterator __last, _ForwardIterator __result) const noexcept {
+ template <class _Policy, class _ForwardIterator1, class _ForwardIterator2>
+ _LIBCPP_HIDE_FROM_ABI optional<_ForwardIterator2> operator()(
+ _Policy&&, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result) const noexcept {
if constexpr (__is_parallel_execution_policy_v<_RawExecutionPolicy> &&
- __has_random_access_iterator_category_or_concept<_InputIterator>::value &&
- __has_random_access_iterator_category_or_concept<_ForwardIterator>::value) {
+ __has_random_access_iterator_category_or_concept<_ForwardIterator1>::value &&
+ __has_random_access_iterator_category_or_concept<_ForwardIterator2>::value) {
auto __res = __pstl::__parallel_for_each_iter_pair<_Backend>(
__first,
__last,
__result,
- [](_InputIterator __brick_first, _InputIterator __brick_last, _ForwardIterator __brick_result) {
+ [](_ForwardIterator1 __brick_first, _ForwardIterator1 __brick_last, _ForwardIterator2 __brick_result) {
std::uninitialized_copy(std::move(__brick_first), std::move(__brick_last), std::move(__brick_result));
});
if (!__res) {
@@ -62,17 +62,17 @@ struct __cpu_parallel_uninitialized_copy {
template <class _Backend, class _RawExecutionPolicy>
struct __cpu_parallel_uninitialized_move {
- template <class _Policy, class _InputIterator, class _ForwardIterator>
- _LIBCPP_HIDE_FROM_ABI optional<_ForwardIterator>
- operator()(_Policy&&, _InputIterator __first, _InputIterator __last, _ForwardIterator __result) const noexcept {
+ template <class _Policy, class _ForwardIterator1, class _ForwardIterator2>
+ _LIBCPP_HIDE_FROM_ABI optional<_ForwardIterator2> operator()(
+ _Policy&&, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result) const noexcept {
if constexpr (__is_parallel_execution_policy_v<_RawExecutionPolicy> &&
- __has_random_access_iterator_category_or_concept<_InputIterator>::value &&
- __has_random_access_iterator_category_or_concept<_ForwardIterator>::value) {
+ __has_random_access_iterator_category_or_concept<_ForwardIterator1>::value &&
+ __has_random_access_iterator_category_or_concept<_ForwardIterator2>::value) {
auto __res = __pstl::__parallel_for_each_iter_pair<_Backend>(
__first,
__last,
__result,
- [](_InputIterator __brick_first, _InputIterator __brick_last, _ForwardIterator __brick_result) {
+ [](_ForwardIterator1 __brick_first, _ForwardIterator1 __brick_last, _ForwardIterator2 __brick_result) {
std::uninitialized_move(std::move(__brick_first), std::move(__brick_last), std::move(__brick_result));
});
if (!__res) {
diff --git a/libcxx/test/libcxx/algorithms/pstl.iterator-requirements.verify.cpp b/libcxx/test/libcxx/algorithms/pstl.iterator-requirements.verify.cpp
index a5ce8b80c381e5..d99869ce73f103 100644
--- a/libcxx/test/libcxx/algorithms/pstl.iterator-requirements.verify.cpp
+++ b/libcxx/test/libcxx/algorithms/pstl.iterator-requirements.verify.cpp
@@ -32,7 +32,6 @@
#include "test_iterators.h"
-using non_input_iterator = cpp17_output_iterator<int*>;
using non_forward_iterator = cpp17_input_iterator<int*>;
using non_bidirectional_iterator = forward_iterator<int*>;
using non_randomaccess_iterator = bidirectional_iterator<int*>;
@@ -40,8 +39,7 @@ struct non_output_iterator : forward_iterator<int*> {
constexpr int const& operator*() const; // prevent it from being an output iterator
};
-void f(non_input_iterator non_input,
- non_forward_iterator non_fwd,
+void f(non_forward_iterator non_fwd,
non_output_iterator non_output,
non_bidirectional_iterator non_bidir,
non_randomaccess_iterator non_random,
@@ -348,17 +346,17 @@ void f(non_input_iterator non_input,
{
std::uninitialized_copy(
- pol, non_input, non_input, it); // expected-error@*:* {{static assertion failed: uninitialized_copy}}
+ pol, non_fwd, non_fwd, it); // expected-error@*:* {{static assertion failed: uninitialized_copy}}
std::uninitialized_copy(pol, it, it, non_fwd); // expected-error@*:* {{static assertion failed: uninitialized_copy}}
std::uninitialized_copy_n(
- pol, non_input, n, it); // expected-error@*:* {{static assertion failed: uninitialized_copy_n}}
+ pol, non_fwd, n, it); // expected-error@*:* {{static assertion failed: uninitialized_copy_n}}
std::uninitialized_copy_n(
pol, it, n, non_fwd); // expected-error@*:* {{static assertion failed: uninitialized_copy_n}}
std::uninitialized_move(
- pol, non_input, non_input, it); // expected-error@*:* {{static assertion failed: uninitialized_move}}
+ pol, non_fwd, non_fwd, it); // expected-error@*:* {{static assertion failed: uninitialized_move}}
std::uninitialized_move(pol, it, it, non_fwd); // expected-error@*:* {{static assertion failed: uninitialized_move}}
std::uninitialized_move_n(
- pol, non_input, n, it); // expected-error@*:* {{static assertion failed: uninitialized_move_n}}
+ pol, non_fwd, n, it); // expected-error@*:* {{static assertion failed: uninitialized_move_n}}
std::uninitialized_move_n(
pol, it, n, non_fwd); // expected-error@*:* {{static assertion failed: uninitialized_move_n}}
}
diff --git a/libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/pstl.uninitialized_copy.pass.cpp b/libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/pstl.uninitialized_copy.pass.cpp
index b4dd55f1d29262..822be98066ba7c 100644
--- a/libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/pstl.uninitialized_copy.pass.cpp
+++ b/libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/pstl.uninitialized_copy.pass.cpp
@@ -13,11 +13,11 @@
// <memory>
// template <class ExecutionPolicy,
-// class InputIterator,...
[truncated]
``````````
</details>
https://github.com/llvm/llvm-project/pull/228462
More information about the libcxx-commits
mailing list