How do I convert between big-endian and little-endian values in C++? I'm using VC++ 6.0.when I used _byteswap_ulong() function it requires the header file intrin.h. When I include the header it reports an error saying incompatible compiler and that intrin.h is for the gcc compiler. So is there any other functions to convert between big-endian and little-endian values in VC++ other than this function?
Asked
Active
Viewed 1.0k times
2
-
Why does gcc's error matter if you're asking for a way to do it in VC++? Anyway, _byteswap_ulong is not a standard function. – jalf Mar 15 '09 at 17:29
2 Answers
10
In POSIX-compliant systems, you have the standard byteswap(3) functions:
#include <arpa/inet.h>
uint32_t htonl(uint32_t hostlong);
uint16_t htons(uint16_t hostshort);
uint32_t ntohl(uint32_t netlong);
uint16_t ntohs(uint16_t netshort);
These are intended specifically for network use, as suggested by the name (host-to-network-long, host-to-network-short, etc.)
GNU and BSD systems also provide the endian(3) functions:
#define _BSD_SOURCE
#include <endian.h>
uint16_t htobe16(uint16_t host_16bits);
uint16_t htole16(uint16_t host_16bits);
uint16_t be16toh(uint16_t big_endian_16bits);
uint16_t le16toh(uint16_t little_endian_16bits);
uint32_t htobe32(uint32_t host_32bits);
uint32_t htole32(uint32_t host_32bits);
uint32_t be32toh(uint32_t big_endian_32bits);
uint32_t le32toh(uint32_t little_endian_32bits);
uint64_t htobe64(uint64_t host_64bits);
uint64_t htole64(uint64_t host_64bits);
uint64_t be64toh(uint64_t big_endian_64bits);
uint64_t le64toh(uint64_t little_endian_64bits);
(On OpenBSD, the number for bit width is always at the end of the function: be64toh() vs. betoh64(), for example.)
Otherwise, most people define their own macros or functions:
#define bswap16(x) ((x)>>8 | ((x)&255)<<8)
#deinfe bswap32(x) ((bswap16((x)>>16)&65535)|(bswap16((x)&65535)<<16))
/* etc. */
You can also use assembly intrinsics, like with the bswap instruction on x86. __builtin_bswap64
in GCC and ICC. Something similar is in VS since VS7.0.

greyfade
- 24,948
- 7
- 64
- 80
-
+1, but I don't think you need to use intrinsics because they are used automatically when you use the library functions. – Jason Cohen Mar 15 '09 at 17:54
-
I don't rely on that. I realize some toolchains are smart enough to do it, but I still never see a compiler turn a fsqrt() call into the 3-instruction SSE equivalent. – greyfade Mar 15 '09 at 17:59
-
greyfade: It depends. VC++ has an option to use intrinsics for built-in functions. And of course, you need to target a platform that supports SSE. GCC has similar options. But of course, if you don't specify to the compiler that SSE is available, it won't be used. – jalf Mar 15 '09 at 18:19
-
Oh, I know this. But even GCC with an appropriate -march switch still sometimes doesn't optimize it that way. (Or, rather, at least not since before GCC 4. I haven't done much experimenting lately. I simply don't rely on it.) – greyfade Mar 15 '09 at 18:51
1
The Docs seem to say these functions live in stdlib.h.

Logan Capaldo
- 39,555
- 5
- 63
- 78
-
1anything starting with an underscore is non-standard by definition. – Evan Teran Mar 15 '09 at 18:18
-
1I don't think he was asking for a standard way, he was asking for a way in VC++, unless I am wildly mistaken? – Logan Capaldo Mar 15 '09 at 18:48