From 91e3674806ee71636a1470bab97499af71c5f508 Mon Sep 17 00:00:00 2001 From: Michael Schellenberger Costa Date: Tue, 21 Feb 2023 10:28:39 +0100 Subject: [PATCH] Move `function` to its own file --- .../std/detail/libcxx/include/CMakeLists.txt | 1 + .../libcxx/include/__functional/function.h | 1251 +++++++++++++++++ .../cuda/std/detail/libcxx/include/functional | 1148 +-------------- 3 files changed, 1253 insertions(+), 1147 deletions(-) create mode 100644 include/cuda/std/detail/libcxx/include/__functional/function.h diff --git a/include/cuda/std/detail/libcxx/include/CMakeLists.txt b/include/cuda/std/detail/libcxx/include/CMakeLists.txt index 338a04da78..e3abcb9b81 100644 --- a/include/cuda/std/detail/libcxx/include/CMakeLists.txt +++ b/include/cuda/std/detail/libcxx/include/CMakeLists.txt @@ -37,6 +37,7 @@ set(files __functional/binder2nd.h __functional/compose.h __functional/default_searcher.h + __functional/function.h __functional/hash.h __functional/identity.h __functional/invoke.h diff --git a/include/cuda/std/detail/libcxx/include/__functional/function.h b/include/cuda/std/detail/libcxx/include/__functional/function.h new file mode 100644 index 0000000000..32ff13aaa3 --- /dev/null +++ b/include/cuda/std/detail/libcxx/include/__functional/function.h @@ -0,0 +1,1251 @@ +// -*- C++ -*- +//===----------------------------------------------------------------------===// +// +// 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) 2022 NVIDIA CORPORATION & AFFILIATES. All rights reserved. +// +//===----------------------------------------------------------------------===// + +#ifndef _LIBCUDACXX___FUNCTIONAL_FUNCTION_H +#define _LIBCUDACXX___FUNCTIONAL_FUNCTION_H + +#ifndef __cuda_std__ + +#ifndef __cuda_std__ +#include <__config> +#include <__functional_base> +#include +#include +#include +#include +#include +#include +#include +#endif // __cuda_std__ + +#include "../__functional/binary_function.h" +#include "../__functional/invoke.h" +#include "../__functional/unary_function.h" +#include "../__iterator/iterator_traits.h" +#include "../__utility/forward.h" +#include "../__utility/move.h" +#include "../__utility/piecewise_construct.h" +#include "../__utility/swap.h" + +#if defined(_LIBCUDACXX_USE_PRAGMA_GCC_SYSTEM_HEADER) +#pragma GCC system_header +#endif + +#ifndef _LIBCUDACXX_CXX03_LANG + +_LIBCUDACXX_BEGIN_NAMESPACE_STD + +// bad_function_call + +class _LIBCUDACXX_EXCEPTION_ABI bad_function_call + : public exception +{ +#ifdef _LIBCUDACXX_ABI_BAD_FUNCTION_CALL_KEY_FUNCTION +public: + virtual ~bad_function_call() _NOEXCEPT; + + virtual const char* what() const _NOEXCEPT; +#endif +}; + +_LIBCUDACXX_NORETURN inline _LIBCUDACXX_INLINE_VISIBILITY +void __throw_bad_function_call() +{ +#ifndef _LIBCUDACXX_NO_EXCEPTIONS + throw bad_function_call(); +#else + _CUDA_VSTD::abort(); +#endif +} + +template class _LIBCUDACXX_TEMPLATE_VIS function; // undefined + +namespace __function +{ + +template +struct __maybe_derive_from_unary_function +{ +}; + +template +struct __maybe_derive_from_unary_function<_Rp(_A1)> + : public __unary_function<_A1, _Rp> +{ +}; + +template +struct __maybe_derive_from_binary_function +{ +}; + +template +struct __maybe_derive_from_binary_function<_Rp(_A1, _A2)> + : public __binary_function<_A1, _A2, _Rp> +{ +}; + +template +_LIBCUDACXX_INLINE_VISIBILITY +bool __not_null(_Fp const&) { return true; } + +template +_LIBCUDACXX_INLINE_VISIBILITY +bool __not_null(_Fp* __ptr) { return __ptr; } + +template +_LIBCUDACXX_INLINE_VISIBILITY +bool __not_null(_Ret _Class::*__ptr) { return __ptr; } + +template +_LIBCUDACXX_INLINE_VISIBILITY +bool __not_null(function<_Fp> const& __f) { return !!__f; } + +#ifdef _LIBCUDACXX_HAS_EXTENSION_BLOCKS +template +_LIBCUDACXX_INLINE_VISIBILITY +bool __not_null(_Rp (^__p)(_Args...)) { return __p; } +#endif + +} // namespace __function + +#ifndef _LIBCUDACXX_CXX03_LANG + +namespace __function { + +// __alloc_func holds a functor and an allocator. + +template class __alloc_func; +template +class __default_alloc_func; + +template +class __alloc_func<_Fp, _Ap, _Rp(_ArgTypes...)> +{ + __compressed_pair<_Fp, _Ap> __f_; + + public: + typedef _LIBCUDACXX_NODEBUG_TYPE _Fp _Target; + typedef _LIBCUDACXX_NODEBUG_TYPE _Ap _Alloc; + + _LIBCUDACXX_INLINE_VISIBILITY + const _Target& __target() const { return __f_.first(); } + + // WIN32 APIs may define __allocator, so use __get_allocator instead. + _LIBCUDACXX_INLINE_VISIBILITY + const _Alloc& __get_allocator() const { return __f_.second(); } + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __alloc_func(_Target&& __f) + : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__f)), + _CUDA_VSTD::forward_as_tuple()) + { + } + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __alloc_func(const _Target& __f, const _Alloc& __a) + : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(__f), + _CUDA_VSTD::forward_as_tuple(__a)) + { + } + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __alloc_func(const _Target& __f, _Alloc&& __a) + : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(__f), + _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__a))) + { + } + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __alloc_func(_Target&& __f, _Alloc&& __a) + : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__f)), + _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__a))) + { + } + + _LIBCUDACXX_INLINE_VISIBILITY + _Rp operator()(_ArgTypes&&... __arg) + { + typedef __invoke_void_return_wrapper<_Rp> _Invoker; + return _Invoker::__call(__f_.first(), + _CUDA_VSTD::forward<_ArgTypes>(__arg)...); + } + + _LIBCUDACXX_INLINE_VISIBILITY + __alloc_func* __clone() const + { + typedef allocator_traits<_Alloc> __alloc_traits; + typedef typename __rebind_alloc_helper<__alloc_traits, __alloc_func>::type _AA; + _AA __a(__f_.second()); + typedef __allocator_destructor<_AA> _Dp; + unique_ptr<__alloc_func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1)); + ::new ((void*)__hold.get()) __alloc_func(__f_.first(), _Alloc(__a)); + return __hold.release(); + } + + _LIBCUDACXX_INLINE_VISIBILITY + void destroy() _NOEXCEPT { __f_.~__compressed_pair<_Target, _Alloc>(); } + + static void __destroy_and_delete(__alloc_func* __f) { + typedef allocator_traits<_Alloc> __alloc_traits; + typedef typename __rebind_alloc_helper<__alloc_traits, __alloc_func>::type _FunAlloc; + _FunAlloc __a(__f->__get_allocator()); + __f->destroy(); + __a.deallocate(__f, 1); + } +}; + +template +class __default_alloc_func<_Fp, _Rp(_ArgTypes...)> { + _Fp __f_; + +public: + typedef _LIBCUDACXX_NODEBUG_TYPE _Fp _Target; + + _LIBCUDACXX_INLINE_VISIBILITY + const _Target& __target() const { return __f_; } + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __default_alloc_func(_Target&& __f) : __f_(_CUDA_VSTD::move(__f)) {} + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __default_alloc_func(const _Target& __f) : __f_(__f) {} + + _LIBCUDACXX_INLINE_VISIBILITY + _Rp operator()(_ArgTypes&&... __arg) { + typedef __invoke_void_return_wrapper<_Rp> _Invoker; + return _Invoker::__call(__f_, _CUDA_VSTD::forward<_ArgTypes>(__arg)...); + } + + _LIBCUDACXX_INLINE_VISIBILITY + __default_alloc_func* __clone() const { + __builtin_new_allocator::__holder_t __hold = + __builtin_new_allocator::__allocate_type<__default_alloc_func>(1); + __default_alloc_func* __res = + ::new ((void*)__hold.get()) __default_alloc_func(__f_); + (void)__hold.release(); + return __res; + } + + _LIBCUDACXX_INLINE_VISIBILITY + void destroy() _NOEXCEPT { __f_.~_Target(); } + + static void __destroy_and_delete(__default_alloc_func* __f) { + __f->destroy(); + __builtin_new_allocator::__deallocate_type<__default_alloc_func>(__f, 1); + } +}; + +// __base provides an abstract interface for copyable functors. + +template class _LIBCUDACXX_TEMPLATE_VIS __base; + +template +class __base<_Rp(_ArgTypes...)> +{ + __base(const __base&); + __base& operator=(const __base&); +public: + _LIBCUDACXX_INLINE_VISIBILITY __base() {} + _LIBCUDACXX_INLINE_VISIBILITY virtual ~__base() {} + virtual __base* __clone() const = 0; + virtual void __clone(__base*) const = 0; + virtual void destroy() _NOEXCEPT = 0; + virtual void destroy_deallocate() _NOEXCEPT = 0; + virtual _Rp operator()(_ArgTypes&& ...) = 0; +#ifndef _LIBCUDACXX_NO_RTTI + virtual const void* target(const type_info&) const _NOEXCEPT = 0; + virtual const type_info& target_type() const _NOEXCEPT = 0; +#endif // _LIBCUDACXX_NO_RTTI +}; + +// __func implements __base for a given functor type. + +template class __func; + +template +class __func<_Fp, _Alloc, _Rp(_ArgTypes...)> + : public __base<_Rp(_ArgTypes...)> +{ + __alloc_func<_Fp, _Alloc, _Rp(_ArgTypes...)> __f_; +public: + _LIBCUDACXX_INLINE_VISIBILITY + explicit __func(_Fp&& __f) + : __f_(_CUDA_VSTD::move(__f)) {} + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __func(const _Fp& __f, const _Alloc& __a) + : __f_(__f, __a) {} + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __func(const _Fp& __f, _Alloc&& __a) + : __f_(__f, _CUDA_VSTD::move(__a)) {} + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __func(_Fp&& __f, _Alloc&& __a) + : __f_(_CUDA_VSTD::move(__f), _CUDA_VSTD::move(__a)) {} + + virtual __base<_Rp(_ArgTypes...)>* __clone() const; + virtual void __clone(__base<_Rp(_ArgTypes...)>*) const; + virtual void destroy() _NOEXCEPT; + virtual void destroy_deallocate() _NOEXCEPT; + virtual _Rp operator()(_ArgTypes&&... __arg); +#ifndef _LIBCUDACXX_NO_RTTI + virtual const void* target(const type_info&) const _NOEXCEPT; + virtual const type_info& target_type() const _NOEXCEPT; +#endif // _LIBCUDACXX_NO_RTTI +}; + +template +__base<_Rp(_ArgTypes...)>* +__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::__clone() const +{ + typedef allocator_traits<_Alloc> __alloc_traits; + typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap; + _Ap __a(__f_.__get_allocator()); + typedef __allocator_destructor<_Ap> _Dp; + unique_ptr<__func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1)); + ::new ((void*)__hold.get()) __func(__f_.__target(), _Alloc(__a)); + return __hold.release(); +} + +template +void +__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::__clone(__base<_Rp(_ArgTypes...)>* __p) const +{ + ::new ((void*)__p) __func(__f_.__target(), __f_.__get_allocator()); +} + +template +void +__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy() _NOEXCEPT +{ + __f_.destroy(); +} + +template +void +__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy_deallocate() _NOEXCEPT +{ + typedef allocator_traits<_Alloc> __alloc_traits; + typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap; + _Ap __a(__f_.__get_allocator()); + __f_.destroy(); + __a.deallocate(this, 1); +} + +template +_Rp +__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::operator()(_ArgTypes&& ... __arg) +{ + return __f_(_CUDA_VSTD::forward<_ArgTypes>(__arg)...); +} + +#ifndef _LIBCUDACXX_NO_RTTI + +template +const void* +__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::target(const type_info& __ti) const _NOEXCEPT +{ + if (__ti == typeid(_Fp)) + return _CUDA_VSTD::addressof(__f_.__target()); + return nullptr; +} + +template +const type_info& +__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::target_type() const _NOEXCEPT +{ + return typeid(_Fp); +} + +#endif // _LIBCUDACXX_NO_RTTI + +// __value_func creates a value-type from a __func. + +template class __value_func; + +template class __value_func<_Rp(_ArgTypes...)> +{ + typename aligned_storage<3 * sizeof(void*)>::type __buf_; + + typedef __base<_Rp(_ArgTypes...)> __func; + __func* __f_; + + _LIBCUDACXX_NO_CFI static __func* __as_base(void* __p) + { + return reinterpret_cast<__func*>(__p); + } + + public: + _LIBCUDACXX_INLINE_VISIBILITY + __value_func() _NOEXCEPT : __f_(nullptr) {} + + template + _LIBCUDACXX_INLINE_VISIBILITY __value_func(_Fp&& __f, const _Alloc& __a) + : __f_(nullptr) + { + typedef allocator_traits<_Alloc> __alloc_traits; + typedef __function::__func<_Fp, _Alloc, _Rp(_ArgTypes...)> _Fun; + typedef typename __rebind_alloc_helper<__alloc_traits, _Fun>::type _FunAlloc; + + if (__function::__not_null(__f)) + { + _FunAlloc __af(__a); + if (sizeof(_Fun) <= sizeof(__buf_) && + is_nothrow_copy_constructible<_Fp>::value && + is_nothrow_copy_constructible<_FunAlloc>::value) + { + __f_ = + ::new ((void*)&__buf_) _Fun(_CUDA_VSTD::move(__f), _Alloc(__af)); + } + else + { + typedef __allocator_destructor<_FunAlloc> _Dp; + unique_ptr<__func, _Dp> __hold(__af.allocate(1), _Dp(__af, 1)); + ::new ((void*)__hold.get()) _Fun(_CUDA_VSTD::move(__f), _Alloc(__a)); + __f_ = __hold.release(); + } + } + } + + template , __value_func>::value>> + _LIBCUDACXX_INLINE_VISIBILITY explicit __value_func(_Fp&& __f) + : __value_func(_CUDA_VSTD::forward<_Fp>(__f), allocator<_Fp>()) {} + + _LIBCUDACXX_INLINE_VISIBILITY + __value_func(const __value_func& __f) + { + if (__f.__f_ == nullptr) + __f_ = nullptr; + else if ((void*)__f.__f_ == &__f.__buf_) + { + __f_ = __as_base(&__buf_); + __f.__f_->__clone(__f_); + } + else + __f_ = __f.__f_->__clone(); + } + + _LIBCUDACXX_INLINE_VISIBILITY + __value_func(__value_func&& __f) _NOEXCEPT + { + if (__f.__f_ == nullptr) + __f_ = nullptr; + else if ((void*)__f.__f_ == &__f.__buf_) + { + __f_ = __as_base(&__buf_); + __f.__f_->__clone(__f_); + } + else + { + __f_ = __f.__f_; + __f.__f_ = nullptr; + } + } + + _LIBCUDACXX_INLINE_VISIBILITY + ~__value_func() + { + if ((void*)__f_ == &__buf_) + __f_->destroy(); + else if (__f_) + __f_->destroy_deallocate(); + } + + _LIBCUDACXX_INLINE_VISIBILITY + __value_func& operator=(__value_func&& __f) + { + *this = nullptr; + if (__f.__f_ == nullptr) + __f_ = nullptr; + else if ((void*)__f.__f_ == &__f.__buf_) + { + __f_ = __as_base(&__buf_); + __f.__f_->__clone(__f_); + } + else + { + __f_ = __f.__f_; + __f.__f_ = nullptr; + } + return *this; + } + + _LIBCUDACXX_INLINE_VISIBILITY + __value_func& operator=(nullptr_t) + { + __func* __f = __f_; + __f_ = nullptr; + if ((void*)__f == &__buf_) + __f->destroy(); + else if (__f) + __f->destroy_deallocate(); + return *this; + } + + _LIBCUDACXX_INLINE_VISIBILITY + _Rp operator()(_ArgTypes&&... __args) const + { + if (__f_ == nullptr) + __throw_bad_function_call(); + return (*__f_)(_CUDA_VSTD::forward<_ArgTypes>(__args)...); + } + + _LIBCUDACXX_INLINE_VISIBILITY + void swap(__value_func& __f) _NOEXCEPT + { + if (&__f == this) + return; + if ((void*)__f_ == &__buf_ && (void*)__f.__f_ == &__f.__buf_) + { + typename aligned_storage::type __tempbuf; + __func* __t = __as_base(&__tempbuf); + __f_->__clone(__t); + __f_->destroy(); + __f_ = nullptr; + __f.__f_->__clone(__as_base(&__buf_)); + __f.__f_->destroy(); + __f.__f_ = nullptr; + __f_ = __as_base(&__buf_); + __t->__clone(__as_base(&__f.__buf_)); + __t->destroy(); + __f.__f_ = __as_base(&__f.__buf_); + } + else if ((void*)__f_ == &__buf_) + { + __f_->__clone(__as_base(&__f.__buf_)); + __f_->destroy(); + __f_ = __f.__f_; + __f.__f_ = __as_base(&__f.__buf_); + } + else if ((void*)__f.__f_ == &__f.__buf_) + { + __f.__f_->__clone(__as_base(&__buf_)); + __f.__f_->destroy(); + __f.__f_ = __f_; + __f_ = __as_base(&__buf_); + } + else + _CUDA_VSTD::swap(__f_, __f.__f_); + } + + _LIBCUDACXX_INLINE_VISIBILITY + _LIBCUDACXX_EXPLICIT operator bool() const _NOEXCEPT { return __f_ != nullptr; } + +#ifndef _LIBCUDACXX_NO_RTTI + _LIBCUDACXX_INLINE_VISIBILITY + const type_info& target_type() const _NOEXCEPT + { + if (__f_ == nullptr) + return typeid(void); + return __f_->target_type(); + } + + template + _LIBCUDACXX_INLINE_VISIBILITY const _Tp* target() const _NOEXCEPT + { + if (__f_ == nullptr) + return nullptr; + return (const _Tp*)__f_->target(typeid(_Tp)); + } +#endif // _LIBCUDACXX_NO_RTTI +}; + +// Storage for a functor object, to be used with __policy to manage copy and +// destruction. +union __policy_storage +{ + mutable char __small[sizeof(void*) * 2]; + void* __large; +}; + +// True if _Fun can safely be held in __policy_storage.__small. +template +struct __use_small_storage + : public integral_constant< + bool, sizeof(_Fun) <= sizeof(__policy_storage) && + _LIBCUDACXX_ALIGNOF(_Fun) <= _LIBCUDACXX_ALIGNOF(__policy_storage) && + is_trivially_copy_constructible<_Fun>::value && + is_trivially_destructible<_Fun>::value> {}; + +// Policy contains information about how to copy, destroy, and move the +// underlying functor. You can think of it as a vtable of sorts. +struct __policy +{ + // Used to copy or destroy __large values. null for trivial objects. + void* (*const __clone)(const void*); + void (*const __destroy)(void*); + + // True if this is the null policy (no value). + const bool __is_null; + + // The target type. May be null if RTTI is disabled. + const type_info* const __type_info; + + // Returns a pointer to a static policy object suitable for the functor + // type. + template + _LIBCUDACXX_INLINE_VISIBILITY static const __policy* __create() + { + return __choose_policy<_Fun>(__use_small_storage<_Fun>()); + } + + _LIBCUDACXX_INLINE_VISIBILITY + static const __policy* __create_empty() + { + static const _LIBCUDACXX_CONSTEXPR __policy __policy_ = {nullptr, nullptr, + true, +#ifndef _LIBCUDACXX_NO_RTTI + &typeid(void) +#else + nullptr +#endif + }; + return &__policy_; + } + + private: + template static void* __large_clone(const void* __s) + { + const _Fun* __f = static_cast(__s); + return __f->__clone(); + } + + template + static void __large_destroy(void* __s) { + _Fun::__destroy_and_delete(static_cast<_Fun*>(__s)); + } + + template + _LIBCUDACXX_INLINE_VISIBILITY static const __policy* + __choose_policy(/* is_small = */ false_type) { + static const _LIBCUDACXX_CONSTEXPR __policy __policy_ = { + &__large_clone<_Fun>, &__large_destroy<_Fun>, false, +#ifndef _LIBCUDACXX_NO_RTTI + &typeid(typename _Fun::_Target) +#else + nullptr +#endif + }; + return &__policy_; + } + + template + _LIBCUDACXX_INLINE_VISIBILITY static const __policy* + __choose_policy(/* is_small = */ true_type) + { + static const _LIBCUDACXX_CONSTEXPR __policy __policy_ = { + nullptr, nullptr, false, +#ifndef _LIBCUDACXX_NO_RTTI + &typeid(typename _Fun::_Target) +#else + nullptr +#endif + }; + return &__policy_; + } +}; + +// Used to choose between perfect forwarding or pass-by-value. Pass-by-value is +// faster for types that can be passed in registers. +template +using __fast_forward = __conditional_t::value, _Tp, _Tp&&>; + +// __policy_invoker calls an instance of __alloc_func held in __policy_storage. + +template struct __policy_invoker; + +template +struct __policy_invoker<_Rp(_ArgTypes...)> +{ + typedef _Rp (*__Call)(const __policy_storage*, + __fast_forward<_ArgTypes>...); + + __Call __call_; + + // Creates an invoker that throws bad_function_call. + _LIBCUDACXX_INLINE_VISIBILITY + __policy_invoker() : __call_(&__call_empty) {} + + // Creates an invoker that calls the given instance of __func. + template + _LIBCUDACXX_INLINE_VISIBILITY static __policy_invoker __create() + { + return __policy_invoker(&__call_impl<_Fun>); + } + + private: + _LIBCUDACXX_INLINE_VISIBILITY + explicit __policy_invoker(__Call __c) : __call_(__c) {} + + static _Rp __call_empty(const __policy_storage*, + __fast_forward<_ArgTypes>...) + { + __throw_bad_function_call(); + } + + template + static _Rp __call_impl(const __policy_storage* __buf, + __fast_forward<_ArgTypes>... __args) + { + _Fun* __f = reinterpret_cast<_Fun*>(__use_small_storage<_Fun>::value + ? &__buf->__small + : __buf->__large); + return (*__f)(_CUDA_VSTD::forward<_ArgTypes>(__args)...); + } +}; + +// __policy_func uses a __policy and __policy_invoker to create a type-erased, +// copyable functor. + +template class __policy_func; + +template class __policy_func<_Rp(_ArgTypes...)> +{ + // Inline storage for small objects. + __policy_storage __buf_; + + // Calls the value stored in __buf_. This could technically be part of + // policy, but storing it here eliminates a level of indirection inside + // operator(). + typedef __function::__policy_invoker<_Rp(_ArgTypes...)> __invoker; + __invoker __invoker_; + + // The policy that describes how to move / copy / destroy __buf_. Never + // null, even if the function is empty. + const __policy* __policy_; + + public: + _LIBCUDACXX_INLINE_VISIBILITY + __policy_func() : __policy_(__policy::__create_empty()) {} + + template + _LIBCUDACXX_INLINE_VISIBILITY __policy_func(_Fp&& __f, const _Alloc& __a) + : __policy_(__policy::__create_empty()) + { + typedef __alloc_func<_Fp, _Alloc, _Rp(_ArgTypes...)> _Fun; + typedef allocator_traits<_Alloc> __alloc_traits; + typedef typename __rebind_alloc_helper<__alloc_traits, _Fun>::type _FunAlloc; + + if (__function::__not_null(__f)) + { + __invoker_ = __invoker::template __create<_Fun>(); + __policy_ = __policy::__create<_Fun>(); + + _FunAlloc __af(__a); + if (__use_small_storage<_Fun>()) + { + ::new ((void*)&__buf_.__small) + _Fun(_CUDA_VSTD::move(__f), _Alloc(__af)); + } + else + { + typedef __allocator_destructor<_FunAlloc> _Dp; + unique_ptr<_Fun, _Dp> __hold(__af.allocate(1), _Dp(__af, 1)); + ::new ((void*)__hold.get()) + _Fun(_CUDA_VSTD::move(__f), _Alloc(__af)); + __buf_.__large = __hold.release(); + } + } + } + + template , __policy_func>::value>> + _LIBCUDACXX_INLINE_VISIBILITY explicit __policy_func(_Fp&& __f) + : __policy_(__policy::__create_empty()) { + typedef __default_alloc_func<_Fp, _Rp(_ArgTypes...)> _Fun; + + if (__function::__not_null(__f)) { + __invoker_ = __invoker::template __create<_Fun>(); + __policy_ = __policy::__create<_Fun>(); + if (__use_small_storage<_Fun>()) { + ::new ((void*)&__buf_.__small) _Fun(_CUDA_VSTD::move(__f)); + } else { + __builtin_new_allocator::__holder_t __hold = + __builtin_new_allocator::__allocate_type<_Fun>(1); + __buf_.__large = ::new ((void*)__hold.get()) _Fun(_CUDA_VSTD::move(__f)); + (void)__hold.release(); + } + } + } + + _LIBCUDACXX_INLINE_VISIBILITY + __policy_func(const __policy_func& __f) + : __buf_(__f.__buf_), __invoker_(__f.__invoker_), + __policy_(__f.__policy_) + { + if (__policy_->__clone) + __buf_.__large = __policy_->__clone(__f.__buf_.__large); + } + + _LIBCUDACXX_INLINE_VISIBILITY + __policy_func(__policy_func&& __f) + : __buf_(__f.__buf_), __invoker_(__f.__invoker_), + __policy_(__f.__policy_) + { + if (__policy_->__destroy) + { + __f.__policy_ = __policy::__create_empty(); + __f.__invoker_ = __invoker(); + } + } + + _LIBCUDACXX_INLINE_VISIBILITY + ~__policy_func() + { + if (__policy_->__destroy) + __policy_->__destroy(__buf_.__large); + } + + _LIBCUDACXX_INLINE_VISIBILITY + __policy_func& operator=(__policy_func&& __f) + { + *this = nullptr; + __buf_ = __f.__buf_; + __invoker_ = __f.__invoker_; + __policy_ = __f.__policy_; + __f.__policy_ = __policy::__create_empty(); + __f.__invoker_ = __invoker(); + return *this; + } + + _LIBCUDACXX_INLINE_VISIBILITY + __policy_func& operator=(nullptr_t) + { + const __policy* __p = __policy_; + __policy_ = __policy::__create_empty(); + __invoker_ = __invoker(); + if (__p->__destroy) + __p->__destroy(__buf_.__large); + return *this; + } + + _LIBCUDACXX_INLINE_VISIBILITY + _Rp operator()(_ArgTypes&&... __args) const + { + return __invoker_.__call_(_CUDA_VSTD::addressof(__buf_), + _CUDA_VSTD::forward<_ArgTypes>(__args)...); + } + + _LIBCUDACXX_INLINE_VISIBILITY + void swap(__policy_func& __f) + { + _CUDA_VSTD::swap(__invoker_, __f.__invoker_); + _CUDA_VSTD::swap(__policy_, __f.__policy_); + _CUDA_VSTD::swap(__buf_, __f.__buf_); + } + + _LIBCUDACXX_INLINE_VISIBILITY + explicit operator bool() const _NOEXCEPT + { + return !__policy_->__is_null; + } + +#ifndef _LIBCUDACXX_NO_RTTI + _LIBCUDACXX_INLINE_VISIBILITY + const type_info& target_type() const _NOEXCEPT + { + return *__policy_->__type_info; + } + + template + _LIBCUDACXX_INLINE_VISIBILITY const _Tp* target() const _NOEXCEPT + { + if (__policy_->__is_null || typeid(_Tp) != *__policy_->__type_info) + return nullptr; + if (__policy_->__clone) // Out of line storage. + return reinterpret_cast(__buf_.__large); + else + return reinterpret_cast(&__buf_.__small); + } +#endif // _LIBCUDACXX_NO_RTTI +}; + +#if defined(_LIBCUDACXX_HAS_BLOCKS_RUNTIME) + +extern "C" void *_Block_copy(const void *); +extern "C" void _Block_release(const void *); + +template +class __func<_Rp1(^)(_ArgTypes1...), _Alloc, _Rp(_ArgTypes...)> + : public __base<_Rp(_ArgTypes...)> +{ + typedef _Rp1(^__block_type)(_ArgTypes1...); + __block_type __f_; + +public: + _LIBCUDACXX_INLINE_VISIBILITY + explicit __func(__block_type const& __f) +#ifdef _LIBCUDACXX_HAS_OBJC_ARC + : __f_(__f) +#else + : __f_(reinterpret_cast<__block_type>(__f ? _Block_copy(__f) : nullptr)) +#endif + { } + + // [TODO] add && to save on a retain + + _LIBCUDACXX_INLINE_VISIBILITY + explicit __func(__block_type __f, const _Alloc& /* unused */) +#ifdef _LIBCUDACXX_HAS_OBJC_ARC + : __f_(__f) +#else + : __f_(reinterpret_cast<__block_type>(__f ? _Block_copy(__f) : nullptr)) +#endif + { } + + virtual __base<_Rp(_ArgTypes...)>* __clone() const { + _LIBCUDACXX_ASSERT(false, + "Block pointers are just pointers, so they should always fit into " + "std::function's small buffer optimization. This function should " + "never be invoked."); + return nullptr; + } + + virtual void __clone(__base<_Rp(_ArgTypes...)>* __p) const { + ::new ((void*)__p) __func(__f_); + } + + virtual void destroy() _NOEXCEPT { +#ifndef _LIBCUDACXX_HAS_OBJC_ARC + if (__f_) + _Block_release(__f_); +#endif + __f_ = 0; + } + + virtual void destroy_deallocate() _NOEXCEPT { + _LIBCUDACXX_ASSERT(false, + "Block pointers are just pointers, so they should always fit into " + "std::function's small buffer optimization. This function should " + "never be invoked."); + } + + virtual _Rp operator()(_ArgTypes&& ... __arg) { + return _CUDA_VSTD::__invoke(__f_, _CUDA_VSTD::forward<_ArgTypes>(__arg)...); + } + +#ifndef _LIBCUDACXX_NO_RTTI + virtual const void* target(type_info const& __ti) const _NOEXCEPT { + if (__ti == typeid(__func::__block_type)) + return &__f_; + return (const void*)nullptr; + } + + virtual const type_info& target_type() const _NOEXCEPT { + return typeid(__func::__block_type); + } +#endif // _LIBCUDACXX_NO_RTTI +}; + +#endif // _LIBCUDACXX_HAS_EXTENSION_BLOCKS + +} // namespace __function + +template +class _LIBCUDACXX_TEMPLATE_VIS function<_Rp(_ArgTypes...)> + : public __function::__maybe_derive_from_unary_function<_Rp(_ArgTypes...)>, + public __function::__maybe_derive_from_binary_function<_Rp(_ArgTypes...)> +{ +#ifndef _LIBCUDACXX_ABI_OPTIMIZED_FUNCTION + typedef __function::__value_func<_Rp(_ArgTypes...)> __func; +#else + typedef __function::__policy_func<_Rp(_ArgTypes...)> __func; +#endif + + __func __f_; + + template , function>, + __invokable<_Fp, _ArgTypes...> + >::value> + struct __callable; + template + struct __callable<_Fp, true> + { + static const bool value = is_void<_Rp>::value || + __is_core_convertible::type, + _Rp>::value; + }; + template + struct __callable<_Fp, false> + { + static const bool value = false; + }; + + template + using _EnableIfLValueCallable = __enable_if_t<__callable<_Fp&>::value>; +public: + typedef _Rp result_type; + + // construct/copy/destroy: + _LIBCUDACXX_INLINE_VISIBILITY + function() _NOEXCEPT { } + _LIBCUDACXX_INLINE_VISIBILITY + function(nullptr_t) _NOEXCEPT {} + function(const function&); + function(function&&) _NOEXCEPT; + template> + function(_Fp); + +#if _LIBCUDACXX_STD_VER <= 14 + template + _LIBCUDACXX_INLINE_VISIBILITY + function(allocator_arg_t, const _Alloc&) _NOEXCEPT {} + template + _LIBCUDACXX_INLINE_VISIBILITY + function(allocator_arg_t, const _Alloc&, nullptr_t) _NOEXCEPT {} + template + function(allocator_arg_t, const _Alloc&, const function&); + template + function(allocator_arg_t, const _Alloc&, function&&); + template> + function(allocator_arg_t, const _Alloc& __a, _Fp __f); +#endif + + function& operator=(const function&); + function& operator=(function&&) _NOEXCEPT; + function& operator=(nullptr_t) _NOEXCEPT; + template>> + function& operator=(_Fp&&); + + ~function(); + + // function modifiers: + void swap(function&) _NOEXCEPT; + +#if _LIBCUDACXX_STD_VER <= 14 + template + _LIBCUDACXX_INLINE_VISIBILITY + void assign(_Fp&& __f, const _Alloc& __a) + {function(allocator_arg, __a, _CUDA_VSTD::forward<_Fp>(__f)).swap(*this);} +#endif + + // function capacity: + _LIBCUDACXX_INLINE_VISIBILITY + _LIBCUDACXX_EXPLICIT operator bool() const _NOEXCEPT { + return static_cast(__f_); + } + + // deleted overloads close possible hole in the type system + template + bool operator==(const function<_R2(_ArgTypes2...)>&) const = delete; + template + bool operator!=(const function<_R2(_ArgTypes2...)>&) const = delete; +public: + // function invocation: + _Rp operator()(_ArgTypes...) const; + +#ifndef _LIBCUDACXX_NO_RTTI + // function target access: + const type_info& target_type() const _NOEXCEPT; + template _Tp* target() _NOEXCEPT; + template const _Tp* target() const _NOEXCEPT; +#endif // _LIBCUDACXX_NO_RTTI +}; + +#if _LIBCUDACXX_STD_VER > 14 +template +function(_Rp(*)(_Ap...)) -> function<_Rp(_Ap...)>; + +template +struct __strip_signature; + +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...)> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile> { using type = _Rp(_Ap...); }; + +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) &> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const &> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile &> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile &> { using type = _Rp(_Ap...); }; + +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) noexcept> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const noexcept> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile noexcept> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile noexcept> { using type = _Rp(_Ap...); }; + +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) & noexcept> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const & noexcept> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile & noexcept> { using type = _Rp(_Ap...); }; +template +struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile & noexcept> { using type = _Rp(_Ap...); }; + +template::type> +function(_Fp) -> function<_Stripped>; +#endif // _LIBCUDACXX_STD_VER > 14 + +template +function<_Rp(_ArgTypes...)>::function(const function& __f) : __f_(__f.__f_) {} + +#if _LIBCUDACXX_STD_VER <= 14 +template +template +function<_Rp(_ArgTypes...)>::function(allocator_arg_t, const _Alloc&, + const function& __f) : __f_(__f.__f_) {} +#endif + +template +function<_Rp(_ArgTypes...)>::function(function&& __f) _NOEXCEPT + : __f_(_CUDA_VSTD::move(__f.__f_)) {} + +#if _LIBCUDACXX_STD_VER <= 14 +template +template +function<_Rp(_ArgTypes...)>::function(allocator_arg_t, const _Alloc&, + function&& __f) + : __f_(_CUDA_VSTD::move(__f.__f_)) {} +#endif + +template +template +function<_Rp(_ArgTypes...)>::function(_Fp __f) : __f_(_CUDA_VSTD::move(__f)) {} + +#if _LIBCUDACXX_STD_VER <= 14 +template +template +function<_Rp(_ArgTypes...)>::function(allocator_arg_t, const _Alloc& __a, + _Fp __f) + : __f_(_CUDA_VSTD::move(__f), __a) {} +#endif + +template +function<_Rp(_ArgTypes...)>& +function<_Rp(_ArgTypes...)>::operator=(const function& __f) +{ + function(__f).swap(*this); + return *this; +} + +template +function<_Rp(_ArgTypes...)>& +function<_Rp(_ArgTypes...)>::operator=(function&& __f) _NOEXCEPT +{ + __f_ = _CUDA_VSTD::move(__f.__f_); + return *this; +} + +template +function<_Rp(_ArgTypes...)>& +function<_Rp(_ArgTypes...)>::operator=(nullptr_t) _NOEXCEPT +{ + __f_ = nullptr; + return *this; +} + +template +template +function<_Rp(_ArgTypes...)>& +function<_Rp(_ArgTypes...)>::operator=(_Fp&& __f) +{ + function(_CUDA_VSTD::forward<_Fp>(__f)).swap(*this); + return *this; +} + +template +function<_Rp(_ArgTypes...)>::~function() {} + +template +void +function<_Rp(_ArgTypes...)>::swap(function& __f) _NOEXCEPT +{ + __f_.swap(__f.__f_); +} + +template +_Rp +function<_Rp(_ArgTypes...)>::operator()(_ArgTypes... __arg) const +{ + return __f_(_CUDA_VSTD::forward<_ArgTypes>(__arg)...); +} + +#ifndef _LIBCUDACXX_NO_RTTI + +template +const type_info& +function<_Rp(_ArgTypes...)>::target_type() const _NOEXCEPT +{ + return __f_.target_type(); +} + +template +template +_Tp* +function<_Rp(_ArgTypes...)>::target() _NOEXCEPT +{ + return (_Tp*)(__f_.template target<_Tp>()); +} + +template +template +const _Tp* +function<_Rp(_ArgTypes...)>::target() const _NOEXCEPT +{ + return __f_.template target<_Tp>(); +} + +#endif // _LIBCUDACXX_NO_RTTI + +template +inline _LIBCUDACXX_INLINE_VISIBILITY +bool +operator==(const function<_Rp(_ArgTypes...)>& __f, nullptr_t) _NOEXCEPT {return !__f;} + +template +inline _LIBCUDACXX_INLINE_VISIBILITY +bool +operator==(nullptr_t, const function<_Rp(_ArgTypes...)>& __f) _NOEXCEPT {return !__f;} + +template +inline _LIBCUDACXX_INLINE_VISIBILITY +bool +operator!=(const function<_Rp(_ArgTypes...)>& __f, nullptr_t) _NOEXCEPT {return (bool)__f;} + +template +inline _LIBCUDACXX_INLINE_VISIBILITY +bool +operator!=(nullptr_t, const function<_Rp(_ArgTypes...)>& __f) _NOEXCEPT {return (bool)__f;} + +template +inline _LIBCUDACXX_INLINE_VISIBILITY +void +swap(function<_Rp(_ArgTypes...)>& __x, function<_Rp(_ArgTypes...)>& __y) _NOEXCEPT +{return __x.swap(__y);} + +#else // _LIBCUDACXX_CXX03_LANG + +#include <__functional_03> + +#endif + +_LIBCUDACXX_END_NAMESPACE_STD + +#endif // _LIBCUDACXX_CXX03_LANG + +#endif // __cuda_std__ + +#endif // _LIBCUDACXX___FUNCTIONAL_FUNCTION_H diff --git a/include/cuda/std/detail/libcxx/include/functional b/include/cuda/std/detail/libcxx/include/functional index 2de5a51874..29b7425411 100644 --- a/include/cuda/std/detail/libcxx/include/functional +++ b/include/cuda/std/detail/libcxx/include/functional @@ -499,15 +499,7 @@ POLICY: For non-variadic implementations, the number of arguments is limited #ifndef __cuda_std__ #include <__config> -#include -#include -#include -#include -#include -#include #include -#include <__functional_base> -#include <__pragma_push> #endif // __cuda_std__ #include "__functional/binary_function.h" @@ -519,6 +511,7 @@ POLICY: For non-variadic implementations, the number of arguments is limited #include "__functional/binder2nd.h" #include "__functional/compose.h" #include "__functional/default_searcher.h" +#include "__functional/function.h" #include "__functional/hash.h" #include "__functional/identity.h" #include "__functional/invoke.h" @@ -535,1148 +528,9 @@ POLICY: For non-variadic implementations, the number of arguments is limited #include "__functional/unary_negate.h" #include "__functional/unwrap_ref.h" #include "__functional/weak_result_type.h" -#include "__memory/addressof.h" -#include "__memory/pointer_traits.h" #if defined(_LIBCUDACXX_USE_PRAGMA_GCC_SYSTEM_HEADER) #pragma GCC system_header #endif -_LIBCUDACXX_BEGIN_NAMESPACE_STD - -#ifndef __cuda_std__ - -//////////////////////////////////////////////////////////////////////////////// -// FUNCTION -//============================================================================== - -// bad_function_call - -class _LIBCUDACXX_EXCEPTION_ABI bad_function_call - : public exception -{ -#ifdef _LIBCUDACXX_ABI_BAD_FUNCTION_CALL_KEY_FUNCTION -public: - virtual ~bad_function_call() _NOEXCEPT; - - virtual const char* what() const _NOEXCEPT; -#endif -}; - -_LIBCUDACXX_NORETURN inline _LIBCUDACXX_INLINE_VISIBILITY -void __throw_bad_function_call() -{ -#ifndef _LIBCUDACXX_NO_EXCEPTIONS - throw bad_function_call(); -#else - _CUDA_VSTD::abort(); -#endif -} - -template class _LIBCUDACXX_TEMPLATE_VIS function; // undefined - -namespace __function -{ - -template -struct __maybe_derive_from_unary_function -{ -}; - -template -struct __maybe_derive_from_unary_function<_Rp(_A1)> - : public __unary_function<_A1, _Rp> -{ -}; - -template -struct __maybe_derive_from_binary_function -{ -}; - -template -struct __maybe_derive_from_binary_function<_Rp(_A1, _A2)> - : public __binary_function<_A1, _A2, _Rp> -{ -}; - -template -_LIBCUDACXX_INLINE_VISIBILITY -bool __not_null(_Fp const&) { return true; } - -template -_LIBCUDACXX_INLINE_VISIBILITY -bool __not_null(_Fp* __ptr) { return __ptr; } - -template -_LIBCUDACXX_INLINE_VISIBILITY -bool __not_null(_Ret _Class::*__ptr) { return __ptr; } - -template -_LIBCUDACXX_INLINE_VISIBILITY -bool __not_null(function<_Fp> const& __f) { return !!__f; } - -} // namespace __function - -#ifndef _LIBCUDACXX_CXX03_LANG - -namespace __function { - -// __alloc_func holds a functor and an allocator. - -template class __alloc_func; -template -class __default_alloc_func; - -template -class __alloc_func<_Fp, _Ap, _Rp(_ArgTypes...)> -{ - __compressed_pair<_Fp, _Ap> __f_; - - public: - typedef _LIBCUDACXX_NODEBUG_TYPE _Fp _Target; - typedef _LIBCUDACXX_NODEBUG_TYPE _Ap _Alloc; - - _LIBCUDACXX_INLINE_VISIBILITY - const _Target& __target() const { return __f_.first(); } - - // WIN32 APIs may define __allocator, so use __get_allocator instead. - _LIBCUDACXX_INLINE_VISIBILITY - const _Alloc& __get_allocator() const { return __f_.second(); } - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __alloc_func(_Target&& __f) - : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__f)), - _CUDA_VSTD::forward_as_tuple()) - { - } - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __alloc_func(const _Target& __f, const _Alloc& __a) - : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(__f), - _CUDA_VSTD::forward_as_tuple(__a)) - { - } - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __alloc_func(const _Target& __f, _Alloc&& __a) - : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(__f), - _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__a))) - { - } - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __alloc_func(_Target&& __f, _Alloc&& __a) - : __f_(piecewise_construct, _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__f)), - _CUDA_VSTD::forward_as_tuple(_CUDA_VSTD::move(__a))) - { - } - - _LIBCUDACXX_INLINE_VISIBILITY - _Rp operator()(_ArgTypes&&... __arg) - { - typedef __invoke_void_return_wrapper<_Rp> _Invoker; - return _Invoker::__call(__f_.first(), - _CUDA_VSTD::forward<_ArgTypes>(__arg)...); - } - - _LIBCUDACXX_INLINE_VISIBILITY - __alloc_func* __clone() const - { - typedef allocator_traits<_Alloc> __alloc_traits; - typedef - typename __rebind_alloc_helper<__alloc_traits, __alloc_func>::type - _AA; - _AA __a(__f_.second()); - typedef __allocator_destructor<_AA> _Dp; - unique_ptr<__alloc_func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1)); - ::new ((void*)__hold.get()) __alloc_func(__f_.first(), _Alloc(__a)); - return __hold.release(); - } - - _LIBCUDACXX_INLINE_VISIBILITY - void destroy() _NOEXCEPT { __f_.~__compressed_pair<_Target, _Alloc>(); } - - static void __destroy_and_delete(__alloc_func* __f) { - typedef allocator_traits<_Alloc> __alloc_traits; - typedef typename __rebind_alloc_helper<__alloc_traits, __alloc_func>::type - _FunAlloc; - _FunAlloc __a(__f->__get_allocator()); - __f->destroy(); - __a.deallocate(__f, 1); - } -}; - -template -class __default_alloc_func<_Fp, _Rp(_ArgTypes...)> { - _Fp __f_; - -public: - typedef _LIBCUDACXX_NODEBUG_TYPE _Fp _Target; - - _LIBCUDACXX_INLINE_VISIBILITY - const _Target& __target() const { return __f_; } - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __default_alloc_func(_Target&& __f) : __f_(std::move(__f)) {} - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __default_alloc_func(const _Target& __f) : __f_(__f) {} - - _LIBCUDACXX_INLINE_VISIBILITY - _Rp operator()(_ArgTypes&&... __arg) { - typedef __invoke_void_return_wrapper<_Rp> _Invoker; - return _Invoker::__call(__f_, _CUDA_VSTD::forward<_ArgTypes>(__arg)...); - } - - _LIBCUDACXX_INLINE_VISIBILITY - __default_alloc_func* __clone() const { - __builtin_new_allocator::__holder_t __hold = - __builtin_new_allocator::__allocate_type<__default_alloc_func>(1); - __default_alloc_func* __res = - ::new (__hold.get()) __default_alloc_func(__f_); - (void)__hold.release(); - return __res; - } - - _LIBCUDACXX_INLINE_VISIBILITY - void destroy() _NOEXCEPT { __f_.~_Target(); } - - static void __destroy_and_delete(__default_alloc_func* __f) { - __f->destroy(); - __builtin_new_allocator::__deallocate_type<__default_alloc_func>(__f, 1); - } -}; - -// __base provides an abstract interface for copyable functors. - -template class __base; - -template -class __base<_Rp(_ArgTypes...)> -{ - __base(const __base&); - __base& operator=(const __base&); -public: - _LIBCUDACXX_INLINE_VISIBILITY __base() {} - _LIBCUDACXX_INLINE_VISIBILITY virtual ~__base() {} - virtual __base* __clone() const = 0; - virtual void __clone(__base*) const = 0; - virtual void destroy() _NOEXCEPT = 0; - virtual void destroy_deallocate() _NOEXCEPT = 0; - virtual _Rp operator()(_ArgTypes&& ...) = 0; -#ifndef _LIBCUDACXX_NO_RTTI - virtual const void* target(const type_info&) const _NOEXCEPT = 0; - virtual const std::type_info& target_type() const _NOEXCEPT = 0; -#endif // _LIBCUDACXX_NO_RTTI -}; - -// __func implements __base for a given functor type. - -template class __func; - -template -class __func<_Fp, _Alloc, _Rp(_ArgTypes...)> - : public __base<_Rp(_ArgTypes...)> -{ - __alloc_func<_Fp, _Alloc, _Rp(_ArgTypes...)> __f_; -public: - _LIBCUDACXX_INLINE_VISIBILITY - explicit __func(_Fp&& __f) - : __f_(_CUDA_VSTD::move(__f)) {} - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __func(const _Fp& __f, const _Alloc& __a) - : __f_(__f, __a) {} - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __func(const _Fp& __f, _Alloc&& __a) - : __f_(__f, _CUDA_VSTD::move(__a)) {} - - _LIBCUDACXX_INLINE_VISIBILITY - explicit __func(_Fp&& __f, _Alloc&& __a) - : __f_(_CUDA_VSTD::move(__f), _CUDA_VSTD::move(__a)) {} - - virtual __base<_Rp(_ArgTypes...)>* __clone() const; - virtual void __clone(__base<_Rp(_ArgTypes...)>*) const; - virtual void destroy() _NOEXCEPT; - virtual void destroy_deallocate() _NOEXCEPT; - virtual _Rp operator()(_ArgTypes&&... __arg); -#ifndef _LIBCUDACXX_NO_RTTI - virtual const void* target(const type_info&) const _NOEXCEPT; - virtual const std::type_info& target_type() const _NOEXCEPT; -#endif // _LIBCUDACXX_NO_RTTI -}; - -template -__base<_Rp(_ArgTypes...)>* -__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::__clone() const -{ - typedef allocator_traits<_Alloc> __alloc_traits; - typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap; - _Ap __a(__f_.__get_allocator()); - typedef __allocator_destructor<_Ap> _Dp; - unique_ptr<__func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1)); - ::new ((void*)__hold.get()) __func(__f_.__target(), _Alloc(__a)); - return __hold.release(); -} - -template -void -__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::__clone(__base<_Rp(_ArgTypes...)>* __p) const -{ - ::new (__p) __func(__f_.__target(), __f_.__get_allocator()); -} - -template -void -__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy() _NOEXCEPT -{ - __f_.destroy(); -} - -template -void -__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy_deallocate() _NOEXCEPT -{ - typedef allocator_traits<_Alloc> __alloc_traits; - typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap; - _Ap __a(__f_.__get_allocator()); - __f_.destroy(); - __a.deallocate(this, 1); -} - -template -_Rp -__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::operator()(_ArgTypes&& ... __arg) -{ - return __f_(_CUDA_VSTD::forward<_ArgTypes>(__arg)...); -} - -#ifndef _LIBCUDACXX_NO_RTTI - -template -const void* -__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::target(const type_info& __ti) const _NOEXCEPT -{ - if (__ti == typeid(_Fp)) - return &__f_.__target(); - return (const void*)0; -} - -template -const std::type_info& -__func<_Fp, _Alloc, _Rp(_ArgTypes...)>::target_type() const _NOEXCEPT -{ - return typeid(_Fp); -} - -#endif // _LIBCUDACXX_NO_RTTI - -// __value_func creates a value-type from a __func. - -template class __value_func; - -template class __value_func<_Rp(_ArgTypes...)> -{ - typename aligned_storage<3 * sizeof(void*)>::type __buf_; - - typedef __base<_Rp(_ArgTypes...)> __func; - __func* __f_; - - _LIBCUDACXX_NO_CFI static __func* __as_base(void* p) - { - return reinterpret_cast<__func*>(p); - } - - public: - _LIBCUDACXX_INLINE_VISIBILITY - __value_func() _NOEXCEPT : __f_(0) {} - - template - _LIBCUDACXX_INLINE_VISIBILITY __value_func(_Fp&& __f, const _Alloc& __a) - : __f_(0) - { - typedef allocator_traits<_Alloc> __alloc_traits; - typedef __function::__func<_Fp, _Alloc, _Rp(_ArgTypes...)> _Fun; - typedef typename __rebind_alloc_helper<__alloc_traits, _Fun>::type - _FunAlloc; - - if (__function::__not_null(__f)) - { - _FunAlloc __af(__a); - if (sizeof(_Fun) <= sizeof(__buf_) && - is_nothrow_copy_constructible<_Fp>::value && - is_nothrow_copy_constructible<_FunAlloc>::value) - { - __f_ = - ::new ((void*)&__buf_) _Fun(_CUDA_VSTD::move(__f), _Alloc(__af)); - } - else - { - typedef __allocator_destructor<_FunAlloc> _Dp; - unique_ptr<__func, _Dp> __hold(__af.allocate(1), _Dp(__af, 1)); - ::new ((void*)__hold.get()) _Fun(_CUDA_VSTD::move(__f), _Alloc(__a)); - __f_ = __hold.release(); - } - } - } - - template , __value_func>::value>::type> - _LIBCUDACXX_INLINE_VISIBILITY explicit __value_func(_Fp&& __f) - : __value_func(std::forward<_Fp>(__f), allocator<_Fp>()) {} - - _LIBCUDACXX_INLINE_VISIBILITY - __value_func(const __value_func& __f) - { - if (__f.__f_ == 0) - __f_ = 0; - else if ((void*)__f.__f_ == &__f.__buf_) - { - __f_ = __as_base(&__buf_); - __f.__f_->__clone(__f_); - } - else - __f_ = __f.__f_->__clone(); - } - - _LIBCUDACXX_INLINE_VISIBILITY - __value_func(__value_func&& __f) _NOEXCEPT - { - if (__f.__f_ == 0) - __f_ = 0; - else if ((void*)__f.__f_ == &__f.__buf_) - { - __f_ = __as_base(&__buf_); - __f.__f_->__clone(__f_); - } - else - { - __f_ = __f.__f_; - __f.__f_ = 0; - } - } - - _LIBCUDACXX_INLINE_VISIBILITY - ~__value_func() - { - if ((void*)__f_ == &__buf_) - __f_->destroy(); - else if (__f_) - __f_->destroy_deallocate(); - } - - _LIBCUDACXX_INLINE_VISIBILITY - __value_func& operator=(__value_func&& __f) - { - *this = nullptr; - if (__f.__f_ == 0) - __f_ = 0; - else if ((void*)__f.__f_ == &__f.__buf_) - { - __f_ = __as_base(&__buf_); - __f.__f_->__clone(__f_); - } - else - { - __f_ = __f.__f_; - __f.__f_ = 0; - } - return *this; - } - - _LIBCUDACXX_INLINE_VISIBILITY - __value_func& operator=(nullptr_t) - { - __func* __f = __f_; - __f_ = 0; - if ((void*)__f == &__buf_) - __f->destroy(); - else if (__f) - __f->destroy_deallocate(); - return *this; - } - - _LIBCUDACXX_INLINE_VISIBILITY - _Rp operator()(_ArgTypes&&... __args) const - { - if (__f_ == 0) - __throw_bad_function_call(); - return (*__f_)(_CUDA_VSTD::forward<_ArgTypes>(__args)...); - } - - _LIBCUDACXX_INLINE_VISIBILITY - void swap(__value_func& __f) _NOEXCEPT - { - if (&__f == this) - return; - if ((void*)__f_ == &__buf_ && (void*)__f.__f_ == &__f.__buf_) - { - typename aligned_storage::type __tempbuf; - __func* __t = __as_base(&__tempbuf); - __f_->__clone(__t); - __f_->destroy(); - __f_ = 0; - __f.__f_->__clone(__as_base(&__buf_)); - __f.__f_->destroy(); - __f.__f_ = 0; - __f_ = __as_base(&__buf_); - __t->__clone(__as_base(&__f.__buf_)); - __t->destroy(); - __f.__f_ = __as_base(&__f.__buf_); - } - else if ((void*)__f_ == &__buf_) - { - __f_->__clone(__as_base(&__f.__buf_)); - __f_->destroy(); - __f_ = __f.__f_; - __f.__f_ = __as_base(&__f.__buf_); - } - else if ((void*)__f.__f_ == &__f.__buf_) - { - __f.__f_->__clone(__as_base(&__buf_)); - __f.__f_->destroy(); - __f.__f_ = __f_; - __f_ = __as_base(&__buf_); - } - else - _CUDA_VSTD::swap(__f_, __f.__f_); - } - - _LIBCUDACXX_INLINE_VISIBILITY - _LIBCUDACXX_EXPLICIT operator bool() const _NOEXCEPT { return __f_ != 0; } - -#ifndef _LIBCUDACXX_NO_RTTI - _LIBCUDACXX_INLINE_VISIBILITY - const std::type_info& target_type() const _NOEXCEPT - { - if (__f_ == 0) - return typeid(void); - return __f_->target_type(); - } - - template - _LIBCUDACXX_INLINE_VISIBILITY const _Tp* target() const _NOEXCEPT - { - if (__f_ == 0) - return 0; - return (const _Tp*)__f_->target(typeid(_Tp)); - } -#endif // _LIBCUDACXX_NO_RTTI -}; - -// Storage for a functor object, to be used with __policy to manage copy and -// destruction. -union __policy_storage -{ - mutable char __small[sizeof(void*) * 2]; - void* __large; -}; - -// True if _Fun can safely be held in __policy_storage.__small. -template -struct __use_small_storage - : public _CUDA_VSTD::integral_constant< - bool, sizeof(_Fun) <= sizeof(__policy_storage) && - _LIBCUDACXX_ALIGNOF(_Fun) <= _LIBCUDACXX_ALIGNOF(__policy_storage) && - _CUDA_VSTD::is_trivially_copy_constructible<_Fun>::value && - _CUDA_VSTD::is_trivially_destructible<_Fun>::value> {}; - -// Policy contains information about how to copy, destroy, and move the -// underlying functor. You can think of it as a vtable of sorts. -struct __policy -{ - // Used to copy or destroy __large values. null for trivial objects. - void* (*const __clone)(const void*); - void (*const __destroy)(void*); - - // True if this is the null policy (no value). - const bool __is_null; - - // The target type. May be null if RTTI is disabled. - const std::type_info* const __type_info; - - // Returns a pointer to a static policy object suitable for the functor - // type. - template - _LIBCUDACXX_INLINE_VISIBILITY static const __policy* __create() - { - return __choose_policy<_Fun>(__use_small_storage<_Fun>()); - } - - _LIBCUDACXX_INLINE_VISIBILITY - static const __policy* __create_empty() - { - static const _LIBCUDACXX_CONSTEXPR __policy __policy_ = {nullptr, nullptr, - true, -#ifndef _LIBCUDACXX_NO_RTTI - &typeid(void) -#else - nullptr -#endif - }; - return &__policy_; - } - - private: - template static void* __large_clone(const void* __s) - { - const _Fun* __f = static_cast(__s); - return __f->__clone(); - } - - template - static void __large_destroy(void* __s) { - _Fun::__destroy_and_delete(static_cast<_Fun*>(__s)); - } - - template - _LIBCUDACXX_INLINE_VISIBILITY static const __policy* - __choose_policy(/* is_small = */ false_type) { - static const _LIBCUDACXX_CONSTEXPR __policy __policy_ = { - &__large_clone<_Fun>, &__large_destroy<_Fun>, false, -#ifndef _LIBCUDACXX_NO_RTTI - &typeid(typename _Fun::_Target) -#else - nullptr -#endif - }; - return &__policy_; - } - - template - _LIBCUDACXX_INLINE_VISIBILITY static const __policy* - __choose_policy(/* is_small = */ true_type) - { - static const _LIBCUDACXX_CONSTEXPR __policy __policy_ = { - nullptr, nullptr, false, -#ifndef _LIBCUDACXX_NO_RTTI - &typeid(typename _Fun::_Target) -#else - nullptr -#endif - }; - return &__policy_; - } -}; - -// Used to choose between perfect forwarding or pass-by-value. Pass-by-value is -// faster for types that can be passed in registers. -template -using __fast_forward = - typename _CUDA_VSTD::conditional<_CUDA_VSTD::is_scalar<_Tp>::value, _Tp, _Tp&&>::type; - -// __policy_invoker calls an instance of __alloc_func held in __policy_storage. - -template struct __policy_invoker; - -template -struct __policy_invoker<_Rp(_ArgTypes...)> -{ - typedef _Rp (*__Call)(const __policy_storage*, - __fast_forward<_ArgTypes>...); - - __Call __call_; - - // Creates an invoker that throws bad_function_call. - _LIBCUDACXX_INLINE_VISIBILITY - __policy_invoker() : __call_(&__call_empty) {} - - // Creates an invoker that calls the given instance of __func. - template - _LIBCUDACXX_INLINE_VISIBILITY static __policy_invoker __create() - { - return __policy_invoker(&__call_impl<_Fun>); - } - - private: - _LIBCUDACXX_INLINE_VISIBILITY - explicit __policy_invoker(__Call __c) : __call_(__c) {} - - static _Rp __call_empty(const __policy_storage*, - __fast_forward<_ArgTypes>...) - { - __throw_bad_function_call(); - } - - template - static _Rp __call_impl(const __policy_storage* __buf, - __fast_forward<_ArgTypes>... __args) - { - _Fun* __f = reinterpret_cast<_Fun*>(__use_small_storage<_Fun>::value - ? &__buf->__small - : __buf->__large); - return (*__f)(_CUDA_VSTD::forward<_ArgTypes>(__args)...); - } -}; - -// __policy_func uses a __policy and __policy_invoker to create a type-erased, -// copyable functor. - -template class __policy_func; - -template class __policy_func<_Rp(_ArgTypes...)> -{ - // Inline storage for small objects. - __policy_storage __buf_; - - // Calls the value stored in __buf_. This could technically be part of - // policy, but storing it here eliminates a level of indirection inside - // operator(). - typedef __function::__policy_invoker<_Rp(_ArgTypes...)> __invoker; - __invoker __invoker_; - - // The policy that describes how to move / copy / destroy __buf_. Never - // null, even if the function is empty. - const __policy* __policy_; - - public: - _LIBCUDACXX_INLINE_VISIBILITY - __policy_func() : __policy_(__policy::__create_empty()) {} - - template - _LIBCUDACXX_INLINE_VISIBILITY __policy_func(_Fp&& __f, const _Alloc& __a) - : __policy_(__policy::__create_empty()) - { - typedef __alloc_func<_Fp, _Alloc, _Rp(_ArgTypes...)> _Fun; - typedef allocator_traits<_Alloc> __alloc_traits; - typedef typename __rebind_alloc_helper<__alloc_traits, _Fun>::type - _FunAlloc; - - if (__function::__not_null(__f)) - { - __invoker_ = __invoker::template __create<_Fun>(); - __policy_ = __policy::__create<_Fun>(); - - _FunAlloc __af(__a); - if (__use_small_storage<_Fun>()) - { - ::new ((void*)&__buf_.__small) - _Fun(_CUDA_VSTD::move(__f), _Alloc(__af)); - } - else - { - typedef __allocator_destructor<_FunAlloc> _Dp; - unique_ptr<_Fun, _Dp> __hold(__af.allocate(1), _Dp(__af, 1)); - ::new ((void*)__hold.get()) - _Fun(_CUDA_VSTD::move(__f), _Alloc(__af)); - __buf_.__large = __hold.release(); - } - } - } - - template , __policy_func>::value>::type> - _LIBCUDACXX_INLINE_VISIBILITY explicit __policy_func(_Fp&& __f) - : __policy_(__policy::__create_empty()) { - typedef __default_alloc_func<_Fp, _Rp(_ArgTypes...)> _Fun; - - if (__function::__not_null(__f)) { - __invoker_ = __invoker::template __create<_Fun>(); - __policy_ = __policy::__create<_Fun>(); - if (__use_small_storage<_Fun>()) { - ::new ((void*)&__buf_.__small) _Fun(_CUDA_VSTD::move(__f)); - } else { - __builtin_new_allocator::__holder_t __hold = - __builtin_new_allocator::__allocate_type<_Fun>(1); - __buf_.__large = ::new (__hold.get()) _Fun(_CUDA_VSTD::move(__f)); - (void)__hold.release(); - } - } - } - - _LIBCUDACXX_INLINE_VISIBILITY - __policy_func(const __policy_func& __f) - : __buf_(__f.__buf_), __invoker_(__f.__invoker_), - __policy_(__f.__policy_) - { - if (__policy_->__clone) - __buf_.__large = __policy_->__clone(__f.__buf_.__large); - } - - _LIBCUDACXX_INLINE_VISIBILITY - __policy_func(__policy_func&& __f) - : __buf_(__f.__buf_), __invoker_(__f.__invoker_), - __policy_(__f.__policy_) - { - if (__policy_->__destroy) - { - __f.__policy_ = __policy::__create_empty(); - __f.__invoker_ = __invoker(); - } - } - - _LIBCUDACXX_INLINE_VISIBILITY - ~__policy_func() - { - if (__policy_->__destroy) - __policy_->__destroy(__buf_.__large); - } - - _LIBCUDACXX_INLINE_VISIBILITY - __policy_func& operator=(__policy_func&& __f) - { - *this = nullptr; - __buf_ = __f.__buf_; - __invoker_ = __f.__invoker_; - __policy_ = __f.__policy_; - __f.__policy_ = __policy::__create_empty(); - __f.__invoker_ = __invoker(); - return *this; - } - - _LIBCUDACXX_INLINE_VISIBILITY - __policy_func& operator=(nullptr_t) - { - const __policy* __p = __policy_; - __policy_ = __policy::__create_empty(); - __invoker_ = __invoker(); - if (__p->__destroy) - __p->__destroy(__buf_.__large); - return *this; - } - - _LIBCUDACXX_INLINE_VISIBILITY - _Rp operator()(_ArgTypes&&... __args) const - { - return __invoker_.__call_(_CUDA_VSTD::addressof(__buf_), - _CUDA_VSTD::forward<_ArgTypes>(__args)...); - } - - _LIBCUDACXX_INLINE_VISIBILITY - void swap(__policy_func& __f) - { - _CUDA_VSTD::swap(__invoker_, __f.__invoker_); - _CUDA_VSTD::swap(__policy_, __f.__policy_); - _CUDA_VSTD::swap(__buf_, __f.__buf_); - } - - _LIBCUDACXX_INLINE_VISIBILITY - explicit operator bool() const _NOEXCEPT - { - return !__policy_->__is_null; - } - -#ifndef _LIBCUDACXX_NO_RTTI - _LIBCUDACXX_INLINE_VISIBILITY - const std::type_info& target_type() const _NOEXCEPT - { - return *__policy_->__type_info; - } - - template - _LIBCUDACXX_INLINE_VISIBILITY const _Tp* target() const _NOEXCEPT - { - if (__policy_->__is_null || typeid(_Tp) != *__policy_->__type_info) - return nullptr; - if (__policy_->__clone) // Out of line storage. - return reinterpret_cast(__buf_.__large); - else - return reinterpret_cast(&__buf_.__small); - } -#endif // _LIBCUDACXX_NO_RTTI -}; - -} // __function - -template -class _LIBCUDACXX_TEMPLATE_VIS function<_Rp(_ArgTypes...)> - : public __function::__maybe_derive_from_unary_function<_Rp(_ArgTypes...)>, - public __function::__maybe_derive_from_binary_function<_Rp(_ArgTypes...)> -{ -#ifndef _LIBCUDACXX_ABI_OPTIMIZED_FUNCTION - typedef __function::__value_func<_Rp(_ArgTypes...)> __func; -#else - typedef __function::__policy_func<_Rp(_ArgTypes...)> __func; -#endif - - __func __f_; - - template , function>, - __invokable<_Fp&, _ArgTypes...> - >::value> - struct __callable; - template - struct __callable<_Fp, true> - { - static const bool value = is_same::value || - is_convertible::type, - _Rp>::value; - }; - template - struct __callable<_Fp, false> - { - static const bool value = false; - }; - - template - using _EnableIfCallable = typename enable_if<__callable<_Fp>::value>::type; -public: - typedef _Rp result_type; - - // construct/copy/destroy: - _LIBCUDACXX_INLINE_VISIBILITY - function() _NOEXCEPT { } - _LIBCUDACXX_INLINE_VISIBILITY - function(nullptr_t) _NOEXCEPT {} - function(const function&); - function(function&&) _NOEXCEPT; - template> - function(_Fp); - -#if _LIBCUDACXX_STD_VER <= 14 - template - _LIBCUDACXX_INLINE_VISIBILITY - function(allocator_arg_t, const _Alloc&) _NOEXCEPT {} - template - _LIBCUDACXX_INLINE_VISIBILITY - function(allocator_arg_t, const _Alloc&, nullptr_t) _NOEXCEPT {} - template - function(allocator_arg_t, const _Alloc&, const function&); - template - function(allocator_arg_t, const _Alloc&, function&&); - template> - function(allocator_arg_t, const _Alloc& __a, _Fp __f); -#endif - - function& operator=(const function&); - function& operator=(function&&) _NOEXCEPT; - function& operator=(nullptr_t) _NOEXCEPT; - template> - function& operator=(_Fp&&); - - ~function(); - - // function modifiers: - void swap(function&) _NOEXCEPT; - -#if _LIBCUDACXX_STD_VER <= 14 - template - _LIBCUDACXX_INLINE_VISIBILITY - void assign(_Fp&& __f, const _Alloc& __a) - {function(allocator_arg, __a, _CUDA_VSTD::forward<_Fp>(__f)).swap(*this);} -#endif - - // function capacity: - _LIBCUDACXX_INLINE_VISIBILITY - _LIBCUDACXX_EXPLICIT operator bool() const _NOEXCEPT { - return static_cast(__f_); - } - - // deleted overloads close possible hole in the type system - template - bool operator==(const function<_R2(_ArgTypes2...)>&) const = delete; - template - bool operator!=(const function<_R2(_ArgTypes2...)>&) const = delete; -public: - // function invocation: - _Rp operator()(_ArgTypes...) const; - -#ifndef _LIBCUDACXX_NO_RTTI - // function target access: - const std::type_info& target_type() const _NOEXCEPT; - template _Tp* target() _NOEXCEPT; - template const _Tp* target() const _NOEXCEPT; -#endif // _LIBCUDACXX_NO_RTTI -}; - -#ifndef _LIBCUDACXX_HAS_NO_DEDUCTION_GUIDES -template -function(_Rp(*)(_Ap...)) -> function<_Rp(_Ap...)>; - -template -struct __strip_signature; - -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...)> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile> { using type = _Rp(_Ap...); }; - -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) &> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const &> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile &> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile &> { using type = _Rp(_Ap...); }; - -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) noexcept> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const noexcept> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile noexcept> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile noexcept> { using type = _Rp(_Ap...); }; - -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) & noexcept> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const & noexcept> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) volatile & noexcept> { using type = _Rp(_Ap...); }; -template -struct __strip_signature<_Rp (_Gp::*) (_Ap...) const volatile & noexcept> { using type = _Rp(_Ap...); }; - -template::type> -function(_Fp) -> function<_Stripped>; -#endif // !_LIBCUDACXX_HAS_NO_DEDUCTION_GUIDES - -template -function<_Rp(_ArgTypes...)>::function(const function& __f) : __f_(__f.__f_) {} - -#if _LIBCUDACXX_STD_VER <= 14 -template -template -function<_Rp(_ArgTypes...)>::function(allocator_arg_t, const _Alloc&, - const function& __f) : __f_(__f.__f_) {} -#endif - -template -function<_Rp(_ArgTypes...)>::function(function&& __f) _NOEXCEPT - : __f_(_CUDA_VSTD::move(__f.__f_)) {} - -#if _LIBCUDACXX_STD_VER <= 14 -template -template -function<_Rp(_ArgTypes...)>::function(allocator_arg_t, const _Alloc&, - function&& __f) - : __f_(_CUDA_VSTD::move(__f.__f_)) {} -#endif - -template -template -function<_Rp(_ArgTypes...)>::function(_Fp __f) : __f_(_CUDA_VSTD::move(__f)) {} - -#if _LIBCUDACXX_STD_VER <= 14 -template -template -function<_Rp(_ArgTypes...)>::function(allocator_arg_t, const _Alloc& __a, - _Fp __f) - : __f_(_CUDA_VSTD::move(__f), __a) {} -#endif - -template -function<_Rp(_ArgTypes...)>& -function<_Rp(_ArgTypes...)>::operator=(const function& __f) -{ - function(__f).swap(*this); - return *this; -} - -template -function<_Rp(_ArgTypes...)>& -function<_Rp(_ArgTypes...)>::operator=(function&& __f) _NOEXCEPT -{ - __f_ = std::move(__f.__f_); - return *this; -} - -template -function<_Rp(_ArgTypes...)>& -function<_Rp(_ArgTypes...)>::operator=(nullptr_t) _NOEXCEPT -{ - __f_ = nullptr; - return *this; -} - -template -template -function<_Rp(_ArgTypes...)>& -function<_Rp(_ArgTypes...)>::operator=(_Fp&& __f) -{ - function(_CUDA_VSTD::forward<_Fp>(__f)).swap(*this); - return *this; -} - -template -function<_Rp(_ArgTypes...)>::~function() {} - -template -void -function<_Rp(_ArgTypes...)>::swap(function& __f) _NOEXCEPT -{ - __f_.swap(__f.__f_); -} - -template -_Rp -function<_Rp(_ArgTypes...)>::operator()(_ArgTypes... __arg) const -{ - return __f_(_CUDA_VSTD::forward<_ArgTypes>(__arg)...); -} - -#ifndef _LIBCUDACXX_NO_RTTI - -template -const std::type_info& -function<_Rp(_ArgTypes...)>::target_type() const _NOEXCEPT -{ - return __f_.target_type(); -} - -template -template -_Tp* -function<_Rp(_ArgTypes...)>::target() _NOEXCEPT -{ - return (_Tp*)(__f_.template target<_Tp>()); -} - -template -template -const _Tp* -function<_Rp(_ArgTypes...)>::target() const _NOEXCEPT -{ - return __f_.template target<_Tp>(); -} - -#endif // _LIBCUDACXX_NO_RTTI - -template -inline _LIBCUDACXX_INLINE_VISIBILITY -bool -operator==(const function<_Rp(_ArgTypes...)>& __f, nullptr_t) _NOEXCEPT {return !__f;} - -template -inline _LIBCUDACXX_INLINE_VISIBILITY -bool -operator==(nullptr_t, const function<_Rp(_ArgTypes...)>& __f) _NOEXCEPT {return !__f;} - -template -inline _LIBCUDACXX_INLINE_VISIBILITY -bool -operator!=(const function<_Rp(_ArgTypes...)>& __f, nullptr_t) _NOEXCEPT {return (bool)__f;} - -template -inline _LIBCUDACXX_INLINE_VISIBILITY -bool -operator!=(nullptr_t, const function<_Rp(_ArgTypes...)>& __f) _NOEXCEPT {return (bool)__f;} - -template -inline _LIBCUDACXX_INLINE_VISIBILITY -void -swap(function<_Rp(_ArgTypes...)>& __x, function<_Rp(_ArgTypes...)>& __y) _NOEXCEPT -{return __x.swap(__y);} - -#else // _LIBCUDACXX_CXX03_LANG - -#include <__functional_03> - -#endif - -#endif // __cuda_std__ - -_LIBCUDACXX_END_NAMESPACE_STD - -#ifndef __cuda_std__ -#include <__pragma_pop> -#endif //__cuda_std__ - #endif // _LIBCUDACXX_FUNCTIONAL