diff --git a/c/common/platform.h b/c/common/platform.h index 84c448c..853fa83 100755 --- a/c/common/platform.h +++ b/c/common/platform.h @@ -213,6 +213,14 @@ #define BROTLI_TARGET_LOONGARCH64 #endif +#if defined(__s390x__) +#define BROTLI_TARGET_S390X +#endif + +#if defined(__mips64) +#define BROTLI_TARGET_MIPS64 +#endif + #if defined(BROTLI_TARGET_X64) || defined(BROTLI_TARGET_ARMV8_64) || \ defined(BROTLI_TARGET_POWERPC64) || defined(BROTLI_TARGET_RISCV64) || \ defined(BROTLI_TARGET_LOONGARCH64) @@ -285,22 +293,42 @@ /* Portable unaligned memory access: read / write values via memcpy. */ static BROTLI_INLINE uint16_t BrotliUnalignedRead16(const void* p) { +#if defined(__mips__) && (!defined(__mips_isa_rev) || __mips_isa_rev < 6) + const struct { uint16_t x; } __attribute__((__packed__)) *t = p; + return t->x; +#else uint16_t t; memcpy(&t, p, sizeof t); return t; +#endif } static BROTLI_INLINE uint32_t BrotliUnalignedRead32(const void* p) { +#if defined(__mips__) && (!defined(__mips_isa_rev) || __mips_isa_rev < 6) + const struct { uint32_t x; } __attribute__((__packed__)) *t = p; + return t->x; +#else uint32_t t; memcpy(&t, p, sizeof t); return t; +#endif } static BROTLI_INLINE uint64_t BrotliUnalignedRead64(const void* p) { +#if defined(__mips__) && (!defined(__mips_isa_rev) || __mips_isa_rev < 6) + const struct { uint64_t x; } __attribute__((__packed__)) *t = p; + return t->x; +#else uint64_t t; memcpy(&t, p, sizeof t); return t; +#endif } static BROTLI_INLINE void BrotliUnalignedWrite64(void* p, uint64_t v) { +#if defined(__mips__) && (!defined(__mips_isa_rev) || __mips_isa_rev < 6) + struct { uint64_t x; } __attribute__((__packed__)) *t = p; + t->x = v; +#else memcpy(p, &v, sizeof v); +#endif } #if BROTLI_LITTLE_ENDIAN @@ -311,31 +339,20 @@ #define BROTLI_UNALIGNED_STORE64LE BrotliUnalignedWrite64 #elif BROTLI_BIG_ENDIAN /* BROTLI_LITTLE_ENDIAN */ /* Explain compiler to byte-swap values. */ -#define BROTLI_BSWAP16_(V) ((uint16_t)( \ - (((V) & 0xFFU) << 8) | \ - (((V) >> 8) & 0xFFU))) static BROTLI_INLINE uint16_t BROTLI_UNALIGNED_LOAD16LE(const void* p) { uint16_t value = BrotliUnalignedRead16(p); - return BROTLI_BSWAP16_(value); + return __builtin_bswap16(value); } -#define BROTLI_BSWAP32_(V) ( \ - (((V) & 0xFFU) << 24) | (((V) & 0xFF00U) << 8) | \ - (((V) >> 8) & 0xFF00U) | (((V) >> 24) & 0xFFU)) static BROTLI_INLINE uint32_t BROTLI_UNALIGNED_LOAD32LE(const void* p) { uint32_t value = BrotliUnalignedRead32(p); - return BROTLI_BSWAP32_(value); + return __builtin_bswap32(value); } -#define BROTLI_BSWAP64_(V) ( \ - (((V) & 0xFFU) << 56) | (((V) & 0xFF00U) << 40) | \ - (((V) & 0xFF0000U) << 24) | (((V) & 0xFF000000U) << 8) | \ - (((V) >> 8) & 0xFF000000U) | (((V) >> 24) & 0xFF0000U) | \ - (((V) >> 40) & 0xFF00U) | (((V) >> 56) & 0xFFU)) static BROTLI_INLINE uint64_t BROTLI_UNALIGNED_LOAD64LE(const void* p) { uint64_t value = BrotliUnalignedRead64(p); - return BROTLI_BSWAP64_(value); + return __builtin_bswap64(value); } static BROTLI_INLINE void BROTLI_UNALIGNED_STORE64LE(void* p, uint64_t v) { - uint64_t value = BROTLI_BSWAP64_(v); + uint64_t value = __builtin_bswap64(v); BrotliUnalignedWrite64(p, value); } #else /* BROTLI_LITTLE_ENDIAN */