sfinae_helpers.h 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. //===----------------------------------------------------------------------===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. #ifndef _LIBCPP___TUPLE_SFINAE_HELPERS_H
  9. #define _LIBCPP___TUPLE_SFINAE_HELPERS_H
  10. #include <__config>
  11. #include <__fwd/tuple.h>
  12. #include <__tuple/make_tuple_types.h>
  13. #include <__tuple/tuple_element.h>
  14. #include <__tuple/tuple_like_ext.h>
  15. #include <__tuple/tuple_size.h>
  16. #include <__tuple/tuple_types.h>
  17. #include <__type_traits/conjunction.h>
  18. #include <__type_traits/enable_if.h>
  19. #include <__type_traits/integral_constant.h>
  20. #include <__type_traits/is_constructible.h>
  21. #include <__type_traits/is_same.h>
  22. #include <__type_traits/remove_cvref.h>
  23. #include <__type_traits/remove_reference.h>
  24. #include <cstddef>
  25. #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
  26. # pragma GCC system_header
  27. #endif
  28. _LIBCPP_BEGIN_NAMESPACE_STD
  29. #ifndef _LIBCPP_CXX03_LANG
  30. struct __tuple_sfinae_base {
  31. template <template <class, class...> class _Trait, class... _LArgs, class... _RArgs>
  32. static auto __do_test(__tuple_types<_LArgs...>, __tuple_types<_RArgs...>)
  33. -> __all<__enable_if_t<_Trait<_LArgs, _RArgs>::value, bool>{true}...>;
  34. template <template <class...> class>
  35. static auto __do_test(...) -> false_type;
  36. template <class _FromArgs, class _ToArgs>
  37. using __constructible = decltype(__do_test<is_constructible>(declval<_ToArgs>(), declval<_FromArgs>()));
  38. };
  39. // __tuple_constructible
  40. template <class _Tp,
  41. class _Up,
  42. bool = __tuple_like_ext<__libcpp_remove_reference_t<_Tp> >::value,
  43. bool = __tuple_like_ext<_Up>::value,
  44. class = void>
  45. struct __tuple_constructible : public false_type {};
  46. template <class _Tp, class _Up>
  47. struct __tuple_constructible<
  48. _Tp,
  49. _Up,
  50. true,
  51. true,
  52. typename enable_if<(tuple_size<typename remove_reference<_Tp>::type>::value == tuple_size<_Up>::value)>::type>
  53. : public __tuple_sfinae_base::__constructible< typename __make_tuple_types<_Tp>::type,
  54. typename __make_tuple_types<_Up>::type > {};
  55. template <size_t _Ip, class... _Tp>
  56. struct _LIBCPP_TEMPLATE_VIS tuple_element<_Ip, tuple<_Tp...> > {
  57. typedef _LIBCPP_NODEBUG typename tuple_element<_Ip, __tuple_types<_Tp...> >::type type;
  58. };
  59. struct _LIBCPP_EXPORTED_FROM_ABI __check_tuple_constructor_fail {
  60. static _LIBCPP_HIDE_FROM_ABI constexpr bool __enable_explicit_default() { return false; }
  61. static _LIBCPP_HIDE_FROM_ABI constexpr bool __enable_implicit_default() { return false; }
  62. template <class...>
  63. static _LIBCPP_HIDE_FROM_ABI constexpr bool __enable_explicit() {
  64. return false;
  65. }
  66. template <class...>
  67. static _LIBCPP_HIDE_FROM_ABI constexpr bool __enable_implicit() {
  68. return false;
  69. }
  70. template <class...>
  71. static _LIBCPP_HIDE_FROM_ABI constexpr bool __enable_assign() {
  72. return false;
  73. }
  74. };
  75. #endif // !defined(_LIBCPP_CXX03_LANG)
  76. #if _LIBCPP_STD_VER >= 17
  77. template <bool _CanCopy, bool _CanMove>
  78. struct __sfinae_ctor_base {};
  79. template <>
  80. struct __sfinae_ctor_base<false, false> {
  81. __sfinae_ctor_base() = default;
  82. __sfinae_ctor_base(__sfinae_ctor_base const&) = delete;
  83. __sfinae_ctor_base(__sfinae_ctor_base&&) = delete;
  84. __sfinae_ctor_base& operator=(__sfinae_ctor_base const&) = default;
  85. __sfinae_ctor_base& operator=(__sfinae_ctor_base&&) = default;
  86. };
  87. template <>
  88. struct __sfinae_ctor_base<true, false> {
  89. __sfinae_ctor_base() = default;
  90. __sfinae_ctor_base(__sfinae_ctor_base const&) = default;
  91. __sfinae_ctor_base(__sfinae_ctor_base&&) = delete;
  92. __sfinae_ctor_base& operator=(__sfinae_ctor_base const&) = default;
  93. __sfinae_ctor_base& operator=(__sfinae_ctor_base&&) = default;
  94. };
  95. template <>
  96. struct __sfinae_ctor_base<false, true> {
  97. __sfinae_ctor_base() = default;
  98. __sfinae_ctor_base(__sfinae_ctor_base const&) = delete;
  99. __sfinae_ctor_base(__sfinae_ctor_base&&) = default;
  100. __sfinae_ctor_base& operator=(__sfinae_ctor_base const&) = default;
  101. __sfinae_ctor_base& operator=(__sfinae_ctor_base&&) = default;
  102. };
  103. template <bool _CanCopy, bool _CanMove>
  104. struct __sfinae_assign_base {};
  105. template <>
  106. struct __sfinae_assign_base<false, false> {
  107. __sfinae_assign_base() = default;
  108. __sfinae_assign_base(__sfinae_assign_base const&) = default;
  109. __sfinae_assign_base(__sfinae_assign_base&&) = default;
  110. __sfinae_assign_base& operator=(__sfinae_assign_base const&) = delete;
  111. __sfinae_assign_base& operator=(__sfinae_assign_base&&) = delete;
  112. };
  113. template <>
  114. struct __sfinae_assign_base<true, false> {
  115. __sfinae_assign_base() = default;
  116. __sfinae_assign_base(__sfinae_assign_base const&) = default;
  117. __sfinae_assign_base(__sfinae_assign_base&&) = default;
  118. __sfinae_assign_base& operator=(__sfinae_assign_base const&) = default;
  119. __sfinae_assign_base& operator=(__sfinae_assign_base&&) = delete;
  120. };
  121. template <>
  122. struct __sfinae_assign_base<false, true> {
  123. __sfinae_assign_base() = default;
  124. __sfinae_assign_base(__sfinae_assign_base const&) = default;
  125. __sfinae_assign_base(__sfinae_assign_base&&) = default;
  126. __sfinae_assign_base& operator=(__sfinae_assign_base const&) = delete;
  127. __sfinae_assign_base& operator=(__sfinae_assign_base&&) = default;
  128. };
  129. #endif // _LIBCPP_STD_VER >= 17
  130. _LIBCPP_END_NAMESPACE_STD
  131. #endif // _LIBCPP___TUPLE_SFINAE_HELPERS_H