--- deliantra/Deliantra-Client/ecb.h 2020/01/11 02:10:03 1.3 +++ deliantra/Deliantra-Client/ecb.h 2020/11/12 03:04:54 1.4 @@ -1,7 +1,7 @@ /* * libecb - http://software.schmorp.de/pkg/libecb * - * Copyright (©) 2009-2015 Marc Alexander Lehmann + * Copyright (©) 2009-2015,2018-2020 Marc Alexander Lehmann * Copyright (©) 2011 Emanuele Giaquinta * All rights reserved. * @@ -42,15 +42,23 @@ #define ECB_H /* 16 bits major, 16 bits minor */ -#define ECB_VERSION 0x00010007 +#define ECB_VERSION 0x00010008 -#ifdef _WIN32 +#include /* for memcpy */ + +#if defined (_WIN32) && !defined (__MINGW32__) typedef signed char int8_t; typedef unsigned char uint8_t; + typedef signed char int_fast8_t; + typedef unsigned char uint_fast8_t; typedef signed short int16_t; typedef unsigned short uint16_t; + typedef signed int int_fast16_t; + typedef unsigned int uint_fast16_t; typedef signed int int32_t; typedef unsigned int uint32_t; + typedef signed int int_fast32_t; + typedef unsigned int uint_fast32_t; #if __GNUC__ typedef signed long long int64_t; typedef unsigned long long uint64_t; @@ -58,6 +66,8 @@ typedef signed __int64 int64_t; typedef unsigned __int64 uint64_t; #endif + typedef int64_t int_fast64_t; + typedef uint64_t uint_fast64_t; #ifdef _WIN64 #define ECB_PTRSIZE 8 typedef uint64_t uintptr_t; @@ -602,6 +612,44 @@ ecb_inline ecb_const uint64_t ecb_rotl64 (uint64_t x, unsigned int count) { return (x >> (64 - count)) | (x << count); } ecb_inline ecb_const uint64_t ecb_rotr64 (uint64_t x, unsigned int count) { return (x << (64 - count)) | (x >> count); } +#if ECB_CPP + +inline uint8_t ecb_ctz (uint8_t v) { return ecb_ctz32 (v); } +inline uint16_t ecb_ctz (uint16_t v) { return ecb_ctz32 (v); } +inline uint32_t ecb_ctz (uint32_t v) { return ecb_ctz32 (v); } +inline uint64_t ecb_ctz (uint64_t v) { return ecb_ctz64 (v); } + +inline bool ecb_is_pot (uint8_t v) { return ecb_is_pot32 (v); } +inline bool ecb_is_pot (uint16_t v) { return ecb_is_pot32 (v); } +inline bool ecb_is_pot (uint32_t v) { return ecb_is_pot32 (v); } +inline bool ecb_is_pot (uint64_t v) { return ecb_is_pot64 (v); } + +inline int ecb_ld (uint8_t v) { return ecb_ld32 (v); } +inline int ecb_ld (uint16_t v) { return ecb_ld32 (v); } +inline int ecb_ld (uint32_t v) { return ecb_ld32 (v); } +inline int ecb_ld (uint64_t v) { return ecb_ld64 (v); } + +inline int ecb_popcount (uint8_t v) { return ecb_popcount32 (v); } +inline int ecb_popcount (uint16_t v) { return ecb_popcount32 (v); } +inline int ecb_popcount (uint32_t v) { return ecb_popcount32 (v); } +inline int ecb_popcount (uint64_t v) { return ecb_popcount64 (v); } + +inline uint8_t ecb_bitrev (uint8_t v) { return ecb_bitrev8 (v); } +inline uint16_t ecb_bitrev (uint16_t v) { return ecb_bitrev16 (v); } +inline uint32_t ecb_bitrev (uint32_t v) { return ecb_bitrev32 (v); } + +inline uint8_t ecb_rotl (uint8_t v, unsigned int count) { return ecb_rotl8 (v, count); } +inline uint16_t ecb_rotl (uint16_t v, unsigned int count) { return ecb_rotl16 (v, count); } +inline uint32_t ecb_rotl (uint32_t v, unsigned int count) { return ecb_rotl32 (v, count); } +inline uint64_t ecb_rotl (uint64_t v, unsigned int count) { return ecb_rotl64 (v, count); } + +inline uint8_t ecb_rotr (uint8_t v, unsigned int count) { return ecb_rotr8 (v, count); } +inline uint16_t ecb_rotr (uint16_t v, unsigned int count) { return ecb_rotr16 (v, count); } +inline uint32_t ecb_rotr (uint32_t v, unsigned int count) { return ecb_rotr32 (v, count); } +inline uint64_t ecb_rotr (uint64_t v, unsigned int count) { return ecb_rotr64 (v, count); } + +#endif + #if ECB_GCC_VERSION(4,3) || (ECB_CLANG_BUILTIN(__builtin_bswap32) && ECB_CLANG_BUILTIN(__builtin_bswap64)) #if ECB_GCC_VERSION(4,8) || ECB_CLANG_BUILTIN(__builtin_bswap16) #define ecb_bswap16(x) __builtin_bswap16 (x) @@ -682,7 +730,81 @@ ecb_inline ecb_const ecb_bool ecb_little_endian (void); ecb_inline ecb_const ecb_bool ecb_little_endian (void) { return ecb_byteorder_helper () == 0x44332211; } +/*****************************************************************************/ +/* unaligned load/store */ + +ecb_inline uint_fast16_t ecb_be_u16_to_host (uint_fast16_t v) { return ecb_little_endian () ? ecb_bswap16 (v) : v; } +ecb_inline uint_fast32_t ecb_be_u32_to_host (uint_fast32_t v) { return ecb_little_endian () ? ecb_bswap32 (v) : v; } +ecb_inline uint_fast64_t ecb_be_u64_to_host (uint_fast64_t v) { return ecb_little_endian () ? ecb_bswap64 (v) : v; } + +ecb_inline uint_fast16_t ecb_le_u16_to_host (uint_fast16_t v) { return ecb_big_endian () ? ecb_bswap16 (v) : v; } +ecb_inline uint_fast32_t ecb_le_u32_to_host (uint_fast32_t v) { return ecb_big_endian () ? ecb_bswap32 (v) : v; } +ecb_inline uint_fast64_t ecb_le_u64_to_host (uint_fast64_t v) { return ecb_big_endian () ? ecb_bswap64 (v) : v; } + +ecb_inline uint_fast16_t ecb_peek_u16_u (const void *ptr) { uint16_t v; memcpy (&v, ptr, sizeof (v)); return v; } +ecb_inline uint_fast32_t ecb_peek_u32_u (const void *ptr) { uint32_t v; memcpy (&v, ptr, sizeof (v)); return v; } +ecb_inline uint_fast64_t ecb_peek_u64_u (const void *ptr) { uint64_t v; memcpy (&v, ptr, sizeof (v)); return v; } + +ecb_inline uint_fast16_t ecb_peek_be_u16_u (const void *ptr) { return ecb_be_u16_to_host (ecb_peek_u16_u (ptr)); } +ecb_inline uint_fast32_t ecb_peek_be_u32_u (const void *ptr) { return ecb_be_u32_to_host (ecb_peek_u32_u (ptr)); } +ecb_inline uint_fast64_t ecb_peek_be_u64_u (const void *ptr) { return ecb_be_u64_to_host (ecb_peek_u64_u (ptr)); } + +ecb_inline uint_fast16_t ecb_peek_le_u16_u (const void *ptr) { return ecb_le_u16_to_host (ecb_peek_u16_u (ptr)); } +ecb_inline uint_fast32_t ecb_peek_le_u32_u (const void *ptr) { return ecb_le_u32_to_host (ecb_peek_u32_u (ptr)); } +ecb_inline uint_fast64_t ecb_peek_le_u64_u (const void *ptr) { return ecb_le_u64_to_host (ecb_peek_u64_u (ptr)); } + +ecb_inline uint_fast16_t ecb_host_to_be_u16 (uint_fast16_t v) { return ecb_little_endian () ? ecb_bswap16 (v) : v; } +ecb_inline uint_fast32_t ecb_host_to_be_u32 (uint_fast32_t v) { return ecb_little_endian () ? ecb_bswap32 (v) : v; } +ecb_inline uint_fast64_t ecb_host_to_be_u64 (uint_fast64_t v) { return ecb_little_endian () ? ecb_bswap64 (v) : v; } + +ecb_inline uint_fast16_t ecb_host_to_le_u16 (uint_fast16_t v) { return ecb_big_endian () ? ecb_bswap16 (v) : v; } +ecb_inline uint_fast32_t ecb_host_to_le_u32 (uint_fast32_t v) { return ecb_big_endian () ? ecb_bswap32 (v) : v; } +ecb_inline uint_fast64_t ecb_host_to_le_u64 (uint_fast64_t v) { return ecb_big_endian () ? ecb_bswap64 (v) : v; } + +ecb_inline void ecb_poke_u16_u (void *ptr, uint16_t v) { memcpy (ptr, &v, sizeof (v)); } +ecb_inline void ecb_poke_u32_u (void *ptr, uint32_t v) { memcpy (ptr, &v, sizeof (v)); } +ecb_inline void ecb_poke_u64_u (void *ptr, uint64_t v) { memcpy (ptr, &v, sizeof (v)); } + +ecb_inline void ecb_poke_be_u16_u (void *ptr, uint_fast16_t v) { ecb_poke_u16_u (ptr, ecb_host_to_be_u16 (v)); } +ecb_inline void ecb_poke_be_u32_u (void *ptr, uint_fast32_t v) { ecb_poke_u32_u (ptr, ecb_host_to_be_u32 (v)); } +ecb_inline void ecb_poke_be_u64_u (void *ptr, uint_fast64_t v) { ecb_poke_u64_u (ptr, ecb_host_to_be_u64 (v)); } + +ecb_inline void ecb_poke_le_u16_u (void *ptr, uint_fast16_t v) { ecb_poke_u16_u (ptr, ecb_host_to_le_u16 (v)); } +ecb_inline void ecb_poke_le_u32_u (void *ptr, uint_fast32_t v) { ecb_poke_u32_u (ptr, ecb_host_to_le_u32 (v)); } +ecb_inline void ecb_poke_le_u64_u (void *ptr, uint_fast64_t v) { ecb_poke_u64_u (ptr, ecb_host_to_le_u64 (v)); } + +#if ECB_CPP + +inline uint8_t ecb_bswap (uint8_t v) { return v; } +inline uint16_t ecb_bswap (uint16_t v) { return ecb_bswap16 (v); } +inline uint32_t ecb_bswap (uint32_t v) { return ecb_bswap32 (v); } +inline uint64_t ecb_bswap (uint64_t v) { return ecb_bswap64 (v); } + +template inline T ecb_be_to_host (T v) { return ecb_little_endian () ? ecb_bswap (v) : v; } +template inline T ecb_le_to_host (T v) { return ecb_big_endian () ? ecb_bswap (v) : v; } +template inline T ecb_peek (const void *ptr) { return *(const T *)ptr; } +template inline T ecb_peek_be (const void *ptr) { return ecb_be_to_host (ecb_peek (ptr)); } +template inline T ecb_peek_le (const void *ptr) { return ecb_le_to_host (ecb_peek (ptr)); } +template inline T ecb_peek_u (const void *ptr) { T v; memcpy (&v, ptr, sizeof (v)); return v; } +template inline T ecb_peek_be_u (const void *ptr) { return ecb_be_to_host (ecb_peek_u (ptr)); } +template inline T ecb_peek_le_u (const void *ptr) { return ecb_le_to_host (ecb_peek_u (ptr)); } + +template inline T ecb_host_to_be (T v) { return ecb_little_endian () ? ecb_bswap (v) : v; } +template inline T ecb_host_to_le (T v) { return ecb_big_endian () ? ecb_bswap (v) : v; } +template inline void ecb_poke (void *ptr, T v) { *(T *)ptr = v; } +template inline void ecb_poke_be (void *ptr, T v) { return ecb_poke (ptr, ecb_host_to_be (v)); } +template inline void ecb_poke_le (void *ptr, T v) { return ecb_poke (ptr, ecb_host_to_le (v)); } +template inline void ecb_poke_u (void *ptr, T v) { memcpy (ptr, &v, sizeof (v)); } +template inline void ecb_poke_be_u (void *ptr, T v) { return ecb_poke_u (ptr, ecb_host_to_be (v)); } +template inline void ecb_poke_le_u (void *ptr, T v) { return ecb_poke_u (ptr, ecb_host_to_le (v)); } + +#endif + +/*****************************************************************************/ +/* division */ + #if ECB_GCC_VERSION(3,0) || ECB_C99 + /* C99 tightened the definition of %, so we can use a more efficient version */ #define ecb_mod(m,n) ((m) % (n) + ((m) % (n) < 0 ? (n) : 0)) #else #define ecb_mod(m,n) ((m) < 0 ? ((n) - 1 - ((-1 - (m)) % (n))) : ((m) % (n))) @@ -704,6 +826,9 @@ #define ecb_div_ru(val,div) ((val) < 0 ? - ((-(val) ) / (div)) : ((val) + (div) - 1) / (div)) #endif +/*****************************************************************************/ +/* array length */ + #if ecb_cplusplus_does_not_suck /* does not work for local types (http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2008/n2657.htm) */ template @@ -715,6 +840,9 @@ #define ecb_array_length(name) (sizeof (name) / sizeof (name [0])) #endif +/*****************************************************************************/ +/* IEEE 754-2008 half float conversions */ + ecb_function_ ecb_const uint32_t ecb_binary16_to_binary32 (uint32_t x); ecb_function_ ecb_const uint32_t ecb_binary16_to_binary32 (uint32_t x) @@ -832,7 +960,6 @@ || (defined __arm__ && (defined __ARM_EABI__ || defined __EABI__ || defined __VFP_FP__ || defined _WIN32_WCE || defined __ANDROID__)) \ || defined __aarch64__ #define ECB_STDFP 1 - #include /* for memcpy */ #else #define ECB_STDFP 0 #endif