第四十九章、listen函數

這一章我們來了解listen函數:

listen函數是幹什麼的呢,它是用來監聽連接申請的,可以將一個主動套接字轉換成被動套接字。

我們來看下listen函數的定義:

int listen (int __fd, int __n)

我們來看下它需要的參數

1、 fd指定一個已綁定未連接套接字接口的描述符

2、 n設置請求隊列的最大長度

listen成功執行時返回0,失敗返回-1

一般服務器需要調用函數listen來監聽連接申請,以便客戶端請求。

listen有兩個功能:

1、 函數socket創建的套接字是主動套接字,可以用來進行主動連接(調用connect函數),但是不能接收連接請求,而服務器的套接字必須能夠接收客戶機的請求。函數listen將一個尚未連接的主動套接字轉換成為一個被動套接字,告訴TCP協議,這個套接字可以接收連接請求。

2、 TCP協議將到達的連接請求排隊,listen函數的第2個參數指定這個隊列的最大長度。

要創建一個監聽套接字,必須首先調用函數socket創建一個主動套接字,然後調用函數bind將它與服務器套接字地址綁定在一起,最後調用函數listen進行轉換,這3步操作是所有TCP服務器所必須的操作。

TCP協議為每個監聽套接字維護兩個隊列。

1、 未完成連接隊列

每個尚未完成3次握手操作的TCP連接在這個隊列中佔有一項。TCP協議在接收到一個客戶機SYN數據段之後,在這個隊列中創建一個新條目,然後發送對客戶機SYN數據段的確認和自己的SYN數據段(ACK+SYN 數據段)等待客戶機對自己的SYN數據段的確認,此時,套接字處於SYN_RCVD狀態。這個條目將保存在這個隊列中,知道客戶機返回對SYN數據段的確認,或者連接超時。

2、完成連接隊列

每個已經完成3次握手操作,但是尚未被應用程序接收(調用函數accept)的TCP連接在這個隊列中佔有一項。當一個未完成連接隊列中的連接接收到SYN數據段的確認之後,完成3次握手操作,TCP協議將它從未完成這個接收隊列移到完成連接隊列中。這個條目將保存在這個隊列中,知道應用程序調用函數accept來接收它。

listen函數的第二個參數隊列最大長度表示這個套接字能夠接收的最大數目的未接受連接。如果一個客戶機SYN數據段達到時,監聽套接字的完成連接隊列已經完了,TCP協議將忽略這個SYN數據段。對於不能接收的SYN數據段,TCP協議不發送RST數據段。


分享到:


相關文章: