0
点赞
收藏
分享

微信扫一扫

计算机网络(十)——TCP

梦为马 2022-04-17 阅读 62

文章目录

1. TCP

TCP是因特网运输层的面向连接的可靠运输协议。

1.1 TCP连接

(1)定义

  • TCP是面向连接的:两个进程进行通信之前,必须先相互握手,以建立确保数据传输的参数。
  • TCP是双工的:进程AB之间建立了TCP连接,则进程A既可以向B发送数据,也可以接收来自进程B的数据。
  • TCP是点对点的:TCP是单个发送方和单个接收方间的连接。

(2)建立TCP连接

  • 三次握手:客户首先发送一个特殊的TCP报文,服务器发送特殊的TCP报文以响应,最后客户再用第三个特殊的TCP报文响应。
    ①前两个报文段不承载有效载荷,第三个报文段可以承载有效载荷。

(3)缓存
在这里插入图片描述

  • 发送缓存: 客户进程通过套接字传递数据流,TCP将数据保存在发送缓存中。
    ①TCP会不时从发送缓存中取出一块数据,为其加上首部字段形成TCP报文段后传送到网络。
  • 接收缓存: 服务器将接收到的TCP报文段中的数据保存在接收缓存中。
  • MSS: 最大报文段长度,即可从缓存中取出并放入报文段的数据数量。

(4)TCP连接的组成

  • 缓存
  • 变量
  • 套接字

1.2 TCP报文段结构

TCP报文段由首部字段和数据字段组成。
(1)首部字段
TCP首部一般是20个字节,UDP首部是8个字节。

  • 源端口号和目的端口号:各占16比特,被用于多路复用和多路分解。
  • 检验和:16比特,用于差错检验。
  • 序号:32比特,用于实现可靠数据传输服务。
  • 确认号:32比特,用于实现可靠数据传输服务。
  • 接收窗口:16比特,用于流量控制。
  • 紧急数据指针:16比特。
  • 首部长度:4比特,指示了以32比特的字为单位的TCP首部字段长度。(一般为5)
  • 标志字段:6比特,包括ACK, PST, SYN, FIN, CWR, ECE, PSH, URG。
  • 选择字段:用于协商最大报文段长度MSS。

在这里插入图片描述

问题:比较UDP, TCP的报文段结构

  • TCP和UDP报文段都是由首部段和数据段组成。
  • TCP和UDP在首部段中都包含源端口号、目的端口号、检验和。
  • TCP的首部字段一般为20字节,UDP为8字节。

参考网址:计算机网络(八)UDP

(2)序号和确认号
定义

  • 序号: 一个报文段的序号是其数据段首字节的字节流编号。
    ①一条TCP连接双方可以随即第选择初始序号,从而减少将已终止连接的仍在网络中报文段误认为有效报文段的可能性。
  • 确认号: 主机正在等待的数据的下一个字节的序号。
    ①一般客户的的确认号是服务器的序号。

累积确认

  • TCP只确认该流中第一个丢失字节为止的字节,或接收方已接受序号n以前包括序号n的分组。
  • 例如:主机A收到主机B包含序号0-535以及900-1000的报文段,没有收到36-899的报文段。则A到B的下一个报文段的确认号为536.

1.3 往返时间的估计与超时

超时间隔必须大于连接的往返时间(RTT),否则会造成不必要的重传。

  • RTT: 一个报文段发出到对报文段的确认被接收的时间间隔。

1.3.1 估计往返时间

(1)EstimatedRTT
希望产生一个EstimatedRTT来接近每个RTT的SampleRTT。

  • 大多数TCP的实现仅在某一时刻做一次SampleRTT的测量。
  • TCP决不为已被重传的报文段计算SampleRTT。
  • 由于路由器拥塞和端系统负载的变化,SampleRTT会发生波动。因此采取对SampleRTT采样取平均,soft update的方法。
    E s t i m a t e d R T T = ( 1 − α ) E s t i m a t e d R T T + α S a m p l e R T T EstimatedRTT = (1-\alpha) EstimatedRTT+\alpha SampleRTT EstimatedRTT=(1α)EstimatedRTT+αSampleRTT
    其中, α \alpha α的推荐值是 α = 0.125 \alpha = 0.125 α=0.125

(2)DevRTT
DevRTT定义了EstimatedRTT的波动情况。
D e v R T T = ( 1 − β ) D e v R T T + β ∣ E s t i m a t e d R T T − S a m p l e R T T ∣ DevRTT = (1-\beta)DevRTT+\beta|EstimatedRTT-SampleRTT| DevRTT=(1β)DevRTT+βEstimatedRTTSampleRTT

其中,如果SampleRTT波动较小(即靠近EstimatedRTT),则DevRTT较小。如果SampleRTT波动较大(EstimatedRTT波动较大),则DevRTT较大。

1.3.2 设置和管理重传超时间隔

超时间隔应该大于等于EstimatedRTT,但不应该比EstimatedRTT大太多。因此要求超时间隔设为EstimatedRTT加上一定余量。

  • 当采样RTT波动较大时,余量应该大些。
  • 当采样RTT波动小时,余量应该小些。

T i m e o u t I n t e r v a l = E s t i m a t e d R T T + 4 ∗ D e v R T T TimeoutInterval = EstimatedRTT + 4 * DevRTT TimeoutInterval=EstimatedRTT+4DevRTT

1.4 可靠数据传输

因特网的网络层服务(IP服务)是不可靠的。IP不保证数据报的交付、不保证数据报的按序交付、不保证数据报中数据的完整性。
核心

  • 超时(分组丢失、提早超时)
  • 累积确认

1.4.1 定义

  • TCP可靠传输服务确保:进程从接收缓存中读出的数据流是无损坏、按序的、无间隙和非冗余的数据流。
  • TCP遵循单一定时器的推荐。

(2)发送方
发送方有3个与发送和重传有关的主要事件。

  • 从上层应用程序接收数据
    ①若发送方缓存未满,生成具有序号NextSeqNum的TCP报文段,发送到网络层。
    ②若定时器没有运行,则启动定时器。
    在这里插入图片描述
  • 定时器超时
    重传具有最小序号的已发送而未确认的报文段,并重启定时器。
    在这里插入图片描述
  • 收到ACK
    收到的ACK字段值为y。因为TCP采用累积确认,所以y确认了字节序号在y之前的所有字节都已经被正确接收。
    ①若 y > S e n d B a s e y > SendBase y>SendBase,则令 S e n d B a s e = y SendBase = y SendBase=y。SendBase表示最小已发送而未确认的字节序号。
    在这里插入图片描述
    注意:
  1. 发送方在三种事件中都尝试启动定时器。在定时器超时时,一定会重启定时器。

(3)接收方
接收方收到来自发送方的TCP报文段后,会回发反馈信息。

  • NAK
    当接收到的报文数据出现差错,返回NAK。

  • ACK
    当报文被接收方正确接收后,会返回ACK报文。但是ACK报文序号会因为报文是否为失序报文而有所不同。
    ①具有所期望序号的按序报文到达延迟ACK,若下一个按序报文没有在一定时间间隔内到达,则发送值为当前序号的ACK。
    ②具有所期望序号的按序报文到达。另一个按序报文段等待ACK传输立即发送累积ACK,ACK值为连续的按序报文中的较大序号。
    ③比期望序号大的失序报文到达立即发送冗余ACK。ACK值为最后一个按序报文的序号,指示下一个期待字节的序号。
    ④已正确接收的报文到达: 立即发送ACK。
    在这里插入图片描述

(4)重传
当定时器超时时,TCP发送方会重传最小的已发送而未确认的报文段。其中,可能因为分组丢失或提前超时导致定时器超时。定时器超时一定会重传分组,但分组丢失不一定会重传分组!

  • 分组丢失:可能不会导致重传。
    累积确认避免重传若报文段n+1的确认报文在报文段n超时之前到达,则不会重传报文段n。
    在这里插入图片描述
    ②一般的,如果一个报文段丢失,就可能引起许多一个接一个的冗余ACK。
  • 提前超时:一定会导致重传。
    在这里插入图片描述

1.4.2 超时间隔加倍

定时器超时会重传最小序号的已发送而未确认的报文段。同时每次TCP重传都会将下一次的超时间隔翻倍。 因此超时间隔在每次重传后呈指数级增长。
(1)超时间隔

  • 定时器超时:超时间隔翻倍。
  • 收到应用程序数据
  • 收到ACK
    T i m e o u t I n t e r v a l = E s t i m a t e d R T T + 4 ∗ D e v R T T TimeoutInterval = EstimatedRTT + 4 * DevRTT TimeoutInterval=EstimatedRTT+4DevRTT

1.4.3 快速重传

解决问题
当超时周期较长时,一个报文段丢失后需要等待较长时间才能重传丢失分组,增加了端到端的时延。

  • 因为接收方收到失序分组后会对已接受的最后一个按序分组进行重复确认,发送一个冗余ACK。
  • 当一个报文段损失,很有可能引起很多的冗余ACK。

快速重传
一旦收到3个冗余ACK,TCP就快速重传。在定时器超时前就重传报文段。
在这里插入图片描述

1.5 流量控制(flow-control)

关键词

  • 接收窗口
  • 接收缓存

TCP为连接的每一侧都设置了接收缓存。当接收方收到正确、按序的字节后,将数据放入接收缓存中。当接收缓存满时,则会将多余字节丢弃。

(1)定义

  • 流量控制服务: 是一个速度匹配服务,使发送方的发送速率与接受方的接收速率相匹配。
  • 拥塞控制: TCP发送方因为IP网络的拥塞而被遏制。
  • 接收窗口: 发送方维护的变量,指示接收方还有多少可用缓存空间。

问题
当发送方发送速率大于接收方接收速率时,会导致连接的接收缓存溢出。

(2)流量控制服务
假设:
在这里插入图片描述
定义:
接收方已发送而未确认的报文段数量LastByteSent-LastByteAcked,不能超过接收方接收缓存空余空间大小rwnd。

  • TCP让发送方维护一个接收窗口,接收窗口用rwnd表示。
    r w n d = R e v B u f f e r − ( L a s t B y t e R e v d − L a s t B y t e R e a d ) rwnd = RevBuffer - (LastByteRevd - LastByteRead) rwnd=RevBuffer(LastByteRevdLastByteRead)
    其中, ( L a s t B y t e R e v d − L a s t B y t e R e a d ) (LastByteRevd - LastByteRead) (LastByteRevdLastByteRead)表示在缓存中还未被读取的字节个数。rwnd表示剩余可用的接受空间大小。
    在这里插入图片描述
  • 发送方轮流跟踪两个变量:LastByteSent, LastByteAcked。其中 L a s t B y t e S e n t − L a s t B y t e A c k e d LastByteSent-LastByteAcked LastByteSentLastByteAcked表示已发送而未确认的报文段个数。接收方需要保证:
    L a s t B y t e S e n t − L a s t B y t e A c k e d ≤ r w n d LastByteSent-LastByteAcked \leq rwnd LastByteSentLastByteAckedrwnd
  • 问题: 当主机B接收缓存存满后,主机A不能发送数据。但是当主机B上的应用程序将缓存清空后,因为TCP不向A发送带有rwnd新值的报文段,主机A陷入阻塞
    解决方法: 当主机B接收窗口为0(接收缓存满了),主机A继续发送只有一个字节数据的报文段。

1.6 TCP连接管理

缺点

  • TCP连接建立会显著增加时延。
  • 许多常见网络攻击利用TCP连接管理中的弱点。

(1)三次握手
TCP连接创建过程称为3次握手。

  • 第一步: 客户端TCP向服务器TCP发送一个SYN报文段
    ①SYN比特置1.
    客户端随机选择一个初始序号client_isn,并置于SYN报文段的序号字段。
    ③SYN报文段中不包含应用层数据。

  • 第二步: 服务器提取出TCP SYN报文段,接着向客户端发送允许连接SYNACK报文段
    ①SYN比特置1,ACK比特置1.
    ②服务器为TCP连接分配TCP缓存和变量
    服务器随机选择一个初始序号server_isn,并置于SYNACK报文段的序号字段。
    ④将SYNACK报文段确认号字段置为client_isn+1
    ⑤SYNACK报文段不包含应用层数据。

  • 第三步: 客户端收到SYNACK报文段,对服务器允许连接的报文段进行确认
    SYN比特置0,ACK比特置1.
    ②客户端为TCP连接分配TCP缓存和变量
    ③报文段序号位置为client_isn+1
    ④报文段确认位置为server_isn+1
    在这里插入图片描述
    (4)四次挥手
    TCP连接结束的过程称为四次挥手。

  • 第一步: 客户端向服务器发送终止报文段。
    ①终止报文段中,FIN比特置1.

  • 第二步: 服务器接收客户端的终止报文段,并对其进行确认。
    ①ACK报文段,ACK比特置1.

  • 第三步: 服务器向客户端发送终止报文段。
    ①终止报文段,FIN比特置1.

  • 第四步: 客户端接收服务器的终止报文段,并对其进行确认。
    ①ACK报文段,ACK比特置1.
    在这里插入图片描述

(3)客户TCP状态序列
在这里插入图片描述
(4)服务器TCP状态序列
在这里插入图片描述

1.7 拥塞控制原理

在实践中,丢包一般是当网络拥塞时路由器缓存溢出引起的。

1.7.1 拥塞原因与代价

原因
随着主机发送速率的增加,网络变得拥塞。(路由器输出链路具有有限的容量)

代价
由发送速率增长导致的排队时延增加、提前超时与分组丢失相关。

  1. 当发送速率接近链路容量时,分组将经历巨大的排队时延
  2. 如果缓存溢出导致分组丢失,发送方必须重传该分组。接收方的吞吐量降低。
  3. 提前超时可能导致重发不必要分组,引发路由器利用链路带宽转发不必要分组。接收方吞吐量下降。
  4. 当分组沿一条路径被丢弃时,上游路由器用于转发该分组的容量被浪费。

其中,分组丢失会导致对供给载荷与链路带宽的浪费。提前超时可能导致浪费链路带宽。

(1)两条连接共享无限缓存的单挑路由
特点:不会发生分组丢失。
在这里插入图片描述
假设:主机A, B向路由器提供流量的速度是 λ i n \lambda_{in} λin字节/秒,路由器输出链路容量大小为R。

  • 接收方的吞吐量(每秒接收的字节数):
    ①当发送速率在0-R/2时,吞吐量等于发送方的发送速率。
    ②当发送速率大于R/2时,吞吐量等于R/2。
    在这里插入图片描述
  • 平均时延
    ①当发送速率接近R/2时,平均时延越来越大。
    ②当发送速率超过R/2时,路由器中分组排队时延趋于无穷大,源和目的之间的平均往返时延也趋于无穷大。
    在这里插入图片描述
  • 网络拥塞的代价1: 当发送速率接近链路容量时,分组将经历巨大的排队时延。

(2)两个发送方和一台具有有限缓存的路由器
特点:当分组到达一个已满缓存时会被丢弃。
在这里插入图片描述
假设:应用程序将初始数据发送到套接字的速率为 λ i n \lambda_{in} λin,主机A, B向路由器提供流量的速度是 λ i n ′ \lambda_{in}' λin字节/秒(初始数据或重传数据),路由器输出链路容量大小为R。

  • 网络拥塞的代价2: 如果缓存溢出导致分组丢失,发送方必须重传该分组。接收方的吞吐量降低。
    ①发送方供给载荷不变时,有效载荷下降。

  • 网络拥塞的代价3: 提前超时可能导致重发不必要分组,引发路由器利用链路带宽转发不必要分组。接收方吞吐量下降。
    ①链路容量一定,转发不必要带宽会浪费占用的链路带宽。
    在这里插入图片描述

(3)4个发送方和具有有限缓存的多台路由器及多跳路径
特点:经路由器转发后的分组发送速率有上限。
在这里插入图片描述
假设:主机向路由器提供流量的速度是 λ i n \lambda_{in} λin字节/秒,路由器输出链路容量大小为R。

  • 网络拥塞的代价4: 当分组沿一条路径被丢弃时,上游路由器用于转发该分组的容量被浪费。

1.7.2 拥塞控制方法

实践中主要采用两种拥塞控制方法,我们根据网络层是否为运输层拥塞控制提供显式帮助进行区分。

  • 端到端拥塞控制:网络层没有为运输层拥塞控制提供显示支持。
    ①TCP采用端到端的拥塞控制方法。
    TCP报文的丢失(超时、3次冗余ACK确认)被认为是网络拥塞控制的迹象,TCP会减小相应的窗口长度。
  • 网络辅助的拥塞控制:路由器向发送方提供关于网络拥塞状态的显式反馈信息。
    ①直接网络反馈
    ②经由接收方的网络反馈
    在这里插入图片描述

1.7.3 TCP拥塞控制

问题

  1. TCP发送方如何限制向连接发送流量的速率。
  2. TCP发送方如何感知源与目的之间是否存在拥塞。
  3. 当TCP发送方感受到拥塞时,如何改变其发送速率。

问题1:TCP发送方如何限制向连接发送流量的速率?

  • 拥塞窗口(congestion window):发送方跟踪一个额外的变量cwnd,它对发送方向网络发送流量的速率进行限制。
    ①发送方中未被确认的数据量不能超过cwnd和rwnd中的最小值:
    L a s t B y t e S e n t − L a s t B y t e A c k e d ≤ min ⁡ c w n d , r w n d LastByteSent - LastByteAcked \leq \min{cwnd, rwnd} LastByteSentLastByteAckedmincwnd,rwnd

问题2:TCP发送方如何感知源与目的之间是否存在拥塞?

我们将TCP发送方的丢包事件定义为:超时或者3次冗余ACK。

  • 自计时: TCP使用确认触发来增大它的窗口长度。当发送方收到以前未确认报文的确认后,增加拥塞窗口长度rwnd。
    ①当确认高速率到达,拥塞窗口则会迅速地增大。
  • 当丢失报文段时应当降低TCP发送方的发送速率。
  • 带宽探测: 为探测拥塞开始出现的速率,TCP发送方需要增加它的传输速率。

问题3:拥塞控制算法

当发送方检测到丢包事件(超时、3次冗余ACK确认)后,应该缩小窗口长度,限制发送速率。
拥塞控制算法包括三个部分:

  • 慢启动
  • 拥塞避免
  • 快速恢复

其中,慢启动和拥塞避免之间的差异在于收到ACK做出增加rwnd的方式。慢启动和拥塞避免是TCP的强制部分,而快速回复是推荐部分。

在这里插入图片描述
(1)慢启动

  • 启动:当一条TCP连接开始时,cwnd值初始化为1个MSS。
  • 报文段确认每当传输的报文首次被确认,cwnd值就增加1个MSS。 拥塞窗口长度呈指数型增长。
    ①增加一个MSS会使下次传输的报文段加倍,从而使在下一次收到的ACK也加倍。
    在这里插入图片描述
  • 超时丢包:TCP发送方将cwnd设置为1个MSS,重启慢启动。并将ssthresh(慢启动阈值)设置为cwnd/2。
  • 3次冗余ACK
    ①Tahoe早期TCP版本:与超时丢包处理方法一致。
    ②Reno:将cwnd减半并加3,同时将 ssthresh(慢启动阈值)设置为cwnd/2,并进入快速修复状态。

(2)拥塞避免

  • 启动: 在慢启动状态下,当rwnd等于ssthresh时,进入拥塞避免状态。
  • ACK每当传输的报文段首次被确认,cwnd增加 M S S ( M S S / c w n d ) MSS (MSS/cwnd) MSS(MSS/cwnd)字节。 拥塞窗口长度呈线性增长。
    在这里插入图片描述
    超时丢包(timeout): 与慢启动算法一样。TCP发送方将cwnd设置为1个MSS,重启慢启动。并将ssthresh(慢启动阈值)设置为cwnd/2。
  • 3次冗余ACK(dupACKcount): TCP将cwnd的值减半加3,并将ssthresh的值记录为cwnd的一半。接着进入快速恢复状态。

(3)快速恢复

  • 启动:在慢启动或拥塞避免状态时,发送方收到3次冗余ACK,进入快速恢复状态。
  • ACK当一个传输的报文首次被确认,令cwnd = ssthresh并进入拥塞避免状态。
  • 超时丢包(timeout):与慢启动算法一样。TCP发送方将cwnd设置为1个MSS,ssthresh设置为cwnd/2,同时重启慢启动。
  • 冗余ACK每当收到冗余ACK,cwnd值就增加1个MSS。

(4)问题:可能的状态变化情况

慢启动

  1. 慢启动 --> 慢启动:timeout
  2. 拥塞避免 --> 慢启动:timeout
  3. 快速恢复 --> 慢启动:timeout

拥塞避免

  1. 慢启动 --> 拥塞避免:cwnd == ssthresh
  2. 快速恢复 --> 拥塞避免:ACK
  3. 拥塞避免 --> 拥塞避免:ACK

快速恢复

  1. 慢启动 --> 快速恢复:3次冗余ACK
  2. 拥塞避免 --> 快速恢复:3次冗余ACK
  3. 快速恢复 --> 快速恢复:冗余ACK
    在这里插入图片描述

例子:TCP拥塞窗口的演化
假设:在T = 8时刻发生了3次冗余ACK

  • Tachoe:不管是超时还是3次冗余ACK的丢包事件,都无条件将其拥塞窗口减为1.
  • Reno:综合了快速恢复。
    在这里插入图片描述

(5)AIMD
忽略一条连接开始时初始的慢启动阶段,假定丢包由3个冗余ACK而不是超时指示。

  • 每个RTT内cwnd线性增加1MSS.
  • 出现3次冗余ACK时cwnd减半加3.

因此TCP拥塞控制常常被称为加性增、乘性减AIMD 拥塞控制方式。AIMD控制引发了”锯齿行为“。
在这里插入图片描述

(6)对TCP吞吐量的宏观描述

  • 当窗口长度为w字节,且当前往返时间是RTT秒时,TCP的发送速率为 w / R T T w / RTT w/RTT
  • 当一个丢包事件发生时,用W表示w的值,让w值减半。假设在连续持续期间RTT和W几乎不变,则TCP传输速率在 W / 2 ∗ R T T W / 2*RTT W/2RTT W / R T T W / RTT W/RTT之间变化。
  • 一条连接的平均吞吐量:
    0.75 × W R T T \frac{0.75 \times W}{RTT} RTT0.75×W
举报

相关推荐

0 条评论