banner
cells

cells

为美好的世界献上 bug

網路位元組順序

字節序#

字節序:存放字節的順序。

字節序與 CPU 架構相關,通常 x86 架構使用小端序,字節序決定數據在內存中存儲的順序。

在網絡通信傳輸數據時需要統一字節序,以確保能夠正常的傳輸和解析數據。

存儲數據方式有:大端序(Big-Endian)和 小端序(Little-Endian)。

大端序:高位字節存儲在低地址,低位字節存儲在高地址(低對高)。

小端序:高位字節存儲在高地址,低位字節存儲在低地址(低對低)。

對於 0x1234 十六進制的數,12 是高位字節,34 是低位字節。而高地址和低地址指的是地址的大小,例如有兩個地址 0x10100x10110x1010 就是低地址,0x1011 就是高地址。

判斷本機字節序#

// 1 Byte = 8 bit(8 位二進制代表一個字節)
// 1 位十六進制代表 4 bit
// short 占 2 Byte = 16 bit
// char 占 1 Byte = 8 bit
// 強轉為 char *,後取出的首地址(低位地址)占 1 Byte
// 將這個低位地址解引用後轉為 short
// 與原始數據中的低位和高位進行比較
// 如果等於高位則說明為大端序(低對高)
// 如果等於低位則說明為小端序(低對低)

// 如果是大端序,低地址存儲數據的高位字節
// 高位字節是 0x12
// &i 取出的是低地址
// (short)*(char *)&i == 0x12
bool isBigEndian() {
    short i = 0x1234;
    return (short)*(char *)&i == 0x12;
}

// 如果是小端序,低地址存儲數據的低位字節
// 低位字節是 0x34
// &i 取出的是低地址
// (short)*(char *)&i == 0x34
bool isLittleEndian() {
    short i = 0x1234;
    return (short)*(char *)&i == 0x34;
}

簡單寫法:

bool isBigEndian() {
    short i = 1;
    return *(char *)&i != 1;
}

轉換本機字節序與網絡字節序#

網絡字節序通常使用大端字節序

POSIX API#

// host to network unsigned short
htons();

// host to network unsigned long
htonl();

// network to host unsigned short
ntohs();

// network to host unsigned long
ntohl();

Boost Asio API#

// host to network unsigned short
boost::asio::detail::socket_ops::host_to_network_short();

// host to network unsigned long
boost::asio::detail::socket_ops::host_to_network_long();

// network to host unsigned short
boost::asio::detail::socket_ops::network_to_host_short();

// network to host unsigned long
boost::asio::detail::socket_ops::network_to_host_long();

在使用這些 API 時,應該確保輸入參數和返回結果都是無符號整型,否則可能存在符號拓展問題。

載入中......
此文章數據所有權由區塊鏈加密技術和智能合約保障僅歸創作者所有。