1、TCP协议头

Sequence Number(seq):32bit,表示tcp包的序列号,根据seq来确认是否有数据包丢失。
Acknowledgment Number(ack):32bit,表示tcp包的确认号。表示已经收到对方多少数据。
2、seq和ack的作用
通过对seq和ack标志位的设置,实现了tcp作为可靠传输协议的部分功能。
3、seq和ack的理解
TCP连接的用途可以简化为下图。客户端把发送区的数据发出去,服务端收到数据后放进自己的接收区;服务端把发送区的数据发出去,客户端收到数据后放进自己的接收区。

对于seq来说,可以理解为,我已经发出了多少数据;
对于ack来说,可以理解为,我已经接收了多少数据。
这是在此次发包的时候,对当前状态的总结,不包括本次发送的包,因为此次发送的动作并没有完成。
4、注意
发出带有SYN或FIN标志的报文,seq需要+1;只带有ACK标志的报文,seq不需要+1。
可以简单理解为带有SYN或FIN标志的包,包大小为1个字节;只带有ACK标志的包,包为空。
5、示例

上图,简单模拟了一个TCP完整的流程。其中:1-3号报文为三次握手,4-5号报文为一次数据发送,6-9号报文为四次挥手。
三次握手
(1)【报文1】Client发送一个[SYN]报文。此时连接还没建立好,对于Client来说,既没有发出过报文,也没有接收到报文,所以seq=0,ack=0。
表示Client现在还没有发出过任何包,也没有收到任何包
(2)【报文2】Server收到[SYN]报文后,发送[SYN,AKC]报文。对于Server来说,他并没有发出过报文,但接收到了【报文1】,所以syn=0,ack=1。
表示Server现在还没有发出去任何包,但接收到了1个字节的包
(3)【报文3】Client收到[SYN, ACK]报文,发送[ACK]报文。对于Client来说,之前已经发出过【报文1】,并接收到了【报文2】,所以syn=1,ack=1。
表示Client端现在已经发出过1个字节,也接收到了1个字节
数据发送
(1)【报文4】Client发送[PSH, ACK]报文,并且data length=100。对于Client来说,虽然发出了【报文1】和【报文3】,但根据上面第4点的注意,【报文3】只带有ACK标志,这个包的大小为0。所以syn=1,ack=1。
表示Client端现在已经发出了1个字节,也接收到了1个字节
(2)【报文5】Server收到[PSH, ACK]报文,发送[ACK]报文。对于Server来说,收到了【报文4】,数据大小为100个字节。所以syn=1, ack=101。
表示Server现在已经发出了1个字节,接收到了101个字节
四次挥手
(1)【报文6】Server端发送一个[FIN]报文。对于Server来说,上一个包发出去的包是【报文5】,只带[ACK]标志。所以syn=1, ack=101。
表示Server现在已经发出了1个字节,接收到了101个字节
(2)【报文7】Client收到[FIN]报文,发送[ACK]报文。对于Client来说,上一个包发出去的包是【报文4】,长度为100字节。所以syn=101,ack=2。
表示Client已经发出了101个字节,接收到了2个字节
(3)【报文8】Client发送[FIN, ACK]报文。对于Client来说,上一个发出去的包是【报文7】,只带有[ACK],包大小为1,所以syn=101,ack=2。
表示Client已经发出了101个字节,接收到了2个字节
(4)【报文9】Server收到[FIN, ACK]报文,发送[ACK]报文。对于Server来说,上一个发出去的包是【报文6】,所以syn=2,ack=101。
表示Server已经发出了2个字节,接收到了101个字节
在此次TCP连接示例中,Client最后状态为发送101个字节,接收到2个字节;Server最后状态为发送2个字节,接收到101个字节。状态匹配正确。
6、其他
- 对于示例中频繁出现的只带有
[ACK]标志的报文,其实就是搭配着seq、ack标志位的使用,一起来确认数据是否到达对端的一种手段。 - 每一次收到报文时,都会比较此次收到的报文中
seq值是否等于上一次发出的报文中ack值;也可以认为每一次发出报文中的ack值其实也是对下一次将要收到的报文seq值的预测。如果值不相等,认为发生了丢包。
TCP协议通过seq和ack确保数据可靠性,seq表示已发送的数据量,ack表示已接收的数据量。在三次握手和四次挥手过程中,seq和ack的配合用于确认连接建立和关闭。示例展示了seq和ack如何在数据传输和确认中变化。



1万+

被折叠的 条评论
为什么被折叠?



