佳木斯湛栽影视文化发展公司

主頁(yè) > 知識(shí)庫(kù) > TCP協(xié)議詳解_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理

TCP協(xié)議詳解_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理

熱門標(biāo)簽:鐵路電話系統(tǒng) 呼叫中心市場(chǎng)需求 銀行業(yè)務(wù) 網(wǎng)站文章發(fā)布 智能手機(jī) 美圖手機(jī) 檢查注冊(cè)表項(xiàng) 服務(wù)器配置

本文描述了TCP協(xié)議,首先簡(jiǎn)單介紹了TCP完成了一些什么功能;介紹了TCP報(bào)文格式,以及典型報(bào)文的數(shù)據(jù)格式;接著從鏈路控制和數(shù)據(jù)傳輸兩個(gè)方面進(jìn)行了介紹,在TCP中鏈路控制和數(shù)據(jù)傳輸是通過(guò)同一個(gè)通道進(jìn)行的,并沒(méi)有區(qū)分控制通道和數(shù)據(jù)通道;在網(wǎng)絡(luò)中傳輸數(shù)據(jù)(控制或真實(shí)數(shù)據(jù)),網(wǎng)絡(luò)可能發(fā)生擁堵,因此接下來(lái)簡(jiǎn)單描述了主機(jī)端進(jìn)行擁塞控制所采取的方法,也簡(jiǎn)單提及了中間路由器/交換機(jī)進(jìn)行擁塞避免所采取的主動(dòng)措施;最后介紹了在TCP中性能分析的一些基本概念點(diǎn),在開發(fā)網(wǎng)絡(luò)應(yīng)用程序的時(shí)候,需要對(duì)應(yīng)用的網(wǎng)絡(luò)需求進(jìn)行一個(gè)估計(jì)。

本文不是TCP的入門資料,閱讀之前需要對(duì)TCP有一些基本認(rèn)識(shí),如三次握手、四次揮手、滑動(dòng)窗口等。

TCP概述

通常說(shuō)到TCP,我們都會(huì)很自然的想到其為上層提供了一個(gè)面向連接、可靠的、端到端的數(shù)據(jù)流服務(wù),也通常用電話線路來(lái)類比一個(gè)TCP連接。但這種類比對(duì)剛接觸到TCP的人來(lái)說(shuō)極易造成誤會(huì),我們需要仔細(xì)審視這些概念,你將會(huì)發(fā)現(xiàn)TCP并不是那么面向連接的、也不是那么可靠的、數(shù)據(jù)也仍然是通過(guò)報(bào)文的方式進(jìn)行傳輸?shù)?。?shí)際上TCP是提供了一種“盡力而為”的數(shù)據(jù)傳輸模型;同時(shí),它也提供了防止網(wǎng)絡(luò)擁塞的主機(jī)端擁塞控制,試圖去了解整個(gè)網(wǎng)絡(luò)的狀況,并采取合適的策略(貌似不是TCP應(yīng)該干的事?)。

TCP的連接并不是指一條實(shí)際的或虛擬的鏈路存在于數(shù)據(jù)交換的兩端,而是指連接的雙方都維護(hù)了一些資源(如輸入輸出緩沖區(qū)、多種定時(shí)器)以及鏈路狀態(tài)的信息,并通過(guò)雙方的控制報(bào)文交互管理狀態(tài)、向用戶提供接口修改這些資源的分配。在“連接控制”小節(jié),我們將會(huì)仔細(xì)審視資源和狀態(tài)(包括控制狀態(tài)的報(bào)文),若控制報(bào)文丟失,那么連接就會(huì)處于一種不一致狀態(tài),TCP通過(guò)一些手段去試圖解決這些問(wèn)題(如持活定時(shí)器、保持定時(shí)器等等)。

TCP提供了可靠的數(shù)據(jù)傳輸服務(wù),其采取的措施是對(duì)控制報(bào)文和數(shù)據(jù)報(bào)文進(jìn)行確認(rèn)、并在超時(shí)之后進(jìn)行重傳;并利用滑動(dòng)窗口協(xié)議解決數(shù)據(jù)數(shù)傳亂序、收發(fā)雙方進(jìn)行流量控制。具體來(lái)說(shuō)就是,對(duì)于發(fā)送方,TCP按照其認(rèn)為最合適的長(zhǎng)度發(fā)送數(shù)據(jù)報(bào)文,并在發(fā)出報(bào)文之后,啟動(dòng)一個(gè)定時(shí)器,等待數(shù)據(jù)的確認(rèn)報(bào)文,若定時(shí)器超時(shí)后仍沒(méi)有收到確認(rèn)報(bào)文,則重傳該報(bào)文;對(duì)于接收方,收到數(shù)據(jù)后,首先檢查報(bào)文校驗(yàn)和,錯(cuò)誤則直接丟棄該報(bào)文,不確認(rèn)(發(fā)送端會(huì)注意到這個(gè)事實(shí),從而重傳);收到重復(fù)報(bào)文,丟棄,不確認(rèn);通過(guò)雙方維護(hù)的滑動(dòng)窗口,TCP會(huì)將亂序報(bào)文排好序后才提交給上層應(yīng)用程序。需要注意的是,流量控制與擁塞控制并不是同一回事,流量控制的目的在于防止發(fā)送端發(fā)送大量數(shù)據(jù),超過(guò)接收端的處理能力,從而導(dǎo)致丟包等;擁塞控制則在于防止網(wǎng)絡(luò)中發(fā)生擁堵,中間路由器或交換機(jī)丟棄報(bào)文的情況。

TCP提供數(shù)據(jù)流服務(wù),上層應(yīng)用傳給TCP的數(shù)據(jù),TCP并不加以區(qū)分,僅僅是按照自己的需求組合、拆分?jǐn)?shù)據(jù),然后傳送給對(duì)端,對(duì)端TCP協(xié)議棧再將數(shù)據(jù)以發(fā)送的順序遞交給上層應(yīng)用。TCP的數(shù)據(jù)傳送仍然是以IP報(bào)文的方式發(fā)送到對(duì)端的,每次盡力發(fā)送MSS大小的報(bào)文,在“數(shù)據(jù)傳輸”小節(jié)我們會(huì)看到諸如Nagle算法、TCP_CORK等對(duì)流中報(bào)文的控制。

TCP本身并不提供報(bào)文邊界之類的東西,但提供了緊急數(shù)據(jù)、PUSH標(biāo)志(并沒(méi)有提供對(duì)外接口)等方式可以模擬報(bào)文。通常,TCP數(shù)據(jù)流的劃分是應(yīng)用程序的事,應(yīng)用程序定義好格式,并自己解析,常見的方案有:

  • 先傳輸固定大小的報(bào)文長(zhǎng)度字段;
  • 按行進(jìn)行分割(或其他分隔符);
  • 固定長(zhǎng)度記錄;
  • 各種編碼方案,如xml、json、ASN.1、tlv等。

TCP報(bào)文

TCP報(bào)文格式

TCP報(bào)文最終是由IP層發(fā)送出去的,封裝報(bào)文如下:

TCP報(bào)文格式如下:

通常使用一個(gè)四元組唯一的表示一個(gè)TCP連接(client-ip, client-port, server-ip, server-port),但需要注意以下事實(shí):

  • 監(jiān)聽服務(wù)器在server-port窗口接受來(lái)自客戶端的連接,并fork一個(gè)子進(jìn)程處理連接,此時(shí),該四元組卻在服務(wù)器對(duì)應(yīng)了兩個(gè)進(jìn)程(監(jiān)聽進(jìn)程只處理SYN報(bào)文,而子進(jìn)程卻只能處理數(shù)據(jù)報(bào)文和FIN等);
  • 連接的化身,這在后面會(huì)詳細(xì)描述。

在TCP首部的圖中,我們主要關(guān)注以下幾個(gè)字段:序號(hào)、首部長(zhǎng)度、6個(gè)標(biāo)志位、選項(xiàng),窗口大小、緊急指針都是以字節(jié)單位,這里并不關(guān)注。

不含選項(xiàng)的TCP首部為20字節(jié),在首部選項(xiàng)中指明了首部有多少個(gè)4字節(jié),由于其占了4位,因此首部最多為60字節(jié)。

序號(hào)字段用來(lái)標(biāo)識(shí)TCP數(shù)據(jù)流中的數(shù)據(jù)字節(jié)流,在建立連接時(shí)會(huì)以一個(gè)ISN進(jìn)行初始化,每個(gè)SYN、FIN等都會(huì)消耗掉一個(gè)序號(hào)。我們并不用太關(guān)心這個(gè)字段,只是需要知道序號(hào)為32位,在長(zhǎng)肥管道(容量較大的網(wǎng)絡(luò)中)序號(hào)可能會(huì)出現(xiàn)回繞,TCP需要識(shí)別。TCP對(duì)該字段也進(jìn)行了相應(yīng)的擴(kuò)充(增加選項(xiàng))。

TCP選項(xiàng)是以1字節(jié)類型、1字節(jié)長(zhǎng)度(可選)、內(nèi)容(可選)來(lái)表示的,可以只有類型,長(zhǎng)度字段包含類型和長(zhǎng)度本身。常見選項(xiàng)如下圖所示,無(wú)操作選項(xiàng)通常用來(lái)作為填充以滿足選項(xiàng)對(duì)齊的要求,tcpdump連接建立的輸出中通常會(huì)包含這些選項(xiàng):

TCP首部中定義了6個(gè)字段,在一個(gè)報(bào)文中,通常只會(huì)出現(xiàn)一個(gè)標(biāo)志,但也允許多個(gè)標(biāo)志同時(shí)出現(xiàn)。

  • URG,緊急指針標(biāo)志位。
  • ACK,確認(rèn)序號(hào)標(biāo)志位,關(guān)于ACK有幾點(diǎn)需要注意:a) ACK是累積的,表示接收方已經(jīng)正確收到了一直到確認(rèn)序號(hào)減一的所有字節(jié);b) TCP通常并不會(huì)對(duì)每個(gè)數(shù)據(jù)包進(jìn)行確認(rèn),而是采用了捎帶確認(rèn)和延遲確認(rèn)的技術(shù),捎帶確認(rèn)是指將ACK報(bào)文合并到數(shù)據(jù)報(bào)文中去,而延遲確認(rèn)是TCP維持了一個(gè)200ms的定時(shí)器,在定時(shí)器過(guò)期前,若有多個(gè)數(shù)據(jù)需要確認(rèn),則一塊進(jìn)行確認(rèn),通常是兩個(gè)報(bào)文確認(rèn)一次,若200ms到了,仍沒(méi)有新數(shù)據(jù)需要確認(rèn),則不再等待,直接確認(rèn)該報(bào)文;c) ACK報(bào)文本身并不會(huì)被確認(rèn),當(dāng)ACK丟失時(shí),需要依靠對(duì)端超時(shí)機(jī)制發(fā)現(xiàn)(后文詳述)。
  • PSH,該標(biāo)志由TCP自動(dòng)設(shè)置(曾經(jīng)允許通過(guò)接口進(jìn)行設(shè)置,當(dāng)前多數(shù)實(shí)現(xiàn)不提供),多數(shù)實(shí)現(xiàn)在發(fā)送者將清空發(fā)送緩沖區(qū)時(shí)設(shè)置該標(biāo)志,即發(fā)送者一次將當(dāng)前發(fā)送緩沖區(qū)的數(shù)據(jù)都發(fā)送出去了。
  • RST,連接重置標(biāo)志位。
  • SYN,同步標(biāo)志位,用來(lái)發(fā)起一個(gè)新建連接。
  • FIN,發(fā)送端已經(jīng)完成了所有的數(shù)據(jù)發(fā)送,不會(huì)再發(fā)送新的數(shù)據(jù),關(guān)閉了其發(fā)送端,若對(duì)端也發(fā)送該標(biāo)志,則完全關(guān)閉連接。

常見報(bào)文

TCP中除了通常的數(shù)據(jù)交換報(bào)文(數(shù)據(jù)報(bào)文詳見后文“數(shù)據(jù)傳輸”小節(jié)),還有以下一些特殊的控制報(bào)文:SYN報(bào)文、ACK報(bào)文、FIN報(bào)文、RST報(bào)文、窗口探測(cè)報(bào)文、持活報(bào)文。這里將常見報(bào)文列出來(lái),一是為了強(qiáng)調(diào)一個(gè)事實(shí),TCP的狀態(tài)變更大部分是通過(guò)報(bào)文交互進(jìn)行的;二是對(duì)各種控制報(bào)文的使用場(chǎng)景進(jìn)行簡(jiǎn)單歸納。

SYN報(bào)文,用于發(fā)起一個(gè)新連接,只包含TCP首部,沒(méi)有數(shù)據(jù)。一個(gè)典型報(bào)文輸出如下:

10:23:17.543837 IP 192.168.47.1.55366 > krt.9876: Flags [S], seq 2289863414, win 8192, options [mss 1460,nop,wscale 2,nop,nop,sackOK], length 0

ACK報(bào)文,用于對(duì)控制報(bào)文(不包括RST)和數(shù)據(jù)報(bào)文進(jìn)行確認(rèn),參考上一小節(jié)關(guān)于ACK的一些注意點(diǎn)。該報(bào)文可以與其他報(bào)文結(jié)合在一起,如SYN、數(shù)據(jù)報(bào)文、FIN報(bào)文等。單獨(dú)的ACK本身不含任何數(shù)據(jù),只有首部,典型報(bào)文輸出如下:

10:23:17.544135 IP 192.168.47.1.55366 > krt.9876: Flags [.], ack 1, win 16425, length 0

FIN報(bào)文,用于通知對(duì)端已經(jīng)發(fā)送完了所有數(shù)據(jù),將發(fā)送緩沖區(qū)中數(shù)據(jù)發(fā)送完成后,可以關(guān)閉連接。詳細(xì)參考后文“連接控制”,用于有序釋放連接或者連接半打開。

RST報(bào)文,當(dāng)向一個(gè)出現(xiàn)錯(cuò)誤的連接發(fā)送一個(gè)報(bào)文的時(shí)候,就收到RST報(bào)文。以下是幾種典型情況(詳細(xì)情景在后文“連接控制”小節(jié)表述):

  • 對(duì)端的相應(yīng)端口上沒(méi)有監(jiān)聽程序
  • 異常終止連接,SO_LINGER。使用異常方式終止連接,而不是正常的有序終止連接orderly release,可以迫使連接直接丟失未發(fā)送的數(shù)據(jù);而接收方收到RST報(bào)文后,read返回reset錯(cuò)誤,從而終止該連接,同時(shí)不會(huì)進(jìn)行ACK。
  • 檢測(cè)半打開連接,一方已經(jīng)關(guān)閉或異常終止連接而另一方還不知道。造成這種狀況的原因在于通信的一方?jīng)]有正確將相應(yīng)的狀態(tài)報(bào)文成功發(fā)送給對(duì)端,如主機(jī)突然掉電導(dǎo)致FIN報(bào)文沒(méi)有發(fā)出去,此時(shí)再寫該socket,則會(huì)得到RST報(bào)文。

窗口探測(cè)報(bào)文(持久探測(cè)報(bào)文),TCP并不會(huì)對(duì)不包含數(shù)據(jù)的ACK報(bào)文進(jìn)行確認(rèn),因此可能出現(xiàn)ACK丟失,從而導(dǎo)致窗口通告失敗。TCP使用persist定時(shí)器,定期的發(fā)送一個(gè)字節(jié)的窗口探測(cè)報(bào)文。探測(cè)報(bào)文總是在5~60s之間,也是采用指數(shù)后退算法,但不超過(guò)60s,該探測(cè)報(bào)文會(huì)一直持續(xù)。實(shí)現(xiàn)時(shí),使用500ms的定時(shí)器。

持活報(bào)文,用于查看連接是否仍然存活的控制報(bào)文。報(bào)文只帶有ACK標(biāo)志,且序號(hào)字段為將要發(fā)送的序號(hào)減一,這樣引起對(duì)端進(jìn)行一個(gè)ACK,表示接收到重復(fù)序號(hào),對(duì)端期望的序號(hào)為下一個(gè)值。

連接控制

TCP是面向連接的協(xié)議,正如前面所描述的,并不存在真實(shí)的物理或虛擬的鏈路,TCP的連接是指在通信的雙方分配了資源和維護(hù)了狀態(tài),并通過(guò)控制報(bào)文控制連接,通過(guò)API協(xié)調(diào)資源。本小節(jié)將詳細(xì)描述實(shí)現(xiàn)中對(duì)TCP的連接控制。需要注意的是,連接的擁塞控制在本小節(jié)不過(guò)多涉及,后面單獨(dú)小節(jié)描述。

4個(gè)定時(shí)器:重傳定時(shí)器、2MSL定時(shí)器、persist定時(shí)器、keepalive定時(shí)器

連接雙方通過(guò)以下一些事件來(lái)維持連接的狀態(tài), 發(fā)送方:發(fā)送緩沖區(qū)、4個(gè)定時(shí)器、發(fā)送窗口、擁塞狀態(tài)計(jì)數(shù)器 接收方:接收緩沖區(qū)、4個(gè)定時(shí)器、接收窗口、擁塞狀態(tài)計(jì)數(shù)器

TCP連接更詳細(xì)的描述 通信雙方通過(guò)一些內(nèi)部狀態(tài)保持了彼此的信息,連接關(guān)系始終保持,并通過(guò)報(bào)文交換來(lái)進(jìn)行連接狀態(tài)的變更。由于是通過(guò)報(bào)文進(jìn)行連接狀態(tài)的維護(hù),所以報(bào)文沒(méi)有正確發(fā)出或被接收到時(shí),連接狀態(tài)就會(huì)變成意料之外了;除確認(rèn)報(bào)文本身不被確認(rèn),其他報(bào)文都會(huì)有確認(rèn)報(bào)文進(jìn)行確認(rèn);報(bào)文(包括確認(rèn)報(bào)文)可能超時(shí)、需要重傳。下面是通信過(guò)程中一些重要報(bào)文的交互序列。

發(fā)送方 網(wǎng)絡(luò)(中間路由器等組成) 接收方

發(fā)送方為Windows,接收方為L(zhǎng)inux,操作如下

krt@krt:~$ perl ksock.pl --sleep-before-listen=1
Windows下
C:Userwin-krtDesktop>telnet 192.168.47.120 9876    krt@krt:~$ sudo tcpdump -n -i eth0 tcp port 9876 tcpdump: verbose output suppressed, use -v or -vv for full protocol decode listening on eth0, link-type EN10MB (Ethernet), capture size 262144 bytes 13:59:16.575626 IP 192.168.47.1.65281 > 192.168.47.120.9876: Flags [S], seq 2588085696, win 8192, options [mss 1460,nop,wscale 2,nop,nop,sackOK], length 0 13:59:16.575678 IP 192.168.47.120.9876 > 192.168.47.1.65281: Flags [S.], seq 3751549776, ack 2588085697, win 29200, options [mss 1460,nop,nop,sackOK,nop,wscale 7], length 0 13:59:16.577107 IP 192.168.47.1.65281 > 192.168.47.120.9876: Flags [.], ack 1, win 16425, length 0 13:59:19.564526 IP 192.168.47.1.65281 > 192.168.47.120.9876: Flags [P.], seq 1:2, ack 1, win 16425, length 1 13:59:19.564747 IP 192.168.47.120.9876 > 192.168.47.1.65281: Flags [.], ack 2, win 229, length 0 13:59:19.565023 IP 192.168.47.120.9876 > 192.168.47.1.65281: Flags [P.], seq 1:13, ack 2, win 229, length 12 13:59:19.763747 IP 192.168.47.120.9876 > 192.168.47.1.65281: Flags [P.], seq 1:13, ack 2, win 229, length 12 13:59:19.763849 IP 192.168.47.1.65281 > 192.168.47.120.9876: Flags [.], ack 13, win 16422, length 0 13:59:19.764023 IP 192.168.47.1.65281 > 192.168.47.120.9876: Flags [.], ack 13, win 16422, options [nop,nop,sack 1 {1:13}], length 0 13:59:23.688209 IP 192.168.47.1.65281 > 192.168.47.120.9876: Flags [F.], seq 2, ack 13, win 16422, length 0 13:59:23.688372 IP 192.168.47.120.9876 > 192.168.47.1.65281: Flags [F.], seq 13, ack 3, win 229, length 0 13:59:23.689053 IP 192.168.47.1.65281 > 192.168.47.120.9876: Flags [.], ack 14, win 16422, length 0

連接建立

連接建立過(guò)程中會(huì)經(jīng)歷被稱為“三次握手”的報(bào)文交互。

連接建立過(guò)程主要目的在于協(xié)商雙方通信的細(xì)節(jié),雙方的初始序列號(hào)、窗口大小、最大報(bào)文段MSS大小等。

連接斷開

數(shù)據(jù)傳輸

數(shù)據(jù)交換(基本的確認(rèn)、超時(shí)、重傳,滑動(dòng)窗口)

交互數(shù)據(jù)和批量數(shù)據(jù)交換

擁塞控制

性能和常用網(wǎng)絡(luò)工具

tcpdump lsof netstat ss /proc
iputils包 net-tools包 iproute2包

您可能感興趣的文章:
  • Java URL自定義私有網(wǎng)絡(luò)協(xié)議
  • SQL Server 2008網(wǎng)絡(luò)協(xié)議深入理解
  • Getmac返回計(jì)算機(jī)中所有網(wǎng)卡的媒體訪問(wèn)控制 (MAC) 地址以及每個(gè)地址的網(wǎng)絡(luò)協(xié)議列表
  • winsockfix網(wǎng)絡(luò)協(xié)議修復(fù)工具
  • python3實(shí)現(xiàn)TCP協(xié)議的簡(jiǎn)單服務(wù)器和客戶端案例(分享)
  • C#基于TCP協(xié)議的服務(wù)器端和客戶端通信編程的基礎(chǔ)教程
  • 使用C語(yǔ)言編寫基于TCP協(xié)議的Socket通訊程序?qū)嵗窒?/li>
  • Android編程使用HTTP協(xié)議與TCP協(xié)議實(shí)現(xiàn)上傳文件的方法
  • Java基于Tcp協(xié)議的socket編程實(shí)例
  • .Net WInform開發(fā)筆記(二)Winform程序運(yùn)行結(jié)構(gòu)圖及TCP協(xié)議在Winform中的應(yīng)用
  • Packetdrill的簡(jiǎn)明使用手冊(cè)

標(biāo)簽:沈陽(yáng) 樂(lè)山 河南 長(zhǎng)治 滄州 紅河 新疆 上海

巨人網(wǎng)絡(luò)通訊聲明:本文標(biāo)題《TCP協(xié)議詳解_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理》,本文關(guān)鍵詞  ;如發(fā)現(xiàn)本文內(nèi)容存在版權(quán)問(wèn)題,煩請(qǐng)?zhí)峁┫嚓P(guān)信息告之我們,我們將及時(shí)溝通與處理。本站內(nèi)容系統(tǒng)采集于網(wǎng)絡(luò),涉及言論、版權(quán)與本站無(wú)關(guān)。
  • 相關(guān)文章
  • 收縮
    • 微信客服
    • 微信二維碼
    • 電話咨詢

    • 400-1100-266
    娱乐| 屏南县| 东山县| 吴忠市| 巴楚县| 宣汉县| 绥滨县| 安庆市| 济宁市| 富阳市| 杭锦后旗| 靖边县| 建宁县| 垣曲县| 丽江市| 闸北区| 庆城县| 太湖县| 彰化市| 正镶白旗| 富宁县| 呼伦贝尔市| 喀什市| 盘山县| 江阴市| 郁南县| 通道| 西乡县| 绿春县| 渝北区| 抚州市| 新巴尔虎右旗| 临沂市| 睢宁县| 运城市| 巴南区| 乌拉特中旗| 塔城市| 宁津县| 隆子县| 化隆|