htons(), htonl(), ntohs(), ntohl()
將多位元組整數型別的資料,從主機的位元組順序轉化為網路位元組順序
原型:
#include <netinet/in.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);
描述:
不同的計算機裡對它們的多位元組整數(例如:一個大於char的整數)使用不同的位元組順序。這就意味著,如果你從intel的盒子中send()一個兩個位元組的短整數到一個Mac中(在它們成為Intel之前),一個計算機認為是數字1,而另外一個計算機會認為它是數字256,反之亦然。
解決這個問題的辦法是:所有的人撇開它們的不同之處,同意摩托羅拉和IBM的順序是正確的,而Intel使用的是怪異的方式,所以我們在將他們傳送出去之前把所有的位元組以“正序”方式排列。既然Intel是一個“反序”的機器,所以呼叫我們需要的,以“網路位元組順序”排列的位元組是很正確的。所以這些函式把你的本機位元組順序轉化為網路位元組順序然後再轉化回來。
(這就意味著,在Intel上面,這些函式把所有的位元組調換過來,而在PowerPC上面,它們什麼都沒有做,因為在那上面位元組本身是以網路位元組順序排列的。但是你依然要在你的程式當中使用它們,因為別的人有可能將它們應用到Intel機器當中,使之依然正常的執行。)
注意到這些型別包含32-位(4個位元組,可能是整數)和16-位(兩個位元組和short很像)資料。64-位的機器可以使用htonll()作為64-位整數,但是我們沒有見到它。你必須自己寫。
不管怎樣,使用這些函式決定於你要從主機位元組順序(你的電腦上的)還是網路位元組順序轉化。如果是"host",函式的第一個字母為"h",否則"network"就為"n"。函式的中間字母總是"to",因為你要從一個轉化到另一個,倒數第二個字母說明你要轉化成什麼。最後一個字母是資料的大小,"s"表示short,"l"表示long。於是:
htons() host to network short
htonl() host to network long
ntohs() network to host short
ntohl() network to host long
返回值
每個函式返回轉化後的值
例子:
uint32_t some_long = 10;
uint16_t some_short = 20;
uint32_t network_byte_order;
// convert and send
network_byte_order = htonl(some_long);
send(s, &network_byte_order, sizeof(uint32_t), 0);
some_short == ntohs(htons(some_short)); // this expression is true