1. 程式人生 > >1、網路協議

1、網路協議

1、TCP/IP

TCP/IP(Transmission Control Protocol/Internet Protocol)是一種可靠的網路資料傳輸控制協議。定義了主機如何連入因特網以及資料之間傳輸的標準。通常將該協議歸類到四個抽象層中,如下圖所示。
TCP:Transmission Control Protocol,傳輸控制協議
UDP:User Datagram Protocol,使用者資料報協議
ICMP:Internet Control Message Protocol,網路控制報文協議,主要用來檢測網路通訊故障和實現鏈路追蹤。如ping
IGMP:Internet Group Management Protocol,internet組管理協議
ARP:Address Resolution Protocol,地址解析協議,根據IP地址獲取實體地址的一個TCP/IP協議。即將IP地址翻譯為MAC地址。
RARP:Reverse Address Resolution Protoco,反向地址解析協議,允許區域網的物理機器從閘道器伺服器的 ARP 表或者快取上請求其 IP 地址。
在這裡插入圖片描述

2、三次握手

三次握手即建立TCP連線,在建立TCP連線時,需要客戶端和服務端總共傳送三個包已確定連線的建立。三次握手的過程如下圖所示。
在這裡插入圖片描述
為了分析三次握手的過程,可以使用wireshark來抓包,在如下圖中,當呼叫active介面之間,前面的三次互動過程就是三次握手的過程。分別標識為SYN、SYN,ACK、ACK,對應了上圖的三個過程。
在這裡插入圖片描述

(1)第一次握手:Client將標誌位SYN置為1,隨機產生一個值seq=J,並將該資料包傳送給Server,Client進入SYN_SENT狀態,等待Server確認。
(2)第二次握手:Server收到資料包後由標誌位SYN=1知道Client請求建立連線,Server將標誌位SYN和ACK都置為1,ack=J+1,隨機產生一個值seq=K,並將該資料包傳送給Client以確認連線請求,Server進入SYN_RCVD狀態。
(3)第三次握手:Client收到確認後,檢查ack是否為J+1,ACK是否為1,如果正確則將標誌位ACK置為1,ack=K+1,並將該資料包傳送給Server,Server檢查ack是否為K+1,ACK是否為1,如果正確則連線建立成功,Client和Server進入ESTABLISHED狀態,完成三次握手,隨後Client與Server之間可以開始傳輸資料了。

SYN攻擊:
在三次握手過程中,Server傳送SYN-ACK之後,收到Client的ACK之前的TCP連線稱為半連線(half-open connect),此時Server處於SYN_RCVD狀態,當收到ACK後,Server轉入ESTABLISHED狀態。SYN攻擊就是Client在短時間內偽造大量不存在的IP地址,並向Server不斷地傳送SYN包,Server回覆確認包,並等待Client的確認,由於源地址是不存在的,因此,Server需要不斷重發直至超時,這些偽造的SYN包將產時間佔用未連線佇列,導致正常的SYN請求因為佇列滿而被丟棄,從而引起網路堵塞甚至系統癱瘓。SYN攻擊時一種典型的DDOS攻擊,檢測SYN攻擊的方式非常簡單,即當Server上有大量半連線狀態且源IP地址是隨機的,則可以斷定遭到SYN攻擊了,使用如下命令可以讓之現行:
#netstat -nap | grep SYN_RECV

3、四次揮手

四次揮手即終止TCP連線。當斷開一個TCP連線時,需要客戶端和服務端總共傳送4個包已確認連線的斷開。
不過,這裡涉及到一個概念。

單工:資料傳輸只支援資料在一個方向上傳輸(如:喇叭)
半雙工:資料傳輸允許資料在兩個方向上傳輸,但是在某一時刻,只允許在一個方向上傳輸,實際上有點像切換方向的單工通訊(如:對講機)
全雙工:資料通訊允許資料同時在兩個方向上傳輸,因此全雙工是兩個單工通訊方式的結合,它要求傳送裝置和接收裝置都有獨立的接收和傳送能力(如:計算機的互動)
在這裡插入圖片描述
由於TCP連線時全雙工的,因此,每個方向都必須要單獨進行關閉,這一原則是當一方完成資料傳送任務後,傳送一個FIN來終止這一方向的連線,收到一個FIN只是意味著這一方向上沒有資料流動了,即不會再收到資料了,但是在這個TCP連線上仍然能夠傳送資料,直到這一方向也傳送了FIN。首先進行關閉的一方將執行主動關閉,而另一方則執行被動關閉,上圖描述的即是如此。
(1)第一次揮手:Client傳送一個FIN,用來關閉Client到Server的資料傳送,Client進入FIN_WAIT_1狀態。
(2)第二次揮手:Server收到FIN後,傳送一個ACK給Client,確認序號為收到序號+1(與SYN相同,一個FIN佔用一個序號),Server進入CLOSE_WAIT狀態。
(3)第三次揮手:Server傳送一個FIN,用來關閉Server到Client的資料傳送,Server進入LAST_ACK狀態。
(4)第四次揮手:Client收到FIN後,Client進入TIME_WAIT狀態,接著傳送一個ACK給Server,確認序號為收到序號+1,Server進入CLOSED狀態,完成四次揮手。

4、TCP通訊的原理

在這裡插入圖片描述
在TCP中的Socket進行通訊的時候,當傳送端呼叫send方法傳送資料的時候,其實資料首先是放在了介於應用層和傳輸層之間的緩衝區中,這個緩衝區是由核心維護的,同時,接收端在呼叫recv方法接收資料的時候,也是從TCP接收緩衝區中獲取資料。最終來交給應用層處理。

5、滑動視窗協議

傳送方和接收方都會維護一個數據幀的序列,這個序列被稱作視窗。傳送方的視窗大小由接收方確認,目的是控制傳送速度,以免接收方的快取不夠大導致溢位,同時控制流量也可以避免網路擁塞。
下面圖中的4,5,6號資料幀已經被髮送出去,但是未收到關聯的ACK,7,8,9幀則是等待發送。可以看出傳送端的視窗大小為6,這是由接受端告知的(事實上必須考慮擁塞視窗cwnd,這裡暫且考慮cwnd>rwnd)。此時如果傳送端收到4號ACK,則視窗的左邊緣向右收縮,視窗的右邊緣則向右擴充套件,此時視窗就向前“滑動了”,即資料幀10也可以被髮送
在這裡插入圖片描述

6、BIO/NIO/AIO

既然知道了TCP通訊的原理,其實也就引出了一個問題,即在TCP通訊的時候,會存在阻塞的情況,即當讀取Socket資料的時候,如果接收緩衝區為空,則Socket的read方法的執行緒會阻塞,類似while迴圈;而對於寫資料到Socket的執行緒來說,當傳送緩衝區被佔滿的時候,在等待緩衝區被釋放的時候,也是阻塞。這種方式即BIO(block io)。

那麼為了解決BIO的問題,後來出現了NIO,NIO的原理是基於事件驅動的, NIO的最重要的地方是當一個連線建立後,不需要對應一個執行緒,這個連線會被註冊到多路複用器上面,所以所有的連線只需要一個執行緒就可以搞定,當這個執行緒中的多路複用器進行輪詢的時候,發現連線上有請求的話,才開啟一個執行緒進行處理,也就是一個請求一個執行緒模式。

AIO與NIO不同,當進行讀寫操作時,只須直接呼叫API的read或write方法即可。這兩種方法均為非同步的,對於讀操作而言,當有流可讀取時,作業系統會將可讀的流傳入read方法的緩衝區,並通知應用程式;對於寫操作而言,當作業系統將write方法傳遞的流寫入完畢時,作業系統主動通知應用程式。 即可以理解為,read/write方法都是非同步的,完成後會主動呼叫回撥函式。

簡單理解的話,可以比作是排隊買票:
1、BIO:採用視窗排隊的方式,效率低下
2、NIO:排隊取號的方式,只需要關注下當前的隊號即可,其他時間可以做自己想做的事情,效率有提高。
3、AIO:網上購票,只需要付款後,等待商家送票上門即可。