没有 htonl/ntohl 的联合和字节顺序
Union and endianness without htonl/ntohl
我想解析我收到的 header TCP 包。
假设这是一个 header 结构:
(2 bytes for commands) + (2 bytes for token) + (4 bytes for data length)
Example of package: 0x01 0x02 0x12 0x34 0x00 0x00 0x00 0x05
There 0x0102 is command, 0x1234 is token and 0x000005 is data length.
我想在 Windows 平台上以有效的方式解析此 header。我为此 header 创建了下一个联合:
typedef union
{
struct
{
uint16_t command;
uint16_t token;
uint32_t data_length;
} field;
char bytes[8];
} MyHeader_t;
MyHeader_t bar;
read_8_bytes(bar.bytes);
std::cout << bar.fields.token << std::endl;
接下来我尝试将上面的包复制到我的 bytes
数组。但是网络包是大字节序的,PC 试图以小字节序读取字段。结果,我的 token
字段等于 0x3412
(而不是 0x1234)。
如何使用单独的字节序避免此问题?
Boost 提供了一个专用于字节顺序的库:
http://www.boost.org/doc/libs/1_61_0/libs/endian/doc/index.html
例如:
boost::endian::big_to_native_inplace(bar.field.command);
或 AndyG:
std::cout << boost::endian::endian_reverse(bar.field.token) << std::endl;
注意:这个库有 3 种处理字节序的方法,你需要花时间选择适合你的情况。
我想解析我收到的 header TCP 包。
假设这是一个 header 结构:
(2 bytes for commands) + (2 bytes for token) + (4 bytes for data length)
Example of package: 0x01 0x02 0x12 0x34 0x00 0x00 0x00 0x05
There 0x0102 is command, 0x1234 is token and 0x000005 is data length.
我想在 Windows 平台上以有效的方式解析此 header。我为此 header 创建了下一个联合:
typedef union
{
struct
{
uint16_t command;
uint16_t token;
uint32_t data_length;
} field;
char bytes[8];
} MyHeader_t;
MyHeader_t bar;
read_8_bytes(bar.bytes);
std::cout << bar.fields.token << std::endl;
接下来我尝试将上面的包复制到我的 bytes
数组。但是网络包是大字节序的,PC 试图以小字节序读取字段。结果,我的 token
字段等于 0x3412
(而不是 0x1234)。
如何使用单独的字节序避免此问题?
Boost 提供了一个专用于字节顺序的库:
http://www.boost.org/doc/libs/1_61_0/libs/endian/doc/index.html
例如:
boost::endian::big_to_native_inplace(bar.field.command);
或 AndyG:
std::cout << boost::endian::endian_reverse(bar.field.token) << std::endl;
注意:这个库有 3 种处理字节序的方法,你需要花时间选择适合你的情况。