前言
关于字节序的问题,查了一些资料:
1.大小端
2.网络字节序
3.大小端与网络字节序
4.socket与字节序
上述资料里有相关概念和知识点的说明,以下会对部分问题做几点总结。
一、主机字节序是什么?
这里以主机字节序作说明,计算机在存储多字节数据时,例如C语言中的整型数据(int),无法用一个字节单元的内存将数据完成保存,因此就需要使用多个字节单元的内存来存储这种数据,带来的问题是,数据的高低字节部分怎样对应内存中的高低地址进行保存呢?所以就产生了大小端数据存储模式,到底是何种模式是跟cpu架构有关系的。如何区分记忆大端序、小端序呢?我是这么理解的:cpu在读取内存数据时,习惯是从低地址开始寻址,如果读到的是数据的高字节部分则是大端序,否则为小端序。
二、网络字节序是什么?
网络字节序:在网络传输过程中的结构,一般而言指的是大端字节序。这是我们规定的多字节数据在网络传输中传输方式,作为网络数据的接收方,规定收到的第一个字节为数据的高字节部分并将其存储在低地址中(大端模式)。
三、主机字节序和网络字节序的转换问题
当进行数据的跨平台(跨cpu架构)网络传输时,需要考虑大小端序的转换问题:
1.当各平台的主机字节序一致时,无需进行转换;
2.当各平台的主机字节序不一致时,需要进行转换,否则将会导致数据错乱;
3.关于字节序转换函数,不同操作系统下有自己的api函数,以下以linux为例简单列举下:
#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);
这些函数名很好记,h表示host,n表示network,l表示32位长整数,s表示16位短整数。例如htonl表示将32位的长整数从主机字节序转换为网络字节序,例如将IP地址转换后准备发送。如果主机是小端字节序,这些函数将参数做相应的大小端转换然后返回,如果主机是大端字节序,这些函数不做转换,将参数原封不动地返回。