Linux socket編程入門及客戶端服務器端通信實現 – 提高篇:TCP連接過程分析



------------------------1  建立連接  ------------------------

終端輸入命令: ./tcpserv & ,使服務器端程序後臺執行

在同一個終端輸入 ./tcpcli 127.0.0.1 命令執行客戶端程序

通過命令:netstat –a | grep 9877 查看相關套接字狀態,其中“*”表示地址通配符,服務器衆所周知的端口號設定爲9877


State 狀態含義:

LISTEN 監聽狀態,即服務器端一個套接字處於監聽狀態,具有通配本地IP地址,本地端口爲9877


下述6列的含義依次爲:

Proto        Recv-Q     Send-Q     Local         Address   ForeignAddress       State


------------------------2  終止連接 ------------------------

當客戶端終止連接時(Ctrl + D),則 netstat –a | grep 9877 查看客戶進入TIME_WAIT狀態,而服務器監聽套接字仍處於LISTEN狀態,即等待另一個客戶連接。


客戶調用socketconnect,後者引起TCP的三路握手過程,當三路握手過程完成後,客戶中connect和服務器中accept均返回,連接建立。此時會有三個睡眠(已阻塞的進程):

客戶進程—fgets調用,因爲未輸入過任何文本,條件爲sk_wait_data

服務器父進程—再次調用accept並阻塞,等待下一個客戶連接,即inet_csk_wait_for_connect

服務器子進程—子進程read等待客戶輸入一行文本期間阻塞,n_tty_read


Ctrl+D結束客戶進程後,查看進程狀態和條件如下圖所示,與上圖對比,可以發現PID-6807 的客戶進程已經不存在了,而PID-6808負責與其通信的服務器端子進程狀態爲ZWCHAN條件說明爲exit,即已終止。

在客戶服務器連接的進程終止後,一部分工作爲主動關閉,即四分組交換序列終止連接的過程;另一部分工作爲服務器子進程終止時,給父進程發送一個SIGCHLD信號,但程序1中父進程並沒有處理,這就導致子進程狀態爲Z,即僵死狀態(S表示爲等待某些資源而睡眠);對於進入僵死狀態的進程,必須通過POSIX信號處理進行清理。




發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章