1
0

endian.h 6.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296
  1. #ifndef __endian_h
  2. #define __endian_h
  3. #ifndef CONFIG
  4. #define CONFIG "config.h"
  5. #endif // CONFIG
  6. #include CONFIG
  7. //
  8. // Unaligned access
  9. //
  10. #define UAA16(p, i) (((PACKED16*)p)->val[i])
  11. #define UAA32(p, i) (((PACKED32*)p)->val[i])
  12. #define UAA64(p, i) (((PACKED64*)p)->val[i])
  13. #define UA64(p) UAA64(p, 0)
  14. #define UA32(p) UAA32(p, 0)
  15. #define UA16(p) UAA16(p, 0)
  16. //
  17. //Byteswap: Use compiler support if available
  18. //
  19. #ifdef __has_builtin // Clang supports this
  20. #if __has_builtin(__builtin_bswap16)
  21. #define BS16(x) __builtin_bswap16(x)
  22. #endif
  23. #if __has_builtin(__builtin_bswap32)
  24. #define BS32(x) __builtin_bswap32(x)
  25. #endif
  26. #if __has_builtin(__builtin_bswap64)
  27. #define BS64(x) __builtin_bswap64(x)
  28. #endif
  29. #endif // has_builtin
  30. #ifdef __GNUC__ // GNU C >= 4.3 has bswap32 and bswap64. GNU C >= 4.8 also has bswap16
  31. #if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ > 2)
  32. #ifndef BS32
  33. #define BS32(x) __builtin_bswap32(x)
  34. #endif
  35. #ifndef BS64
  36. #define BS64(x) __builtin_bswap64(x)
  37. #endif
  38. #if (__GNUC__ > 4) || (__GNUC_MINOR__ > 7)
  39. #ifndef BS16
  40. #define BS16(x) __builtin_bswap16(x)
  41. #endif
  42. #endif // GNU C > 4.7
  43. #endif // __GNUC__ > 4
  44. #endif // __GNUC__
  45. //
  46. // Byteorder
  47. //
  48. #if defined(__linux__) || defined(__GLIBC__) || defined(__CYGWIN__)
  49. #include <endian.h>
  50. #include <byteswap.h>
  51. #ifndef BS16
  52. #define BS16(x) bswap_16(x)
  53. #endif
  54. #ifndef BS32
  55. #define BS32(x) bswap_32(x)
  56. #endif
  57. #ifndef BS64
  58. #define BS64(x) bswap_64(x)
  59. #endif
  60. #elif defined(__sun__)
  61. #include <sys/byteorder.h>
  62. #ifndef BS16
  63. #define BS16(x) BSWAP_16(x)
  64. #endif
  65. #ifndef BS32
  66. #define BS32(x) BSWAP_32(x)
  67. #endif
  68. #ifndef BS64
  69. #define BS64(x) BSWAP_64(x)
  70. #endif
  71. #define __LITTLE_ENDIAN 1234
  72. #define __BIG_ENDIAN 4321
  73. #ifdef _LITTLE_ENDIAN
  74. #define __BYTE_ORDER __LITTLE_ENDIAN
  75. #else
  76. #define __BYTE_ORDER __BIG_ENDIAN
  77. #endif
  78. #elif __minix__ || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__DragonFly__) || defined(__OpenBSD__)
  79. #include <sys/types.h>
  80. #include <sys/endian.h>
  81. #define __BYTE_ORDER _BYTE_ORDER
  82. #define __LITTLE_ENDIAN _LITTLE_ENDIAN
  83. #define __BIG_ENDIAN _BIG_ENDIAN
  84. #ifdef __OpenBSD__
  85. #ifndef BS16
  86. #define BS16 swap16
  87. #endif
  88. #ifndef BS32
  89. #define BS32 swap32
  90. #endif
  91. #ifndef BS64
  92. #define BS64 swap64
  93. #endif
  94. #else // !__OpenBSD__
  95. #ifndef BS16
  96. #define BS16 bswap16
  97. #endif
  98. #ifndef BS32
  99. #define BS32 bswap32
  100. #endif
  101. #ifndef BS64
  102. #define BS64 bswap64
  103. #endif
  104. #endif // !__OpenBSD__
  105. #elif defined(__APPLE__)
  106. #include <sys/types.h>
  107. #include <machine/endian.h>
  108. #include <libkern/OSByteOrder.h>
  109. #define __BYTE_ORDER _BYTE_ORDER
  110. #define __LITTLE_ENDIAN _LITTLE_ENDIAN
  111. #define __BIG_ENDIAN _BIG_ENDIAN
  112. #ifndef BS16
  113. #define BS16 OSSwapInt16
  114. #endif
  115. #ifndef BS32
  116. #define BS32 OSSwapInt32
  117. #endif
  118. #ifndef BS64
  119. #define BS64 OSSwapInt64
  120. #endif
  121. #elif defined(_WIN32)
  122. #define __LITTLE_ENDIAN 1234
  123. #define __BIG_ENDIAN 4321
  124. #define __BYTE_ORDER __LITTLE_ENDIAN
  125. #include <stdlib.h>
  126. #ifndef BS16
  127. #define BS16 _byteswap_ushort
  128. #endif
  129. #ifndef BS32
  130. #define BS32 _byteswap_ulong
  131. #endif
  132. #ifndef BS64
  133. #define BS64 _byteswap_uint64
  134. #endif
  135. #endif // Byteorder in different OS
  136. #if defined(__BYTE_ORDER) && defined(__BIG_ENDIAN) && defined(__LITTLE_ENDIAN) \
  137. && defined(BS16) && defined(BS32) && defined(BS64)
  138. #if __BYTE_ORDER == __LITTLE_ENDIAN
  139. #define __BE16(x) BS16(x)
  140. #define __LE16(x) (x)
  141. #define __BE32(x) BS32(x)
  142. #define __LE32(x) (x)
  143. #define __BE64(x) BS64(x)
  144. #define __LE64(x) (x)
  145. #else // __BYTE_ORDER == __BIG_ENDIAN
  146. #define __BE16(x) (x)
  147. #define __LE16(x) BS16(x)
  148. #define __BE32(x) (x)
  149. #define __LE32(x) BS32(x)
  150. #define __BE64(x) (x)
  151. #define __LE64(x) BS64(x)
  152. #endif // __BYTE_ORDER
  153. #define PUT_UAA64BE(p, v, i) ( UAA64(p, i) = __BE64(v) )
  154. #define PUT_UAA32BE(p, v, i) ( UAA32(p, i) = __BE32(v) )
  155. #define PUT_UAA16BE(p, v, i) ( UAA16(p, i) = __BE16(v) )
  156. #define PUT_UAA64LE(p, v, i) ( UAA64(p, i) = __LE64(v) )
  157. #define PUT_UAA32LE(p, v, i) ( UAA32(p, i) = __LE32(v) )
  158. #define PUT_UAA16LE(p, v, i) ( UAA16(p, i) = __LE16(v) )
  159. #define GET_UAA64BE(p, i) __BE64(UAA64(p, i))
  160. #define GET_UAA32BE(p, i) __BE32(UAA32(p, i))
  161. #define GET_UAA16BE(p, i) __BE16(UAA16(p, i))
  162. #define GET_UAA64LE(p, i) __LE64(UAA64(p, i))
  163. #define GET_UAA32LE(p, i) __LE32(UAA32(p, i))
  164. #define GET_UAA16LE(p, i) __LE16(UAA16(p, i))
  165. #define BE16(x) __BE16(x)
  166. #define LE16(x) __LE16(x)
  167. #define BE32(x) __BE32(x)
  168. #define LE32(x) __LE32(x)
  169. #define BE64(x) __BE64(x)
  170. #define LE64(x) __LE64(x)
  171. #else // ! defined(__BYTE_ORDER)
  172. extern void PUT_UAA64BE(void *p, unsigned long long v, unsigned int i);
  173. extern void PUT_UAA32BE(void *p, unsigned int v, unsigned int i);
  174. extern void PUT_UAA16BE(void *p, unsigned short v, unsigned int i);
  175. extern void PUT_UAA64LE(void *p, unsigned long long v, unsigned int i);
  176. extern void PUT_UAA32LE(void *p, unsigned int v, unsigned int i);
  177. extern void PUT_UAA16LE(void *p, unsigned short v, unsigned int i);
  178. extern unsigned long long GET_UAA64BE(void *p, unsigned int i);
  179. extern unsigned int GET_UAA32BE(void *p, unsigned int i);
  180. extern unsigned short GET_UAA16BE(void *p, unsigned int i);
  181. extern unsigned long long GET_UAA64LE(void *p, unsigned int i);
  182. extern unsigned int GET_UAA32LE(void *p, unsigned int i);
  183. extern unsigned short GET_UAA16LE(void *p, unsigned int i);
  184. extern unsigned short BE16(unsigned short x);
  185. extern unsigned short LE16(unsigned short x);
  186. extern unsigned int BE32(unsigned int x);
  187. extern unsigned int LE32(unsigned int x);
  188. extern unsigned long long BE64(unsigned long long x);
  189. extern unsigned long long LE64(unsigned long long x);
  190. #endif // defined(__BYTE_ORDER)
  191. #define PUT_UA64BE(p, v) PUT_UAA64BE(p, v, 0)
  192. #define PUT_UA32BE(p, v) PUT_UAA32BE(p, v, 0)
  193. #define PUT_UA16BE(p, v) PUT_UAA16BE(p, v, 0)
  194. #define PUT_UA64LE(p, v) PUT_UAA64LE(p, v, 0)
  195. #define PUT_UA32LE(p, v) PUT_UAA32LE(p, v, 0)
  196. #define PUT_UA16LE(p, v) PUT_UAA16LE(p, v, 0)
  197. #define GET_UA64BE(p) GET_UAA64BE(p, 0)
  198. #define GET_UA32BE(p) GET_UAA32BE(p, 0)
  199. #define GET_UA16BE(p) GET_UAA16BE(p, 0)
  200. #define GET_UA64LE(p) GET_UAA64LE(p, 0)
  201. #define GET_UA32LE(p) GET_UAA32LE(p, 0)
  202. #define GET_UA16LE(p) GET_UAA16LE(p, 0)
  203. #endif // __endian_h