SOCKADDR_STORAGE結構中取IP地址和端口

本人在作IOCP模型的編程時,
遇到一個問題
就是從SOCKADDR_STORAGE結構中,取出客戶的IP地址和端口,以利於統計
由於SOCKADDR_STORAGE結構比較複雜,並且兼容了IPV4和IPV6的版本,是直接取不出來的,
仔細研究"windows 網絡編程"中的代碼,意識到,無論怎麼樣,在收發消息的函數中,確定是要用到IP和Port信息的,
收發消息函數以下:
編程

1 rc=WSARecvFrom(sock->s,&wbuf,1,&bytes,&flags,(SOCKADDR*)&recvobj->addr,&recvobj->addrLen,&recvobj->ol,NULL);
2 rc = WSASendTo(sock->s,&wbuf,1,&bytes,0,(SOCKADDR*)&sendobj->addr,sendobj->addrLen,&sendobj->ol,NULL);


這兩個函數都用到告終構SOCKADDR,把SOCKADDR_STORAGE結構,強制轉換成了SOCKADDR結構,
而SOCKADDR結構以下:

windows

1 struct sockaddr {
2 unsigned  short  sa_family;     /* address family, AF_xxx */
3 char  sa_data[14];                 /* 14 bytes of protocol address */
4 };


而在個人意識中,好像還有一個結構與於幾乎是等價的,就是sockaddr_in結構,以下:

網絡

1 struct  sockaddr_in {
2 short  int  sin_family;                      /* Address family */
3 unsigned  short  int  sin_port;       /* Port number */       此爲端口
4 struct  in_addr  sin_addr;              /* Internet address */  此爲IP地址,
5 unsigned  char  sin_zero[8];         /* Same size as struct sockaddr */
6 };


看到上面的結構,勝利就在眼前了,再加把勁

函數

1 in_addr結構定義以下:
2 struct  in_addr {
3 unsigned  long  s_addr;
4 };


從上述結構得知,IP地址是以無符號長整型方式存儲的,可是在計算機中,是相似於"192.168.1.3"格式的
因此從sockaddr_in結構中取IP,確定有必定的函數,直接轉換過來,查找資料得知
inet_ntoa()函數實現上述格式,即"192.168.1.3"
而inet_addr()函數恰與它相反,即把"192.168.1.3"轉換爲無符號長整型.

以上都準備好了,就能夠進行轉換了,以下:


spa

1 SOCKADDR_STORAGE    ssaddr;
2 int rc=WSASendTo(sock->s,&wbuf,1,&bytes,0,(SOCKADDR*)&ssaddr,sendobj->addrLen,&sendobj->ol,NULL)


此函數調用成功後,ssaddr中會被填入對方(即客戶)的IP地址和端口,
強制轉換後:

code

1 char  *temp;
2 temp=inet_ntoa(((sockaddr_in*)((SOCKADDR*)&sendobj->addr))->sin_addr);




orm

1 temp=inet_ntoa(((sockaddr_in*)&sendobj->addr)->sin_addr);


取得端口的信息,方法同上ci

相關文章
相關標籤/搜索