9
9
#ifndef _LIBCPP___UTILITY_CMP_H
10
10
#define _LIBCPP___UTILITY_CMP_H
11
11
12
+ #include " __assert"
12
13
#include < __config>
13
14
#include < __type_traits/integer_traits.h>
14
15
#include < __type_traits/is_signed.h>
@@ -26,16 +27,18 @@ _LIBCPP_BEGIN_NAMESPACE_STD
26
27
27
28
#if _LIBCPP_STD_VER >= 20
28
29
30
+ template <__signed_or_unsigned_integer _Tp, __signed_integer _Ip>
31
+ inline constexpr bool __comparison_can_promote_to =
32
+ __signed_integer<_Tp> ? sizeof (_Tp) <= sizeof (_Ip) : sizeof (_Tp) < sizeof (_Ip);
33
+
29
34
template <__signed_or_unsigned_integer _Tp, __signed_or_unsigned_integer _Up>
30
35
_LIBCPP_HIDE_FROM_ABI constexpr bool cmp_equal (_Tp __t , _Up __u) noexcept {
31
- if constexpr (sizeof (_Tp) < sizeof (int ) && sizeof (_Up) < sizeof (int )) {
32
- __builtin_assume (__t < numeric_limits<int >::max () && __u < numeric_limits<int >::max ());
36
+ if constexpr (is_signed_v<_Tp> == is_signed_v<_Up>)
37
+ return __t == __u;
38
+ else if constexpr (__comparison_can_promote_to<_Tp, int > && __comparison_can_promote_to<_Up, int >)
33
39
return static_cast <int >(__t ) == static_cast <int >(__u);
34
- } else if constexpr (sizeof (_Tp) < sizeof (long long ) && sizeof (_Up) < sizeof (long long )) {
35
- __builtin_assume (__t < numeric_limits<long long >::max () && __u < numeric_limits<long long >::max ());
40
+ else if constexpr (__comparison_can_promote_to<_Tp, long long > && __comparison_can_promote_to<_Up, long long >)
36
41
return static_cast <long long >(__t ) == static_cast <long long >(__u);
37
- } else if constexpr (is_signed_v<_Tp> == is_signed_v<_Up>)
38
- return __t == __u;
39
42
else if constexpr (is_signed_v<_Tp>)
40
43
return __t < 0 ? false : make_unsigned_t <_Tp>(__t ) == __u;
41
44
else
@@ -49,14 +52,12 @@ _LIBCPP_HIDE_FROM_ABI constexpr bool cmp_not_equal(_Tp __t, _Up __u) noexcept {
49
52
50
53
template <__signed_or_unsigned_integer _Tp, __signed_or_unsigned_integer _Up>
51
54
_LIBCPP_HIDE_FROM_ABI constexpr bool cmp_less (_Tp __t , _Up __u) noexcept {
52
- if constexpr (sizeof (_Tp) < sizeof (int ) && sizeof (_Up) < sizeof (int )) {
53
- __builtin_assume (__t < numeric_limits<int >::max () && __u < numeric_limits<int >::max ());
55
+ if constexpr (is_signed_v<_Tp> == is_signed_v<_Up>)
56
+ return __t < __u;
57
+ else if constexpr (__comparison_can_promote_to<_Tp, int > && __comparison_can_promote_to<_Up, int >)
54
58
return static_cast <int >(__t ) < static_cast <int >(__u);
55
- } else if constexpr (sizeof (_Tp) < sizeof (long long ) && sizeof (_Up) < sizeof (long long )) {
56
- __builtin_assume (__t < numeric_limits<long long >::max () && __u < numeric_limits<long long >::max ());
59
+ else if constexpr (__comparison_can_promote_to<_Tp, long long > && __comparison_can_promote_to<_Up, long long >)
57
60
return static_cast <long long >(__t ) < static_cast <long long >(__u);
58
- } else if constexpr (is_signed_v<_Tp> == is_signed_v<_Up>)
59
- return __t < __u;
60
61
else if constexpr (is_signed_v<_Tp>)
61
62
return __t < 0 ? true : make_unsigned_t <_Tp>(__t ) < __u;
62
63
else
0 commit comments