TCP/IP 協定
關於該協定的詳細內容可自行查閱 <<TCP/IP 詳解 捲 1:協定>>
PHP 的 tcp/udp API 內容是 PHP 手冊上的內容
測試的 PHP 版本
TCP的連線建立與關閉狀態及資料傳輸通訊過程
PHP 程式碼 【就是手冊的例子了】
<?php /** * Created by PhpStorm. * User: [email protected] * Date: 2019/6/19 * Time: 9:55 */ error_reporting(E_ALL); /* Allow the script to hang around waiting for connections. */ set_time_limit(0); /* Turn on implicit output flushing so we see what we're getting * as it comes in. */ ob_implicit_flush(); $address = '0.0.0.0'; //要監聽的ip地址 $port = 54321;//要監聽的埠 //建立一個socket AF_INET是一個協定族 (一般都有AF_INET,AF_INET6,AF_UNIX c語言提供也是,只不過是地址族),而PHP叫網路協定 //C語言提供的協定族是PF_INET,PF_INET6,PF_UNIX //SOCK_STREAM sock的服務型別 這裡是位元組流的服務型別用於TCP if (($sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP)) === false) { echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "n"; } //socket選項 ,選項一般在socket建立後設定 用於設定TCP的連線屬性 //選項幾乎和c差不多一樣 //一般來說這些選項我們可以通過修改系統核心來調整 if (!socket_set_option($sock, SOL_SOCKET, SO_REUSEADDR, 1)) { echo 'Unable to set option on socket: '. socket_strerror(socket_last_error()) . PHP_EOL; } if (!socket_set_option($sock, SOL_SOCKET, SO_REUSEPORT, 1)) { echo 'Unable to set option on socket: '. socket_strerror(socket_last_error()) . PHP_EOL; } //係結【有的叫命名socket】 if (socket_bind($sock, $address, $port) === false) { echo "socket_bind() failed: reason: " . socket_strerror(socket_last_error($sock)) . "n"; } //監聽 此時伺服器進入 LISTEN狀態 if (socket_listen($sock, 5) === false) { echo "socket_listen() failed: reason: " . socket_strerror(socket_last_error($sock)) . "n"; } do { //接受用戶端連線sock 從系統核心接受佇列裡取 如果取出則雙方進入了ESTABLISHED狀態 if (($msgsock = socket_accept($sock)) === false) { echo "socket_accept() failed: reason: " . socket_strerror(socket_last_error($sock)) . "n"; break; } /* Send instructions. */ $msg = "nWelcome to the PHP Test Server. n" . "To quit, type 'quit'. To shut down the server type 'shutdown'.n"; socket_write($msgsock, $msg, strlen($msg)); do { //讀用戶端資料【從TCP接收接受緩衝區取】 if (false === ($buf = socket_read($msgsock, 2048, PHP_NORMAL_READ))) { echo "socket_read() failed: reason: " . socket_strerror(socket_last_error($msgsock)) . "n"; break 2; } if (!$buf = trim($buf)) { continue; } if ($buf == 'quit') { break; } if ($buf == 'shutdown') { //傳送FIN結束報文,正常情況伺服器會進入CLOSED狀態 socket_close($msgsock); break 2; } $talkback = "PHP: You said '$buf'.n"; socket_write($msgsock, $talkback, strlen($talkback)); echo "$bufn"; } while (true); socket_close($msgsock); } while (true); socket_close($sock);
socket 服務型別
TCP/IP 選項檔案
然後我們啟動服務
服務狀態檢視命令:netstat -ntlapc
可每隔一秒重新整理一次狀態
tcpdump 工具:
tcpdump -A -XX -i lo
用戶端我們使用 telent 工具連線測試 即可
測試圖如下
連線和關閉圖
如果是用戶端發起的關閉則狀態則是:
用戶端先傳送一個結束報文 FIN 包,此時處於 FIN_WAIT1 狀態,伺服器確認應答處於 CLOSE_WAIT 狀態
此時用戶端處於 FIN_WAIT2 狀態,當伺服器也發了一次 FIN 結束報文時,伺服器處於 LAST_LOCK 狀態,用戶端確認後處於 TIME_WAIT 狀態,伺服器則是關閉 CLOSED 了
狀態轉移圖
不管你用的是 PHP 提供的 SOCKET API 還是 SWOOLE 或是 C 寫的測試都一樣的!
以上就是TCP 的連線建立與關閉狀態及資料傳輸通訊過程【含有 PHP socket API 測試實驗程式碼】的詳細內容,更多請關注TW511.COM其它相關文章!