From 2c9afd2e5b798005d58009522e393e0365f0bc60 Mon Sep 17 00:00:00 2001 From: codingwithmagga Date: Fri, 19 Jun 2026 16:02:45 +0200 Subject: [PATCH 01/11] Rework constant_sequence taking a single auto NTTP to a variadic NTTP --- libcudacxx/include/cuda/__argument/argument.h | 163 +++++++++++++----- .../cuda/argument/argument_traits.pass.cpp | 54 +++--- .../cuda/argument/static_argument.pass.cpp | 60 ++++--- .../cuda/argument/usage_example.pass.cpp | 28 ++- 4 files changed, 204 insertions(+), 101 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index 0877a8df6d1..a11f8a91179 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -40,6 +40,7 @@ #include #include #include +#include #include #include @@ -111,16 +112,79 @@ class constant }; //! @brief Wraps a compile-time constant argument sequence. -template +template class __constant_sequence { public: - using value_type = ::cuda::std::remove_cvref_t; - using __element_type = __element_type_of_t; - - static_assert(__is_sequence_v, "The value type of __constant_sequence must be a sequence"); + using __element_type = ::cuda::std::remove_cvref_t; + using value_type = ::cuda::std::array<__element_type, sizeof...(Vs)>; + static constexpr ::cuda::std::size_t size = sizeof...(Vs); }; +template +struct __is_builtin_array : ::cuda::std::false_type +{}; + +template +struct __is_builtin_array : ::cuda::std::true_type +{}; + +template +struct __is_cuda_array : ::cuda::std::false_type +{}; + +template +struct __is_cuda_array<::cuda::std::array> : ::cuda::std::true_type +{}; + +template +struct __array_extent; + +template +struct __array_extent : ::cuda::std::integral_constant<::cuda::std::size_t, N>{}; + +template +struct __array_extent<::cuda::std::array> : ::cuda::std::integral_constant<::cuda::std::size_t, N>{}; + +template +inline constexpr bool __always_false_v = false; + +template +constexpr auto make_constant_sequence_impl(::cuda::std::index_sequence) +{ + using raw_array = ::cuda::std::remove_const_t<::cuda::std::remove_reference_t>; + + if constexpr (__is_builtin_array::value) + { + using T = ::cuda::std::remove_cv_t<::cuda::std::remove_extent_t>; + return __constant_sequence{}; + } + else if constexpr (__is_cuda_array::value) + { + using T = typename raw_array::value_type; + return __constant_sequence{}; + } + else + { + static_assert(__always_false_v, "unsupported array type"); + } +} + +//! @brief Makes a compile-time constant argument sequence. +//! In C++17, Arr must have static storage duration. +template +constexpr auto make_constant_sequence() +{ + using raw_array = ::cuda::std::remove_cv_t<::cuda::std::remove_reference_t>; + + static_assert(__is_builtin_array::value || __is_cuda_array::value, + "make_constant_sequence requires a cuda::std::array or non-empty C-style array"); + + constexpr ::cuda::std::size_t N = __array_extent::value; + + return make_constant_sequence_impl(::cuda::std::make_index_sequence{}); +} + // __assert_in_range // ===================================================================== @@ -621,8 +685,8 @@ template inline constexpr bool __is_wrapper_v> = true; template inline constexpr bool __is_wrapper_v> = true; -template -inline constexpr bool __is_wrapper_v<__constant_sequence<_Value>> = true; +template +inline constexpr bool __is_wrapper_v<__constant_sequence> = true; template inline constexpr bool __is_wrapper_v<__immediate_sequence<_Arg, _StaticBounds>> = true; template @@ -662,11 +726,11 @@ __unwrap(const constant<_Value, _Tp>&) noexcept return constant<_Value, _Tp>::__get_value(); } -template -[[nodiscard]] _CCCL_API constexpr ::cuda::std::remove_cvref_t -__unwrap(const __constant_sequence<_Value>&) noexcept +//! Unwraps a compile-time constant argument sequence into a canonical cuda::std::array value. +template +[[nodiscard]] _CCCL_API constexpr auto __unwrap(const __constant_sequence&) noexcept { - return _Value; + return ::cuda::std::array{Vs...}; } template @@ -735,32 +799,48 @@ _CCCL_API constexpr auto __constant_compute_highest() noexcept return constant<_Value, _Tp>::__get_value(); } -template -_CCCL_API constexpr auto __constant_sequence_compute_lowest() noexcept +template +_CCCL_API constexpr T __constant_sequence_compute_lowest() noexcept { - using _ElementType = __element_type_of_t<::cuda::std::remove_cvref_t>; - auto __first = _Value.begin(); - auto __last = _Value.end(); - - if (__first == __last) + if constexpr (sizeof...(Vs) == 0) { - return ::cuda::std::numeric_limits<_ElementType>::lowest(); + return ::cuda::std::numeric_limits::lowest(); + } + else + { + constexpr T values[] = {Vs...}; + T __min = values[0]; + for (T __v : values) + { + if (__v < __min) + { + __min = __v; + } + } + return __min; } - return static_cast<_ElementType>(*::cuda::std::min_element(__first, __last)); } -template -_CCCL_API constexpr auto __constant_sequence_compute_highest() noexcept +template +_CCCL_API constexpr T __constant_sequence_compute_highest() noexcept { - using _ElementType = __element_type_of_t<::cuda::std::remove_cvref_t>; - auto __first = _Value.begin(); - auto __last = _Value.end(); - - if (__first == __last) + if constexpr (sizeof...(Vs) == 0) { - return (::cuda::std::numeric_limits<_ElementType>::max)(); + return ::cuda::std::numeric_limits::max(); + } + else + { + constexpr T values[] = {Vs...}; + T __max = values[0]; + for (T __v : values) + { + if (__v > __max) + { + __max = __v; + } + } + return __max; } - return static_cast<_ElementType>(*::cuda::std::max_element(__first, __last)); } // ===================================================================== @@ -811,17 +891,16 @@ struct __traits_impl> static constexpr element_type highest = __wrapper_static_highest(); }; -template -struct __traits_impl<__constant_sequence<_Value>> +template +struct __traits_impl<__constant_sequence> { - using value_type = ::cuda::std::remove_cvref_t; - using element_type = __element_type_of_t; - static_assert(__is_sequence_v, "The value type of __constant_sequence must be a sequence"); + using element_type = ::cuda::std::remove_cvref_t; + using value_type = ::cuda::std::array; static constexpr bool is_constant = true; static constexpr bool is_deferred = false; static constexpr bool is_single_value = false; - static constexpr element_type lowest = __constant_sequence_compute_lowest<_Value>(); - static constexpr element_type highest = __constant_sequence_compute_highest<_Value>(); + static constexpr element_type lowest = __constant_sequence_compute_lowest(); + static constexpr element_type highest = __constant_sequence_compute_highest(); }; template @@ -896,10 +975,10 @@ template return __constant_compute_lowest<_Value, _Tp>(); } -template -[[nodiscard]] _CCCL_API constexpr auto __lowest_(__constant_sequence<_Value>) noexcept +template +[[nodiscard]] _CCCL_API constexpr auto __lowest_(__constant_sequence) noexcept { - return __constant_sequence_compute_lowest<_Value>(); + return __constant_sequence_compute_lowest(); } template @@ -949,10 +1028,10 @@ template return __constant_compute_highest<_Value, _Tp>(); } -template -[[nodiscard]] _CCCL_API constexpr auto __highest_(__constant_sequence<_Value>) noexcept +template +[[nodiscard]] _CCCL_API constexpr auto __highest_(__constant_sequence) noexcept { - return __constant_sequence_compute_highest<_Value>(); + return __constant_sequence_compute_highest(); } template diff --git a/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp b/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp index aaf57291e23..89b4494a8df 100644 --- a/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp +++ b/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp @@ -103,9 +103,13 @@ TEST_FUNC void test() static_assert(!cuda::args::__traits>::is_deferred); static_assert(!cuda::args::__traits>>::is_deferred); static_assert(!cuda::args::__traits>::is_deferred); -#if TEST_HAS_CLASS_NTTP - static_assert(!cuda::args::__traits{1, 2, 3}>>::is_deferred); -#endif // TEST_HAS_CLASS_NTTP + + static_assert(!cuda::args::__traits>::is_deferred); + static constexpr int carr[] = {1, 2, 3}; + static constexpr ::cuda::std::array cudaarr = {1, 2, 3}; + static_assert(!cuda::args::__traits())>::is_deferred); + static_assert(!cuda::args::__traits())>::is_deferred); + static_assert(cuda::args::__traits>>::is_deferred); static_assert(cuda::args::__traits>>::is_deferred); @@ -118,10 +122,11 @@ TEST_FUNC void test() static_assert(cuda::args::__traits>>::is_single_value); static_assert(!cuda::args::__traits>>::is_single_value); static_assert(cuda::args::__traits>::is_single_value); -#if TEST_HAS_CLASS_NTTP - static_assert( - !cuda::args::__traits{1, 2, 3}>>::is_single_value); -#endif // TEST_HAS_CLASS_NTTP + + static_assert(!cuda::args::__traits>::is_single_value); + static_assert(!cuda::args::__traits())>::is_single_value); + static_assert(!cuda::args::__traits())>::is_single_value); + static_assert(cuda::args::__traits>::is_single_value); static_assert(!cuda::args::__traits>>::is_single_value); @@ -134,11 +139,15 @@ TEST_FUNC void test() cuda::std::span>); static_assert(cuda::std::is_same_v>::value_type, int>); static_assert(cuda::std::is_same_v>::value_type, float>); -#if TEST_HAS_CLASS_NTTP - static_assert(cuda::std::is_same_v< - cuda::args::__traits{1, 2, 3}>>::value_type, - cuda::std::array>); -#endif // TEST_HAS_CLASS_NTTP + + static_assert(cuda::std::is_same_v>::value_type, + cuda::std::array>); + static_assert( + cuda::std::is_same_v())>::value_type, + cuda::std::array>); + static_assert( + cuda::std::is_same_v())>::value_type, + cuda::std::array>); // --- argument_traits: lowest / highest --- @@ -155,10 +164,13 @@ TEST_FUNC void test() == 8); static_assert(cuda::args::__traits>::lowest == 10.0f); static_assert(cuda::args::__traits>::highest == 10.0f); -#if TEST_HAS_CLASS_NTTP - static_assert(cuda::args::__traits{3, 1, 2}>>::lowest == 1); - static_assert(cuda::args::__traits{3, 1, 2}>>::highest == 3); -#endif // TEST_HAS_CLASS_NTTP + + static_assert(cuda::args::__traits>::lowest == 1); + static_assert(cuda::args::__traits>::highest == 3); + static_assert(cuda::args::__traits())>::lowest == 1); + static_assert(cuda::args::__traits())>::highest == 3); + static_assert(cuda::args::__traits())>::lowest == 1); + static_assert(cuda::args::__traits())>::highest == 3); // --- Free function bounds on plain values --- @@ -166,16 +178,6 @@ TEST_FUNC void test() static_assert(cuda::args::__highest_(42) == (cuda::std::numeric_limits::max)()); static_assert(cuda::args::__lowest_(1.0f) == cuda::std::numeric_limits::lowest()); static_assert(cuda::args::__highest_(1.0f) == (cuda::std::numeric_limits::max)()); - - // --- Scalar and sequence wrappers expose distinct single-value traits --- - - static_assert(cuda::args::__traits>::is_single_value); - static_assert(cuda::args::__traits>::is_single_value); - static_assert(!cuda::args::__traits>>::is_single_value); -#if TEST_HAS_CLASS_NTTP - static_assert( - !cuda::args::__traits{1, 2, 3}>>::is_single_value); -#endif // TEST_HAS_CLASS_NTTP } int main(int, char**) diff --git a/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp b/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp index f3cc7a2a993..3b85a8db9a8 100644 --- a/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp +++ b/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp @@ -55,16 +55,24 @@ TEST_FUNC void test() } #endif // TEST_HAS_CLASS_NTTP -#if TEST_HAS_CLASS_NTTP // Array sequence { - constexpr auto sa_arr = cuda::args::__constant_sequence{128, 256, 512}>{}; + static constexpr int carr[] = {128, 256, 512}; + constexpr auto sa_arr = cuda::args::make_constant_sequence(); + static_assert(cuda::args::__unwrap(sa_arr)[0] == 128); + static_assert(cuda::args::__unwrap(sa_arr)[1] == 256); + static_assert(cuda::args::__unwrap(sa_arr)[2] == 512); + static_assert(cuda::std::is_same_v>); + } + + { + static constexpr ::cuda::std::array cudaarr = {128, 256, 512}; + constexpr auto sa_arr = cuda::args::make_constant_sequence(); static_assert(cuda::args::__unwrap(sa_arr)[0] == 128); static_assert(cuda::args::__unwrap(sa_arr)[1] == 256); static_assert(cuda::args::__unwrap(sa_arr)[2] == 512); static_assert(cuda::std::is_same_v>); } -#endif // TEST_HAS_CLASS_NTTP // Bounds: scalar { @@ -73,23 +81,27 @@ TEST_FUNC void test() static_assert(cuda::args::__highest_(sa) == 42); } -#if TEST_HAS_CLASS_NTTP // Bounds: array sequence computes lowest/highest of elements { - constexpr auto sa = cuda::args::__constant_sequence{128, 256, 512}>{}; + static constexpr int carr[] = {128, 256, 512}; + constexpr auto sa = cuda::args::make_constant_sequence(); + static_assert(cuda::args::__lowest_(sa) == 128); + static_assert(cuda::args::__highest_(sa) == 512); + } + { + static constexpr ::cuda::std::array cudaarr = {128, 256, 512}; + constexpr auto sa = cuda::args::make_constant_sequence(); static_assert(cuda::args::__lowest_(sa) == 128); static_assert(cuda::args::__highest_(sa) == 512); } -#endif // TEST_HAS_CLASS_NTTP -#if TEST_HAS_CLASS_NTTP // Bounds: empty array sequence has unconstrained element bounds { - constexpr auto sa = cuda::args::__constant_sequence{}>{}; + static constexpr ::cuda::std::array cudaarr = {}; + constexpr auto sa = cuda::args::make_constant_sequence(); static_assert(cuda::args::__lowest_(sa) == cuda::std::numeric_limits::lowest()); static_assert(cuda::args::__highest_(sa) == (cuda::std::numeric_limits::max)()); } -#endif // TEST_HAS_CLASS_NTTP // Traits { @@ -114,25 +126,29 @@ TEST_FUNC void test() static_assert(traits::highest == 10.0f); } -#if TEST_HAS_CLASS_NTTP // Sequence traits { - using traits = cuda::args::__traits{1, 2, 3}>>; + static constexpr int carr[] = {1, 2, 3}; + using traits = cuda::args::__traits())>; + static_assert(traits::is_constant); + static_assert(!traits::is_deferred); + static_assert(!traits::is_single_value); + static_assert(cuda::std::is_same_v>); + static_assert(cuda::std::is_same_v); + } + { + static constexpr ::cuda::std::array cudaarr = {1, 2, 3}; + using traits = cuda::args::__traits())>; static_assert(traits::is_constant); static_assert(!traits::is_deferred); static_assert(!traits::is_single_value); static_assert(cuda::std::is_same_v>); static_assert(cuda::std::is_same_v); } -#endif // TEST_HAS_CLASS_NTTP - // Single value: scalar is single, sequence is not + // Single value: scalar is single { static_assert(!cuda::args::__is_sequence_v>::value_type>); -#if TEST_HAS_CLASS_NTTP - static_assert( - !cuda::args::__traits{1, 2, 3}>>::is_single_value); -#endif // TEST_HAS_CLASS_NTTP } // Unwrap: scalar @@ -149,16 +165,6 @@ TEST_FUNC void test() static_assert(val == 10.0f); static_assert(cuda::std::is_same_v); } - -#if TEST_HAS_CLASS_NTTP - // Unwrap: sequence - { - constexpr auto sa = cuda::args::__constant_sequence{10, 20, 30}>{}; - constexpr auto val = cuda::args::__unwrap(sa); - static_assert(val[0] == 10); - static_assert(val[2] == 30); - } -#endif // TEST_HAS_CLASS_NTTP } int main(int, char**) diff --git a/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp b/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp index eada29e23de..ad54a8c745e 100644 --- a/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp +++ b/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp @@ -73,6 +73,11 @@ TEST_FUNC constexpr int process_segments(_SegSizeArg __seg_size) } } +constexpr ::cuda::std::array cudaarr_shared = {64, 128, 256}; +constexpr int carr_shared[] = {64, 128, 256}; +constexpr ::cuda::std::array cudaarr_global = {64, 128, 512}; +constexpr int carr_global[] = {64, 128, 512}; + TEST_FUNC constexpr bool test() { // Plain scalar: no bounds, global memory, buffer clamped to default @@ -101,10 +106,15 @@ TEST_FUNC constexpr bool test() assert(process_segments(seg_size) == 128); } -#if TEST_HAS_CLASS_NTTP // __constant_sequence: array sequence, highest fits in shared memory { - constexpr auto seg_sizes = cuda::args::__constant_sequence{}; + constexpr auto seg_sizes = cuda::args::make_constant_sequence(); + static_assert(select_variant(seg_sizes) == algorithm_variant::shared_memory); + assert(compute_buffer_size(seg_sizes, 3) == 256 * 3); + assert(process_segments(seg_sizes) == 64 + 128 + 256); + } + { + constexpr auto seg_sizes = cuda::args::make_constant_sequence(); static_assert(select_variant(seg_sizes) == algorithm_variant::shared_memory); assert(compute_buffer_size(seg_sizes, 3) == 256 * 3); assert(process_segments(seg_sizes) == 64 + 128 + 256); @@ -112,12 +122,17 @@ TEST_FUNC constexpr bool test() // __constant_sequence: array sequence, highest exceeds shared memory, buffer clamped { - constexpr auto seg_sizes = cuda::args::__constant_sequence{}; + constexpr auto seg_sizes = cuda::args::make_constant_sequence(); + static_assert(select_variant(seg_sizes) == algorithm_variant::global_memory); + assert(compute_buffer_size(seg_sizes, 3) == 512 * 3); + assert(process_segments(seg_sizes) == 64 + 128 + 512); + } + { + constexpr auto seg_sizes = cuda::args::make_constant_sequence(); static_assert(select_variant(seg_sizes) == algorithm_variant::global_memory); assert(compute_buffer_size(seg_sizes, 3) == 512 * 3); assert(process_segments(seg_sizes) == 64 + 128 + 512); } -#endif // TEST_HAS_CLASS_NTTP // immediate: tight static bounds, shared memory, buffer = value { @@ -145,8 +160,9 @@ TEST_FUNC constexpr bool test() // __immediate_sequence: per-segment span with runtime bounds only { - int sizes[3] = {64, 128, 96}; - auto seg_sizes = cuda::args::__immediate_sequence{cuda::std::span{sizes, 3}, cuda::args::bounds(1, 200)}; + int sizes[3] = {64, 128, 96}; + [[maybe_unused]] auto seg_sizes = + cuda::args::__immediate_sequence{cuda::std::span{sizes, 3}, cuda::args::bounds(1, 200)}; assert(select_variant(seg_sizes) == algorithm_variant::global_memory); assert(compute_buffer_size(seg_sizes, 3) == 200 * 3); assert(process_segments(seg_sizes) == 64 + 128 + 96); From 7ed4d84926a9846183262ed796bf1972b3985d87 Mon Sep 17 00:00:00 2001 From: "Schoos, Marco" Date: Mon, 22 Jun 2026 14:49:01 +0200 Subject: [PATCH 02/11] Fix template parameter naming --- libcudacxx/include/cuda/__argument/argument.h | 100 +++++++++--------- 1 file changed, 50 insertions(+), 50 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index a11f8a91179..3d5d6d4f957 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -112,39 +112,39 @@ class constant }; //! @brief Wraps a compile-time constant argument sequence. -template +template class __constant_sequence { public: - using __element_type = ::cuda::std::remove_cvref_t; - using value_type = ::cuda::std::array<__element_type, sizeof...(Vs)>; - static constexpr ::cuda::std::size_t size = sizeof...(Vs); + using __element_type = ::cuda::std::remove_cvref_t<_Tp>; + using value_type = ::cuda::std::array<__element_type, sizeof...(_Vs)>; + static constexpr ::cuda::std::size_t size = sizeof...(_Vs); }; -template +template struct __is_builtin_array : ::cuda::std::false_type {}; -template -struct __is_builtin_array : ::cuda::std::true_type +template +struct __is_builtin_array<_Tp[_Size]> : ::cuda::std::true_type {}; -template +template struct __is_cuda_array : ::cuda::std::false_type {}; -template -struct __is_cuda_array<::cuda::std::array> : ::cuda::std::true_type +template +struct __is_cuda_array<::cuda::std::array<_Tp, _Size>> : ::cuda::std::true_type {}; -template +template struct __array_extent; -template -struct __array_extent : ::cuda::std::integral_constant<::cuda::std::size_t, N>{}; +template +struct __array_extent<_Tp[_Size]> : ::cuda::std::integral_constant<::cuda::std::size_t, _Size>{}; -template -struct __array_extent<::cuda::std::array> : ::cuda::std::integral_constant<::cuda::std::size_t, N>{}; +template +struct __array_extent<::cuda::std::array<_Tp, _Size>> : ::cuda::std::integral_constant<::cuda::std::size_t, _Size>{}; template inline constexpr bool __always_false_v = false; @@ -156,13 +156,13 @@ constexpr auto make_constant_sequence_impl(::cuda::std::index_sequence) if constexpr (__is_builtin_array::value) { - using T = ::cuda::std::remove_cv_t<::cuda::std::remove_extent_t>; - return __constant_sequence{}; + using _Tp = ::cuda::std::remove_cv_t<::cuda::std::remove_extent_t>; + return __constant_sequence<_Tp, Arr[Is]...>{}; } else if constexpr (__is_cuda_array::value) { - using T = typename raw_array::value_type; - return __constant_sequence{}; + using _Tp = typename raw_array::value_type; + return __constant_sequence<_Tp, Arr[Is]...>{}; } else { @@ -685,8 +685,8 @@ template inline constexpr bool __is_wrapper_v> = true; template inline constexpr bool __is_wrapper_v> = true; -template -inline constexpr bool __is_wrapper_v<__constant_sequence> = true; +template +inline constexpr bool __is_wrapper_v<__constant_sequence<_Tp, _Vs...>> = true; template inline constexpr bool __is_wrapper_v<__immediate_sequence<_Arg, _StaticBounds>> = true; template @@ -727,10 +727,10 @@ __unwrap(const constant<_Value, _Tp>&) noexcept } //! Unwraps a compile-time constant argument sequence into a canonical cuda::std::array value. -template -[[nodiscard]] _CCCL_API constexpr auto __unwrap(const __constant_sequence&) noexcept +template +[[nodiscard]] _CCCL_API constexpr auto __unwrap(const __constant_sequence<_Tp, _Vs...>&) noexcept { - return ::cuda::std::array{Vs...}; + return ::cuda::std::array<_Tp, sizeof...(_Vs)>{_Vs...}; } template @@ -799,18 +799,18 @@ _CCCL_API constexpr auto __constant_compute_highest() noexcept return constant<_Value, _Tp>::__get_value(); } -template -_CCCL_API constexpr T __constant_sequence_compute_lowest() noexcept +template +_CCCL_API constexpr _Tp __constant_sequence_compute_lowest() noexcept { - if constexpr (sizeof...(Vs) == 0) + if constexpr (sizeof...(_Vs) == 0) { - return ::cuda::std::numeric_limits::lowest(); + return ::cuda::std::numeric_limits<_Tp>::lowest(); } else { - constexpr T values[] = {Vs...}; - T __min = values[0]; - for (T __v : values) + constexpr _Tp values[] = {_Vs...}; + _Tp __min = values[0]; + for (_Tp __v : values) { if (__v < __min) { @@ -821,18 +821,18 @@ _CCCL_API constexpr T __constant_sequence_compute_lowest() noexcept } } -template -_CCCL_API constexpr T __constant_sequence_compute_highest() noexcept +template +_CCCL_API constexpr _Tp __constant_sequence_compute_highest() noexcept { - if constexpr (sizeof...(Vs) == 0) + if constexpr (sizeof...(_Vs) == 0) { - return ::cuda::std::numeric_limits::max(); + return ::cuda::std::numeric_limits<_Tp>::max(); } else { - constexpr T values[] = {Vs...}; - T __max = values[0]; - for (T __v : values) + constexpr _Tp values[] = {_Vs...}; + _Tp __max = values[0]; + for (_Tp __v : values) { if (__v > __max) { @@ -891,16 +891,16 @@ struct __traits_impl> static constexpr element_type highest = __wrapper_static_highest(); }; -template -struct __traits_impl<__constant_sequence> +template +struct __traits_impl<__constant_sequence<_Tp, _Vs...>> { - using element_type = ::cuda::std::remove_cvref_t; - using value_type = ::cuda::std::array; + using element_type = ::cuda::std::remove_cvref_t<_Tp>; + using value_type = ::cuda::std::array; static constexpr bool is_constant = true; static constexpr bool is_deferred = false; static constexpr bool is_single_value = false; - static constexpr element_type lowest = __constant_sequence_compute_lowest(); - static constexpr element_type highest = __constant_sequence_compute_highest(); + static constexpr element_type lowest = __constant_sequence_compute_lowest<_Tp, _Vs...>(); + static constexpr element_type highest = __constant_sequence_compute_highest<_Tp, _Vs...>(); }; template @@ -975,10 +975,10 @@ template return __constant_compute_lowest<_Value, _Tp>(); } -template -[[nodiscard]] _CCCL_API constexpr auto __lowest_(__constant_sequence) noexcept +template +[[nodiscard]] _CCCL_API constexpr auto __lowest_(__constant_sequence<_Tp, _Vs...>) noexcept { - return __constant_sequence_compute_lowest(); + return __constant_sequence_compute_lowest<_Tp, _Vs...>(); } template @@ -1028,10 +1028,10 @@ template return __constant_compute_highest<_Value, _Tp>(); } -template -[[nodiscard]] _CCCL_API constexpr auto __highest_(__constant_sequence) noexcept +template +[[nodiscard]] _CCCL_API constexpr auto __highest_(__constant_sequence<_Tp, _Vs...>) noexcept { - return __constant_sequence_compute_highest(); + return __constant_sequence_compute_highest<_Tp, _Vs...>(); } template From 23f15cf1a926ba09f48b2537b356cdfe36304d76 Mon Sep 17 00:00:00 2001 From: "Schoos, Marco" Date: Mon, 22 Jun 2026 14:55:21 +0200 Subject: [PATCH 03/11] Add _CCCL_API for make_constant_sequence. Add "__" prefix to funtions --- libcudacxx/include/cuda/__argument/argument.h | 6 +++--- .../cuda/argument/argument_traits.pass.cpp | 20 +++++++++---------- .../cuda/argument/static_argument.pass.cpp | 14 ++++++------- .../cuda/argument/usage_example.pass.cpp | 8 ++++---- 4 files changed, 24 insertions(+), 24 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index 3d5d6d4f957..b989383ffe4 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -150,7 +150,7 @@ template inline constexpr bool __always_false_v = false; template -constexpr auto make_constant_sequence_impl(::cuda::std::index_sequence) +_CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequence) { using raw_array = ::cuda::std::remove_const_t<::cuda::std::remove_reference_t>; @@ -173,7 +173,7 @@ constexpr auto make_constant_sequence_impl(::cuda::std::index_sequence) //! @brief Makes a compile-time constant argument sequence. //! In C++17, Arr must have static storage duration. template -constexpr auto make_constant_sequence() +_CCCL_API constexpr auto __make_constant_sequence() { using raw_array = ::cuda::std::remove_cv_t<::cuda::std::remove_reference_t>; @@ -182,7 +182,7 @@ constexpr auto make_constant_sequence() constexpr ::cuda::std::size_t N = __array_extent::value; - return make_constant_sequence_impl(::cuda::std::make_index_sequence{}); + return __make_constant_sequence_impl(::cuda::std::make_index_sequence{}); } // __assert_in_range diff --git a/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp b/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp index 89b4494a8df..e3fef4affb8 100644 --- a/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp +++ b/libcudacxx/test/libcudacxx/cuda/argument/argument_traits.pass.cpp @@ -107,8 +107,8 @@ TEST_FUNC void test() static_assert(!cuda::args::__traits>::is_deferred); static constexpr int carr[] = {1, 2, 3}; static constexpr ::cuda::std::array cudaarr = {1, 2, 3}; - static_assert(!cuda::args::__traits())>::is_deferred); - static_assert(!cuda::args::__traits())>::is_deferred); + static_assert(!cuda::args::__traits())>::is_deferred); + static_assert(!cuda::args::__traits())>::is_deferred); static_assert(cuda::args::__traits>>::is_deferred); static_assert(cuda::args::__traits>>::is_deferred); @@ -124,8 +124,8 @@ TEST_FUNC void test() static_assert(cuda::args::__traits>::is_single_value); static_assert(!cuda::args::__traits>::is_single_value); - static_assert(!cuda::args::__traits())>::is_single_value); - static_assert(!cuda::args::__traits())>::is_single_value); + static_assert(!cuda::args::__traits())>::is_single_value); + static_assert(!cuda::args::__traits())>::is_single_value); static_assert(cuda::args::__traits>::is_single_value); static_assert(!cuda::args::__traits>>::is_single_value); @@ -143,10 +143,10 @@ TEST_FUNC void test() static_assert(cuda::std::is_same_v>::value_type, cuda::std::array>); static_assert( - cuda::std::is_same_v())>::value_type, + cuda::std::is_same_v())>::value_type, cuda::std::array>); static_assert( - cuda::std::is_same_v())>::value_type, + cuda::std::is_same_v())>::value_type, cuda::std::array>); // --- argument_traits: lowest / highest --- @@ -167,10 +167,10 @@ TEST_FUNC void test() static_assert(cuda::args::__traits>::lowest == 1); static_assert(cuda::args::__traits>::highest == 3); - static_assert(cuda::args::__traits())>::lowest == 1); - static_assert(cuda::args::__traits())>::highest == 3); - static_assert(cuda::args::__traits())>::lowest == 1); - static_assert(cuda::args::__traits())>::highest == 3); + static_assert(cuda::args::__traits())>::lowest == 1); + static_assert(cuda::args::__traits())>::highest == 3); + static_assert(cuda::args::__traits())>::lowest == 1); + static_assert(cuda::args::__traits())>::highest == 3); // --- Free function bounds on plain values --- diff --git a/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp b/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp index 3b85a8db9a8..b7d98a70aae 100644 --- a/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp +++ b/libcudacxx/test/libcudacxx/cuda/argument/static_argument.pass.cpp @@ -58,7 +58,7 @@ TEST_FUNC void test() // Array sequence { static constexpr int carr[] = {128, 256, 512}; - constexpr auto sa_arr = cuda::args::make_constant_sequence(); + constexpr auto sa_arr = cuda::args::__make_constant_sequence(); static_assert(cuda::args::__unwrap(sa_arr)[0] == 128); static_assert(cuda::args::__unwrap(sa_arr)[1] == 256); static_assert(cuda::args::__unwrap(sa_arr)[2] == 512); @@ -67,7 +67,7 @@ TEST_FUNC void test() { static constexpr ::cuda::std::array cudaarr = {128, 256, 512}; - constexpr auto sa_arr = cuda::args::make_constant_sequence(); + constexpr auto sa_arr = cuda::args::__make_constant_sequence(); static_assert(cuda::args::__unwrap(sa_arr)[0] == 128); static_assert(cuda::args::__unwrap(sa_arr)[1] == 256); static_assert(cuda::args::__unwrap(sa_arr)[2] == 512); @@ -84,13 +84,13 @@ TEST_FUNC void test() // Bounds: array sequence computes lowest/highest of elements { static constexpr int carr[] = {128, 256, 512}; - constexpr auto sa = cuda::args::make_constant_sequence(); + constexpr auto sa = cuda::args::__make_constant_sequence(); static_assert(cuda::args::__lowest_(sa) == 128); static_assert(cuda::args::__highest_(sa) == 512); } { static constexpr ::cuda::std::array cudaarr = {128, 256, 512}; - constexpr auto sa = cuda::args::make_constant_sequence(); + constexpr auto sa = cuda::args::__make_constant_sequence(); static_assert(cuda::args::__lowest_(sa) == 128); static_assert(cuda::args::__highest_(sa) == 512); } @@ -98,7 +98,7 @@ TEST_FUNC void test() // Bounds: empty array sequence has unconstrained element bounds { static constexpr ::cuda::std::array cudaarr = {}; - constexpr auto sa = cuda::args::make_constant_sequence(); + constexpr auto sa = cuda::args::__make_constant_sequence(); static_assert(cuda::args::__lowest_(sa) == cuda::std::numeric_limits::lowest()); static_assert(cuda::args::__highest_(sa) == (cuda::std::numeric_limits::max)()); } @@ -129,7 +129,7 @@ TEST_FUNC void test() // Sequence traits { static constexpr int carr[] = {1, 2, 3}; - using traits = cuda::args::__traits())>; + using traits = cuda::args::__traits())>; static_assert(traits::is_constant); static_assert(!traits::is_deferred); static_assert(!traits::is_single_value); @@ -138,7 +138,7 @@ TEST_FUNC void test() } { static constexpr ::cuda::std::array cudaarr = {1, 2, 3}; - using traits = cuda::args::__traits())>; + using traits = cuda::args::__traits())>; static_assert(traits::is_constant); static_assert(!traits::is_deferred); static_assert(!traits::is_single_value); diff --git a/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp b/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp index ad54a8c745e..c8801a56472 100644 --- a/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp +++ b/libcudacxx/test/libcudacxx/cuda/argument/usage_example.pass.cpp @@ -108,13 +108,13 @@ TEST_FUNC constexpr bool test() // __constant_sequence: array sequence, highest fits in shared memory { - constexpr auto seg_sizes = cuda::args::make_constant_sequence(); + constexpr auto seg_sizes = cuda::args::__make_constant_sequence(); static_assert(select_variant(seg_sizes) == algorithm_variant::shared_memory); assert(compute_buffer_size(seg_sizes, 3) == 256 * 3); assert(process_segments(seg_sizes) == 64 + 128 + 256); } { - constexpr auto seg_sizes = cuda::args::make_constant_sequence(); + constexpr auto seg_sizes = cuda::args::__make_constant_sequence(); static_assert(select_variant(seg_sizes) == algorithm_variant::shared_memory); assert(compute_buffer_size(seg_sizes, 3) == 256 * 3); assert(process_segments(seg_sizes) == 64 + 128 + 256); @@ -122,13 +122,13 @@ TEST_FUNC constexpr bool test() // __constant_sequence: array sequence, highest exceeds shared memory, buffer clamped { - constexpr auto seg_sizes = cuda::args::make_constant_sequence(); + constexpr auto seg_sizes = cuda::args::__make_constant_sequence(); static_assert(select_variant(seg_sizes) == algorithm_variant::global_memory); assert(compute_buffer_size(seg_sizes, 3) == 512 * 3); assert(process_segments(seg_sizes) == 64 + 128 + 512); } { - constexpr auto seg_sizes = cuda::args::make_constant_sequence(); + constexpr auto seg_sizes = cuda::args::__make_constant_sequence(); static_assert(select_variant(seg_sizes) == algorithm_variant::global_memory); assert(compute_buffer_size(seg_sizes, 3) == 512 * 3); assert(process_segments(seg_sizes) == 64 + 128 + 512); From c7c27f9ba57033d89f936c56adcecf91f5cd01c8 Mon Sep 17 00:00:00 2001 From: "Schoos, Marco" Date: Mon, 22 Jun 2026 14:58:34 +0200 Subject: [PATCH 04/11] Remove cv of _Tp in __unwrap function --- libcudacxx/include/cuda/__argument/argument.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index b989383ffe4..4e8654bef6d 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -730,7 +730,7 @@ __unwrap(const constant<_Value, _Tp>&) noexcept template [[nodiscard]] _CCCL_API constexpr auto __unwrap(const __constant_sequence<_Tp, _Vs...>&) noexcept { - return ::cuda::std::array<_Tp, sizeof...(_Vs)>{_Vs...}; + return ::cuda::std::array<::cuda::std::remove_cvref_t<_Tp>, sizeof...(_Vs)>{_Vs...}; } template From a62cb39109f04e674313838b91a41856fc0af174 Mon Sep 17 00:00:00 2001 From: "Schoos, Marco" Date: Mon, 22 Jun 2026 15:00:55 +0200 Subject: [PATCH 05/11] Use safe version of max() function call --- libcudacxx/include/cuda/__argument/argument.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index 4e8654bef6d..4459b9540b1 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -826,7 +826,7 @@ _CCCL_API constexpr _Tp __constant_sequence_compute_highest() noexcept { if constexpr (sizeof...(_Vs) == 0) { - return ::cuda::std::numeric_limits<_Tp>::max(); + return (::cuda::std::numeric_limits<_Tp>::max)(); } else { From 6bf8684e703a5cd69b45207cd315a8d16dacd2f3 Mon Sep 17 00:00:00 2001 From: "Schoos, Marco" Date: Mon, 22 Jun 2026 15:52:47 +0200 Subject: [PATCH 06/11] Replace custom traits with existing ones --- libcudacxx/include/cuda/__argument/argument.h | 44 +++++++------------ 1 file changed, 15 insertions(+), 29 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index 4459b9540b1..fc7f1ebaa9c 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -28,8 +28,10 @@ #include #include #include +#include #include #include +#include #include #include #include @@ -121,31 +123,6 @@ class __constant_sequence static constexpr ::cuda::std::size_t size = sizeof...(_Vs); }; -template -struct __is_builtin_array : ::cuda::std::false_type -{}; - -template -struct __is_builtin_array<_Tp[_Size]> : ::cuda::std::true_type -{}; - -template -struct __is_cuda_array : ::cuda::std::false_type -{}; - -template -struct __is_cuda_array<::cuda::std::array<_Tp, _Size>> : ::cuda::std::true_type -{}; - -template -struct __array_extent; - -template -struct __array_extent<_Tp[_Size]> : ::cuda::std::integral_constant<::cuda::std::size_t, _Size>{}; - -template -struct __array_extent<::cuda::std::array<_Tp, _Size>> : ::cuda::std::integral_constant<::cuda::std::size_t, _Size>{}; - template inline constexpr bool __always_false_v = false; @@ -154,12 +131,12 @@ _CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequen { using raw_array = ::cuda::std::remove_const_t<::cuda::std::remove_reference_t>; - if constexpr (__is_builtin_array::value) + if constexpr (::cuda::std::is_bounded_array_v) { using _Tp = ::cuda::std::remove_cv_t<::cuda::std::remove_extent_t>; return __constant_sequence<_Tp, Arr[Is]...>{}; } - else if constexpr (__is_cuda_array::value) + else if constexpr (::cuda::std::__is_cuda_std_array_v) { using _Tp = typename raw_array::value_type; return __constant_sequence<_Tp, Arr[Is]...>{}; @@ -177,10 +154,19 @@ _CCCL_API constexpr auto __make_constant_sequence() { using raw_array = ::cuda::std::remove_cv_t<::cuda::std::remove_reference_t>; - static_assert(__is_builtin_array::value || __is_cuda_array::value, + static_assert(::cuda::std::is_bounded_array_v || ::cuda::std::__is_cuda_std_array_v, "make_constant_sequence requires a cuda::std::array or non-empty C-style array"); - constexpr ::cuda::std::size_t N = __array_extent::value; + constexpr ::cuda::std::size_t N = []() constexpr { + if constexpr (::cuda::std::is_bounded_array_v) + { + return ::cuda::std::extent_v; + } + else + { + return ::cuda::std::tuple_size_v; + } + }(); return __make_constant_sequence_impl(::cuda::std::make_index_sequence{}); } From f1a042639ff0e905321f9ace45704ad3bc0545fd Mon Sep 17 00:00:00 2001 From: codingwithmagga Date: Mon, 22 Jun 2026 20:10:53 +0200 Subject: [PATCH 07/11] Replace __always_false_v with existing trait --- libcudacxx/include/cuda/__argument/argument.h | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index fc7f1ebaa9c..5b682ac585f 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -123,9 +123,6 @@ class __constant_sequence static constexpr ::cuda::std::size_t size = sizeof...(_Vs); }; -template -inline constexpr bool __always_false_v = false; - template _CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequence) { @@ -143,7 +140,7 @@ _CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequen } else { - static_assert(__always_false_v, "unsupported array type"); + static_assert(::cuda::std::__always_false_v, "unsupported array type"); } } From 1580330ff24137eef0f60a5fc939dab8ce363943 Mon Sep 17 00:00:00 2001 From: codingwithmagga Date: Mon, 22 Jun 2026 20:12:29 +0200 Subject: [PATCH 08/11] Rename template parameter --- libcudacxx/include/cuda/__argument/argument.h | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index 5b682ac585f..974f7be0f2e 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -123,20 +123,20 @@ class __constant_sequence static constexpr ::cuda::std::size_t size = sizeof...(_Vs); }; -template -_CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequence) +template +_CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequence<_Is...>) { - using raw_array = ::cuda::std::remove_const_t<::cuda::std::remove_reference_t>; + using raw_array = ::cuda::std::remove_const_t<::cuda::std::remove_reference_t>; if constexpr (::cuda::std::is_bounded_array_v) { using _Tp = ::cuda::std::remove_cv_t<::cuda::std::remove_extent_t>; - return __constant_sequence<_Tp, Arr[Is]...>{}; + return __constant_sequence<_Tp, _Arr[_Is]...>{}; } else if constexpr (::cuda::std::__is_cuda_std_array_v) { using _Tp = typename raw_array::value_type; - return __constant_sequence<_Tp, Arr[Is]...>{}; + return __constant_sequence<_Tp, _Arr[_Is]...>{}; } else { From 199c31253d8469c9f236e32fc75ba2cd33f45414 Mon Sep 17 00:00:00 2001 From: codingwithmagga Date: Mon, 22 Jun 2026 20:15:21 +0200 Subject: [PATCH 09/11] Apply suggestion for __raw_array --- libcudacxx/include/cuda/__argument/argument.h | 22 +++++++++---------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index 974f7be0f2e..4a785a32e67 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -126,21 +126,21 @@ class __constant_sequence template _CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequence<_Is...>) { - using raw_array = ::cuda::std::remove_const_t<::cuda::std::remove_reference_t>; + using __raw_array = ::cuda::std::remove_cvref_t; - if constexpr (::cuda::std::is_bounded_array_v) + if constexpr (::cuda::std::is_bounded_array_v<__raw_array>) { - using _Tp = ::cuda::std::remove_cv_t<::cuda::std::remove_extent_t>; + using _Tp = ::cuda::std::remove_cv_t<::cuda::std::remove_extent_t<__raw_array>>; return __constant_sequence<_Tp, _Arr[_Is]...>{}; } - else if constexpr (::cuda::std::__is_cuda_std_array_v) + else if constexpr (::cuda::std::__is_cuda_std_array_v<__raw_array>) { - using _Tp = typename raw_array::value_type; + using _Tp = typename __raw_array::value_type; return __constant_sequence<_Tp, _Arr[_Is]...>{}; } else { - static_assert(::cuda::std::__always_false_v, "unsupported array type"); + static_assert(::cuda::std::__always_false_v<__raw_array>, "unsupported array type"); } } @@ -149,19 +149,19 @@ _CCCL_API constexpr auto __make_constant_sequence_impl(::cuda::std::index_sequen template _CCCL_API constexpr auto __make_constant_sequence() { - using raw_array = ::cuda::std::remove_cv_t<::cuda::std::remove_reference_t>; + using __raw_array = ::cuda::std::remove_cv_t<::cuda::std::remove_reference_t>; - static_assert(::cuda::std::is_bounded_array_v || ::cuda::std::__is_cuda_std_array_v, + static_assert(::cuda::std::is_bounded_array_v<__raw_array> || ::cuda::std::__is_cuda_std_array_v<__raw_array>, "make_constant_sequence requires a cuda::std::array or non-empty C-style array"); constexpr ::cuda::std::size_t N = []() constexpr { - if constexpr (::cuda::std::is_bounded_array_v) + if constexpr (::cuda::std::is_bounded_array_v<__raw_array>) { - return ::cuda::std::extent_v; + return ::cuda::std::extent_v<__raw_array>; } else { - return ::cuda::std::tuple_size_v; + return ::cuda::std::tuple_size_v<__raw_array>; } }(); From bc667511ec4992baa780e284124967da2b877e40 Mon Sep 17 00:00:00 2001 From: codingwithmagga Date: Mon, 22 Jun 2026 20:22:06 +0200 Subject: [PATCH 10/11] Use min and max_element in lowest resp. highest computation of constant sequence --- libcudacxx/include/cuda/__argument/argument.h | 24 ++++--------------- 1 file changed, 4 insertions(+), 20 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index 4a785a32e67..9dc4b36f53d 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -791,16 +791,8 @@ _CCCL_API constexpr _Tp __constant_sequence_compute_lowest() noexcept } else { - constexpr _Tp values[] = {_Vs...}; - _Tp __min = values[0]; - for (_Tp __v : values) - { - if (__v < __min) - { - __min = __v; - } - } - return __min; + constexpr _Tp __values[] = {_Vs...}; + return static_cast<_Tp>(*::cuda::std::min_element(__values, __values + sizeof...(_Vs))); } } @@ -813,16 +805,8 @@ _CCCL_API constexpr _Tp __constant_sequence_compute_highest() noexcept } else { - constexpr _Tp values[] = {_Vs...}; - _Tp __max = values[0]; - for (_Tp __v : values) - { - if (__v > __max) - { - __max = __v; - } - } - return __max; + constexpr _Tp __values[] = {_Vs...}; + return static_cast<_Tp>(*::cuda::std::max_element(__values, __values + sizeof...(_Vs))); } } From 7e70275946a6a1825119218f6e2df03751b1f88b Mon Sep 17 00:00:00 2001 From: codingwithmagga Date: Fri, 26 Jun 2026 10:07:16 +0200 Subject: [PATCH 11/11] Fix merging conflict, use new __type_lowest and __type_highest function for constant_sequence --- libcudacxx/include/cuda/__argument/argument.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/libcudacxx/include/cuda/__argument/argument.h b/libcudacxx/include/cuda/__argument/argument.h index b757020f4e8..81f1d180589 100644 --- a/libcudacxx/include/cuda/__argument/argument.h +++ b/libcudacxx/include/cuda/__argument/argument.h @@ -787,7 +787,7 @@ _CCCL_API constexpr _Tp __constant_sequence_compute_lowest() noexcept { if constexpr (sizeof...(_Vs) == 0) { - return ::cuda::std::numeric_limits<_Tp>::lowest(); + return __type_lowest<_Tp>(); } else { @@ -801,7 +801,7 @@ _CCCL_API constexpr _Tp __constant_sequence_compute_highest() noexcept { if constexpr (sizeof...(_Vs) == 0) { - return (::cuda::std::numeric_limits<_Tp>::max)(); + return __type_highest<_Tp>(); } else {