byteswap.h
1 // Copyright (c) 2014-present The Bitcoin Core developers 2 // Distributed under the MIT software license, see the accompanying 3 // file COPYING or http://www.opensource.org/licenses/mit-license.php. 4 5 #ifndef BITCOIN_COMPAT_BYTESWAP_H 6 #define BITCOIN_COMPAT_BYTESWAP_H 7 8 #include <cstdint> 9 #ifdef _MSC_VER 10 #include <cstdlib> 11 #endif 12 13 14 // All internal_bswap_* functions can be replaced with std::byteswap once we 15 // require c++23. Both libstdc++ and libc++ implement std::byteswap via these 16 // builtins. 17 18 #ifndef DISABLE_BUILTIN_BSWAPS 19 # if defined __has_builtin 20 # if __has_builtin(__builtin_bswap16) 21 # define bitcoin_builtin_bswap16(x) __builtin_bswap16(x) 22 # endif 23 # if __has_builtin(__builtin_bswap32) 24 # define bitcoin_builtin_bswap32(x) __builtin_bswap32(x) 25 # endif 26 # if __has_builtin(__builtin_bswap64) 27 # define bitcoin_builtin_bswap64(x) __builtin_bswap64(x) 28 # endif 29 # elif defined(_MSC_VER) 30 # define bitcoin_builtin_bswap16(x) _byteswap_ushort(x) 31 # define bitcoin_builtin_bswap32(x) _byteswap_ulong(x) 32 # define bitcoin_builtin_bswap64(x) _byteswap_uint64(x) 33 # endif 34 #endif 35 36 // MSVC's _byteswap_* functions are not constexpr 37 38 #ifndef _MSC_VER 39 #define BSWAP_CONSTEXPR constexpr 40 #else 41 #define BSWAP_CONSTEXPR 42 #endif 43 44 inline BSWAP_CONSTEXPR uint16_t internal_bswap_16(uint16_t x) 45 { 46 #ifdef bitcoin_builtin_bswap16 47 return bitcoin_builtin_bswap16(x); 48 #else 49 return (x >> 8) | (x << 8); 50 #endif 51 } 52 53 inline BSWAP_CONSTEXPR uint32_t internal_bswap_32(uint32_t x) 54 { 55 #ifdef bitcoin_builtin_bswap32 56 return bitcoin_builtin_bswap32(x); 57 #else 58 return (((x & 0xff000000U) >> 24) | ((x & 0x00ff0000U) >> 8) | 59 ((x & 0x0000ff00U) << 8) | ((x & 0x000000ffU) << 24)); 60 #endif 61 } 62 63 inline BSWAP_CONSTEXPR uint64_t internal_bswap_64(uint64_t x) 64 { 65 #ifdef bitcoin_builtin_bswap64 66 return bitcoin_builtin_bswap64(x); 67 #else 68 return (((x & 0xff00000000000000ull) >> 56) 69 | ((x & 0x00ff000000000000ull) >> 40) 70 | ((x & 0x0000ff0000000000ull) >> 24) 71 | ((x & 0x000000ff00000000ull) >> 8) 72 | ((x & 0x00000000ff000000ull) << 8) 73 | ((x & 0x0000000000ff0000ull) << 24) 74 | ((x & 0x000000000000ff00ull) << 40) 75 | ((x & 0x00000000000000ffull) << 56)); 76 #endif 77 } 78 79 #endif // BITCOIN_COMPAT_BYTESWAP_H