日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

网络编程——sockaddr 与 sockaddr_in

發(fā)布時間:2023/12/18 编程问答 48 豆豆
生活随笔 收集整理的這篇文章主要介紹了 网络编程——sockaddr 与 sockaddr_in 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

struct sockaddr 這個結(jié)構(gòu)體是linux的網(wǎng)絡(luò)編程接口中用來表示IP地址的標(biāo)準(zhǔn)結(jié)構(gòu)體,bind、connect等函數(shù)中都需要這個結(jié)構(gòu)體,這個結(jié)構(gòu)體是兼容IPV4和IPV6的。

在實際編程中這個結(jié)構(gòu)體會被一個struct sockaddr_in所填充。

sockaddr

用于存儲參與(IP)Windows套接字通信的計算機上的一個internet協(xié)議(IP)地址。為了統(tǒng)一地址結(jié)構(gòu)的表示方法 ,統(tǒng)一接口函數(shù),使得不同的地址結(jié)構(gòu)可以被bind()、connect()、recvfrom()、sendto()等函數(shù)調(diào)用。但一般的編程中并不直接對此數(shù)據(jù)結(jié)構(gòu)進行操作,而使用另一個與之等價的數(shù)據(jù)結(jié)構(gòu)sockaddr_in。這是由于Microsoft TCP/IP套接字開發(fā)人員的工具箱僅支持internet地址字段,而實際填充字段的每一部分則遵循sockaddr_in數(shù)據(jù)結(jié)構(gòu),兩者大小都是16字節(jié),所以二者之間可以進行切換。

sockaddr 在bind的man手冊中提到

struct sockaddr {sa_family_t sa_family; //所選協(xié)議族AF_INETchar sa_data[14]; //ip地址及端口號 } 說明: sa_family :是2字節(jié)的地址家族,一般都是“AF_xxx”的形式,它的值包括三種:AF_INET,AF_INET6和AF_UNSPEC。 如果指定AF_INET,那么函數(shù)就不能返回任何IPV6相關(guān)的地址信息;如果僅指定了AF_INET6,則就不能返回任何IPV4地址信息。 AF_UNSPEC則意味著函數(shù)返回的是適用于指定主機名和服務(wù)名且適合任何協(xié)議族的地址。如果某個主機既有AAAA記錄(IPV6)地址,同時又有A記錄(IPV4)地址,那么AAAA記錄將作為sockaddr_in6結(jié)構(gòu)返回,而A記錄則作為sockaddr_in結(jié)構(gòu)返回 通常用的都是AF_INET。

sockaddr_in

struct sockaddr_in {short int sin_family; /* Address family */unsigned short int sin_port; /* Port number */struct in_addr sin_addr; /* Internet address */unsigned char sin_zero[8]; /* Same size as struct sockaddr */};sin_family:指代協(xié)議族,在socket編程中只能是AF_INETsin_port:存儲端口號(使用網(wǎng)絡(luò)字節(jié)順序)sin_addr:存儲IP地址,使用in_addr這個數(shù)據(jù)結(jié)構(gòu)sin_zero:是為了讓sockaddr與sockaddr_in兩個數(shù)據(jù)結(jié)構(gòu)保持大小相同而保留的空字節(jié)。 而其中in_addr結(jié)構(gòu)的定義如下: typedef struct in_addr {union {struct{ unsigned char s_b1,s_b2, s_b3,s_b4;} S_un_b;struct{ unsigned short s_w1, s_w2;} S_un_w;unsigned long S_addr;} S_un;} IN_ADDR; 闡述下in_addr的含義,很顯然它是一個存儲ip地址的共用體有三種表達方式: 第一種用四個字節(jié)來表示IP地址的四個數(shù)字; 第二種用兩個雙字節(jié)來表示IP地址; 第三種用一個長整型來表示IP地址。 給in_addr賦值的一種最簡單方法是使用inet_addr函數(shù),它可以把一個代表IP地址的字符串賦值轉(zhuǎn)換為in_addr類型,如addrto.sin_addr.s_addr=inet_addr("192.168.0.2"); 其反函數(shù)是inet_ntoa,可以把一個in_addr類型轉(zhuǎn)換為一個字符串。

雖然是兩個結(jié)構(gòu)體可是二者的占用的內(nèi)存是一致的,因此可以互相轉(zhuǎn)化。

sockaddr常用于bind、connect、recvfrom、sendto等函數(shù)的參數(shù),指明地址信息。是一種通用的套接字地址。

而sockaddr_in 一般是儲存地址和端口的。用于信息的顯示及存儲使用

例如:

struct sockaddr_in addr_server;addr_server.sin_family = AF_INET; addr_server.sin_port = htons(RPORT); addr_server.sin_addr.s_addr = inet_addr(RHOST);

然而,在類似于bind accept的函數(shù)中

ret = bind(fd_sock, (struct sockaddr *)&addr_server, sizeof(addr_server)); if(ret < 0) {perror("bind");return -1; }

之前只是這樣的記下來了,可是知道一天,想顯示所連接的客戶端的ip地址的時候,就發(fā)現(xiàn)了問題所在

char *inet_ntoa(struct in_addr in);

函數(shù)原型是這樣的,可是在

struct in_addr {in_addr_t s_addr; };

這個in_addr是sockaddr_in的一個mamber

fd_connection = accept(fd_sock, (struct sockaddr *)&addr_client, &addr_client_len);if(fd_connection < 0){perror("accept");return -1;}printf("connected! : %d\n", fd_connection);printf("%s%s\n", "the client ip is :", inet_ntoa(addr_client.sin_addr));

  

轉(zhuǎn)載于:https://www.cnblogs.com/wuyepeng/p/9721546.html

總結(jié)

以上是生活随笔為你收集整理的网络编程——sockaddr 与 sockaddr_in的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。