TCP协议详解

文章详细介绍了TCP协议的特性,包括其面向连接、可靠传输、字节流特性和头部结构。接着阐述了TCP连接的三次握手过程,解释了为何需要三次握手来确保双方的通信能力。此外,还讨论了断开连接的四次挥手及超时重传、滑动窗口、拥塞控制策略(慢开始、拥塞避免、快重传和快恢复)等关键概念,确保数据传输的高效和稳定性。
摘要由CSDN通过智能技术生成

TCP协议特性

1、面向连接的
2、提供可靠的全双工传输
3、面向字节流的
4、保证数据顺序和正确性
4、属于传输层协议

TCP协议头

在这里插入图片描述
TCP协议头总长度位20个字节如上图所示

  1. 源端口号占16位(source port) :客户端发起TCP请求时所使用的端口号,端口号范围0~65535
  2. 目的端口号占16位(destination port) :客户端需要访问的服务端使用的端口号,端口号范围0~65535
  3. 序列号占32位(sequence number) : 数据包序列号,用于保证数据报的有序传输,由发送方生成发送到接收方
  4. 确认号占32位(acknowledgment number) :数据包应答序号,用于保证数据的可靠传输,接收方在成功接收到发送方的数据包后,后返回应答序号给发送方,表示数据报成功被接收。一般位序列号加1
  5. 首部长度占4位(data offset) :首部长度表示从源端口号首端到选项末端之间的数据长度。
  6. 保留位占6位(reserved) :用于后期扩展使用默认填充0
  7. URG占1位 :紧急位标志,当置位时,表示紧急指针段有效,此数据包中包含紧急数据,需要尽快发送
  8. ACK占1位 :确认序号位,置位时表示数据包中确认序号有效。
  9. PSH占1位 :被置位时,表示该报文具有高优先级,需要尽快传输,不需要等待发送缓冲区满后再发送。
  10. PST占1位 :被置位时,表示连接出现异常,连接需要断开重连;又称复位报文
  11. SYN占1位 :被置位时,表示此报文为同步报文,tcp建立连接时会将其置位
  12. FIN占1位:被置位时,表示此报文为断开连接报文,tcp在断开连接时,会发送,四次挥手时,客户端和服务端都会发送此标识位。
  13. 窗口大小占用16位(window):表示允许对方发送的最大数据量。
  14. 校验码占16位(check number) :用于校验数据在传输过程中有没有被改变,采用CRC算法,被改变的报文会被丢弃。
  15. 紧急指针占16位(urgent pointer):当URG位为1时,用于指出紧急数据的长度。

TCP状态迁移

在这里插入图片描述

  1. CLOSED:起始点,在超时或者连接关闭时候进入此状态,这并不是一个真正的状态,而是这个状态图的假想起点和终点。
  2. LISTEN:服务器端等待连接的状态。服务器调用 socket,bind,listen函数之后进入此状态,开始监听客户端发过来的连接请求。称为应用程序被动打开,等到客户端连接请求。
  3. SYN_SENT:客户端第一次握手发生阶段,客户端主动发起连接。客户端调用 connect请求与服务器建立连接,发送SYN包( SYN=1,seq=x )给服务器端,然后进入 SYN_SENT 状态,等待服务器端确认。如果服务器端不能连接,则直接进入CLOSED状态。
  4. SYN_RCVD:第二次握手发生阶段,服务器端接收到客户端的 SYN,此时服务器由 LISTEN 进入SYN_RCVD状态;同时服务器端回应ACK包( SYN=1,ACK=1,seq=y,ack=x+1)。特殊转换:当客户端在发送 SYN 的同时也收到服务器端的SYN请求,即两个同时发起连接请求,那么客户端就会从 SYN_SENT 转换到 SYN_REVD 状态。
  5. ESTABLISHED:第三次握手发生阶段,客户端接收到服务器端的 ACK +SYN包后,也会发送一个 ACK确认包(ACK=1,ack=y+1),客户端进入ESTABLISHED 状态,表明客户端这边已经准备好,但TCP需要两端都准备好才可以进行数据传输。服务器端收到客户端的 ACK 之后会从 SYN_RCVD 状态转移到 ESTABLISHED状态,表明服务器端也准备好进行数据传输了。
  6. FIN_WAIT_1:第一次挥手。主动关闭的一方发送 FIN (FIN=1,seq=u)给对方,然后等待对方返回 ACK 。调用 close第一次挥手就进入此状态。
  7. CLOSE_WAIT:接收到FIN(FIN=1,seq=u) 之后,被动关闭的一方进入此状态。然后发送 ACK(ACK=1,FIN=1,ack=u+1,seq=w)。之所以叫 CLOSE_WAIT 是因为被动关闭的一方此时正在等待上层应用程序发出关闭连接指令。TCP关闭是全双工过程,被动方接收到FIN 后也需要调用 close 关闭,这个 CLOSE_WAIT 就是处于这个状态,等待发送 FIN,发送了FIN 则进入 LAST_ACK 状态。
  8. FIN_WAIT_2:主动端先执行主动关闭发送FIN,然后接收到被动方返回的 ACK (ACK=1,ack=u+1)后进入此状态。
  9. LAST_ACK:被动方发起关闭请求,由状态CLOSE_WAIT 进入此状态,具体动作是发送 FIN(ACK=1,FIN=1,seq=w,ack=u+1)给对方,同时在接收到ACK(ACK=1,ack=w+1) 时进入CLOSED状态。
  10. CLOSING:两边同时发起关闭请求时(即主动方发送FIN,等待被动方返回ACK,同时被动方也发送了FIN,在接收到被动方FIN到接收到被动方返回ACK之间的这个状态被称为CLOSING),主动方会由FIN_WAIT_1 进入此状态,等待被动方返回ACK。
  11. TIME_WAIT:从状态变迁图会看到,四次挥手操作最后都会经过这样一个状态然后进入CLOSED状态。共有三个状态会进入该状态。

三次握手建立连接

在这里插入图片描述
三次握手主要作用:

  • 是确认双方的收发功能都是正常的
  • 确认双方的初始化序列号,为后续可靠传输做准备
  1. 第一次握手由客户端主动发起连接,TCP头中SYN位置1,seq=x(随机数),同时客户端状态由CLOSED转化为SYN_SEND状态。
  2. 第二次握手由服务端发起,对客户端发送的FIN进行ACK回复,并发送FIN给客户端。在服务端收到SYN=1,seq=x后,回复ACK和FIN到客户端即ACK=1,FIN=1,ack=x+1,seq=y(随机数),然后客户端由LISTEN状态转换为SYN_RCVD状态
  3. 第三次握手由客户端发起,对服务端发送的FIN进行应对即ACK=1,ack=y+1,状态从SYN_SEND转换为ESTABLISHED。
  4. 当服务端收到客户端的ACK后表示三次握手结束。服务端状态也进入ESTABLISHED。后续客户端和服务端可以互相发送数据。
    注:三次握手的三个数据包中其中第一次和第二次是包是不可以携带数据的,第三次握手是可以携带工具的。

四次挥手断开连接

在这里插入图片描述

  1. 第一次挥手即为主动断开连接的一方,可以是客户端也可以是服务端,发送FIN=1,seq=u到被动断开一方。以上图例以客户端断开连接为例。当客户端发送FIN后客户端会从ESTABLISHED状态转换为FIN_WAIT_1状态。
  2. 第二次挥手服务端在接收到客户端的FIN数据包后,对客户端进行应答发送ACK=1,seq=v,ack=u+1,服务端状态由ESTABLISHED变化为CLOSE_WAIT,客户端在接收到ACK后状态会从FIN_WAIT_1转变为FIN_WAIT_2。
  3. 第三次挥手为服务端发送FIN=1,ACK=1,seq=w,ack=u+1到客户端表示服务端没有数据要发送了要断开连接。发送后状态由CLOSE_WAIT转变为LAST_ACK状态。
  4. 客户端在接收到服务端的FIN后会回复ACK给服务端即ACK=1,ack=w+1,seq=u+1。此时客户端等待2MSL后变为CLOSED状态。服务端在接收到客户端应对的ACK后状态从LAST_ACK转变为CLOSED。

超时重传机制

超时重传即在数据报文发送后,开始计时到等待到应答到来的这段时间。如果超过这段时间没有收到对端的应答,那么就会重新发送数据。发送数据报文后到等待应答到来的这段时间叫做超时重传时间RTO(Retransmission Time-Out)。同时还有一个RTT(Round Trip Time)是指报文往返时间,即报文发送的时间戳到接收到应答时的时间戳的这段时间。
超时重传时间的设定是一个比较复杂的问题,太短则会出现很多不必要的重传,增加网络的负载;如果时间太长,那么网络的空闲时间会增多,降低传输效率。

滑动窗口

在这里插入图片描述
滑动窗口分为发送窗口接收窗口
发送滑动窗口大小为上图蓝色矩形SND.WND=20;#1区域位置的数据表示已经发送且接收到了对方的ACK应答的数据;#2区域的数据表示已经发送但是还没有接收到对方的ACK应答的数据。#3区域的数据表示未发送但允许发送的数据。#4区域表示需要发送但是当前不允许发送的数据。接收缓冲区同理。

拥塞控制

在这里插入图片描述

慢开始

发送方会维持一个拥塞窗口cwnd的状态变量,拥塞窗口的大小取决于拥塞程度,并且会在收发包过程中动态的进行变化。发送方会让本端的发送窗口等于拥塞窗口。
首先以指数方式进行增加发送数据包的数量,当网络出现阻塞的情况,拥塞窗口就会减小。
假设cwnd初始值为1,那么先发送1个数据包,在成功接收到应答后,将cwndx2=2,此时允许发送2个数据包,收到应答后再将cwndx2=4,此时允许发送4个数据包,以此类推。当出现没有及时收到ACK时认为网络出现拥堵,此时将cwnd/2,然后重新开始慢开始,以此循环。

拥塞避免

拥塞避免算法是让拥塞窗口缓慢增长,每经过一个往返时间RTT就把发送方的拥塞窗口cwnd加1,而不是加倍,拥塞窗口按线性增长。
不论是在慢开始期间还是拥塞避免期间,只要判断网络发生了拥塞ssthresh就设置为当前发送窗口大小的一半,然后重新开始执行慢开始算法,这样做的目的是迅速减少主机发送到网络中的分组数,使发生拥塞的路由器有足够的时间把队列中积压的分组处理完毕。

快重传

在这里插入图片描述

快重传要求接收方在收到一个失序的报文段后立即发出重复确认,为的是让发送方知道有一个报文丢失了,快速重传算法规定,发送方只要一连收到三个重复确认就应当立即重传对方还没有接收到的报文段,而不必继续等待设置的重传计时器时间到期。

快恢复

在这里插入图片描述

快恢复算法适合快重传算法配合使用的
(1)当发送方连续收到三个重复确认的时候,执行“乘法减小”算法,将ssthresh门限减半(为了预防网络发生拥塞),但是接下来不执行慢开始算法,因为如果网络发生拥塞的话就不会收到好几个重复的确认,所以发送方现在认为网络可能没有出现拥塞。
(2)此时不会执行慢开始算法,而是将拥塞窗口cwnd设置为ssthresh减半后的值,然后执行拥塞避免算法,让cwnd缓慢变大。

思考

TCP为什么要三次握手?

三次握手时为了确认收发双方的接收和发送能力都是正常的。如果少于三次那么不能达到确认双方收发功能正常的效果,如果超过三次则没会出现多余。

  1. 第一次握手由客户端发起到服务器,此步骤服务器知道客户端的发送功能是正常的
  2. 第二次握手由服务器应答数据到客户端,此步骤客户端可以确认客户端的发送功能,服务器可以确认服务器的收发功能是正常的,但此时服务器不知道客户端的数据接收功能是否正常。
  3. 第三次握手,客户端应答数据到服务器端,此步骤服务器可以确认客户端的接收功能是正常的。
    注意:如果只有两次握手,那么只能确认客户端的发送能力正常、服务端的接收和发送能力正常,但是服务端无法确认客户户端接收能力是否正常,只有收到ACK应答才能证明客户端接收功能正常。

TCP为什么要四次挥手?

tcp的数据传输是双向的,在一方没有数据要发送了的情况下就可以主动发起断开连接,被动断开方在接收到主动方的断开连接后会发送确认数据包,此时表示主动发的发送连接和被动方的接收连接断开;此时被动方还是可以发送数据给主动方的,当被动方没有数据要发送的时候再发送断开命令到主动方,主动发再对被动方应答可以断开连接,此时被动方的发送连接和主动方的接收连接断开,此时TCP连接完全断开。

TCP最后一次挥手为什么需要等待2MSL

保证客户端发送给服务端的ACK能成功到达。如果客户端最后一次回复的ACK丢失的话,服务端会超时重传FIN给客户端,等待2MSL可以确保在ACK丢失后还能够接收到服务端的超时重传FIN,客户端在接收到FIN后再次发送ACK到服务端。在TIMEI_WAIT状态下收发双方的端口号不可使用,要等待2MSL后才能使用。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值