diff options
author | Cyrille Bagard <nocbos@gmail.com> | 2018-01-24 17:50:40 (GMT) |
---|---|---|
committer | Cyrille Bagard <nocbos@gmail.com> | 2018-01-24 17:51:11 (GMT) |
commit | 304445ae3f7a159be55fa91b95428251ef8a362e (patch) | |
tree | aa923090096e5d93a03ac262651d1fc622e7a60d /src/common | |
parent | f4c12b7fdc0482461f5c52161ea852c9d152cc4e (diff) |
Improved the support of some unusual endiannesses.
Diffstat (limited to 'src/common')
-rwxr-xr-x | src/common/endianness.c | 212 | ||||
-rwxr-xr-x | src/common/endianness.h | 4 |
2 files changed, 131 insertions, 85 deletions
diff --git a/src/common/endianness.c b/src/common/endianness.c index 4dcee22..3aeca00 100755 --- a/src/common/endianness.c +++ b/src/common/endianness.c @@ -24,11 +24,25 @@ #include "endianness.h" +#include <assert.h> #include <stdarg.h> #include <string.h> +/** + * Mutualisation des aiguillages... + */ + +#if __BYTE_ORDER != __LITTLE_ENDIAN && __BYTE_ORDER != __BIG_ENDIAN + + /* __PDP_ENDIAN et Cie... */ +# error "Congratulations! Your byte order is not supported!" + +#endif + + + /* ---------------------------------------------------------------------------------- */ /* CONVERSION ENTRE BOUTISMES */ /* ---------------------------------------------------------------------------------- */ @@ -63,18 +77,10 @@ uint16_t swap_u16(const uint16_t *value, SourceEndian endian) result = ((*value >> 0) & 0xff) << 8 | ((*value >> 8) & 0xff) << 0; -#else - -# error "TODO : PDP !" - #endif break; - case SRE_MIDDLE: - /* TODO */ - break; - case SRE_BIG: #if __BYTE_ORDER == __LITTLE_ENDIAN @@ -85,14 +91,13 @@ uint16_t swap_u16(const uint16_t *value, SourceEndian endian) result = *value; -#else - -# error "TODO : PDP !" - #endif break; + default: + assert(false); + break; } @@ -131,18 +136,10 @@ uint32_t swap_u32(const uint32_t *value, SourceEndian endian) result = ((*value >> 0) & 0xff) << 24 | ((*value >> 8) & 0xff) << 16 | ((*value >> 16) & 0xff) << 8 | ((*value >> 24) & 0xff) << 0; -#else - -# error "TODO : PDP !" - #endif break; - case SRE_MIDDLE: - /* TODO */ - break; - case SRE_BIG: #if __BYTE_ORDER == __LITTLE_ENDIAN @@ -154,14 +151,13 @@ uint32_t swap_u32(const uint32_t *value, SourceEndian endian) result = *value; -#else - -# error "TODO : PDP !" - #endif break; + default: + assert(false); + break; } @@ -202,18 +198,10 @@ uint64_t swap_u64(const uint64_t *value, SourceEndian endian) | ((*value >> 32) & 0xff) << 24 | ((*value >> 40) & 0xff) << 16 | ((*value >> 48) & 0xff) << 8 | ((*value >> 56) & 0xff) << 0; -#else - -# error "TODO : PDP !" - #endif break; - case SRE_MIDDLE: - /* TODO */ - break; - case SRE_BIG: #if __BYTE_ORDER == __LITTLE_ENDIAN @@ -227,14 +215,13 @@ uint64_t swap_u64(const uint64_t *value, SourceEndian endian) result = *value; -#else - -# error "TODO : PDP !" - #endif break; + default: + assert(false); + break; } @@ -349,16 +336,36 @@ bool read_u16(uint16_t *target, const bin_t *data, phys_t *pos, phys_t end, Sour *target = data[*pos + 1] | (uint16_t)data[*pos] << 8; -#else +#endif + + break; + + case SRE_LITTLE_WORD: + +#if __BYTE_ORDER == __LITTLE_ENDIAN -# error "TODO : PDP !" + *target = data[*pos] << 8 | (uint16_t)data[*pos + 1]; + +#elif __BYTE_ORDER == __BIG_ENDIAN + + *target = data[*pos + 1] << 8 | (uint16_t)data[*pos]; #endif break; - case SRE_MIDDLE: - /* TODO */ + case SRE_BIG_WORD: + +#if __BYTE_ORDER == __LITTLE_ENDIAN + + *target = data[*pos + 1] << 8 | (uint16_t)data[*pos]; + +#elif __BYTE_ORDER == __BIG_ENDIAN + + *target = data[*pos] << 8 | (uint16_t)data[*pos + 1]; + +#endif + break; case SRE_BIG: @@ -371,14 +378,13 @@ bool read_u16(uint16_t *target, const bin_t *data, phys_t *pos, phys_t end, Sour *target = data[*pos] | (uint16_t)data[*pos + 1] << 8; -#else - -# error "TODO : PDP !" - #endif break; + default: + return false; + break; } @@ -424,16 +430,40 @@ bool read_u32(uint32_t *target, const bin_t *data, phys_t *pos, phys_t end, Sour *target = data[*pos + 3] | (uint32_t)data[*pos + 2] << 8; *target |= data[*pos + 1] << 16 | (uint32_t)data[*pos] << 24; -#else +#endif + + break; + + case SRE_LITTLE_WORD: -# error "TODO : PDP !" +#if __BYTE_ORDER == __LITTLE_ENDIAN + + *target = data[*pos] << 8 | (uint32_t)data[*pos + 1]; + *target |= data[*pos + 2] << 24 | (uint32_t)data[*pos + 3] << 16; + +#elif __BYTE_ORDER == __BIG_ENDIAN + + *target = data[*pos + 3] << 8 | (uint32_t)data[*pos + 2]; + *target |= data[*pos + 1] << 24 | (uint32_t)data[*pos] << 16; #endif break; - case SRE_MIDDLE: - /* TODO */ + case SRE_BIG_WORD: + +#if __BYTE_ORDER == __LITTLE_ENDIAN + + *target = data[*pos + 3] << 8 | (uint32_t)data[*pos + 2]; + *target |= data[*pos + 1] << 24 | (uint32_t)data[*pos] << 16; + +#elif __BYTE_ORDER == __BIG_ENDIAN + + *target = data[*pos] << 8 | (uint32_t)data[*pos + 1]; + *target |= data[*pos + 2] << 24 | (uint32_t)data[*pos + 3] << 16; + +#endif + break; case SRE_BIG: @@ -448,14 +478,13 @@ bool read_u32(uint32_t *target, const bin_t *data, phys_t *pos, phys_t end, Sour *target = data[*pos] | (uint32_t)data[*pos + 1] << 8; *target |= data[*pos + 2] << 16 | (uint32_t)data[*pos + 3] << 24; -#else - -# error "TODO : PDP !" - #endif break; + default: + return false; + break; } @@ -505,16 +534,48 @@ bool read_u64(uint64_t *target, const bin_t *data, phys_t *pos, phys_t end, Sour *target |= (uint64_t)data[*pos + 3] << 32 | (uint64_t)data[*pos + 2] << 40; *target |= (uint64_t)data[*pos + 1] << 48 | (uint64_t)data[*pos] << 56; -#else +#endif + + break; + + case SRE_LITTLE_WORD: + +#if __BYTE_ORDER == __LITTLE_ENDIAN -# error "TODO : PDP !" + *target = (uint64_t)data[*pos] << 8 | (uint64_t)data[*pos + 1]; + *target |= (uint64_t)data[*pos + 2] << 24 | (uint64_t)data[*pos + 3] << 16; + *target |= (uint64_t)data[*pos + 4] << 40 | (uint64_t)data[*pos + 5] << 32; + *target |= (uint64_t)data[*pos + 6] << 56 | (uint64_t)data[*pos + 7] << 48; + +#elif __BYTE_ORDER == __BIG_ENDIAN + + *target = (uint64_t)data[*pos + 7] << 8 | (uint64_t)data[*pos + 6]; + *target |= (uint64_t)data[*pos + 5] << 24 | (uint64_t)data[*pos + 4] << 16; + *target |= (uint64_t)data[*pos + 3] << 40 | (uint64_t)data[*pos + 2] << 32; + *target |= (uint64_t)data[*pos + 1] << 56 | (uint64_t)data[*pos] << 48; #endif break; - case SRE_MIDDLE: - /* TODO */ + case SRE_BIG_WORD: + +#if __BYTE_ORDER == __LITTLE_ENDIAN + + *target = (uint64_t)data[*pos + 7] << 8 | (uint64_t)data[*pos + 6]; + *target |= (uint64_t)data[*pos + 5] << 24 | (uint64_t)data[*pos + 4] << 16; + *target |= (uint64_t)data[*pos + 3] << 40 | (uint64_t)data[*pos + 2] << 32; + *target |= (uint64_t)data[*pos + 1] << 56 | (uint64_t)data[*pos] << 48; + +#elif __BYTE_ORDER == __BIG_ENDIAN + + *target = (uint64_t)data[*pos] << 8| (uint64_t)data[*pos + 1]; + *target |= (uint64_t)data[*pos + 2] << 24 | (uint64_t)data[*pos + 3] << 16; + *target |= (uint64_t)data[*pos + 4] << 40 | (uint64_t)data[*pos + 5] << 32; + *target |= (uint64_t)data[*pos + 6] << 56 | (uint64_t)data[*pos + 7] << 48; + +#endif + break; case SRE_BIG: @@ -533,14 +594,13 @@ bool read_u64(uint64_t *target, const bin_t *data, phys_t *pos, phys_t end, Sour *target |= (uint64_t)data[*pos + 4] << 32 | (uint64_t)data[*pos + 5] << 40; *target |= (uint64_t)data[*pos + 6] << 48 | (uint64_t)data[*pos + 7] << 56; -#else - -# error "TODO : PDP !" - #endif break; + default: + return false; + break; } @@ -589,18 +649,10 @@ bool _write_un(const bin_t *value, size_t size, bin_t *data, off_t *pos, off_t e for (i = 0; i < size; i++, (*pos)++) *(data + *pos) = *(value + size - i - 1); -#else - -# error "TODO : PDP !" - #endif break; - case SRE_MIDDLE: - return false; /* TODO ! */ - break; - case SRE_BIG: #if __BYTE_ORDER == __LITTLE_ENDIAN @@ -613,14 +665,14 @@ bool _write_un(const bin_t *value, size_t size, bin_t *data, off_t *pos, off_t e memcpy(&data[*pos], value, size); (*pos) += size; -#else - -# error "TODO : PDP !" - #endif break; + default: + return false; + break; + } return true; @@ -785,18 +837,10 @@ bool _strtoun(uint8_t n, const char *data, size_t *pos, size_t end, SourceEndian *target64 |= ((uint64_t)tmp) << (8 * (n - 1 - i)); -#else - -# error "TODO : PDP !" - #endif break; - case SRE_MIDDLE: - /* TODO */ - break; - case SRE_BIG: #if __BYTE_ORDER == __LITTLE_ENDIAN @@ -807,14 +851,14 @@ bool _strtoun(uint8_t n, const char *data, size_t *pos, size_t end, SourceEndian *target64 |= ((uint64_t)tmp) << (8 * i); -#else - -# error "TODO : PDP !" - #endif break; + default: + return false; + break; + } } diff --git a/src/common/endianness.h b/src/common/endianness.h index 5ceb2ee..625b7fd 100755 --- a/src/common/endianness.h +++ b/src/common/endianness.h @@ -37,12 +37,14 @@ typedef enum _SourceEndian { SRE_LITTLE, /* Petits boutistes */ - SRE_MIDDLE, /* Moyens boutistes */ + SRE_LITTLE_WORD, /* Moyens, façon Honeywell */ + SRE_BIG_WORD, /* Moyens, façon PDP-11 */ SRE_BIG /* Gros boutistes */ } SourceEndian; + /* --------------------------- CONVERSION ENTRE BOUTISMES --------------------------- */ |