17#if defined(BOTAN_SIMD_USE_SSSE3)
18 const __m128i BSWAP_MASK = _mm_set_epi8(0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15);
19 return SIMD_4x32(_mm_shuffle_epi8(in.
raw(), BSWAP_MASK));
20#elif defined(BOTAN_SIMD_USE_NEON)
21 const uint8_t maskb[16] = {15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0};
22 const uint8x16_t mask = vld1q_u8(maskb);
23 return SIMD_4x32(vreinterpretq_u32_u8(vqtbl1q_u8(vreinterpretq_u8_u32(in.
raw()), mask)));
24#elif defined(BOTAN_SIMD_USE_ALTIVEC)
25 const __vector
unsigned char mask = {15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0};
32 static_assert(M == 0x00 || M == 0x01 || M == 0x10 || M == 0x11,
"Valid clmul mode");
34#if defined(BOTAN_SIMD_USE_SSSE3)
36#elif defined(BOTAN_SIMD_USE_NEON)
37 const uint64_t a = vgetq_lane_u64(vreinterpretq_u64_u32(x.
raw()), M & 0x01);
38 const uint64_t b = vgetq_lane_u64(vreinterpretq_u64_u32(H.
raw()), (M & 0x10) >> 4);
40 #if defined(BOTAN_BUILD_COMPILER_IS_MSVC)
41 __n64 a1 = {a}, b1 = {b};
44 return SIMD_4x32(
reinterpret_cast<uint32x4_t
>(vmull_p64(a, b)));
47#elif defined(BOTAN_SIMD_USE_ALTIVEC)
49 constexpr uint8_t flip = (std::endian::native == std::endian::big) ? 0x11 : 0x00;
54 if constexpr(std::endian::native == std::endian::big) {
59 if constexpr(M == (0x11 ^ flip)) {
62 }
else if constexpr(M == (0x10 ^ flip)) {
64 }
else if constexpr(M == (0x01 ^ flip)) {
66 }
else if constexpr(M == (0x00 ^ flip)) {
67 i1 = mask_lo.
andc(i1);
68 i2 = mask_lo.
andc(i2);
71 auto i1v =
reinterpret_cast<__vector
unsigned long long>(i1.
raw());
72 auto i2v =
reinterpret_cast<__vector
unsigned long long>(i2.
raw());
74 #if BOTAN_COMPILER_HAS_BUILTIN(__builtin_crypto_vpmsumd)
75 auto rv = __builtin_crypto_vpmsumd(i1v, i2v);
77 auto rv = __builtin_altivec_crypto_vpmsumd(i1v, i2v);
80 auto z =
SIMD_4x32(
reinterpret_cast<__vector
unsigned int>(rv));
82 if constexpr(std::endian::native == std::endian::big) {