[INFRA] Import NVIDIA/CCCL upstream as optimization reference library

CCCL (CUDA C++ Core Libraries) provides:
- CUB: device/block/warp-level GPU primitives (reduce, scan, sort, topk)
- Thrust: high-level parallel algorithms (transform_reduce, sort, scan)
- libcudacxx: CUDA C++ standard library (atomics, barriers, memory)
- cudax: experimental features (memory resources, allocators)
- Tuning policies: per-SM hardware-specific algorithm parameters

Competition optimization vectors mapped to CCCL:
- Output TPS (83% weight): warp_reduce, block_reduce, device_topk
- Input TPS (14% weight): device_scan, block_load, prefetch
- Cache TPS (3% weight): prefix caching strategy patterns
- Memory (0.9 util): pooled/cached/buddy allocators

Source: https://github.com/NVIDIA/cccl (shallow clone, HEAD only)
License: Apache-2.0
This commit is contained in:
EngineX CI
2026-07-30 09:35:51 +00:00
parent b4d01f481e
commit 56fd68e7dd
8871 changed files with 1454674 additions and 0 deletions

View File

@@ -0,0 +1,190 @@
//===----------------------------------------------------------------------===//
//
// 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
// SPDX-FileCopyrightText: Copyright (c) 2025 NVIDIA CORPORATION & AFFILIATES.
//
//===----------------------------------------------------------------------===//
#ifndef _CUDA_STD___STRING_CHAR_TRAITS_H
#define _CUDA_STD___STRING_CHAR_TRAITS_H
#include <cuda/std/detail/__config>
#if defined(_CCCL_IMPLICIT_SYSTEM_HEADER_GCC)
# pragma GCC system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_CLANG)
# pragma clang system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_MSVC)
# pragma system_header
#endif // no system header
#include <cuda/std/__cstddef/types.h>
#include <cuda/std/__fwd/char_traits.h>
#include <cuda/std/__string/constexpr_c_functions.h>
#include <cuda/std/__type_traits/is_same.h>
#include <cuda/std/cstdint>
#include <cuda/std/__cccl/prologue.h>
_CCCL_BEGIN_NAMESPACE_CUDA_STD
template <class _CharT, class _IntT, _IntT _EOFVal = _IntT(-1) /*todo: remove default argument*/>
struct __cccl_char_traits_impl
{
using char_type = _CharT;
using int_type = _IntT;
#if 0 // todo: add stream support
using off_type = streamoff;
using pos_type = fpos<mbstate_t>;
using state_type = mbstate_t;
#endif
#if _LIBCUDACXX_HAS_SPACESHIP_OPERATOR()
using comparison_category = strong_ordering;
#endif // _LIBCUDACXX_HAS_SPACESHIP_OPERATOR()
_CCCL_API static constexpr void assign(char_type& __lhs, const char_type& __rhs) noexcept
{
__lhs = __rhs;
}
[[nodiscard]] _CCCL_API static constexpr bool eq(char_type __lhs, char_type __rhs) noexcept
{
return __lhs == __rhs;
}
[[nodiscard]] _CCCL_API static constexpr bool lt(char_type __lhs, char_type __rhs) noexcept
{
if constexpr (is_same_v<char_type, char>)
{
return static_cast<unsigned char>(__lhs) < static_cast<unsigned char>(__rhs);
}
else
{
return __lhs < __rhs;
}
}
[[nodiscard]] _CCCL_API static constexpr int
compare(const char_type* __lhs, const char_type* __rhs, size_t __count) noexcept
{
if (__count > 0)
{
_CCCL_ASSERT(__lhs != nullptr, "char_traits::compare: lhs pointer is null");
_CCCL_ASSERT(__rhs != nullptr, "char_traits::compare: rhs pointer is null");
}
return ::cuda::std::__cccl_memcmp(__lhs, __rhs, __count);
}
[[nodiscard]] _CCCL_API inline static size_t constexpr length(const char_type* __s) noexcept
{
_CCCL_ASSERT(__s != nullptr, "char_traits::length: nullptr passed as an argument");
return ::cuda::std::__cccl_strlen(__s);
}
[[nodiscard]] _CCCL_API static constexpr const char_type*
find(const char_type* __s, size_t __n, const char_type& __a) noexcept
{
if (__n > 0)
{
_CCCL_ASSERT(__s != nullptr, "char_traits::find: nullptr passed as an argument");
}
return ::cuda::std::__cccl_memchr<const char_type>(__s, __a, __n);
}
_CCCL_API static constexpr char_type* move(char_type* __s1, const char_type* __s2, size_t __n) noexcept
{
if (__n > 0)
{
_CCCL_ASSERT(__s1 != nullptr, "char_traits::move: destination pointer is null");
_CCCL_ASSERT(__s2 != nullptr, "char_traits::move: source pointer is null");
}
return ::cuda::std::__cccl_memmove(__s1, __s2, __n);
}
_CCCL_API static constexpr char_type* copy(char_type* __s1, const char_type* __s2, size_t __n) noexcept
{
if (__n > 0)
{
_CCCL_ASSERT(__s1 != nullptr, "char_traits::copy: destination pointer is null");
_CCCL_ASSERT(__s2 != nullptr, "char_traits::copy: source pointer is null");
}
return ::cuda::std::__cccl_memcpy(__s1, __s2, __n);
}
_CCCL_API static constexpr char_type* assign(char_type* __s, size_t __n, char_type __a) noexcept
{
if (__n > 0)
{
_CCCL_ASSERT(__s != nullptr, "char_traits::assign: destination pointer is null");
}
return ::cuda::std::__cccl_memset(__s, __a, __n);
}
[[nodiscard]] _CCCL_API static constexpr char_type to_char_type(int_type __c) noexcept
{
return char_type(__c);
}
[[nodiscard]] _CCCL_API static constexpr int_type to_int_type(char_type __c) noexcept
{
if constexpr (is_same_v<char_type, char>)
{
return int_type(static_cast<unsigned char>(__c));
}
else
{
return int_type(__c);
}
}
[[nodiscard]] _CCCL_API static constexpr bool eq_int_type(int_type __lhs, int_type __rhs) noexcept
{
return __lhs == __rhs;
}
#if 0 // todo: add EOF support
[[nodiscard]] _CCCL_API static constexpr int_type eof() noexcept
{
return _EOFVal;
}
[[nodiscard]] _CCCL_API static constexpr int_type not_eof(int_type __c) noexcept
{
return eq_int_type(__c, eof()) ? static_cast<int_type>(~eof()) : __c;
}
#endif
};
template <>
struct _CCCL_TYPE_VISIBILITY_DEFAULT char_traits<char> : __cccl_char_traits_impl<char, int /*, EOF*/>
{};
#if _CCCL_HAS_CHAR8_T()
template <>
struct _CCCL_TYPE_VISIBILITY_DEFAULT char_traits<char8_t> : __cccl_char_traits_impl<char8_t, unsigned /*, ??? */>
{};
#endif // _CCCL_HAS_CHAR8_T()
template <>
struct _CCCL_TYPE_VISIBILITY_DEFAULT
char_traits<char16_t> : __cccl_char_traits_impl<char16_t, uint_least16_t /*, ??? */>
{};
template <>
struct _CCCL_TYPE_VISIBILITY_DEFAULT
char_traits<char32_t> : __cccl_char_traits_impl<char32_t, uint_least32_t /*, ??? */>
{};
#if _CCCL_HAS_WCHAR_T()
template <>
struct _CCCL_TYPE_VISIBILITY_DEFAULT char_traits<wchar_t> : __cccl_char_traits_impl<wchar_t, wint_t /*, WEOF*/>
{};
#endif // _CCCL_HAS_WCHAR_T()
_CCCL_END_NAMESPACE_CUDA_STD
#include <cuda/std/__cccl/epilogue.h>
#endif // _CUDA_STD___STRING_CHAR_TRAITS_H

View File

@@ -0,0 +1,595 @@
//===----------------------------------------------------------------------===//
//
// Part of libcu++, the C++ Standard Library for your entire system,
// 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
// SPDX-FileCopyrightText: Copyright (c) 2025 NVIDIA CORPORATION & AFFILIATES.
//
//===----------------------------------------------------------------------===//
#ifndef _CUDA_STD___STRING_CONSTEXPR_C_FUNCTIONS_H
#define _CUDA_STD___STRING_CONSTEXPR_C_FUNCTIONS_H
#include <cuda/std/detail/__config>
#if defined(_CCCL_IMPLICIT_SYSTEM_HEADER_GCC)
# pragma GCC system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_CLANG)
# pragma clang system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_MSVC)
# pragma system_header
#endif // no system header
#include <cuda/std/__cstddef/types.h>
#include <cuda/std/__type_traits/make_nbit_int.h>
#include <cuda/std/__type_traits/remove_const.h>
#include <cuda/std/climits>
#if _CCCL_HOSTED()
# include <cstring>
#elif _CCCL_HOSTJIT()
# include <string.h>
#endif // _CCCL_HOSTJIT()
#include <cuda/std/__cccl/prologue.h>
_CCCL_BEGIN_NAMESPACE_CUDA_STD
// __cccl_strcpy
template <class _CharT>
_CCCL_API constexpr _CharT*
__cccl_strcpy_impl_constexpr(_CharT* _CCCL_RESTRICT __dst, const _CharT* _CCCL_RESTRICT __src) noexcept
{
_CharT* __dst_it = __dst;
while ((*__dst_it++ = *__src++) != _CharT('\0'))
{
}
return __dst;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _CharT>
_CCCL_HOST_API _CharT* __cccl_strcpy_impl_host(_CharT* _CCCL_RESTRICT __dst, const _CharT* _CCCL_RESTRICT __src) noexcept
{
if constexpr (sizeof(_CharT) == 1)
{
return reinterpret_cast<_CharT*>(::strcpy(reinterpret_cast<char*>(__dst), reinterpret_cast<const char*>(__src)));
}
else
{
return ::cuda::std::__cccl_strcpy_impl_constexpr(__dst, __src);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _CharT>
_CCCL_API constexpr _CharT* __cccl_strcpy(_CharT* _CCCL_RESTRICT __dst, const _CharT* _CCCL_RESTRICT __src) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_strcpy_impl_host(__dst, __src);))
}
return ::cuda::std::__cccl_strcpy_impl_constexpr(__dst, __src);
}
// __cccl_strncpy
template <class _CharT>
_CCCL_API constexpr _CharT*
__cccl_strncpy_impl_constexpr(_CharT* _CCCL_RESTRICT __dst, const _CharT* _CCCL_RESTRICT __src, size_t __n) noexcept
{
_CharT* __dst_it = __dst;
while (__n--)
{
if ((*__dst_it++ = *__src++) == _CharT('\0')) // NOLINT(bugprone-assignment-in-if-condition)
{
while (__n--)
{
*__dst_it++ = _CharT('\0');
}
break;
}
}
return __dst;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _CharT>
_CCCL_HOST_API _CharT*
__cccl_strncpy_impl_host(_CharT* _CCCL_RESTRICT __dst, const _CharT* _CCCL_RESTRICT __src, size_t __n) noexcept
{
if constexpr (sizeof(_CharT) == 1)
{
return reinterpret_cast<_CharT*>(
::strncpy(reinterpret_cast<char*>(__dst), reinterpret_cast<const char*>(__src), __n));
}
else
{
return ::cuda::std::__cccl_strncpy_impl_constexpr(__dst, __src, __n);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _CharT>
_CCCL_API constexpr _CharT*
__cccl_strncpy(_CharT* _CCCL_RESTRICT __dst, const _CharT* _CCCL_RESTRICT __src, size_t __n) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_strncpy_impl_host(__dst, __src, __n);))
}
return ::cuda::std::__cccl_strncpy_impl_constexpr(__dst, __src, __n);
}
// __cccl_strlen
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr size_t __cccl_strlen_impl_constexpr(const _CharT* __ptr) noexcept
{
size_t __len = 0;
while (*__ptr++ != _CharT('\0'))
{
++__len;
}
return __len;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_HOST_API size_t __cccl_strlen_impl_host(const _CharT* __ptr) noexcept
{
if constexpr (sizeof(_CharT) == 1)
{
return ::strlen(reinterpret_cast<const char*>(__ptr));
}
else
{
return ::cuda::std::__cccl_strlen_impl_constexpr(__ptr);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr size_t __cccl_strlen(const _CharT* __ptr) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_strlen_impl_host(__ptr);))
}
return ::cuda::std::__cccl_strlen_impl_constexpr(__ptr);
}
// __cccl_strcmp
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr int __cccl_strcmp_impl_constexpr(const _CharT* __lhs, const _CharT* __rhs) noexcept
{
using _UCharT = __make_nbit_uint_t<sizeof(_CharT) * CHAR_BIT>;
bool __reached_end = false;
while (*__lhs == *__rhs)
{
if (*__lhs == _CharT('\0'))
{
__reached_end = true;
break;
}
++__lhs;
++__rhs;
}
return __reached_end ? 0 : (static_cast<_UCharT>(*__lhs) < static_cast<_UCharT>(*__rhs)) ? -1 : 1;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_HOST_API int __cccl_strcmp_impl_host(const _CharT* __lhs, const _CharT* __rhs) noexcept
{
if constexpr (sizeof(_CharT) == 1)
{
return ::strcmp(reinterpret_cast<const char*>(__lhs), reinterpret_cast<const char*>(__rhs));
}
else
{
return ::cuda::std::__cccl_strcmp_impl_constexpr(__lhs, __rhs);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr int __cccl_strcmp(const _CharT* __lhs, const _CharT* __rhs) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_strcmp_impl_host(__lhs, __rhs);))
}
return ::cuda::std::__cccl_strcmp_impl_constexpr(__lhs, __rhs);
}
// __cccl_strncmp
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr int
__cccl_strncmp_impl_constexpr(const _CharT* __lhs, const _CharT* __rhs, size_t __n) noexcept
{
using _UCharT = __make_nbit_uint_t<sizeof(_CharT) * CHAR_BIT>;
int __result = 0;
while (__n--)
{
if (*__lhs != *__rhs)
{
__result = (static_cast<_UCharT>(*__lhs) < static_cast<_UCharT>(*__rhs)) ? -1 : 1;
break;
}
if (*__lhs == _CharT('\0'))
{
break;
}
++__lhs;
++__rhs;
}
return __result;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_HOST_API int __cccl_strncmp_impl_host(const _CharT* __lhs, const _CharT* __rhs, size_t __n) noexcept
{
if constexpr (sizeof(_CharT) == 1)
{
return ::strncmp(reinterpret_cast<const char*>(__lhs), reinterpret_cast<const char*>(__rhs), __n);
}
else
{
return ::cuda::std::__cccl_strncmp_impl_constexpr(__lhs, __rhs, __n);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr int __cccl_strncmp(const _CharT* __lhs, const _CharT* __rhs, size_t __n) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_strncmp_impl_host(__lhs, __rhs, __n);))
}
return ::cuda::std::__cccl_strncmp_impl_constexpr(__lhs, __rhs, __n);
}
// __cccl_strchr
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr _CharT* __cccl_strchr_impl_constexpr(_CharT* __ptr, _CharT __c) noexcept
{
bool __reached_end = false;
while (*__ptr != __c)
{
if (*__ptr == _CharT('\0'))
{
__reached_end = true;
break;
}
++__ptr;
}
return __reached_end ? nullptr : __ptr;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_HOST_API _CharT* __cccl_strchr_impl_host(_CharT* __ptr, _CharT __c) noexcept
{
if constexpr (sizeof(_CharT) == 1)
{
using _Up = remove_const_t<_CharT>;
return const_cast<_CharT*>(
reinterpret_cast<_Up*>(::strchr(reinterpret_cast<char*>(const_cast<_Up*>(__ptr)), static_cast<int>(__c))));
}
else
{
return ::cuda::std::__cccl_strchr_impl_constexpr<_CharT>(__ptr, __c);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr _CharT* __cccl_strchr(_CharT* __ptr, _CharT __c) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_strchr_impl_host<_CharT>(__ptr, __c);))
}
return ::cuda::std::__cccl_strchr_impl_constexpr<_CharT>(__ptr, __c);
}
// __cccl_strrchr
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr _CharT* __cccl_strrchr_impl_constexpr(_CharT* __ptr, _CharT __c) noexcept
{
if (__c == _CharT('\0'))
{
return __ptr + ::cuda::std::__cccl_strlen(__ptr);
}
_CharT* __last{};
while (*__ptr != _CharT('\0'))
{
if (*__ptr == __c)
{
__last = __ptr;
}
++__ptr;
}
return __last;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_HOST_API _CharT* __cccl_strrchr_impl_host(_CharT* __ptr, _CharT __c) noexcept
{
if constexpr (sizeof(_CharT) == 1)
{
using _Up = remove_const_t<_CharT>;
return const_cast<_CharT*>(
reinterpret_cast<_Up*>(::strrchr(reinterpret_cast<char*>(const_cast<_Up*>(__ptr)), static_cast<int>(__c))));
}
else
{
return ::cuda::std::__cccl_strrchr_impl_constexpr<_CharT>(__ptr, __c);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _CharT>
[[nodiscard]] _CCCL_API constexpr _CharT* __cccl_strrchr(_CharT* __ptr, _CharT __c) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_strrchr_impl_host<_CharT>(__ptr, __c);))
}
return ::cuda::std::__cccl_strrchr_impl_constexpr<_CharT>(__ptr, __c);
}
// __cccl_memchr
template <class _Tp>
[[nodiscard]] _CCCL_API constexpr _Tp* __cccl_memchr_impl_constexpr(_Tp* __ptr, _Tp __c, size_t __n) noexcept
{
_Tp* __result = nullptr;
while (__n--)
{
if (*__ptr == __c)
{
__result = __ptr;
break;
}
++__ptr;
}
return __result;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _Tp>
[[nodiscard]] _CCCL_HOST_API _Tp* __cccl_memchr_impl_host(_Tp* __ptr, _Tp __c, size_t __n) noexcept
{
if constexpr (sizeof(_Tp) == 1)
{
using _Up = remove_const_t<_Tp>;
return const_cast<_Tp*>(reinterpret_cast<_Up*>(::memchr(const_cast<_Up*>(__ptr), static_cast<int>(__c), __n)));
}
else
{
return ::cuda::std::__cccl_memchr_impl_constexpr<_Tp>(__ptr, __c, __n);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _Tp>
[[nodiscard]] _CCCL_API constexpr _Tp* __cccl_memchr(_Tp* __ptr, _Tp __c, size_t __n) noexcept
{
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_memchr_impl_host<_Tp>(__ptr, __c, __n);))
}
return ::cuda::std::__cccl_memchr_impl_constexpr<_Tp>(__ptr, __c, __n);
}
// __cccl_memmove
template <class _Tp>
[[nodiscard]] _CCCL_API constexpr _Tp* __cccl_memmove_impl_constexpr(_Tp* __dst, const _Tp* __src, size_t __n) noexcept
{
const auto __dst_copy = __dst;
if (__src < __dst && __dst < __src + __n)
{
__dst += __n;
__src += __n;
while (__n-- > 0)
{
*--__dst = *--__src;
}
}
else
{
while (__n-- > 0)
{
*__dst++ = *__src++;
}
}
return __dst_copy;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _Tp>
[[nodiscard]] _CCCL_HOST_API _Tp* __cccl_memmove_impl_host(_Tp* __dst, const _Tp* __src, size_t __n) noexcept
{
return reinterpret_cast<_Tp*>(::memmove(__dst, __src, __n * sizeof(_Tp)));
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _Tp>
_CCCL_API constexpr _Tp* __cccl_memmove(_Tp* __dst, const _Tp* __src, size_t __n) noexcept
{
#if !_CCCL_TILE_COMPILATION() // error: "call to non-tile function not supported!"
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
# if defined(_CCCL_BUILTIN_MEMMOVE)
return reinterpret_cast<_Tp*>(_CCCL_BUILTIN_MEMMOVE(__dst, __src, __n * sizeof(_Tp)));
# else // ^^^ _CCCL_BUILTIN_MEMMOVE ^^^ / vvv !_CCCL_BUILTIN_MEMMOVE vvv
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_memmove_impl_host(__dst, __src, __n);))
# endif // ^^^ !_CCCL_BUILTIN_MEMMOVE ^^^
}
#endif // !_CCCL_TILE_COMPILATION()
return ::cuda::std::__cccl_memmove_impl_constexpr(__dst, __src, __n);
}
// __cccl_memcmp
template <class _Tp>
[[nodiscard]] _CCCL_API constexpr int
__cccl_memcmp_impl_constexpr(const _Tp* __lhs, const _Tp* __rhs, size_t __n) noexcept
{
using _Up = __make_nbit_uint_t<sizeof(_Tp) * CHAR_BIT>;
int __result = 0;
while (__n--)
{
if (*__lhs != *__rhs)
{
__result = static_cast<_Up>(*__lhs) < static_cast<_Up>(*__rhs) ? -1 : 1;
break;
}
++__lhs;
++__rhs;
}
return __result;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _Tp>
[[nodiscard]] _CCCL_HOST_API int __cccl_memcmp_impl_host(const _Tp* __lhs, const _Tp* __rhs, size_t __n) noexcept
{
if constexpr (sizeof(_Tp) == 1)
{
return ::memcmp(__lhs, __rhs, __n);
}
else
{
return ::cuda::std::__cccl_memcmp_impl_constexpr(__lhs, __rhs, __n);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _Tp>
[[nodiscard]] _CCCL_API constexpr int __cccl_memcmp(const _Tp* __lhs, const _Tp* __rhs, size_t __n) noexcept
{
#if !_CCCL_TILE_COMPILATION() // error: "call to non-tile function not supported!"
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
# if defined(_CCCL_BUILTIN_MEMCMP)
return _CCCL_BUILTIN_MEMCMP(__lhs, __rhs, __n * sizeof(_Tp));
# else // ^^^ _CCCL_BUILTIN_MEMCMP ^^^ / vvv !_CCCL_BUILTIN_MEMCMP vvv
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_memcmp_impl_host(__lhs, __rhs, __n);))
# endif // ^^^ !_CCCL_BUILTIN_MEMCMP ^^^
}
#endif // !_CCCL_TILE_COMPILATION()
return ::cuda::std::__cccl_memcmp_impl_constexpr(__lhs, __rhs, __n);
}
// __cccl_memcpy
template <class _Tp>
[[nodiscard]] _CCCL_API constexpr _Tp*
__cccl_memcpy_impl_constexpr(_Tp* _CCCL_RESTRICT __dst, const _Tp* _CCCL_RESTRICT __src, size_t __n) noexcept
{
const auto __dst_copy = __dst;
while (__n--)
{
*__dst++ = *__src++;
}
return __dst_copy;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _Tp>
[[nodiscard]] _CCCL_HOST_API _Tp*
__cccl_memcpy_impl_host(_Tp* _CCCL_RESTRICT __dst, const _Tp* _CCCL_RESTRICT __src, size_t __n) noexcept
{
return reinterpret_cast<_Tp*>(::memcpy(__dst, __src, __n * sizeof(_Tp)));
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _Tp>
_CCCL_API constexpr _Tp* __cccl_memcpy(_Tp* _CCCL_RESTRICT __dst, const _Tp* _CCCL_RESTRICT __src, size_t __n) noexcept
{
#if !_CCCL_TILE_COMPILATION() // error: "call to non-tile function not supported!"
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
# if defined(_CCCL_BUILTIN_MEMCPY)
return reinterpret_cast<_Tp*>(_CCCL_BUILTIN_MEMCPY(__dst, __src, __n * sizeof(_Tp)));
# else // ^^^ _CCCL_BUILTIN_MEMCPY ^^^ / vvv !_CCCL_BUILTIN_MEMCPY vvv
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_memcpy_impl_host(__dst, __src, __n);))
# endif // ^^^ !_CCCL_BUILTIN_MEMCPY ^^^
}
#endif // !_CCCL_TILE_COMPILATION()
return ::cuda::std::__cccl_memcpy_impl_constexpr(__dst, __src, __n);
}
// __cccl_memset
template <class _Tp>
[[nodiscard]] _CCCL_API constexpr _Tp* __cccl_memset_impl_constexpr(_Tp* __ptr, _Tp __c, size_t __n) noexcept
{
const auto __ptr_copy = __ptr;
while (__n--)
{
*__ptr++ = __c;
}
return __ptr_copy;
}
#if !_CCCL_COMPILER(NVRTC)
template <class _Tp>
[[nodiscard]] _CCCL_HOST_API _Tp* __cccl_memset_impl_host(_Tp* __ptr, _Tp __c, size_t __n) noexcept
{
if constexpr (sizeof(_Tp) == 1)
{
return reinterpret_cast<_Tp*>(::memset(__ptr, static_cast<int>(__c), __n));
}
else
{
return ::cuda::std::__cccl_memset_impl_constexpr(__ptr, __c, __n);
}
}
#endif // !_CCCL_COMPILER(NVRTC)
template <class _Tp>
_CCCL_API constexpr _Tp* __cccl_memset(_Tp* __ptr, _Tp __c, size_t __n) noexcept
{
#if !_CCCL_TILE_COMPILATION() // error: "call to non-tile function not supported!"
_CCCL_IF_NOT_CONSTEVAL_DEFAULT
{
# if defined(_CCCL_BUILTIN_MEMSET)
return reinterpret_cast<_Tp*>(_CCCL_BUILTIN_MEMSET(__ptr, __c, __n * sizeof(_Tp)));
# else // ^^^ _CCCL_BUILTIN_MEMSET ^^^ / vvv !_CCCL_BUILTIN_MEMSET vvv
NV_IF_TARGET(NV_IS_HOST, (return ::cuda::std::__cccl_memset_impl_host(__ptr, __c, __n);))
# endif // ^^^ !_CCCL_BUILTIN_MEMSET ^^^
}
#endif // !_CCCL_TILE_COMPILATION()
return ::cuda::std::__cccl_memset_impl_constexpr(__ptr, __c, __n);
}
_CCCL_END_NAMESPACE_CUDA_STD
#include <cuda/std/__cccl/epilogue.h>
#endif // _CUDA_STD___STRING_CONSTEXPR_C_FUNCTIONS_H

View File

@@ -0,0 +1,314 @@
//===----------------------------------------------------------------------===//
//
// 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
// SPDX-FileCopyrightText: Copyright (c) 2025 NVIDIA CORPORATION & AFFILIATES.
//
//===----------------------------------------------------------------------===//
#ifndef _CUDA_STD___STRING_HELPER_FUNCTIONS_H
#define _CUDA_STD___STRING_HELPER_FUNCTIONS_H
#include <cuda/std/detail/__config>
#if defined(_CCCL_IMPLICIT_SYSTEM_HEADER_GCC)
# pragma GCC system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_CLANG)
# pragma clang system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_MSVC)
# pragma system_header
#endif // no system header
#include <cuda/std/__algorithm/find.h>
#include <cuda/std/__algorithm/find_end.h>
#include <cuda/std/__algorithm/find_first_of.h>
#include <cuda/std/__algorithm/min.h>
#include <cuda/std/__cstddef/types.h>
#include <cuda/std/__iterator/iterator_traits.h>
#include <cuda/std/__string/char_traits.h>
#include <cuda/std/__cccl/prologue.h>
_CCCL_BEGIN_NAMESPACE_CUDA_STD
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT __cccl_str_find(const _CharT* __p, _SizeT __sz, _CharT __c, _SizeT __pos) noexcept
{
if (__pos >= __sz)
{
return __npos;
}
const _CharT* __r = _Traits::find(__p + __pos, __sz - __pos, __c);
if (__r == nullptr)
{
return __npos;
}
return static_cast<_SizeT>(__r - __p);
}
template <class _CharT, class _Traits>
_CCCL_API constexpr const _CharT*
__cccl_search_substring(const _CharT* __first1, const _CharT* __last1, const _CharT* __first2, const _CharT* __last2)
{
// Take advantage of knowing source and pattern lengths.
// Stop short when source is smaller than pattern.
const ptrdiff_t __len2 = __last2 - __first2;
if (__len2 == 0)
{
return __first1;
}
ptrdiff_t __len1 = __last1 - __first1;
if (__len1 < __len2)
{
return __last1;
}
// First element of __first2 is loop invariant.
_CharT __f2 = *__first2;
while (true)
{
__len1 = __last1 - __first1;
// Check whether __first1 still has at least __len2 bytes.
if (__len1 < __len2)
{
// return __last1;
break;
}
// Find __f2 the first byte matching in __first1.
__first1 = _Traits::find(__first1, __len1 - __len2 + 1, __f2);
if (__first1 == 0)
{
// return __last1;
break;
}
// It is faster to compare from the first byte of __first1 even if we
// already know that it matches the first byte of __first2: this is because
// __first2 is most likely aligned, as it is user's "pattern" string, and
// __first1 + 1 is most likely not aligned, as the match is in the middle of
// the string.
if (_Traits::compare(__first1, __first2, __len2) == 0)
{
// return __first1;
__last1 = __first1;
break;
}
++__first1;
}
return __last1;
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT
__cccl_str_find(const _CharT* __p, _SizeT __sz, const _CharT* __s, _SizeT __pos, _SizeT __n) noexcept
{
if (__pos > __sz)
{
return __npos;
}
if (__n == 0) // There is nothing to search, just return __pos.
{
return __pos;
}
const _CharT* __r = ::cuda::std::__cccl_search_substring<_CharT, _Traits>(__p + __pos, __p + __sz, __s, __s + __n);
if (__r == __p + __sz)
{
return __npos;
}
return static_cast<_SizeT>(__r - __p);
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT __cccl_str_rfind(const _CharT* __p, _SizeT __sz, _CharT __c, _SizeT __pos) noexcept
{
if (__sz < 1)
{
return __npos;
}
if (__pos < __sz)
{
++__pos;
}
else
{
__pos = __sz;
}
_SizeT __result = __npos;
for (const _CharT* __ps = __p + __pos; __ps != __p;)
{
if (_Traits::eq(*--__ps, __c))
{
__result = static_cast<_SizeT>(__ps - __p);
break;
}
}
return __result;
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT
__cccl_str_rfind(const _CharT* __p, _SizeT __sz, const _CharT* __s, _SizeT __pos, _SizeT __n) noexcept
{
__pos = ::cuda::std::min(__pos, __sz);
if (__n < __sz - __pos)
{
__pos += __n;
}
else
{
__pos = __sz;
}
const _CharT* __r = ::cuda::std::__find_end(
__p, __p + __pos, __s, __s + __n, _Traits::eq, random_access_iterator_tag(), random_access_iterator_tag());
if (__n > 0 && __r == __p + __pos)
{
return __npos;
}
return static_cast<_SizeT>(__r - __p);
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT
__cccl_str_find_first_of(const _CharT* __p, _SizeT __sz, const _CharT* __s, _SizeT __pos, _SizeT __n) noexcept
{
if (__pos >= __sz || __n == 0)
{
return __npos;
}
const _CharT* __r = ::cuda::std::__find_first_of_ce(__p + __pos, __p + __sz, __s, __s + __n, _Traits::eq);
if (__r == __p + __sz)
{
return __npos;
}
return static_cast<_SizeT>(__r - __p);
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT
__cccl_str_find_last_of(const _CharT* __p, _SizeT __sz, const _CharT* __s, _SizeT __pos, _SizeT __n) noexcept
{
if (__n == 0)
{
return __npos;
}
if (__pos < __sz)
{
++__pos;
}
else
{
__pos = __sz;
}
_SizeT __result = __npos;
for (const _CharT* __ps = __p + __pos; __ps != __p;)
{
if (_Traits::find(__s, __n, *--__ps) != nullptr)
{
__result = static_cast<_SizeT>(__ps - __p);
break;
}
}
return __result;
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT
__cccl_str_find_first_not_of(const _CharT* __p, _SizeT __sz, const _CharT* __s, _SizeT __pos, _SizeT __n) noexcept
{
if (__pos >= __sz)
{
return __npos;
}
const _CharT* __pe = __p + __sz;
_SizeT __result = __npos;
for (const _CharT* __ps = __p + __pos; __ps != __pe; ++__ps)
{
if (_Traits::find(__s, __n, *__ps) == nullptr)
{
__result = static_cast<_SizeT>(__ps - __p);
break;
}
}
return __result;
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT
__cccl_str_find_first_not_of(const _CharT* __p, _SizeT __sz, _CharT __c, _SizeT __pos) noexcept
{
_SizeT __result = __npos;
if (__pos < __sz)
{
const _CharT* __pe = __p + __sz;
for (const _CharT* __ps = __p + __pos; __ps != __pe; ++__ps)
{
if (!_Traits::eq(*__ps, __c))
{
__result = static_cast<_SizeT>(__ps - __p);
break;
}
}
}
return __result;
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT
__cccl_str_find_last_not_of(const _CharT* __p, _SizeT __sz, const _CharT* __s, _SizeT __pos, _SizeT __n) noexcept
{
if (__pos < __sz)
{
++__pos;
}
else
{
__pos = __sz;
}
_SizeT __result = __npos;
for (const _CharT* __ps = __p + __pos; __ps != __p;)
{
if (_Traits::find(__s, __n, *--__ps) == nullptr)
{
__result = static_cast<_SizeT>(__ps - __p);
break;
}
}
return __result;
}
template <class _CharT, class _SizeT, class _Traits, _SizeT __npos>
_CCCL_API constexpr _SizeT __cccl_str_find_last_not_of(const _CharT* __p, _SizeT __sz, _CharT __c, _SizeT __pos) noexcept
{
if (__pos < __sz)
{
++__pos;
}
else
{
__pos = __sz;
}
_SizeT __result = __npos;
for (const _CharT* __ps = __p + __pos; __ps != __p;)
{
if (!_Traits::eq(*--__ps, __c))
{
__result = static_cast<_SizeT>(__ps - __p);
break;
}
}
return __result;
}
_CCCL_END_NAMESPACE_CUDA_STD
#include <cuda/std/__cccl/epilogue.h>
#endif // _CUDA_STD___STRING_HELPER_FUNCTIONS_H

View File

@@ -0,0 +1,253 @@
//===----------------------------------------------------------------------===//
//
// 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
// SPDX-FileCopyrightText: Copyright (c) 2023 NVIDIA CORPORATION & AFFILIATES.
//
//===----------------------------------------------------------------------===//
#ifndef _CUDA_STD___STRING_STRING_VIEW_H
#define _CUDA_STD___STRING_STRING_VIEW_H
#include <cuda/std/detail/__config>
#if defined(_CCCL_IMPLICIT_SYSTEM_HEADER_GCC)
# pragma GCC system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_CLANG)
# pragma clang system_header
#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_MSVC)
# pragma system_header
#endif // no system header
#if _LIBCUDACXX_HAS_SPACESHIP_OPERATOR()
# include <cuda/std/compare>
#endif
#include <cuda/std/__exception/exception_macros.h>
#include <cuda/std/__host_stdlib/stdexcept>
#include <cuda/std/__string/char_traits.h>
#include <cuda/std/__type_traits/is_constant_evaluated.h>
#include <cuda/std/cstddef>
#include <cuda/std/__cccl/prologue.h>
_CCCL_BEGIN_NAMESPACE_CUDA_STD
struct __string_view
{
_CCCL_API constexpr __string_view(char const* __str, size_t __len) noexcept
: __str_(__str)
, __len_(__len)
{}
_CCCL_API constexpr explicit __string_view(char const* __str) noexcept
: __str_(__str)
, __len_(__strlen_(__str))
{}
[[nodiscard]] _CCCL_API constexpr size_t size() const noexcept
{
return __len_;
}
[[nodiscard]] _CCCL_API constexpr char const* data() const noexcept
{
return __str_;
}
[[nodiscard]] _CCCL_API constexpr char const* begin() const noexcept
{
return __str_;
}
[[nodiscard]] _CCCL_API constexpr char const* end() const noexcept
{
return __str_ + __len_;
}
[[nodiscard]] _CCCL_API constexpr char const& operator[](ptrdiff_t __n) const noexcept
{
return __str_[__n];
}
[[nodiscard]] _CCCL_API constexpr __string_view substr(ptrdiff_t __start, ptrdiff_t __stop) const
{
return __string_view(__str_ + __check_offset(__start, __len_), __check_offset(__stop - __start, __len_));
}
private:
[[nodiscard]] _CCCL_API static constexpr int
__compare_(char const* __s1, size_t __len1, char const* __s2, size_t __len2, size_t __n) noexcept
{
int __result = int(__len1) - int(__len2);
if (__n)
{
for (;; ++__s1, ++__s2)
{
if (*__s1 < *__s2)
{
__result = -1;
break;
}
if (*__s2 < *__s1)
{
__result = 1;
break;
}
if (0 == --__n)
{
break;
}
}
}
return __result;
}
template <bool _Forward>
[[nodiscard]] _CCCL_API static constexpr ptrdiff_t
__find(const char* __needle, size_t __needle_size, const char* __haystack_begin, const char* __haystack_end) noexcept
{
ptrdiff_t __result = -1;
char const* __it = __haystack_begin;
for (; __it != __haystack_end; (_Forward ? ++__it : --__it))
{
size_t __i = 0;
for (; __i != __needle_size; ++__i)
{
if ((_Forward ? __it : __it - 1)[__i] != __needle[__i])
{
break;
}
}
if (__i == __needle_size)
{
__result = _Forward ? __it - __haystack_begin : __it - __haystack_end - 1;
break;
}
}
return __result;
}
public:
template <size_t _Np>
[[nodiscard]] _CCCL_API constexpr ptrdiff_t find(const char (&__other)[_Np]) const noexcept
{
return ((_Np - 1) > __len_) ? -1 : __find<true>(__other, _Np - 1, __str_, __str_ + __len_ - (_Np - 1) + 1);
}
template <size_t _Np>
[[nodiscard]] _CCCL_API constexpr ptrdiff_t find_end(const char (&__other)[_Np]) const noexcept
{
return ((_Np - 1) > __len_) ? -1 : __find<false>(__other, _Np - 1, __str_ + __len_ - (_Np - 1) + 1, __str_);
}
private:
// This overload is selected when we're not in a constant evaluated context.
// Compare the two strings' addresses as a shortcut, and fall back to a string
// comparison it they are not equal.
[[nodiscard]] _CCCL_API inline int __compare(__string_view const& __other, false_type) const noexcept
{
return __str_ == __other.__str_
? int(__len_) - int(__other.__len_)
: __compare_(__str_, __len_, __other.__str_, __other.__len_, (__min_) (__len_, __other.__len_));
}
// This overload is selected when we're in a constant evaluated context. We
// cannot compare the two strings' addresses so fall back to a string
// comparison.
[[nodiscard]] _CCCL_API constexpr int __compare(__string_view const& __other, true_type) const noexcept
{
return __compare_(__str_, __len_, __other.__str_, __other.__len_, (__min_) (__len_, __other.__len_));
}
public:
[[nodiscard]] _CCCL_API constexpr int compare(__string_view const& __other) const noexcept
{
// If we're in a constant evaluated context, we cannot compare the __str_
// members for equality.
return __compare(__other, bool_constant<__cccl_default_is_constant_evaluated()>());
}
[[nodiscard]] _CCCL_API friend constexpr bool
operator==(__string_view const& __lhs, __string_view const& __rhs) noexcept
{
return __lhs.__len_ == __rhs.__len_ && __lhs.compare(__rhs) == 0;
}
#if _LIBCUDACXX_HAS_SPACESHIP_OPERATOR()
[[nodiscard]]
_CCCL_API friend constexpr auto operator<=>(__string_view const& __lhs, __string_view const& __rhs) noexcept
{
return __lhs.compare(__rhs) <=> 0;
}
#else // ^^^ _LIBCUDACXX_HAS_SPACESHIP_OPERATOR() ^^^ / vvv !_LIBCUDACXX_HAS_SPACESHIP_OPERATOR()
[[nodiscard]]
_CCCL_API friend constexpr bool operator!=(__string_view const& __lhs, __string_view const& __rhs) noexcept
{
return !(__lhs == __rhs);
}
[[nodiscard]] _CCCL_API friend constexpr bool
operator<(__string_view const& __lhs, __string_view const& __rhs) noexcept
{
return __lhs.compare(__rhs) < 0;
}
[[nodiscard]] _CCCL_API friend constexpr bool
operator<=(__string_view const& __lhs, __string_view const& __rhs) noexcept
{
return __lhs.compare(__rhs) <= 0;
}
[[nodiscard]] _CCCL_API friend constexpr bool
operator>(__string_view const& __lhs, __string_view const& __rhs) noexcept
{
return __lhs.compare(__rhs) > 0;
}
[[nodiscard]] _CCCL_API friend constexpr bool
operator>=(__string_view const& __lhs, __string_view const& __rhs) noexcept
{
return __lhs.compare(__rhs) >= 0;
}
#endif // !_LIBCUDACXX_HAS_SPACESHIP_OPERATOR()
private:
[[nodiscard]] _CCCL_API static constexpr size_t __min_(size_t __x, size_t __y) noexcept
{
return __x < __y ? __x : __y;
}
[[nodiscard]] _CCCL_API static constexpr size_t __strlen_0x_(char const* __str, size_t __len) noexcept
{
return *__str ? __strlen_0x_(__str + 1, __len + 1) : __len;
}
[[nodiscard]] _CCCL_API static constexpr size_t __strlen_(char const* __str) noexcept
{
return ::cuda::std::char_traits<char>::length(__str);
}
[[nodiscard]] _CCCL_API static constexpr size_t __check_offset(ptrdiff_t __diff, size_t __len)
{
if (__diff < 0 || static_cast<size_t>(__diff) > __len)
{
_CCCL_THROW(::std::out_of_range, "__string_view index out of range");
}
return static_cast<size_t>(__diff);
}
char const* __str_;
size_t __len_;
};
_CCCL_END_NAMESPACE_CUDA_STD
#include <cuda/std/__cccl/epilogue.h>
#endif // _CUDA_STD___STRING_STRING_VIEW_H