20hi_warning_ignore_msvc(26818)
22namespace hi::inline v1 {
24template<s
size_t A, s
size_t B, s
size_t C, s
size_t D>
25[[nodiscard]]
constexpr static int _mm_swizzle_ps_permute_mask() noexcept
27 static_assert(A >= -3 and A < 4);
28 static_assert(B >= -3 and B < 4);
29 static_assert(C >= -3 and C < 4);
30 static_assert(D >= -3 and D < 4);
34 case 0: r |= 0b00'00'00'00;
break;
35 case 1: r |= 0b00'00'00'01;
break;
36 case 2: r |= 0b00'00'00'10;
break;
37 case 3: r |= 0b00'00'00'11;
break;
38 case -1: r |= 0b00'00'00'00;
break;
39 case -2: r |= 0b00'00'00'00;
break;
42 case 0: r |= 0b00'00'00'00;
break;
43 case 1: r |= 0b00'00'01'00;
break;
44 case 2: r |= 0b00'00'10'00;
break;
45 case 3: r |= 0b00'00'11'00;
break;
46 case -1: r |= 0b00'00'01'00;
break;
47 case -2: r |= 0b00'00'01'00;
break;
50 case 0: r |= 0b00'00'00'00;
break;
51 case 1: r |= 0b00'01'00'00;
break;
52 case 2: r |= 0b00'10'00'00;
break;
53 case 3: r |= 0b00'11'00'00;
break;
54 case -1: r |= 0b00'10'00'00;
break;
55 case -2: r |= 0b00'10'00'00;
break;
58 case 0: r |= 0b00'00'00'00;
break;
59 case 1: r |= 0b01'00'00'00;
break;
60 case 2: r |= 0b10'00'00'00;
break;
61 case 3: r |= 0b11'00'00'00;
break;
62 case -1: r |= 0b11'00'00'00;
break;
63 case -2: r |= 0b11'00'00'00;
break;
68template<s
size_t A, s
size_t B, s
size_t C, s
size_t D>
69[[nodiscard]]
constexpr static int _mm_swizzle_ps_not_one_mask() noexcept
71 static_assert(A >= -3 && A < 4);
72 static_assert(B >= -3 && B < 4);
73 static_assert(C >= -3 && C < 4);
74 static_assert(D >= -3 && D < 4);
77 r |= (A == -2) ? 0 : 0b0001;
78 r |= (B == -2) ? 0 : 0b0010;
79 r |= (C == -2) ? 0 : 0b0100;
80 r |= (D == -2) ? 0 : 0b1000;
84template<s
size_t A, s
size_t B, s
size_t C, s
size_t D>
85[[nodiscard]]
constexpr static int _mm_swizzle_ps_number_mask() noexcept
87 static_assert(A >= -3 && A < 4);
88 static_assert(B >= -3 && B < 4);
89 static_assert(C >= -3 && C < 4);
90 static_assert(D >= -3 && D < 4);
93 r |= A < 0 ? 0b0001 : 0;
94 r |= B < 0 ? 0b0010 : 0;
95 r |= C < 0 ? 0b0100 : 0;
96 r |= D < 0 ? 0b1000 : 0;
100template<s
size_t A, s
size_t B, s
size_t C, s
size_t D>
101[[nodiscard]] __m128 _mm_swizzle_ps(__m128
const &value)
noexcept
103 static_assert(A >= -3 && A < 4);
104 static_assert(B >= -3 && B < 4);
105 static_assert(C >= -3 && C < 4);
106 static_assert(D >= -3 && D < 4);
108 constexpr int permute_mask = _mm_swizzle_ps_permute_mask<A, B, C, D>();
109 constexpr int not_one_mask = _mm_swizzle_ps_not_one_mask<A, B, C, D>();
110 constexpr int number_mask = _mm_swizzle_ps_number_mask<A, B, C, D>();
114 if constexpr (permute_mask != 0b11'10'01'00) {
115 swizzled = _mm_permute_ps(value, permute_mask);
120 __m128 numbers = _mm_undefined_ps();
121 if constexpr (not_one_mask == 0b0000) {
122 numbers = _mm_set_ps1(1.0f);
123 }
else if constexpr (not_one_mask == 0b1111) {
124 numbers = _mm_setzero_ps();
125 }
else if constexpr (not_one_mask == 0b1110) {
126 numbers = _mm_set_ss(1.0f);
128 hilet _1111 = _mm_set_ps1(1.0f);
129 numbers = _mm_insert_ps(_1111, _1111, not_one_mask);
132 __m128 result = _mm_undefined_ps();
133 if constexpr (number_mask == 0b0000) {
135 }
else if constexpr (number_mask == 0b1111) {
137 }
else if constexpr (((not_one_mask | ~number_mask) & 0b1111) == 0b1111) {
138 result = _mm_insert_ps(swizzled, swizzled, number_mask);
140 result = _mm_blend_ps(swizzled, numbers, number_mask);
145template<s
size_t A, s
size_t B, s
size_t C, s
size_t D>
146[[nodiscard]] __m128i _mm_swizzle_epi32(__m128i
const &value)
noexcept
148 return _mm_castps_si128(_mm_swizzle_ps<A, B, C, D>(_mm_castsi128_ps(value)));
152[[nodiscard]] __m128d _mm_swizzle_pd(__m128d
const &value)
noexcept
154 constexpr auto A1 = A >= 0 ? A * 2 : A;
155 constexpr auto A2 = A >= 0 ? A1 + 1 : A1;
156 constexpr auto B1 = B >= 0 ? B * 2 : B;
157 constexpr auto B2 = B >= 0 ? B1 + 1 : B1;
159 return _mm_castps_pd(_mm_swizzle_ps<A1, A2, B1, B2>(_mm_castpd_ps(value)));
163[[nodiscard]] __m128i _mm_swizzle_epi64(__m128i
const &value)
noexcept
165 return _mm_castpd_si128(_mm_swizzle_pd<A, B>(_mm_castsi128_pd(value)));
This file includes required definitions.
std::ptrdiff_t ssize_t
Signed size/index into an array.
Definition required.hpp:162
#define hilet
Invariant should be the default for variables.
Definition required.hpp:23
Functions and macros for handling architectural difference between compilers, CPUs and operating syst...