localhost上的网络字节顺序

时间:2014-01-18 09:02:49

标签: c++ windows winapi winsock endianness

我正在使用Winsock API开发网络应用程序。每当我测试应用程序发送一些字节时,例如在数组中:

char[0] = '1';
char[1] = '2';
char[2] = '3';
char[3] = '4';
char[4] = '\0';

我使用sendrecv套接字来接收在localhost上运行的另一个应用程序上的字节,然后字节顺序似乎根本没有改变。是因为我在localhost服务器上测试它吗?网络字节顺序是否会改变为:

char[0] = '\0';
char[1] = '4';
char[2] = '3';
char[3] = '2';
char[4] = '1';

如果我通过互联网收到它?

2 个答案:

答案 0 :(得分:2)

8位字符数组和字符串不会受到网络字节顺序问题的影响。由于数组中的每个单独的char已经按顺序排列,并且使用数组中的下一个char字节进行排序...这是受影响的short,int和long。

此外,进行任何字节交换的不是send和recv调用。字节交换与处理器如何在内存中布局整数有关:

要了解字节顺序问题,请考虑英特尔芯片上的以下代码:

// code that demonstrates how integer values are laid out in memory
int msg = 0x01020304;
char* buffer = (char*)&msg;
for (int x = 0; x < 4; x++)
    printf("%d %d %d %d\n", buffer[0], buffer[1], buffer[2], buffer[3]);

打印出的结果是:

4 3 2 1

这表明x86处理器按照您可能期望的相反顺序排列整数的内存字节。最低有效字节或整数首先在内存中排序。这是Little Endian。

在旧的Sun工作站等Sparc芯片上打印出相同的代码:

1 2 3 4

这是Big Endian。

只有当您将数据写入磁盘或网络时,内存序列的字节顺序才会重要。一旦另一台计算机读取另一台计算机写出的字节序列,那么读取整数的CPU将根据它自己的字节序来解释它。

字节顺序通常在将整数写入文件或流式传输到网络时很重要。如果没有应用程序开发人员的转换,传递给send()的原始缓冲区就会在处理器将字节输出到内存中时完全传输。有关从Big Endian(也称为网络字节顺序)转换整数和短路的更多详细信息,请参阅htonl和朋友。

答案 1 :(得分:1)

当您查看字节流并决定解释数据时,字节顺序才会发挥作用。

例如,如果你有字节流:

'1' '2' '3' '4' '0'

然后你决定将数据解释为一个字符流,然后假设每个字符有一个字节,你就得到一个包含字符串“1234”的数组。

但是,如果您决定将数据解释为int,那么字节顺序将起作用,因为您有多个字节用于编码数据类型(int)。上述流的值具有十六进制值:

0x31 0x32 0x33 0x34 0x00

(0x31是十进制值'1'等)

这是字节序发挥作用的地方。您需要知道流中数据的字节顺序,以便在反序列化时可以将其成功转换回正确的值。