Skip to content

Commit 7891959

Browse files
ZERICO2005adriweb
authored andcommitted
type_traits now uses clang builtin's when possible
1 parent 9074b35 commit 7891959

File tree

1 file changed

+114
-121
lines changed

1 file changed

+114
-121
lines changed

src/libcxx/include/type_traits

Lines changed: 114 additions & 121 deletions
Original file line numberDiff line numberDiff line change
@@ -79,68 +79,24 @@ template<class _Tp> using remove_volatile_t = typename remove_volatile<_Tp>::typ
7979
template<class _Tp> using remove_cv = remove_const<remove_volatile_t<_Tp>>;
8080
template<class _Tp> using remove_cv_t = typename remove_cv<_Tp>::type;
8181

82-
// classification traits:
83-
template<class> struct is_const : false_type {};
84-
template<class _Tp> struct is_const<_Tp const> : true_type {};
85-
template<class _Tp> inline constexpr bool is_const_v = is_const<_Tp>::value;
86-
87-
template<class> struct is_volatile : false_type {};
88-
template<class _Tp> struct is_volatile<_Tp volatile> : true_type {};
89-
template<class _Tp> inline constexpr bool is_volatile_v = is_volatile<_Tp>::value;
90-
91-
template<class> struct is_lvalue_reference : false_type {};
92-
template<class _Tp> struct is_lvalue_reference<_Tp&> : true_type {};
93-
template<class _Tp> inline constexpr bool is_lvalue_reference_v = is_lvalue_reference<_Tp>::value;
94-
95-
template<class> struct is_rvalue_reference : false_type {};
96-
template<class _Tp> struct is_rvalue_reference<_Tp&&> : true_type {};
97-
template<class _Tp> inline constexpr bool is_rvalue_reference_v = is_rvalue_reference<_Tp>::value;
98-
99-
template<class _Tp> using is_reference = disjunction<is_lvalue_reference<_Tp>, is_rvalue_reference<_Tp>>;
100-
template<class _Tp> inline constexpr bool is_reference_v = is_reference<_Tp>::value;
101-
102-
template<class _Tp> struct __member_pointer : false_type {};
103-
template<class _Tp, class _Cp> struct __member_pointer<_Tp _Cp::*> : true_type {};
104-
template<class _Tp> using is_member_pointer = __member_pointer<remove_cv_t<_Tp>>;
105-
template<class _Tp> inline constexpr bool is_member_pointer_v = is_member_pointer<_Tp>::value;
106-
10782
// primary type categories:
108-
template<class _Tp> using is_void = is_same<remove_cv_t<_Tp>, void>;
109-
template<class _Tp> inline constexpr bool is_void_v = is_void<_Tp>::value;
83+
#if __has_builtin(__is_void)
84+
template<class _Tp> inline constexpr bool is_void_v = __is_void(_Tp);
85+
template<class _Tp> using is_void = bool_constant<is_void_v<_Tp>>;
86+
#endif
11087

11188
template<class _Tp> using is_null_pointer = is_same<remove_cv_t<_Tp>, nullptr_t>;
11289
template<class _Tp> inline constexpr bool is_null_pointer_v = is_null_pointer<_Tp>::value;
11390

114-
template<class _Tp> struct __integral : false_type {};
115-
template<> struct __integral< bool> : true_type {};
116-
template<> struct __integral< char> : true_type {};
117-
template<> struct __integral< signed char> : true_type {};
118-
template<> struct __integral<unsigned char> : true_type {};
119-
template<> struct __integral< wchar_t> : true_type {};
120-
#if __cplusplus >= 202002L
121-
template<> struct __integral< char8_t> : true_type {};
122-
#endif
123-
template<> struct __integral< char16_t> : true_type {};
124-
template<> struct __integral< char32_t> : true_type {};
125-
template<> struct __integral< signed short> : true_type {};
126-
template<> struct __integral<unsigned short> : true_type {};
127-
template<> struct __integral< signed int> : true_type {};
128-
template<> struct __integral<unsigned int> : true_type {};
129-
template<> struct __integral< signed long> : true_type {};
130-
template<> struct __integral<unsigned long> : true_type {};
131-
template<> struct __integral< signed __int48> : true_type {};
132-
template<> struct __integral<unsigned __int48> : true_type {};
133-
template<> struct __integral< signed long long> : true_type {};
134-
template<> struct __integral<unsigned long long> : true_type {};
135-
template<class _Tp> using is_integral = __integral<remove_cv_t<_Tp>>;
136-
template<class _Tp> inline constexpr bool is_integral_v = is_integral<_Tp>::value;
137-
138-
template<class _Tp> struct __floating_point : false_type {};
139-
template<> struct __floating_point< float> : true_type {};
140-
template<> struct __floating_point< double> : true_type {};
141-
template<> struct __floating_point<long double> : true_type {};
142-
template<class _Tp> using is_floating_point = __floating_point<remove_cv_t<_Tp>>;
143-
template<class _Tp> inline constexpr bool is_floating_point_v = is_floating_point<_Tp>::value;
91+
#if __has_builtin(__is_integral)
92+
template<class _Tp> inline constexpr bool is_integral_v = __is_integral(_Tp);
93+
template<class _Tp> using is_integral = bool_constant<is_integral_v<_Tp>>;
94+
#endif
95+
96+
#if __has_builtin(__is_floating_point)
97+
template<class _Tp> inline constexpr bool is_floating_point_v = __is_floating_point(_Tp);
98+
template<class _Tp> using is_floating_point = bool_constant<is_floating_point_v<_Tp>>;
99+
#endif
144100

145101
#if __has_builtin(__is_array)
146102
template<class _Tp> inline constexpr bool is_array_v = __is_array(_Tp);
@@ -162,50 +118,82 @@ template<class _Tp> inline constexpr bool is_class_v = __is_class(_Tp);
162118
template<class _Tp> using is_class = bool_constant<is_class_v<_Tp>>;
163119
#endif
164120

165-
template<class _Tp> using is_function = negation<disjunction<is_const<_Tp const>, is_reference<_Tp>>>;
166-
template<class _Tp> inline constexpr bool is_function_v = is_function<_Tp>::value;
121+
#if __has_builtin(__is_function)
122+
template<class _Tp> inline constexpr bool is_function_v = __is_function(_Tp);
123+
template<class _Tp> using is_function = bool_constant<is_function_v<_Tp>>;
124+
#endif
125+
126+
#if __has_builtin(__is_pointer)
127+
template<class _Tp> inline constexpr bool is_pointer_v = __is_pointer(_Tp);
128+
template<class _Tp> using is_pointer = bool_constant<is_pointer_v<_Tp>>;
129+
#endif
130+
131+
#if __has_builtin(__is_lvalue_reference)
132+
template<class _Tp> inline constexpr bool is_lvalue_reference_v = __is_lvalue_reference(_Tp);
133+
template<class _Tp> using is_lvalue_reference = bool_constant<is_lvalue_reference_v<_Tp>>;
134+
#endif
167135

168-
template<class> struct is_pointer : false_type {};
169-
template<class _Tp> struct is_pointer<_Tp*> : true_type {};
170-
template<class _Tp> inline constexpr bool is_pointer_v = is_pointer<_Tp>::value;
136+
#if __has_builtin(__is_rvalue_reference)
137+
template<class _Tp> inline constexpr bool is_rvalue_reference_v = __is_rvalue_reference(_Tp);
138+
template<class _Tp> using is_rvalue_reference = bool_constant<is_rvalue_reference_v<_Tp>>;
139+
#endif
171140

172-
template<class _Tp> struct __member_function_pointer : false_type {};
173-
template<class _Tp, class _Cp> struct __member_function_pointer<_Tp _Cp::*> : is_function<_Tp> {};
174-
template<class _Tp> using is_member_function_pointer = __member_function_pointer<remove_cv_t<_Tp>>;
175-
template<class _Tp> inline constexpr bool is_member_function_pointer_v = is_member_function_pointer<_Tp>::value;
141+
#if __has_builtin(__is_member_object_pointer)
142+
template<class _Tp> inline constexpr bool is_member_object_pointer_v = __is_member_object_pointer(_Tp);
143+
template<class _Tp> using is_member_object_pointer = bool_constant<is_member_object_pointer_v<_Tp>>;
144+
#endif
176145

177-
template<class _Tp> struct __member_object_pointer : false_type {};
178-
template<class _Tp, class _Cp> struct __member_object_pointer<_Tp _Cp::*> : negation<is_function<_Tp>> {};
179-
template<class _Tp> using is_member_object_pointer = __member_object_pointer<remove_cv_t<_Tp>>;
180-
template<class _Tp> inline constexpr bool is_member_object_pointer_v = is_member_object_pointer<_Tp>::value;
146+
#if __has_builtin(__is_member_function_pointer)
147+
template<class _Tp> inline constexpr bool is_member_function_pointer_v = __is_member_function_pointer(_Tp);
148+
template<class _Tp> using is_member_function_pointer = bool_constant<is_member_function_pointer_v<_Tp>>;
149+
#endif
181150

182151
// composite type categories:
152+
#if __has_builtin(__is_fundamental)
153+
template<class _Tp> inline constexpr bool is_fundamental_v = __is_fundamental(_Tp);
154+
template<class _Tp> using is_fundamental = bool_constant<is_fundamental_v<_Tp>>;
155+
#endif
156+
157+
#if __has_builtin(__is_arithmetic)
158+
template<class _Tp> inline constexpr bool is_arithmetic_v = __is_arithmetic(_Tp);
159+
template<class _Tp> using is_arithmetic = bool_constant<is_arithmetic_v<_Tp>>;
160+
#endif
161+
162+
#if __has_builtin(__is_scalar)
163+
template<class _Tp> inline constexpr bool is_scalar_v = __is_scalar(_Tp);
164+
template<class _Tp> using is_scalar = bool_constant<is_scalar_v<_Tp>>;
165+
#endif
166+
167+
#if __has_builtin(__is_object)
168+
template<class _Tp> inline constexpr bool is_object_v = __is_object(_Tp);
169+
template<class _Tp> using is_object = bool_constant<is_object_v<_Tp>>;
170+
#endif
183171

184-
template<class _Tp> using is_arithmetic = disjunction<is_integral<_Tp>, is_floating_point<_Tp>>;
185-
template<class _Tp> inline constexpr bool is_arithmetic_v = is_arithmetic<_Tp>::value;
172+
#if __has_builtin(__is_compound)
173+
template<class _Tp> inline constexpr bool is_compound_v = __is_compound(_Tp);
174+
template<class _Tp> using is_compound = bool_constant<is_compound_v<_Tp>>;
175+
#endif
186176

187-
template<class _Tp> using is_fundamental = disjunction<is_void<_Tp>, is_null_pointer<_Tp>, is_arithmetic<_Tp>>;
188-
template<class _Tp> inline constexpr bool is_fundamental_v = is_fundamental<_Tp>::value;
177+
#if __has_builtin(__is_reference)
178+
template<class _Tp> inline constexpr bool is_reference_v = __is_reference(_Tp);
179+
template<class _Tp> using is_reference = bool_constant<is_reference_v<_Tp>>;
180+
#endif
189181

190-
template <class _Tp> struct is_scalar : public integral_constant<bool,
191-
is_arithmetic<_Tp>::value ||
192-
is_member_pointer<_Tp>::value ||
193-
is_pointer<_Tp>::value ||
194-
is_null_pointer<_Tp>::value ||
195-
is_enum<_Tp>::value
196-
> {};
197-
template <class _Tp> inline constexpr bool is_scalar_v = is_scalar<_Tp>::value;
182+
#if __has_builtin(__is_member_pointer)
183+
template<class _Tp> inline constexpr bool is_member_pointer_v = __is_member_pointer(_Tp);
184+
template<class _Tp> using is_member_pointer = bool_constant<is_member_pointer_v<_Tp>>;
185+
#endif
198186

199-
template <class _Tp> struct is_object : integral_constant<bool,
200-
is_scalar<_Tp>::value ||
201-
is_array<_Tp>::value ||
202-
is_union<_Tp>::value ||
203-
is_class<_Tp>::value
204-
> {};
205-
template <class _Tp> inline constexpr bool is_object_v = is_object<_Tp>::value;
187+
// type properties:
188+
#if __has_builtin(__is_const)
189+
template<class _Tp> inline constexpr bool is_const_v = __is_const(_Tp);
190+
template<class _Tp> using is_const = bool_constant<is_const_v<_Tp>>;
191+
#endif
206192

207-
template<class _Tp> struct is_compound : std::integral_constant<bool, !std::is_fundamental<_Tp>::value> {};
208-
template<class _Tp> inline constexpr bool is_compound_v = is_compound<_Tp>::value;
193+
#if __has_builtin(__is_volatile)
194+
template<class _Tp> inline constexpr bool is_volatile_v = __is_volatile(_Tp);
195+
template<class _Tp> using is_volatile = bool_constant<is_volatile_v<_Tp>>;
196+
#endif
209197

210198
#if __has_builtin(__is_trivial)
211199
template<class _Tp> inline constexpr bool is_trivial_v = __is_trivial(_Tp);
@@ -297,60 +285,60 @@ template<class _Tp> struct remove_reference<_Tp&> : type_identity<_Tp> {};
297285
template<class _Tp> struct remove_reference<_Tp&&> : type_identity<_Tp> {};
298286
template<class _Tp> using remove_reference_t = typename remove_reference<_Tp>::type;
299287

300-
template <class _Tp> using __remove_cvref_t = typename remove_cv<typename remove_reference<_Tp>::type>::type;
301-
template <class _Tp> struct remove_cvref { using type = __remove_cvref_t<_Tp>; };
302-
template <class _Tp> using remove_cvref_t = typename remove_cvref<_Tp>::type;
288+
template<class _Tp> using __remove_cvref_t = typename remove_cv<typename remove_reference<_Tp>::type>::type;
289+
template<class _Tp> struct remove_cvref { using type = __remove_cvref_t<_Tp>; };
290+
template<class _Tp> using remove_cvref_t = typename remove_cvref<_Tp>::type;
303291

304-
template<class _Tp> auto __add_pointer(int) -> type_identity<_Tp*>;
305-
template<class _Tp> auto __add_pointer(...) -> type_identity<_Tp>;
306-
template<class _Tp> using add_pointer = decltype(__add_pointer<_Tp>(0));
292+
template<class _Tp> auto __ezcxx_add_pointer(int) -> type_identity<_Tp*>;
293+
template<class _Tp> auto __ezcxx_add_pointer(...) -> type_identity<_Tp>;
294+
template<class _Tp> using add_pointer = decltype(__ezcxx_add_pointer<_Tp>(0));
307295
template<class _Tp> using add_pointer_t = typename add_pointer<_Tp>::type;
308296

309-
template<class _Tp> auto __add_lvalue_reference(int) -> type_identity<_Tp&>;
310-
template<class _Tp> auto __add_lvalue_reference(...) -> type_identity<_Tp>;
311-
template<class _Tp> using add_lvalue_reference = decltype(__add_lvalue_reference<_Tp>(0));
297+
template<class _Tp> auto __ezcxx_add_lvalue_reference(int) -> type_identity<_Tp&>;
298+
template<class _Tp> auto __ezcxx_add_lvalue_reference(...) -> type_identity<_Tp>;
299+
template<class _Tp> using add_lvalue_reference = decltype(__ezcxx_add_lvalue_reference<_Tp>(0));
312300
template<class _Tp> using add_lvalue_reference_t = typename add_lvalue_reference<_Tp>::type;
313301

314-
template<class _Tp> auto __add_rvalue_reference(int) -> type_identity<_Tp&&>;
315-
template<class _Tp> auto __add_rvalue_reference(...) -> type_identity<_Tp>;
316-
template<class _Tp> using add_rvalue_reference = decltype(__add_rvalue_reference<_Tp>(0));
302+
template<class _Tp> auto __ezcxx_add_rvalue_reference(int) -> type_identity<_Tp&&>;
303+
template<class _Tp> auto __ezcxx_add_rvalue_reference(...) -> type_identity<_Tp>;
304+
template<class _Tp> using add_rvalue_reference = decltype(__ezcxx_add_rvalue_reference<_Tp>(0));
317305
template<class _Tp> using add_rvalue_reference_t = typename add_rvalue_reference<_Tp>::type;
318306

319307
// alignment_of:
320-
template <class _Tp> struct alignment_of
308+
template<class _Tp> struct alignment_of
321309
: public integral_constant<size_t, alignof(_Tp)> {};
322-
template <class _Tp> inline constexpr size_t alignment_of_v = alignment_of<_Tp>::value;
310+
template<class _Tp> inline constexpr size_t alignment_of_v = alignment_of<_Tp>::value;
323311

324312
// rank/extent:
325-
template <class _Tp> struct rank
313+
template<class _Tp> struct rank
326314
: public integral_constant<size_t, 0> {};
327-
template <class _Tp> struct rank<_Tp[]>
315+
template<class _Tp> struct rank<_Tp[]>
328316
: public integral_constant<size_t, rank<_Tp>::value + 1> {};
329-
template <class _Tp, size_t _Np> struct rank<_Tp[_Np]>
317+
template<class _Tp, size_t _Np> struct rank<_Tp[_Np]>
330318
: public integral_constant<size_t, rank<_Tp>::value + 1> {};
331-
template <class _Tp> inline constexpr size_t rank_v = rank<_Tp>::value;
319+
template<class _Tp> inline constexpr size_t rank_v = rank<_Tp>::value;
332320

333-
template <class _Tp, unsigned _Ip = 0> struct extent
321+
template<class _Tp, unsigned _Ip = 0> struct extent
334322
: public integral_constant<size_t, 0> {};
335-
template <class _Tp> struct extent<_Tp[], 0>
323+
template<class _Tp> struct extent<_Tp[], 0>
336324
: public integral_constant<size_t, 0> {};
337-
template <class _Tp, unsigned _Ip> struct extent<_Tp[], _Ip>
325+
template<class _Tp, unsigned _Ip> struct extent<_Tp[], _Ip>
338326
: public integral_constant<size_t, extent<_Tp, _Ip-1>::value> {};
339-
template <class _Tp, size_t _Np> struct extent<_Tp[_Np], 0>
327+
template<class _Tp, size_t _Np> struct extent<_Tp[_Np], 0>
340328
: public integral_constant<size_t, _Np> {};
341-
template <class _Tp, size_t _Np, unsigned _Ip> struct extent<_Tp[_Np], _Ip>
329+
template<class _Tp, size_t _Np, unsigned _Ip> struct extent<_Tp[_Np], _Ip>
342330
: public integral_constant<size_t, extent<_Tp, _Ip-1>::value> {};
343-
template <class _Tp, unsigned _Ip = 0> inline constexpr size_t extent_v = extent<_Tp, _Ip>::value;
331+
template<class _Tp, unsigned _Ip = 0> inline constexpr size_t extent_v = extent<_Tp, _Ip>::value;
344332

345333
template<class _Tp> struct remove_extent { typedef _Tp type; };
346334
template<class _Tp> struct remove_extent<_Tp[]> { typedef _Tp type; };
347335
template<class _Tp, size_t _Np> struct remove_extent<_Tp[_Np]> { typedef _Tp type; };
348-
template <class _Tp> using remove_extent_t = typename remove_extent<_Tp>::type;
336+
template<class _Tp> using remove_extent_t = typename remove_extent<_Tp>::type;
349337

350-
template <class _Tp> struct remove_all_extents { typedef _Tp type; };
351-
template <class _Tp> struct remove_all_extents<_Tp[]> { typedef typename remove_all_extents<_Tp>::type type; };
352-
template <class _Tp, size_t _Np> struct remove_all_extents<_Tp[_Np]> { typedef typename remove_all_extents<_Tp>::type type; };
353-
template <class _Tp> using remove_all_extents_t = typename remove_all_extents<_Tp>::type;
338+
template<class _Tp> struct remove_all_extents { typedef _Tp type; };
339+
template<class _Tp> struct remove_all_extents<_Tp[]> { typedef typename remove_all_extents<_Tp>::type type; };
340+
template<class _Tp, size_t _Np> struct remove_all_extents<_Tp[_Np]> { typedef typename remove_all_extents<_Tp>::type type; };
341+
template<class _Tp> using remove_all_extents_t = typename remove_all_extents<_Tp>::type;
354342

355343
// decay:
356344
template<class _Tp>
@@ -368,7 +356,7 @@ public:
368356
>::type
369357
>::type type;
370358
};
371-
template <class _Tp> using decay_t = typename decay<_Tp>::type;
359+
template<class _Tp> using decay_t = typename decay<_Tp>::type;
372360

373361
// underlying_type:
374362

@@ -469,6 +457,11 @@ template<class _Tp> inline constexpr bool is_trivially_destructible_v = __is_tri
469457
template<class _Tp> using is_trivially_destructible = bool_constant<is_trivially_destructible_v<_Tp>>;
470458
#endif
471459

460+
#if __has_builtin(__is_nothrow_destructible)
461+
template<class _Tp> inline constexpr bool is_nothrow_destructible_v = __is_nothrow_destructible(_Tp);
462+
template<class _Tp> using is_nothrow_destructible = bool_constant<is_nothrow_destructible_v<_Tp>>;
463+
#endif
464+
472465
#if __has_builtin(__has_virtual_destructor)
473466
template<class _Tp> inline constexpr bool has_virtual_destructor_v = __has_virtual_destructor(_Tp);
474467
template<class _Tp> using has_virtual_destructor = bool_constant<has_virtual_destructor_v<_Tp>>;

0 commit comments

Comments
 (0)