Всем привет!
Сейчас у меня такой код:
// Source.hpp
/**
* @brief Method that checks the endian type on the system.
* @return DATA_LITTLE_ENDIAN(0x02) - if on the system little endian, otherwise - DATA_BIG_ENDIAN(0x01).
*/
static inline DATA_ENDIAN_TYPE CheckSystemEndian(void) noexcept
{
const union {
const uint16_t value;
const uint8_t data[sizeof(uint16_t)];
} endian { 0x0102 };
return static_cast
Class Foo
{
static const DATA_ENDIAN_TYPE system_endian;
}
// Source.cpp
inline const DATA_ENDIAN_TYPE BinaryDataEngine::system_endian = CheckSystemEndian();
Что требуется:
Мне хочется решать эту задачу в compile-time, следовательно необходимо переделать функция CheckSystemEndian() на constexp. Однако в этой задаче мне очень мешает union
Ошибка следующая:
constexpr function never produces a constant expression.
Read of member 'data' of union with active member 'value' is not allowed in a constant expression.
Подсткажите, пожалуйста, способ, как можно добиться требуемой функциональности в compile-time.
Спасибо.
Ответ
Насколько я знаю, определить порядок байт (endianness) на этапе компиляции невозможно в принципе (стандартными средствами). Тут нужен reinterpret_cast, а он не считается constexpr выражением.
В С++20 для этого появится std::endian, и можно будет писать так:
#include
constexpr bool is_big_endian = std::endian::native == std::endian::big;
constexpr bool is_little_endian = std::endian::native == std::endian::little;
Дожидаясь С++20, можно использовать нестандартные фичи компиляторов. Например, GCC умеет так:
constexpr bool is_big_endian = __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__;
constexpr bool is_little_endian = __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__;
Кроме того, у вас в программе неопределенное поведение, ведь С++, в отличие от С, не позволяет читать из неактивного поля union'а. Пруф.
Вот пример, как можно исправить код:
static inline DATA_ENDIAN_TYPE CheckSystemEndian(void) noexcept
{
const uint16_t value = 0x0102;
return static_cast
К тому же, так он еще и места меньше занимает.
Комментариев нет:
Отправить комментарий