1// -*- C++ -*- 2//===----------------------------------------------------------------------===// 3// 4// The LLVM Compiler Infrastructure 5// 6// This file is dual licensed under the MIT and the University of Illinois Open 7// Source Licenses. See LICENSE.TXT for details. 8// 9//===----------------------------------------------------------------------===// 10 11#ifndef _LIBCPP_FUNCTIONAL_BASE 12#define _LIBCPP_FUNCTIONAL_BASE 13 14#include <__config> 15#include <type_traits> 16#include <typeinfo> 17#include <exception> 18#include <new> 19#include <utility> 20 21#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 22#pragma GCC system_header 23#endif 24 25_LIBCPP_BEGIN_NAMESPACE_STD 26 27template <class _Arg1, class _Arg2, class _Result> 28struct _LIBCPP_TEMPLATE_VIS binary_function 29{ 30 typedef _Arg1 first_argument_type; 31 typedef _Arg2 second_argument_type; 32 typedef _Result result_type; 33}; 34 35template <class _Tp> 36struct __has_result_type 37{ 38private: 39 struct __two {char __lx; char __lxx;}; 40 template <class _Up> static __two __test(...); 41 template <class _Up> static char __test(typename _Up::result_type* = 0); 42public: 43 static const bool value = sizeof(__test<_Tp>(0)) == 1; 44}; 45 46#if _LIBCPP_STD_VER > 11 47template <class _Tp = void> 48#else 49template <class _Tp> 50#endif 51struct _LIBCPP_TEMPLATE_VIS less : binary_function<_Tp, _Tp, bool> 52{ 53 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 54 bool operator()(const _Tp& __x, const _Tp& __y) const 55 {return __x < __y;} 56}; 57 58#if _LIBCPP_STD_VER > 11 59template <> 60struct _LIBCPP_TEMPLATE_VIS less<void> 61{ 62 template <class _T1, class _T2> 63 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 64 auto operator()(_T1&& __t, _T2&& __u) const 65 _NOEXCEPT_(noexcept(_VSTD::forward<_T1>(__t) < _VSTD::forward<_T2>(__u))) 66 -> decltype (_VSTD::forward<_T1>(__t) < _VSTD::forward<_T2>(__u)) 67 { return _VSTD::forward<_T1>(__t) < _VSTD::forward<_T2>(__u); } 68 typedef void is_transparent; 69}; 70#endif 71 72// __weak_result_type 73 74template <class _Tp> 75struct __derives_from_unary_function 76{ 77private: 78 struct __two {char __lx; char __lxx;}; 79 static __two __test(...); 80 template <class _Ap, class _Rp> 81 static unary_function<_Ap, _Rp> 82 __test(const volatile unary_function<_Ap, _Rp>*); 83public: 84 static const bool value = !is_same<decltype(__test((_Tp*)0)), __two>::value; 85 typedef decltype(__test((_Tp*)0)) type; 86}; 87 88template <class _Tp> 89struct __derives_from_binary_function 90{ 91private: 92 struct __two {char __lx; char __lxx;}; 93 static __two __test(...); 94 template <class _A1, class _A2, class _Rp> 95 static binary_function<_A1, _A2, _Rp> 96 __test(const volatile binary_function<_A1, _A2, _Rp>*); 97public: 98 static const bool value = !is_same<decltype(__test((_Tp*)0)), __two>::value; 99 typedef decltype(__test((_Tp*)0)) type; 100}; 101 102template <class _Tp, bool = __derives_from_unary_function<_Tp>::value> 103struct __maybe_derive_from_unary_function // bool is true 104 : public __derives_from_unary_function<_Tp>::type 105{ 106}; 107 108template <class _Tp> 109struct __maybe_derive_from_unary_function<_Tp, false> 110{ 111}; 112 113template <class _Tp, bool = __derives_from_binary_function<_Tp>::value> 114struct __maybe_derive_from_binary_function // bool is true 115 : public __derives_from_binary_function<_Tp>::type 116{ 117}; 118 119template <class _Tp> 120struct __maybe_derive_from_binary_function<_Tp, false> 121{ 122}; 123 124template <class _Tp, bool = __has_result_type<_Tp>::value> 125struct __weak_result_type_imp // bool is true 126 : public __maybe_derive_from_unary_function<_Tp>, 127 public __maybe_derive_from_binary_function<_Tp> 128{ 129 typedef typename _Tp::result_type result_type; 130}; 131 132template <class _Tp> 133struct __weak_result_type_imp<_Tp, false> 134 : public __maybe_derive_from_unary_function<_Tp>, 135 public __maybe_derive_from_binary_function<_Tp> 136{ 137}; 138 139template <class _Tp> 140struct __weak_result_type 141 : public __weak_result_type_imp<_Tp> 142{ 143}; 144 145// 0 argument case 146 147template <class _Rp> 148struct __weak_result_type<_Rp ()> 149{ 150 typedef _Rp result_type; 151}; 152 153template <class _Rp> 154struct __weak_result_type<_Rp (&)()> 155{ 156 typedef _Rp result_type; 157}; 158 159template <class _Rp> 160struct __weak_result_type<_Rp (*)()> 161{ 162 typedef _Rp result_type; 163}; 164 165// 1 argument case 166 167template <class _Rp, class _A1> 168struct __weak_result_type<_Rp (_A1)> 169 : public unary_function<_A1, _Rp> 170{ 171}; 172 173template <class _Rp, class _A1> 174struct __weak_result_type<_Rp (&)(_A1)> 175 : public unary_function<_A1, _Rp> 176{ 177}; 178 179template <class _Rp, class _A1> 180struct __weak_result_type<_Rp (*)(_A1)> 181 : public unary_function<_A1, _Rp> 182{ 183}; 184 185template <class _Rp, class _Cp> 186struct __weak_result_type<_Rp (_Cp::*)()> 187 : public unary_function<_Cp*, _Rp> 188{ 189}; 190 191template <class _Rp, class _Cp> 192struct __weak_result_type<_Rp (_Cp::*)() const> 193 : public unary_function<const _Cp*, _Rp> 194{ 195}; 196 197template <class _Rp, class _Cp> 198struct __weak_result_type<_Rp (_Cp::*)() volatile> 199 : public unary_function<volatile _Cp*, _Rp> 200{ 201}; 202 203template <class _Rp, class _Cp> 204struct __weak_result_type<_Rp (_Cp::*)() const volatile> 205 : public unary_function<const volatile _Cp*, _Rp> 206{ 207}; 208 209// 2 argument case 210 211template <class _Rp, class _A1, class _A2> 212struct __weak_result_type<_Rp (_A1, _A2)> 213 : public binary_function<_A1, _A2, _Rp> 214{ 215}; 216 217template <class _Rp, class _A1, class _A2> 218struct __weak_result_type<_Rp (*)(_A1, _A2)> 219 : public binary_function<_A1, _A2, _Rp> 220{ 221}; 222 223template <class _Rp, class _A1, class _A2> 224struct __weak_result_type<_Rp (&)(_A1, _A2)> 225 : public binary_function<_A1, _A2, _Rp> 226{ 227}; 228 229template <class _Rp, class _Cp, class _A1> 230struct __weak_result_type<_Rp (_Cp::*)(_A1)> 231 : public binary_function<_Cp*, _A1, _Rp> 232{ 233}; 234 235template <class _Rp, class _Cp, class _A1> 236struct __weak_result_type<_Rp (_Cp::*)(_A1) const> 237 : public binary_function<const _Cp*, _A1, _Rp> 238{ 239}; 240 241template <class _Rp, class _Cp, class _A1> 242struct __weak_result_type<_Rp (_Cp::*)(_A1) volatile> 243 : public binary_function<volatile _Cp*, _A1, _Rp> 244{ 245}; 246 247template <class _Rp, class _Cp, class _A1> 248struct __weak_result_type<_Rp (_Cp::*)(_A1) const volatile> 249 : public binary_function<const volatile _Cp*, _A1, _Rp> 250{ 251}; 252 253 254#ifndef _LIBCPP_HAS_NO_VARIADICS 255// 3 or more arguments 256 257template <class _Rp, class _A1, class _A2, class _A3, class ..._A4> 258struct __weak_result_type<_Rp (_A1, _A2, _A3, _A4...)> 259{ 260 typedef _Rp result_type; 261}; 262 263template <class _Rp, class _A1, class _A2, class _A3, class ..._A4> 264struct __weak_result_type<_Rp (&)(_A1, _A2, _A3, _A4...)> 265{ 266 typedef _Rp result_type; 267}; 268 269template <class _Rp, class _A1, class _A2, class _A3, class ..._A4> 270struct __weak_result_type<_Rp (*)(_A1, _A2, _A3, _A4...)> 271{ 272 typedef _Rp result_type; 273}; 274 275template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> 276struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...)> 277{ 278 typedef _Rp result_type; 279}; 280 281template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> 282struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...) const> 283{ 284 typedef _Rp result_type; 285}; 286 287template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> 288struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...) volatile> 289{ 290 typedef _Rp result_type; 291}; 292 293template <class _Rp, class _Cp, class _A1, class _A2, class ..._A3> 294struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2, _A3...) const volatile> 295{ 296 typedef _Rp result_type; 297}; 298 299#endif // _LIBCPP_HAS_NO_VARIADICS 300 301#ifndef _LIBCPP_CXX03_LANG 302 303template <class _Tp, class ..._Args> 304struct __invoke_return 305{ 306 typedef decltype(__invoke(_VSTD::declval<_Tp>(), _VSTD::declval<_Args>()...)) type; 307}; 308 309#else // defined(_LIBCPP_CXX03_LANG) 310 311#include <__functional_base_03> 312 313#endif // !defined(_LIBCPP_CXX03_LANG) 314 315 316template <class _Ret> 317struct __invoke_void_return_wrapper 318{ 319#ifndef _LIBCPP_HAS_NO_VARIADICS 320 template <class ..._Args> 321 static _Ret __call(_Args&&... __args) { 322 return __invoke(_VSTD::forward<_Args>(__args)...); 323 } 324#else 325 template <class _Fn> 326 static _Ret __call(_Fn __f) { 327 return __invoke(__f); 328 } 329 330 template <class _Fn, class _A0> 331 static _Ret __call(_Fn __f, _A0& __a0) { 332 return __invoke(__f, __a0); 333 } 334 335 template <class _Fn, class _A0, class _A1> 336 static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1) { 337 return __invoke(__f, __a0, __a1); 338 } 339 340 template <class _Fn, class _A0, class _A1, class _A2> 341 static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2){ 342 return __invoke(__f, __a0, __a1, __a2); 343 } 344#endif 345}; 346 347template <> 348struct __invoke_void_return_wrapper<void> 349{ 350#ifndef _LIBCPP_HAS_NO_VARIADICS 351 template <class ..._Args> 352 static void __call(_Args&&... __args) { 353 __invoke(_VSTD::forward<_Args>(__args)...); 354 } 355#else 356 template <class _Fn> 357 static void __call(_Fn __f) { 358 __invoke(__f); 359 } 360 361 template <class _Fn, class _A0> 362 static void __call(_Fn __f, _A0& __a0) { 363 __invoke(__f, __a0); 364 } 365 366 template <class _Fn, class _A0, class _A1> 367 static void __call(_Fn __f, _A0& __a0, _A1& __a1) { 368 __invoke(__f, __a0, __a1); 369 } 370 371 template <class _Fn, class _A0, class _A1, class _A2> 372 static void __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2) { 373 __invoke(__f, __a0, __a1, __a2); 374 } 375#endif 376}; 377 378template <class _Tp> 379class _LIBCPP_TEMPLATE_VIS reference_wrapper 380 : public __weak_result_type<_Tp> 381{ 382public: 383 // types 384 typedef _Tp type; 385private: 386 type* __f_; 387 388public: 389 // construct/copy/destroy 390 _LIBCPP_INLINE_VISIBILITY reference_wrapper(type& __f) _NOEXCEPT 391 : __f_(_VSTD::addressof(__f)) {} 392#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES 393 private: reference_wrapper(type&&); public: // = delete; // do not bind to temps 394#endif 395 396 // access 397 _LIBCPP_INLINE_VISIBILITY operator type& () const _NOEXCEPT {return *__f_;} 398 _LIBCPP_INLINE_VISIBILITY type& get() const _NOEXCEPT {return *__f_;} 399 400#ifndef _LIBCPP_HAS_NO_VARIADICS 401 // invoke 402 template <class... _ArgTypes> 403 _LIBCPP_INLINE_VISIBILITY 404 typename __invoke_of<type&, _ArgTypes...>::type 405 operator() (_ArgTypes&&... __args) const { 406 return __invoke(get(), _VSTD::forward<_ArgTypes>(__args)...); 407 } 408#else 409 410 _LIBCPP_INLINE_VISIBILITY 411 typename __invoke_return<type>::type 412 operator() () const { 413 return __invoke(get()); 414 } 415 416 template <class _A0> 417 _LIBCPP_INLINE_VISIBILITY 418 typename __invoke_return0<type, _A0>::type 419 operator() (_A0& __a0) const { 420 return __invoke(get(), __a0); 421 } 422 423 template <class _A0> 424 _LIBCPP_INLINE_VISIBILITY 425 typename __invoke_return0<type, _A0 const>::type 426 operator() (_A0 const& __a0) const { 427 return __invoke(get(), __a0); 428 } 429 430 template <class _A0, class _A1> 431 _LIBCPP_INLINE_VISIBILITY 432 typename __invoke_return1<type, _A0, _A1>::type 433 operator() (_A0& __a0, _A1& __a1) const { 434 return __invoke(get(), __a0, __a1); 435 } 436 437 template <class _A0, class _A1> 438 _LIBCPP_INLINE_VISIBILITY 439 typename __invoke_return1<type, _A0 const, _A1>::type 440 operator() (_A0 const& __a0, _A1& __a1) const { 441 return __invoke(get(), __a0, __a1); 442 } 443 444 template <class _A0, class _A1> 445 _LIBCPP_INLINE_VISIBILITY 446 typename __invoke_return1<type, _A0, _A1 const>::type 447 operator() (_A0& __a0, _A1 const& __a1) const { 448 return __invoke(get(), __a0, __a1); 449 } 450 451 template <class _A0, class _A1> 452 _LIBCPP_INLINE_VISIBILITY 453 typename __invoke_return1<type, _A0 const, _A1 const>::type 454 operator() (_A0 const& __a0, _A1 const& __a1) const { 455 return __invoke(get(), __a0, __a1); 456 } 457 458 template <class _A0, class _A1, class _A2> 459 _LIBCPP_INLINE_VISIBILITY 460 typename __invoke_return2<type, _A0, _A1, _A2>::type 461 operator() (_A0& __a0, _A1& __a1, _A2& __a2) const { 462 return __invoke(get(), __a0, __a1, __a2); 463 } 464 465 template <class _A0, class _A1, class _A2> 466 _LIBCPP_INLINE_VISIBILITY 467 typename __invoke_return2<type, _A0 const, _A1, _A2>::type 468 operator() (_A0 const& __a0, _A1& __a1, _A2& __a2) const { 469 return __invoke(get(), __a0, __a1, __a2); 470 } 471 472 template <class _A0, class _A1, class _A2> 473 _LIBCPP_INLINE_VISIBILITY 474 typename __invoke_return2<type, _A0, _A1 const, _A2>::type 475 operator() (_A0& __a0, _A1 const& __a1, _A2& __a2) const { 476 return __invoke(get(), __a0, __a1, __a2); 477 } 478 479 template <class _A0, class _A1, class _A2> 480 _LIBCPP_INLINE_VISIBILITY 481 typename __invoke_return2<type, _A0, _A1, _A2 const>::type 482 operator() (_A0& __a0, _A1& __a1, _A2 const& __a2) const { 483 return __invoke(get(), __a0, __a1, __a2); 484 } 485 486 template <class _A0, class _A1, class _A2> 487 _LIBCPP_INLINE_VISIBILITY 488 typename __invoke_return2<type, _A0 const, _A1 const, _A2>::type 489 operator() (_A0 const& __a0, _A1 const& __a1, _A2& __a2) const { 490 return __invoke(get(), __a0, __a1, __a2); 491 } 492 493 template <class _A0, class _A1, class _A2> 494 _LIBCPP_INLINE_VISIBILITY 495 typename __invoke_return2<type, _A0 const, _A1, _A2 const>::type 496 operator() (_A0 const& __a0, _A1& __a1, _A2 const& __a2) const { 497 return __invoke(get(), __a0, __a1, __a2); 498 } 499 500 template <class _A0, class _A1, class _A2> 501 _LIBCPP_INLINE_VISIBILITY 502 typename __invoke_return2<type, _A0, _A1 const, _A2 const>::type 503 operator() (_A0& __a0, _A1 const& __a1, _A2 const& __a2) const { 504 return __invoke(get(), __a0, __a1, __a2); 505 } 506 507 template <class _A0, class _A1, class _A2> 508 _LIBCPP_INLINE_VISIBILITY 509 typename __invoke_return2<type, _A0 const, _A1 const, _A2 const>::type 510 operator() (_A0 const& __a0, _A1 const& __a1, _A2 const& __a2) const { 511 return __invoke(get(), __a0, __a1, __a2); 512 } 513#endif // _LIBCPP_HAS_NO_VARIADICS 514}; 515 516 517template <class _Tp> 518inline _LIBCPP_INLINE_VISIBILITY 519reference_wrapper<_Tp> 520ref(_Tp& __t) _NOEXCEPT 521{ 522 return reference_wrapper<_Tp>(__t); 523} 524 525template <class _Tp> 526inline _LIBCPP_INLINE_VISIBILITY 527reference_wrapper<_Tp> 528ref(reference_wrapper<_Tp> __t) _NOEXCEPT 529{ 530 return ref(__t.get()); 531} 532 533template <class _Tp> 534inline _LIBCPP_INLINE_VISIBILITY 535reference_wrapper<const _Tp> 536cref(const _Tp& __t) _NOEXCEPT 537{ 538 return reference_wrapper<const _Tp>(__t); 539} 540 541template <class _Tp> 542inline _LIBCPP_INLINE_VISIBILITY 543reference_wrapper<const _Tp> 544cref(reference_wrapper<_Tp> __t) _NOEXCEPT 545{ 546 return cref(__t.get()); 547} 548 549#ifndef _LIBCPP_CXX03_LANG 550template <class _Tp> void ref(const _Tp&&) = delete; 551template <class _Tp> void cref(const _Tp&&) = delete; 552#endif 553 554#if _LIBCPP_STD_VER > 11 555template <class _Tp1, class _Tp2 = void> 556struct __is_transparent 557{ 558private: 559 struct __two {char __lx; char __lxx;}; 560 template <class _Up> static __two __test(...); 561 template <class _Up> static char __test(typename _Up::is_transparent* = 0); 562public: 563 static const bool value = sizeof(__test<_Tp1>(0)) == 1; 564}; 565#endif 566 567// allocator_arg_t 568 569struct _LIBCPP_TEMPLATE_VIS allocator_arg_t { }; 570 571#if defined(_LIBCPP_HAS_NO_CONSTEXPR) || defined(_LIBCPP_BUILDING_MEMORY) 572extern const allocator_arg_t allocator_arg; 573#else 574constexpr allocator_arg_t allocator_arg = allocator_arg_t(); 575#endif 576 577// uses_allocator 578 579template <class _Tp> 580struct __has_allocator_type 581{ 582private: 583 struct __two {char __lx; char __lxx;}; 584 template <class _Up> static __two __test(...); 585 template <class _Up> static char __test(typename _Up::allocator_type* = 0); 586public: 587 static const bool value = sizeof(__test<_Tp>(0)) == 1; 588}; 589 590template <class _Tp, class _Alloc, bool = __has_allocator_type<_Tp>::value> 591struct __uses_allocator 592 : public integral_constant<bool, 593 is_convertible<_Alloc, typename _Tp::allocator_type>::value> 594{ 595}; 596 597template <class _Tp, class _Alloc> 598struct __uses_allocator<_Tp, _Alloc, false> 599 : public false_type 600{ 601}; 602 603template <class _Tp, class _Alloc> 604struct _LIBCPP_TEMPLATE_VIS uses_allocator 605 : public __uses_allocator<_Tp, _Alloc> 606{ 607}; 608 609#if _LIBCPP_STD_VER > 14 610template <class _Tp, class _Alloc> 611constexpr size_t uses_allocator_v = uses_allocator<_Tp, _Alloc>::value; 612#endif 613 614#ifndef _LIBCPP_HAS_NO_VARIADICS 615 616// allocator construction 617 618template <class _Tp, class _Alloc, class ..._Args> 619struct __uses_alloc_ctor_imp 620{ 621 typedef typename __uncvref<_Alloc>::type _RawAlloc; 622 static const bool __ua = uses_allocator<_Tp, _RawAlloc>::value; 623 static const bool __ic = 624 is_constructible<_Tp, allocator_arg_t, _Alloc, _Args...>::value; 625 static const int value = __ua ? 2 - __ic : 0; 626}; 627 628template <class _Tp, class _Alloc, class ..._Args> 629struct __uses_alloc_ctor 630 : integral_constant<int, __uses_alloc_ctor_imp<_Tp, _Alloc, _Args...>::value> 631 {}; 632 633template <class _Tp, class _Allocator, class... _Args> 634inline _LIBCPP_INLINE_VISIBILITY 635void __user_alloc_construct_impl (integral_constant<int, 0>, _Tp *__storage, const _Allocator &, _Args &&... __args ) 636{ 637 new (__storage) _Tp (_VSTD::forward<_Args>(__args)...); 638} 639 640// FIXME: This should have a version which takes a non-const alloc. 641template <class _Tp, class _Allocator, class... _Args> 642inline _LIBCPP_INLINE_VISIBILITY 643void __user_alloc_construct_impl (integral_constant<int, 1>, _Tp *__storage, const _Allocator &__a, _Args &&... __args ) 644{ 645 new (__storage) _Tp (allocator_arg, __a, _VSTD::forward<_Args>(__args)...); 646} 647 648// FIXME: This should have a version which takes a non-const alloc. 649template <class _Tp, class _Allocator, class... _Args> 650inline _LIBCPP_INLINE_VISIBILITY 651void __user_alloc_construct_impl (integral_constant<int, 2>, _Tp *__storage, const _Allocator &__a, _Args &&... __args ) 652{ 653 new (__storage) _Tp (_VSTD::forward<_Args>(__args)..., __a); 654} 655 656// FIXME: Theis should have a version which takes a non-const alloc. 657template <class _Tp, class _Allocator, class... _Args> 658inline _LIBCPP_INLINE_VISIBILITY 659void __user_alloc_construct (_Tp *__storage, const _Allocator &__a, _Args &&... __args) 660{ 661 __user_alloc_construct_impl( 662 __uses_alloc_ctor<_Tp, _Allocator>(), 663 __storage, __a, _VSTD::forward<_Args>(__args)... 664 ); 665} 666#endif // _LIBCPP_HAS_NO_VARIADICS 667 668_LIBCPP_END_NAMESPACE_STD 669 670#endif // _LIBCPP_FUNCTIONAL_BASE 671