趣谈网络协议---TCP协议:因性恶而复杂,先恶后善反轻松

TCP包头格式
在这里插入图片描述

  • 序号解决包的乱序问题。
  • 确认序号确认对方收到,没有收到则重新发送。
  • 状态位维护连接的状态。SYN发起连接,ACK回复,RST重新连接,FIN结束连接。
  • 窗口大小用于流量控制。

TCP三次握手
在这里插入图片描述
为什么是3次握手?
1、为了防止已失效的连接请求报文段突然又回到服务端。

两次次握手:A的请求连接B的报文在网络中滞留,延误到连接释放后才到达B,B以为是A新发起的连接请求,同意建立连接,浪费了资源:端口、内存等。

而三次握手可防止上述情况发生,因为A不确认,B就不会建立连接。

大部分情况下,A和B建立连接后,A会马上发数据。如果不发,B可以开启keepalive,发送探活包。B也可以对于长时间不发包的客户端,主动关闭。

2、商量TCP包的序号。每个连接都要有不同的序号,起始序号随时间变化。

TCP4次挥手
在这里插入图片描述
为什么是4次挥手?
对于双向连接,2次握手只是断开单向连接,双向断开就需要4次挥手。第2、3次挥手不能合在一起,因为此时只能表明A不发送数据了,B可能还有数据要发送。

为什么A第4次挥手确认了ACK后,再TIME-WATI状态要等2MSL?
1、确认B收到最后的ACK。假如B没有收到ACK,会超时重传FIN,那么A在2MSL内就能重新收到FIN,于是再发送ACK。

有一种异常情况,B超过2MSL仍然没有收到ACK,即便重发FIN,A也不会再发送ACK了,而是发送RST,这样B就知道A已经离开。

2、防止已失效的报文段出现在下次连接中。A在发送最后一个ACK之后,再经过经过2MSL,就可以使本链接持续时间内所产生的所有报文段都从网络中消失。从而保证在关闭连接后不会有还在网络中滞留的报文段去骚扰B。

TCP状态机
在这里插入图片描述
如何实现一个靠谱的协议?
为保证顺序性,每个包都有一个ID。

为保证不丢包,对于发送的包都要进行应答,应答不是一个一个来,而是应答某个之前的ID,表示都收到了,称累计确认或累计应答。

为记录发送包和接受包,在发送端和接受端分别都有缓存来保存这些记录。

流量控制
流量控制,通过滑动窗口控制发送方的速度,防止将接收方塞满。接收方在对包的确认中,会携带一个窗口大小,叫Advertised window。

发送端:
在这里插入图片描述
接收端:
在这里插入图片描述
MaxRcvBuffer 为最大缓存量。

NextByteExpected 和 LastByteRead 的差是还没被应用层读取的部分占用掉 MaxRcvBuffer 的量,定义为 A。

AdvertisedWindow 其实是 MaxRcvBuffer 减去 A。

当接收方来不及处理,窗口中全是“接收已确认”,即窗口大小为0,发送方会定时发送窗口探测数据包。为防止低能窗口综合征,当窗口大小达到一定值,或为缓存区一半时,才更新窗口。

顺序问题和丢包问题
借助滑动窗口解决。

假设4的确认到了,5的ACK丢了,6、7的数据包丢了。

1、一种方法是超时重传。对每个发送了但没有收到ACK的包,设一个定时器,超时后重传。时间应大于RTT,否则会引起不必要的重传。

估计往返时间,需要TCP通过采样RTT,然后加权平均。除了采样RTT,还要采样RTT的波动范围,计算出一个估计的超时时间。称自适应
重传算法(Adaptive Retransmission Algorithm)。

7再次超时,超时间隔加倍。两次超时,不宜频繁反复发送。

2、另一种是快速重传。当接收方收到一个序号大于下一个所期望的报文段时,发送3个冗余的ACK,客户端收到后,可在定时器过期前,重传丢失的报文段。

3、还有一种方式时Selective Acknoledgment(SACK)。在TCP头里加SACK,可将缓存地图发送给发送方。例如可发送ACK6、SASCK8、SACK9,发送方
便可看出是7丢了。

拥塞控制问题
拥塞控制,通过拥塞窗口控制发送方的速度,防止将网络塞满。

LastByteSent - LastByteAcked <= min {cwnd, rwnd} ,拥塞窗口和滑动窗口共同控制发送的速度。

如何判断网络是否满?丢包,超时重传。

慢启动阶段:需要试探性的发包,一开始cwnd=1,收到一个确认加1,于是下次发送2个包。窗口大小就会不断翻倍,指数增长。

拥塞避免阶段:窗口大小达到ssthresh后,开始线性增加。

直到出现丢包,ssthresh = cwnd / 2,cwnd = 1,重新开始慢启动。

快速重传:但将传输速度一下子降下来会导致网络卡顿,这时可以使用快速重传。在超时前收到3个冗余的ACK后,认为网络拥塞情况不是很严重,ssthresh = cwnd / 2,cwnd = cwnd / 2,当三个包返回时,cwnd = sshthresh + 3。

在这里插入图片描述
TCP的拥塞控制要避免的两个现象是有问题的。

1、丢包不代表网络已满。公网带宽不满也会丢包。

2、要等中间设备的缓存都填满了,才发生丢包,降低速度为时已晚。

为优化这两个问题,有了TCP BBR拥塞算法。企图找一个平衡点,通过不断加快发送速度,填满网络,但不填满中间设备的缓存,可达到高带宽和低时延的平衡。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值