M5Utility 0.3.1 git rev:a8c5625
Loading...
Searching...
No Matches
endianness.hpp
Go to the documentation of this file.
1/*
2 * SPDX-FileCopyrightText: 2024 M5Stack Technology CO LTD
3 *
4 * SPDX-License-Identifier: MIT
5 */
10#ifndef M5_UTILITY_STL_ENDIANNESS_HPP
11#define M5_UTILITY_STL_ENDIANNESS_HPP
12
13#if __cplusplus >= 202002L
14// #pragma message("Using std::endian")
15#include <bit>
16#elif __has_include(<endian.h>)
17// #pragma message("Using endian.h")
18#include <endian.h>
19#elif __has_include(<machine/endian.h>)
20// #pragma message("Using machine/endian.h")
21#include <machine/endian.h>
22#else
23// #pragma message("Using hacked")
24#include <cstdint>
25#endif
26
27namespace m5 {
28namespace stl {
29
30// C++20 or later
31#if __cplusplus >= 202002L || DOXYGEN_PROCESS
32
33using endian = std::endian;
34
35// endian header
36#elif __has_include(<endian.h>) || __has_include(<machine/endian.h>)
37
38enum class endian {
39#if defined(__BYTE_ORDER)
40 little = __LITTLE_ENDIAN,
41 big = __BIG_ENDIAN,
42 native = __BYTE_ORDER
43#elif defined(_BYTE_ORDER)
44 little = _LITTLE_ENDIAN,
45 big = _BIG_ENDIAN,
46 native = _BYTE_ORDER
47#elif defined(BYTE_ORDER)
48 little = LITTLE_ENDIAN,
49 big = BIG_ENDIAN,
50 native = BYTE_ORDER
51#else
52 little = 0,
53 big = 0,
54 native = 0,
55#endif
56};
57
58#elif defined(__BYTE_ORDER__)
59
60enum class endian { little = __ORDER_LITTLE_ENDIAN__, big = __ORDER_BIG_ENDIAN__, native = __BYTE_ORDER__ };
61
62// MSVC defines none of the macros above, so say it outright: every target it
63// supports (x86, x64, ARM64) is little endian. Without this the runtime
64// detection below would be taken, and that one violates strict aliasing.
65#elif defined(_MSC_VER)
66
67enum class endian { little = 0, big = 1, native = little };
68
69#else
70#pragma message( \
71 "Cannot determine byte order at compile time. Falling back to runtime detection (strict aliasing violation).")
73constexpr uint32_t val32 = 0x11223344;
74constexpr uint8_t ref8 = static_cast<const uint8_t&>(val32);
76enum class endian { little = 0x44, big = 0x11, native = ref8 };
77#endif
78} // namespace stl
79
84namespace endian {
87constexpr bool little = m5::stl::endian::native == m5::stl::endian::little;
88constexpr bool big = m5::stl::endian::native == m5::stl::endian::big;
89constexpr bool other = !little && !big;
91
92static_assert(little || big || other, "Unable to determine endianness");
93static_assert(((int)little + (int)big + (int)other) == 1, "Endian matches more than one");
94} // namespace endian
95} // namespace m5
96
97#endif
constexpr bool little
true if little endian.
Definition endianness.hpp:87
constexpr bool other
true if other endian.
Definition endianness.hpp:89
constexpr bool big
true if big endian.
Definition endianness.hpp:88
endianness detection
Top level namespace of M5.
Definition base64.cpp:39
STL compatibility functions and classes.