天天看點

socket程式設計的3個api

  • 英文小冊原文位址:beej.us/guide/bgnet…
  • 作者:Beej
  • 中文翻譯位址:www.chanmufeng.com/posts/netwo…

close()與shutdown()

當你玩兒夠了​

​send()​

​​和​

​recv()​

​​,你可能想關閉你的​

​socket descriptor​

​​連接配接了,這個操作很簡單,隻需要調用​

​close()​

​函數就可以了:

close(sockfd)      

這将避免​

​sockfd​

​​進行更多的讀寫操作,任何想要對這個​

​socket​

​進行讀寫的操作都會報錯。

如果你想對​

​socket​

​​關閉的姿勢多一點控制,那你應該使用的是​

​shutdown()​

​​函數,它允許選擇性地切斷單向連接配接或者雙向連接配接(這一點和​

​close()​

​一樣)。文法如下:

int shutdown(int sockfd, int;      

​sockfd​

​​表示你想關閉的​

​socket file descriptor​

​​,​

​how​

​的參數以及含義見下表:

how的值 含義
禁止接收資料
1 禁止發送資料
2 禁止接收、發送資料(和​

​close()​

​相同)

​shutdown()​

​​成功時傳回​

​0​

​​,失敗時傳回​

​-1​

​​,并且設定全局變量​

​errno​

​。

如果你在​

​unconnected datagram socket​

​​上使用​

​shutdown()​

​​,它隻會單純地讓​

​socket​

​​無法繼續進行​

​send()​

​​和​

​recv()​

​​調用。如果你想讓​

​shutdown()​

​​發揮原本的作用,那麼你應該把它用在使用了​

​connect()​

​​函數的​

​datagram socket​

​身上。

需要強調的是,​

​shutdown()​

​​并不會實際關閉​

​file descriptor​

​​,隻是改變了可用狀态而已。想要真正釋放​

​file descriptor​

​​,你還是得調用​

​close()​

​。

沒了。

「對了,如果你用的是​

​Windows​

​​和​

​Winsock​

​​,你需要用的是​

​closesocket()​

​​,而不是​

​close()​

​,謹記!」

getpeername()

這個函數有點簡單。

簡單到我都不想單獨把它列出來,但是我還是列出來了。

​getpeername()​

​​會告訴你另一端連接配接的​

​stream socket​

​是誰。文法如下:

#include <sys/socket.h>

int getpeername(int sockfd, struct sockaddr *addr, int;      

​sockfd​

​​是一個已連接配接的​

​stream socket​

​​;​

​addr​

​​是一個指向​

​struct sockaddr​

​​ (或者 ​

​struct sockaddr_in​

​​) 結構的指針,結構中存儲了連接配接的另一頭兒的資訊;​

​addrlen​

​​是一個​

​int​

​​型指針,這個int變量應該被初始化為 ​

​sizeof *addr​

​​ 或者 ​

​sizeof(struct sockaddr)​

​。

函數異常時會傳回​

​-1​

​​,并且設定全局變量​

​errno​

​。

一旦你擷取了對面的位址,你就可以使用 ​

​inet_ntop()​

​​, ​

​getnameinfo()​

​​, 或者 ​

​gethostbyaddr()​

​ 列印出來或者擷取更多資訊(但是别妄想能擷取到别人的登入名哦~)。

gethostname

這貨比 ​

​getpeername()​

​ 還簡單。

​gethostname()​

​​會傳回程式所有的主機名稱,這個主機名稱可以繼續用在 ​

​gethostbyname()​

​中來确定主機的IP位址。

還能玩得更花一點兒嗎?

#include <unistd.h>

int gethostname(char *hostname, size_t;