24#define ALIGNAS_SSE alignas(SSE_ALIGNMENT)
30template<
typename T> [[nodiscard]]
static ALWAYS_INLINE T unalignedLoad(
const void* p)
33 memcpy(&
t, p,
sizeof(
t));
38 memcpy(p, &
t,
sizeof(
t));
42 return unalignedLoad<uint16_t>(p);
45 return unalignedLoad<uint32_t>(p);
48 return unalignedLoad<uint64_t>(p);
73# define __has_builtin(x) 0
77#if defined(__GNUC__) && defined(__GNUC_MINOR__)
78# define GNUC_PREREQ(maj, min) \
79 (((maj) * 100 + (min)) <= (__GNUC__ * 100 + __GNUC_MINOR__))
81# define GNUC_PREREQ(maj, min) 0
84template<
size_t A,
typename T>
88 assert((std::bit_cast<uintptr_t>(ptr) % A) == 0);
91#if __has_builtin(__builtin_assume_aligned) || GNUC_PREREQ(4, 7)
92 ptr =
static_cast<T* __restrict
>(__builtin_assume_aligned(ptr, A));
98template<
typename T>
static ALWAYS_INLINE void assume_SSE_aligned(
100 T* __restrict & ptr) { assume_aligned<16>(ptr); }
102 T* __restrict & ) { }
ALWAYS_INLINE uint64_t unalignedLoad64(const void *p)
ALWAYS_INLINE void unalignedStore64(void *p, uint64_t v)
ALWAYS_INLINE uint16_t unalignedLoad16(const void *p)
constexpr size_t SSE_ALIGNMENT
ALWAYS_INLINE void unalignedStore16(void *p, uint16_t v)
ALWAYS_INLINE void unalignedStore32(void *p, uint32_t v)
ALWAYS_INLINE uint32_t unalignedLoad32(const void *p)