Since C++20 we can have:
constexpr bool is_little_endian = std::endian::native == std::endian::little;
I would like to have code that does this if it is available, otherwise does runtime detection. Is this possible?
Maybe the code would look like:
template<bool b = std_endian_exists_v> constexpr bool is_little_endian;
template<> constexpr bool is_little_endian<true> = std::endian::native == std::endian::little;
template<> constexpr bool is_little_endian<false> = runtime_detection();
I am aware that testing __cplusplus
via preprocessor is possible, however compilers phase in C++20 support in various stages so this is not a reliable indicator in either direction.
I am aware that testing
__cplusplus
via preprocessor is possible, however compilers phase in C++20 support in various stages so this is not a reliable indicator in either direction.
Indeed! In fact, this is why we now have an entirely new method of detecting feature support for compilers that are in various stages of release: feature-test macros! If you look at SD-FeatureTest, there are large tables of macros corresponding to each language and library feature adopted into the standard, where each macro will be defined with the specified value once a feature is adopted.
In your specific case, you want __cpp_lib_endian
.
Now the problem with library macros is that we started added them before we added a place to put them - which would be <version>
. If you're on a compiler that has <version>
(which would be gcc 9+, clang 7+ with libc++, and I don't know about MSVC), you can just include that. But it might not, so you might also have to try to include the correct header (in this case <bit>
).
#if __has_include(<bit>)
# include <bit>
# ifdef __cpp_lib_endian
# define HAS_ENDIAN 1
# endif
#endif
#ifdef HAS_ENDIAN
constexpr bool is_little_endian = std::endian::native == std::endian::little;
#else
constexpr bool is_little_endian = /* ... figure it out ... */;
#endif
Although it might be better to do:
#ifdef HAS_ENDIAN
using my_endian = std::endian;
#else
enum class my_endian {
// copy some existing implementation
};
#endif
constexpr bool is_little_endian = my_endian::native == my_endian::little;
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With