-
最新文章
-
热门文章
-
热评好文
-
最新评论
-
yanyiwxy:好干!!!
-
wx5916600de51e9:66666
-
wx5eb8fc190868a:jjjj
-
咖啡:赞一个~
-
咖啡:写的真不错啊~
-
目录
-
TCP协议全称为:Transmission Control Protocol
,是一种面向链接、保证数据传输安全、可靠的数据传输协议。为了确保数据的可靠传输,不仅需要对发出的每个字节进行编号确认,还需要验证每一个数据包的有效性。每个TCP数据包是封闭在IP包中的,每个一IP包的后面紧跟着的是TCP头,TCP报文格式如下:
源端口和目的端口字段
序列号字段
CP序列号(Sequence Number):占 32 位。它表示本报文段所发送数据的第一个字节的编号。在 TCP 连接中,所传送的字节流的每一个字节都会按顺序编号。当SYN标记不为1时,这是当前数据分段第一个字母的序列号;如果SYN的值是1时,这个字段的值就是初始序列值(ISN),用于对序列号进行同步。这时,第一个字节的序列号比这个字段的值大1,也就是ISN加1。
确认号字段
TCP 确认号(Acknowledgment Number,ACK Number):占 32 位。它表示接收方期望收到发送方下一个报文段的第一个字节数据的编号。其值是接收计算机即将接收到的下一个序列号,也就是下一个接收到的字节的序列号加1。
数据偏移字段
TCP 首部长度(Header Length):数据偏移是指数据段中的“数据”部分起始处距离 TCP 数据段起始处的字节偏移量,占 4 位。其实这里的“数据偏移”也是在确定 TCP 数据段头部分的长度,告诉接收端的应用程序,数据从何处开始。
保留字段
保留(Reserved):占 4 位。为 TCP 将来的发展预留空间,目前必须全部为 0。
标志位字段
窗口大小字段
窗口大小(Window Size):占 16 位。它表示从 Ack Number 开始还可以接收多少字节的数据量,也表示当前接收端的接收窗口还有多少剩余空间。该字段可以用于 TCP 的流量控制。
TCP 校验和字段
校验位(TCP Checksum):占 16 位。它用于确认传输的数据是否有损坏。发送端基于数据内容校验生成一个数值,接收端根据接收的数据校验生成一个值。两个值必须相同,才能证明数据是有效的。如果两个值不同,则丢掉这个数据包。Checksum 是根据伪头 + TCP 头 + TCP 数据三部分进行计算的。
紧急指针字段
紧急指针(Urgent Pointer):仅当前面的 URG 控制位为 1 时才有意义。它指出本数据段中为紧急数据的字节数,占 16 位。当所有紧急数据处理完后,TCP 就会告诉应用程序恢复到正常操作。即使当前窗口大小为 0,也是可以发送紧急数据的,因为紧急数据无须缓存。
可选项字段
选项(Option):长度不定,但长度必须是 32bits 的整数倍。
TCP建立连接需要三个步骤,也就是大家熟知的三次握手。下图了正常情形下通过三次握手建立连接的过程:
SYN
设置为1,表示希望建立连接。这个包中的假设seq为x
。SYN
数据包后,会进入SYN_SENT
状态SYN
数据后,响应一个数据包将SYN
和ACK
设置为1,假设这个响应包的序列号为y
,同时期望下一次收到的数据库的序列为x+1
SYN_RECD
状态ACK
标志设置为1,序列号为x + 1
,期望下一次收到的数据包的序列号为y+1
以为验证三次握手是否描述正确,在下使用Wireshark
进行抓包验证。首先使用ping
命令获取www.baidu.com
的ip地址:
正在 Ping www.a.shifen.com [183.232.231.174] 具有 32 字节的数据: 来自 183.232.231.174 的回复: 字节=32 时间=16ms TTL=54 来自 183.232.231.174 的回复: 字节=32 时间=16ms TTL=54 来自 183.232.231.174 的回复: 字节=32 时间=16ms TTL=54 183.232.231.172 的 Ping 统计信息: 数据包: 已发送 = 3,已接收 = 3,丢失 = 0 (0% 丢失), 往返行程的估计时间(以毫秒为单位): 最短 = 16ms,最长 = 16ms,平均 = 16ms
以上输出显示www.baidu.com
的ip地址: 183.232.231.174
,然后使用Wireshark
的过滤器仅显示与www.baidu.com
通信的tcp
数据包:
ip.src_host == "183.232.231.174" or ip.dst_host == "183.232.231.174" and tcp
使用Wireshark
抓包分析后,验证TCP正常连接三次握手与上节描述的一致。
为什么是三次握手?三次握手主要有两个目的:信息对等和防止超时。
两台机器通信时都需要确认四个信息:
第一次握手A机器向B机器发送SYN
数据包,此时只有B机器能确认自己收报文的能力和对方发报文的能力。
一次握手完成B机器能够确认的信息有:
每二次握手后B响应A机器的SYN
数据包,此时A机器就能确认:自己发报文的能力、自己收报文的能力、对方发报文的能力、对方收报文的能力
二次握手完成A机器能够确认的信息有:
每三次握手后A应答B机器的SYN + ACK
数据包,此时B机器就能确认:自己发报文的能力、对方收报文的能力
二次握手完成A机器能够确认的信息有:
至此经过三次握手A、B机器就能做到信息对等,双方都能确认自己和对方的收、发报文的能力,最后方便理解将信息对等制作成一个小表格:
三次握手除了保证信息对等也是了防止请求超时导致脏连接。TTL网络报文的生存往往会超过TCP请求超时时间,如果两次握手就能创建连接,传输数据并释放连接后,第一个超时的连接请求才到达B机器,B机器 会以为是 A 创建新连接的请求,然后确认同意创建连接。因为A机器的状态不是SYN_SENT
,所以会直接丢弃了B的确认数据,导致 B 机器单方面的创建连接完毕。
如果是三次握手,则 B 机器收到连接请求后,同样会向 A 机器确同意创建连接,但因为 A 不是SYN_SENT
状态,所以 A机器 不会回复 B 机器确认创建连接请求,而 B 机器到一段时间后由于长时间没有收到确认信息,最终会导致连接创建失败,因此不会出现脏连接。
TCP是全双工通信,双方都能作为数据的发送方和接收方,但TCP会有断开的时候。TCP建立连接需要三次握手而断开连接却要四次,如图所示为TCP断开连接四次挥手过程:
FIN
设置为1,假设序列号为u
,发完关闭数据包后此时 A 机器处理FIN_WAIT_1
状态ACK
标志设置为1,seq为v
,ack为u+1
,随后 B 机器处于 CLOSE_WAIT
状态FIN_WAIT_2
状态,继续等待 B 机器的FIN
数据包FIN
和ACK
标志设置为1,seq为w
,ack为u+1
,随后处于LAST_WAIT
状态等待 A 机器的应答FIN
数据包后,随后发送ACK
数据包,seq为u+1
,ack为w+1
, 此时 A 机器处理TIME_WAIT
状态ACK
响应包后,进行CLOSED
状态,连接正常关闭TIME_WAIT
状态等待2MSL
后,也进入CLOSEED
状态,连接关闭什么是2MSL:MSL是Maximum Segment Lifetime英文的缩写,中文可以译为“报文最大生存时间”,
2MSL即两倍的MSL
四次挥手断开连接可以用更形象的方式来表达:
抓包过程与与三次握手抓包过程一致,这里不描述。直接看访问后抓包的截图:
192.168.1.6
这台机器(也就是客户机),发送了一个FIN
包,seq为80
,ack为2782
183.232.231.174
(服务器),对192.168.1.6
这台机器(也就是客户机)发送了一个ACK
包,seq为2782
,ack为81
183.232.231.174
(服务器),对192.168.1.6
这台机器(也就是客户机)发送了一个ACK
和FIN
包,seq为2782
,ack为81
192.168.1.6
,向服务器响应了一个ACK
包,seq为81
,ack为2783
四次挥手流程与我们描述的一致。
主动要求关闭的机器(机器A)表示收到对方的FIN
报文后,并发送出ACK
报文后,进行TIME_WAIT
状态,等待2MSL
后进行CLOSED
状态。如果在TIME_WAIT_1
时收到FIN
标志和ACK
标志报文时,可以直接进入TIME_WAIT
状态,而无需进入TIME_WAIT_2
状态。
确认被动关闭(机器B)能够顺利进入CLOSED
状态
假如A机器发送最后一个ACK
后,但由于网络原因ACK
包未能到达 B 机器,此时 B机器通常会认为 A机器 没有收到 FIN+ACK
报文,会重发一次FIN+ACK
报文。如果 A机器 发送最后一个ACK
后,自私的关闭连接进入 CLOSED
状态,就可能导致 B 无法收到ACK
报文,无法正常关闭。
防止失效请求
TIME_WAIT 状态可以防止已失效的请求包与正常连接的请求数据包混淆而发生异常。因为TIME_WAIT 状态无法真正释放句柄资源,在此期间, Socket中使用的本地端口在默认情况下不能再被使用。
被动关闭的机器(机器B)在收到对方发送的,FIN
报文后,马上回复ACK
报文,进入CLOSE_WAIT
状态。通知应用程序,处理剩下的数据,释放资源。
感谢大家看到这里,文章有不足,欢迎大家指出;如果你觉得写得不错,那就给我一个赞吧。
也欢迎大家关注我的公众号:程序员麦冬,每天更新行业资讯!
赞赏
0人进行了赞赏支持
0
收藏
Ctrl+Enter 发布
发布
取消