|
16 | 16 | #include <__algorithm/unwrap_iter.h> |
17 | 17 | #include <__config> |
18 | 18 | #include <__functional/identity.h> |
| 19 | +#include <__iterator/aliasing_iterator.h> |
19 | 20 | #include <__type_traits/desugars_to.h> |
20 | 21 | #include <__type_traits/invoke.h> |
21 | 22 | #include <__type_traits/is_constant_evaluated.h> |
@@ -55,18 +56,13 @@ __mismatch(_Iter1 __first1, _Sent1 __last1, _Iter2 __first2, _Pred& __pred, _Pro |
55 | 56 |
|
56 | 57 | #if _LIBCPP_VECTORIZE_ALGORITHMS |
57 | 58 |
|
58 | | -template <class _Tp, |
59 | | - class _Pred, |
60 | | - class _Proj1, |
61 | | - class _Proj2, |
62 | | - __enable_if_t<is_integral<_Tp>::value && __desugars_to_v<__equal_tag, _Pred, _Tp, _Tp> && |
63 | | - __is_identity<_Proj1>::value && __is_identity<_Proj2>::value, |
64 | | - int> = 0> |
65 | | -_LIBCPP_NODISCARD _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 pair<_Tp*, _Tp*> |
66 | | -__mismatch(_Tp* __first1, _Tp* __last1, _Tp* __first2, _Pred& __pred, _Proj1& __proj1, _Proj2& __proj2) { |
| 59 | +template <class _Iter> |
| 60 | +_LIBCPP_NODISCARD _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 pair<_Iter, _Iter> |
| 61 | +__mismatch_vectorized(_Iter __first1, _Iter __last1, _Iter __first2) { |
| 62 | + using __value_type = __iter_value_type<_Iter>; |
67 | 63 | constexpr size_t __unroll_count = 4; |
68 | | - constexpr size_t __vec_size = __native_vector_size<_Tp>; |
69 | | - using __vec = __simd_vector<_Tp, __vec_size>; |
| 64 | + constexpr size_t __vec_size = __native_vector_size<__value_type>; |
| 65 | + using __vec = __simd_vector<__value_type, __vec_size>; |
70 | 66 |
|
71 | 67 | if (!__libcpp_is_constant_evaluated()) { |
72 | 68 | auto __orig_first1 = __first1; |
@@ -116,9 +112,41 @@ __mismatch(_Tp* __first1, _Tp* __last1, _Tp* __first2, _Pred& __pred, _Proj1& __ |
116 | 112 | } // else loop over the elements individually |
117 | 113 | } |
118 | 114 |
|
119 | | - return std::__mismatch_loop(__first1, __last1, __first2, __pred, __proj1, __proj2); |
| 115 | + __equal_to __pred; |
| 116 | + __identity __proj; |
| 117 | + return std::__mismatch_loop(__first1, __last1, __first2, __pred, __proj, __proj); |
| 118 | +} |
| 119 | + |
| 120 | +template <class _Tp, |
| 121 | + class _Pred, |
| 122 | + class _Proj1, |
| 123 | + class _Proj2, |
| 124 | + __enable_if_t<is_integral<_Tp>::value && __desugars_to_v<__equal_tag, _Pred, _Tp, _Tp> && |
| 125 | + __is_identity<_Proj1>::value && __is_identity<_Proj2>::value, |
| 126 | + int> = 0> |
| 127 | +_LIBCPP_NODISCARD _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 pair<_Tp*, _Tp*> |
| 128 | +__mismatch(_Tp* __first1, _Tp* __last1, _Tp* __first2, _Pred&, _Proj1&, _Proj2&) { |
| 129 | + return std::__mismatch_vectorized(__first1, __last1, __first2); |
120 | 130 | } |
121 | 131 |
|
| 132 | +template <class _Tp, |
| 133 | + class _Pred, |
| 134 | + class _Proj1, |
| 135 | + class _Proj2, |
| 136 | + __enable_if_t<!is_integral<_Tp>::value && __desugars_to_v<__equal_tag, _Pred, _Tp, _Tp> && |
| 137 | + __is_identity<_Proj1>::value && __is_identity<_Proj2>::value && |
| 138 | + __can_map_to_integer_v<_Tp> && __libcpp_is_trivially_equality_comparable<_Tp, _Tp>::value, |
| 139 | + int> = 0> |
| 140 | +_LIBCPP_NODISCARD _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 pair<_Tp*, _Tp*> |
| 141 | +__mismatch(_Tp* __first1, _Tp* __last1, _Tp* __first2, _Pred& __pred, _Proj1& __proj1, _Proj2& __proj2) { |
| 142 | + if (__libcpp_is_constant_evaluated()) { |
| 143 | + return std::__mismatch_loop(__first1, __last1, __first2, __pred, __proj1, __proj2); |
| 144 | + } else { |
| 145 | + using _Iter = __aliasing_iterator<_Tp*, __get_as_integer_type_t<_Tp>>; |
| 146 | + auto __ret = std::__mismatch_vectorized(_Iter(__first1), _Iter(__last1), _Iter(__first2)); |
| 147 | + return {__ret.first.__base(), __ret.second.__base()}; |
| 148 | + } |
| 149 | +} |
122 | 150 | #endif // _LIBCPP_VECTORIZE_ALGORITHMS |
123 | 151 |
|
124 | 152 | template <class _InputIterator1, class _InputIterator2, class _BinaryPredicate> |
|
0 commit comments