diff options
Diffstat (limited to 'libcxx/include/__functional_base')
| -rw-r--r-- | libcxx/include/__functional_base | 652 | 
1 files changed, 652 insertions, 0 deletions
diff --git a/libcxx/include/__functional_base b/libcxx/include/__functional_base new file mode 100644 index 0000000000000..ca761c409b627 --- /dev/null +++ b/libcxx/include/__functional_base @@ -0,0 +1,652 @@ +// -*- 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 +// +//===----------------------------------------------------------------------===// + +#ifndef _LIBCPP_FUNCTIONAL_BASE +#define _LIBCPP_FUNCTIONAL_BASE + +#include <__config> +#include <type_traits> +#include <typeinfo> +#include <exception> +#include <new> +#include <utility> + +#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) +#pragma GCC system_header +#endif + +_LIBCPP_BEGIN_NAMESPACE_STD + +template <class _Arg1, class _Arg2, class _Result> +struct _LIBCPP_TEMPLATE_VIS binary_function +{ +    typedef _Arg1   first_argument_type; +    typedef _Arg2   second_argument_type; +    typedef _Result result_type; +}; + +template <class _Tp> +struct __has_result_type +{ +private: +    struct __two {char __lx; char __lxx;}; +    template <class _Up> static __two __test(...); +    template <class _Up> static char __test(typename _Up::result_type* = 0); +public: +    static const bool value = sizeof(__test<_Tp>(0)) == 1; +}; + +#if _LIBCPP_STD_VER > 11 +template <class _Tp = void> +#else +template <class _Tp> +#endif +struct _LIBCPP_TEMPLATE_VIS less : binary_function<_Tp, _Tp, bool> +{ +    _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY +    bool operator()(const _Tp& __x, const _Tp& __y) const +        {return __x < __y;} +}; + +#if _LIBCPP_STD_VER > 11 +template <> +struct _LIBCPP_TEMPLATE_VIS less<void> +{ +    template <class _T1, class _T2> +    _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY +    auto operator()(_T1&& __t, _T2&& __u) const +    _NOEXCEPT_(noexcept(_VSTD::forward<_T1>(__t) < _VSTD::forward<_T2>(__u))) +    -> decltype        (_VSTD::forward<_T1>(__t) < _VSTD::forward<_T2>(__u)) +        { return        _VSTD::forward<_T1>(__t) < _VSTD::forward<_T2>(__u); } +    typedef void is_transparent; +}; +#endif + +// __weak_result_type + +template <class _Tp> +struct __derives_from_unary_function +{ +private: +    struct __two {char __lx; char __lxx;}; +    static __two __test(...); +    template <class _Ap, class _Rp> +        static unary_function<_Ap, _Rp> +        __test(const volatile unary_function<_Ap, _Rp>*); +public: +    static const bool value = !is_same<decltype(__test((_Tp*)0)), __two>::value; +    typedef decltype(__test((_Tp*)0)) type; +}; + +template <class _Tp> +struct __derives_from_binary_function +{ +private: +    struct __two {char __lx; char __lxx;}; +    static __two __test(...); +    template <class _A1, class _A2, class _Rp> +        static binary_function<_A1, _A2, _Rp> +        __test(const volatile binary_function<_A1, _A2, _Rp>*); +public: +    static const bool value = !is_same<decltype(__test((_Tp*)0)), __two>::value; +    typedef decltype(__test((_Tp*)0)) type; +}; + +template <class _Tp, bool = __derives_from_unary_function<_Tp>::value> +struct __maybe_derive_from_unary_function  // bool is true +    : public __derives_from_unary_function<_Tp>::type +{ +}; + +template <class _Tp> +struct __maybe_derive_from_unary_function<_Tp, false> +{ +}; + +template <class _Tp, bool = __derives_from_binary_function<_Tp>::value> +struct __maybe_derive_from_binary_function  // bool is true +    : public __derives_from_binary_function<_Tp>::type +{ +}; + +template <class _Tp> +struct __maybe_derive_from_binary_function<_Tp, false> +{ +}; + +template <class _Tp, bool = __has_result_type<_Tp>::value> +struct __weak_result_type_imp // bool is true +    : public __maybe_derive_from_unary_function<_Tp>, +      public __maybe_derive_from_binary_function<_Tp> +{ +    typedef _LIBCPP_NODEBUG_TYPE typename _Tp::result_type result_type; +}; + +template <class _Tp> +struct __weak_result_type_imp<_Tp, false> +    : public __maybe_derive_from_unary_function<_Tp>, +      public __maybe_derive_from_binary_function<_Tp> +{ +}; + +template <class _Tp> +struct __weak_result_type +    : public __weak_result_type_imp<_Tp> +{ +}; + +// 0 argument case + +template <class _Rp> +struct __weak_result_type<_Rp ()> +{ +    typedef _LIBCPP_NODEBUG_TYPE  _Rp result_type; +}; + +template <class _Rp> +struct __weak_result_type<_Rp (&)()> +{ +    typedef _LIBCPP_NODEBUG_TYPE  _Rp result_type; +}; + +template <class _Rp> +struct __weak_result_type<_Rp (*)()> +{ +    typedef _LIBCPP_NODEBUG_TYPE  _Rp result_type; +}; + +// 1 argument case + +template <class _Rp, class _A1> +struct __weak_result_type<_Rp (_A1)> +    : public unary_function<_A1, _Rp> +{ +}; + +template <class _Rp, class _A1> +struct __weak_result_type<_Rp (&)(_A1)> +    : public unary_function<_A1, _Rp> +{ +}; + +template <class _Rp, class _A1> +struct __weak_result_type<_Rp (*)(_A1)> +    : public unary_function<_A1, _Rp> +{ +}; + +template <class _Rp, class _Cp> +struct __weak_result_type<_Rp (_Cp::*)()> +    : public unary_function<_Cp*, _Rp> +{ +}; + +template <class _Rp, class _Cp> +struct __weak_result_type<_Rp (_Cp::*)() const> +    : public unary_function<const _Cp*, _Rp> +{ +}; + +template <class _Rp, class _Cp> +struct __weak_result_type<_Rp (_Cp::*)() volatile> +    : public unary_function<volatile _Cp*, _Rp> +{ +}; + +template <class _Rp, class _Cp> +struct __weak_result_type<_Rp (_Cp::*)() const volatile> +    : public unary_function<const volatile _Cp*, _Rp> +{ +}; + +// 2 argument case + +template <class _Rp, class _A1, class _A2> +struct __weak_result_type<_Rp (_A1, _A2)> +    : public binary_function<_A1, _A2, _Rp> +{ +}; + +template <class _Rp, class _A1, class _A2> +struct __weak_result_type<_Rp (*)(_A1, _A2)> +    : public binary_function<_A1, _A2, _Rp> +{ +}; + +template <class _Rp, class _A1, class _A2> +struct __weak_result_type<_Rp (&)(_A1, _A2)> +    : public binary_function<_A1, _A2, _Rp> +{ +}; + +template <class _Rp, class _Cp, class _A1> +struct __weak_result_type<_Rp (_Cp::*)(_A1)> +    : public binary_function<_Cp*, _A1, _Rp> +{ +}; + +template <class _Rp, class _Cp, class _A1> +struct __weak_result_type<_Rp (_Cp::*)(_A1) const> +    : public binary_function<const _Cp*, _A1, _Rp> +{ +}; + +template <class _Rp, class _Cp, class _A1> +struct __weak_result_type<_Rp (_Cp::*)(_A1) volatile> +    : public binary_function<volatile _Cp*, _A1, _Rp> +{ +}; + +template <class _Rp, class _Cp, class _A1> +struct __weak_result_type<_Rp (_Cp::*)(_A1) const volatile> +    : public binary_function<const volatile _Cp*, _A1, _Rp> +{ +}; + + +#ifndef _LIBCPP_CXX03_LANG +// 3 or more arguments + +template <class _Rp, class _A1, class _A2, class _A3, class ..._A4> +struct __weak_result_type<_Rp (_A1, _A2, _A3, _A4...)> +{ +    typedef _Rp result_type; +}; + +template <class _Rp, class _A1, class _A2, class _A3, class ..._A4> +struct __weak_result_type<_Rp (&)(_A1, _A2, _A3, _A4...)> +{ +    typedef _Rp result_type; +}; + +template <class _Rp, class _A1, class _A2, class _A3, class ..._A4> +struct __weak_result_type<_Rp (*)(_A1, _A2, _A3, _A4...)> +{ +    typedef _Rp result_type; +}; + +template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> +struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...)> +{ +    typedef _Rp result_type; +}; + +template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> +struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...) const> +{ +    typedef _Rp result_type; +}; + +template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> +struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...) volatile> +{ +    typedef _Rp result_type; +}; + +template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> +struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...) const volatile> +{ +    typedef _Rp result_type; +}; + +template <class _Tp, class ..._Args> +struct __invoke_return +{ +    typedef decltype(__invoke(_VSTD::declval<_Tp>(), _VSTD::declval<_Args>()...)) type; +}; + +#else // defined(_LIBCPP_CXX03_LANG) + +#include <__functional_base_03> + +#endif  // !defined(_LIBCPP_CXX03_LANG) + + +template <class _Ret> +struct __invoke_void_return_wrapper +{ +#ifndef _LIBCPP_CXX03_LANG +    template <class ..._Args> +    static _Ret __call(_Args&&... __args) { +        return __invoke(_VSTD::forward<_Args>(__args)...); +    } +#else +    template <class _Fn> +    static _Ret __call(_Fn __f) { +        return __invoke(__f); +    } + +    template <class _Fn, class _A0> +    static _Ret __call(_Fn __f, _A0& __a0) { +        return __invoke(__f, __a0); +    } + +    template <class _Fn, class _A0, class _A1> +    static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1) { +        return __invoke(__f, __a0, __a1); +    } + +    template <class _Fn, class _A0, class _A1, class _A2> +    static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2){ +        return __invoke(__f, __a0, __a1, __a2); +    } +#endif +}; + +template <> +struct __invoke_void_return_wrapper<void> +{ +#ifndef _LIBCPP_CXX03_LANG +    template <class ..._Args> +    static void __call(_Args&&... __args) { +        __invoke(_VSTD::forward<_Args>(__args)...); +    } +#else +    template <class _Fn> +    static void __call(_Fn __f) { +        __invoke(__f); +    } + +    template <class _Fn, class _A0> +    static void __call(_Fn __f, _A0& __a0) { +        __invoke(__f, __a0); +    } + +    template <class _Fn, class _A0, class _A1> +    static void __call(_Fn __f, _A0& __a0, _A1& __a1) { +        __invoke(__f, __a0, __a1); +    } + +    template <class _Fn, class _A0, class _A1, class _A2> +    static void __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2) { +        __invoke(__f, __a0, __a1, __a2); +    } +#endif +}; + +template <class _Tp> +class _LIBCPP_TEMPLATE_VIS reference_wrapper +    : public __weak_result_type<_Tp> +{ +public: +    // types +    typedef _Tp type; +private: +    type* __f_; + +public: +    // construct/copy/destroy +    _LIBCPP_INLINE_VISIBILITY reference_wrapper(type& __f) _NOEXCEPT +        : __f_(_VSTD::addressof(__f)) {} +#ifndef _LIBCPP_CXX03_LANG +    private: reference_wrapper(type&&); public: // = delete; // do not bind to temps +#endif + +    // access +    _LIBCPP_INLINE_VISIBILITY operator type&    () const _NOEXCEPT {return *__f_;} +    _LIBCPP_INLINE_VISIBILITY          type& get() const _NOEXCEPT {return *__f_;} + +#ifndef _LIBCPP_CXX03_LANG +    // invoke +    template <class... _ArgTypes> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_of<type&, _ArgTypes...>::type +    operator() (_ArgTypes&&... __args) const { +        return __invoke(get(), _VSTD::forward<_ArgTypes>(__args)...); +    } +#else + +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return<type>::type +    operator() () const { +        return __invoke(get()); +    } + +    template <class _A0> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return0<type, _A0>::type +    operator() (_A0& __a0) const { +        return __invoke(get(), __a0); +    } + +    template <class _A0> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return0<type, _A0 const>::type +    operator() (_A0 const& __a0) const { +        return __invoke(get(), __a0); +    } + +    template <class _A0, class _A1> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return1<type, _A0, _A1>::type +    operator() (_A0& __a0, _A1& __a1) const { +        return __invoke(get(), __a0, __a1); +    } + +    template <class _A0, class _A1> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return1<type, _A0 const, _A1>::type +    operator() (_A0 const& __a0, _A1& __a1) const { +        return __invoke(get(), __a0, __a1); +    } + +    template <class _A0, class _A1> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return1<type, _A0, _A1 const>::type +    operator() (_A0& __a0, _A1 const& __a1) const { +        return __invoke(get(), __a0, __a1); +    } + +    template <class _A0, class _A1> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return1<type, _A0 const, _A1 const>::type +    operator() (_A0 const& __a0, _A1 const& __a1) const { +        return __invoke(get(), __a0, __a1); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0, _A1, _A2>::type +    operator() (_A0& __a0, _A1& __a1, _A2& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0 const, _A1, _A2>::type +    operator() (_A0 const& __a0, _A1& __a1, _A2& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0, _A1 const, _A2>::type +    operator() (_A0& __a0, _A1 const& __a1, _A2& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0, _A1, _A2 const>::type +    operator() (_A0& __a0, _A1& __a1, _A2 const& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0 const, _A1 const, _A2>::type +    operator() (_A0 const& __a0, _A1 const& __a1, _A2& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0 const, _A1, _A2 const>::type +    operator() (_A0 const& __a0, _A1& __a1, _A2 const& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0, _A1 const, _A2 const>::type +    operator() (_A0& __a0, _A1 const& __a1, _A2 const& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } + +    template <class _A0, class _A1, class _A2> +    _LIBCPP_INLINE_VISIBILITY +    typename __invoke_return2<type, _A0 const, _A1 const, _A2 const>::type +    operator() (_A0 const& __a0, _A1 const& __a1, _A2 const& __a2) const { +        return __invoke(get(), __a0, __a1, __a2); +    } +#endif // _LIBCPP_CXX03_LANG +}; + + +template <class _Tp> +inline _LIBCPP_INLINE_VISIBILITY +reference_wrapper<_Tp> +ref(_Tp& __t) _NOEXCEPT +{ +    return reference_wrapper<_Tp>(__t); +} + +template <class _Tp> +inline _LIBCPP_INLINE_VISIBILITY +reference_wrapper<_Tp> +ref(reference_wrapper<_Tp> __t) _NOEXCEPT +{ +    return ref(__t.get()); +} + +template <class _Tp> +inline _LIBCPP_INLINE_VISIBILITY +reference_wrapper<const _Tp> +cref(const _Tp& __t) _NOEXCEPT +{ +    return reference_wrapper<const _Tp>(__t); +} + +template <class _Tp> +inline _LIBCPP_INLINE_VISIBILITY +reference_wrapper<const _Tp> +cref(reference_wrapper<_Tp> __t) _NOEXCEPT +{ +    return cref(__t.get()); +} + +#ifndef _LIBCPP_CXX03_LANG +template <class _Tp> void ref(const _Tp&&) = delete; +template <class _Tp> void cref(const _Tp&&) = delete; +#endif + +#if _LIBCPP_STD_VER > 11 +template <class _Tp, class, class = void> +struct __is_transparent : false_type {}; + +template <class _Tp, class _Up> +struct __is_transparent<_Tp, _Up, +                        typename __void_t<typename _Tp::is_transparent>::type> +   : true_type {}; +#endif + +// allocator_arg_t + +struct _LIBCPP_TEMPLATE_VIS allocator_arg_t { explicit allocator_arg_t() = default; }; + +#if defined(_LIBCPP_CXX03_LANG) || defined(_LIBCPP_BUILDING_LIBRARY) +extern _LIBCPP_EXPORTED_FROM_ABI const allocator_arg_t allocator_arg; +#else +/* _LIBCPP_INLINE_VAR */ constexpr allocator_arg_t allocator_arg = allocator_arg_t(); +#endif + +// uses_allocator + +template <class _Tp> +struct __has_allocator_type +{ +private: +    struct __two {char __lx; char __lxx;}; +    template <class _Up> static __two __test(...); +    template <class _Up> static char __test(typename _Up::allocator_type* = 0); +public: +    static const bool value = sizeof(__test<_Tp>(0)) == 1; +}; + +template <class _Tp, class _Alloc, bool = __has_allocator_type<_Tp>::value> +struct __uses_allocator +    : public integral_constant<bool, +        is_convertible<_Alloc, typename _Tp::allocator_type>::value> +{ +}; + +template <class _Tp, class _Alloc> +struct __uses_allocator<_Tp, _Alloc, false> +    : public false_type +{ +}; + +template <class _Tp, class _Alloc> +struct _LIBCPP_TEMPLATE_VIS uses_allocator +    : public __uses_allocator<_Tp, _Alloc> +{ +}; + +#if _LIBCPP_STD_VER > 14 +template <class _Tp, class _Alloc> +_LIBCPP_INLINE_VAR constexpr size_t uses_allocator_v = uses_allocator<_Tp, _Alloc>::value; +#endif + +#ifndef _LIBCPP_CXX03_LANG + +// allocator construction + +template <class _Tp, class _Alloc, class ..._Args> +struct __uses_alloc_ctor_imp +{ +    typedef _LIBCPP_NODEBUG_TYPE typename __uncvref<_Alloc>::type _RawAlloc; +    static const bool __ua = uses_allocator<_Tp, _RawAlloc>::value; +    static const bool __ic = +        is_constructible<_Tp, allocator_arg_t, _Alloc, _Args...>::value; +    static const int value = __ua ? 2 - __ic : 0; +}; + +template <class _Tp, class _Alloc, class ..._Args> +struct __uses_alloc_ctor +    : integral_constant<int, __uses_alloc_ctor_imp<_Tp, _Alloc, _Args...>::value> +    {}; + +template <class _Tp, class _Allocator, class... _Args> +inline _LIBCPP_INLINE_VISIBILITY +void __user_alloc_construct_impl (integral_constant<int, 0>, _Tp *__storage, const _Allocator &, _Args &&... __args ) +{ +    new (__storage) _Tp (_VSTD::forward<_Args>(__args)...); +} + +// FIXME: This should have a version which takes a non-const alloc. +template <class _Tp, class _Allocator, class... _Args> +inline _LIBCPP_INLINE_VISIBILITY +void __user_alloc_construct_impl (integral_constant<int, 1>, _Tp *__storage, const _Allocator &__a, _Args &&... __args ) +{ +    new (__storage) _Tp (allocator_arg, __a, _VSTD::forward<_Args>(__args)...); +} + +// FIXME: This should have a version which takes a non-const alloc. +template <class _Tp, class _Allocator, class... _Args> +inline _LIBCPP_INLINE_VISIBILITY +void __user_alloc_construct_impl (integral_constant<int, 2>, _Tp *__storage, const _Allocator &__a, _Args &&... __args ) +{ +    new (__storage) _Tp (_VSTD::forward<_Args>(__args)..., __a); +} + +#endif  // _LIBCPP_CXX03_LANG + +_LIBCPP_END_NAMESPACE_STD + +#endif  // _LIBCPP_FUNCTIONAL_BASE  | 
