当前位置:   article > 正文

【Linux】三次握手和四次挥手详解_linux三次握手

linux三次握手

三次握手和四次挥手

​ TCP 协议提供的是:面向连接、可靠的、字节流服务。使用 TCP 协议通信的双发必须先建立连接,然后才能开始数据的读写。双方都必须为该连接分配必要的内核资源,以管理连接的状态和连接上数据的传输。 TCP 连接是全双工的,双方的数据可以通过一个连接进行读写。完成数据交换之后,通信双方都必须断开连接以释放系统资源。

TCP流式服务的特点:发送和接收的次数不对应,会出现沾包问题

TCP协议报头
在这里插入图片描述

6位标志位包含如下几项

(1)URG标志,表示紧急指针(urgent pointer)是否有效

(2)ACK标志(Acknowledge Character),表示确认号是否有效,我们称携带ACK标志的TCP报文段为确认报文段,是在数据通信传说中,接收站发给发送站的一种传输控制字符,表示确认发来的数据已经接受无误。ACL确认序号的值是对方发送的序号值+数据长度

(3)PSH标志,提示接收端应用程序应该立即从TCP接收缓冲区中读走数据,为接收后续数据腾出空间(如果应用程序不将接收到的数据读走,它们就会一直停留在TCP 接收缓冲区中)

(4)RST标志,表示要求对方重新建立连接,我们称携带RST标志的TCP报文段为复位报文段

(5)SYN 标志(Synchronize),表示请求建立一个连接,我们称携带SYN 标志的TCP报文段为同步报文段,是客户端第一次发出的连接信号,之后会收到服务器的ACK信号;

(6)FIN标志(Finish),表示通知对方本端要关闭连接了,我们称携带FIN标志的TCP报文段为结束报文段

窗口大小: 指的是缓冲区大小

TCP状态转换图

状态转换图

为什么说TCP是安全可靠的协议?

​ TCP是面向连接的安全的数据传输, 在客户端与服务端建立建立的时候要经过三次握手的过程, 在客户端与服务端断开连接的时候要经历四次挥手的过程, 下图是客户端与服务端三次握手建立连接, 数据传输和断开连接四次挥手的全过程。

TCP时序:

在这里插入图片描述

建立连接(three-way hand shake)

TCP三次握手发生在内核执行connect()函数的时候

·主动打开(passive open):服务器必须准备好接受外来的连接,通常通过socket、bind和listen完成。

·被动打开(active open):客户端通过connect发起主动打开。

TCP建立连接的三次握手图
在这里插入图片描述

客户端与服务器三次握手过程介绍

  1. 服务器准备好接受外来连接,通常通过socket、bind和listen完成。(服务器:CLOSED->LISTEN)
  2. 客户端通过connect连接服务器,客户端TCP将发送一个SYN包,告诉服务器客户端将在待建立连接发送数据的初始序列号。(客户端:CLOSED->SYN_SENT)
  3. 服务器端必须ACK客户端SYN,同时发送一个SYN,告诉客户端,服务器将在待建立连接发送数据的初始序列号。(服务器:SYN_RCVD)
  4. 客户端必须ACK服务器SYN。(客户端:SYN_SENT->ESTABLISHED)
  5. 服务器接收到客户端ACK。(服务器:SYN_RECV->ESTABLISHED)

对应的状态转移图

状态转移图

建立连接同时打开(simultaneous open)

这种情况发生在两端几乎同时发送SYN并且这两个SYN在网络中交错的情形。这种情况可能发生,但是非常罕见。

例如,主机A的应用程序使用本地端口7777,并与主机B的端口8888执行主动打开。主机B的应用程序使用本地端口8888,并与主机A的端口7777执行主动打开。

下图给出同时打开过程:

同时打开过程

下图给出同时打开的状态转移图:

状态转换图

说明:从目前个人经验来看,这种场景没有遇到过,但这是完整理解TCP状态转移必须的一部分。

tcpdump抓包观察TCP的链接的建立和关闭;

建立连接失败

考虑场景1:
当客户端尚未接收到服务器ACK+SYN,异常退出(崩溃退出)。这时,当客户端接收到服务器的ACK+SYN时,客户端回复RST(reset)。此时服务器处于SYN_RCVD状态,当接收到客户端RST时,则从SYN_RCVD转移到LISTEN状态。

具体过程:

  1. 服务器准备好接受外来连接,通常通过socket、bind和listen完成。(服务器:CLOSED->LISTEN)
  2. 客户端通过connect连接服务器,客户端TCP将发送一个SYN包,告诉服务器,客户端将在待建立连接发送数据的初始序列号。然后客户端异常退出。(客户端:CLOSED->SYN_SENT,然后突然crash,则退出SYN_SENT)
  3. 服务器端ACK客户端SYN,同时发送一个SYN,告诉客户端,服务器将在待建立连接发送数据的初始序列号。(服务器:SYN_RCVD)
  4. 客户端找不到服务器ACK+SYN对应的SYN_SENT状态的socket,则响应RST。(服务器:SYN_RCVD->LISTEN)

下图给出建立连接失败的状态转移图:

状态转换图

考虑场景2:
服务器的进程异常退出,客户端不知道。那么客户端发送SYN后,服务器端响应RST,则客户端建立连接失败。

考虑场景2:服务器机器关闭,导致服务器IP不可达。那么客户端发送SYN后,超时重发,超过重试次数,最终TIMEOUT,则客户端建立连接失败。

具体过程:

  1. 假设服务器进程退出。(服务器:LISTEN->CLOSED)
  2. 客户端通过connect连接服务器,客户端TCP将发送一个SYN包,告诉服务器,客户将在待建立连接发送数据的初始序列号。(客户端:CLOSED->SYN_SENT)
  3. 服务器端收到客户端SYN,响应RST(服务器:CLOSED)
  4. 客户收到RST。(客户端:SYN_SENT->CLOSED)

建立连接失败的状态转移图

状态转换图

数据传输阶段

在这里插入图片描述

四次挥手阶段

服务器或者客户端执行close()函数的时候执行四次挥手

·主动关闭(active close):某个应用程序首先调用close,发送一个FIN包。

·被动关闭(passive close):接收到FIN的对端执行被动关闭。

TCP连接断开的四次挥手过程图
在这里插入图片描述

客户端与服务器的四次挥手过程:

  1. 某个应用程序首先调用close,该端发送一个FIN包,表示数据发送完毕,该应用程序再无更多数据发送给对端。(例如HTTP服务器发送Reponse数据给client后,再无多余数据发送,则Server可以执行主动关闭)(主动端:ESTABLISHED->FIN_WAIT_1)
  2. 接收到FIN的对端执行被动关闭。首先ACK这个收到的FIN包。该FIN包的接收也作为一个文件结束符(EOF)传递给应用程序(放在已排队等候该应用进程接收的任何其他数据之后),因为FIN包意味着接收端应用进程在相应的连接上再无额外数据可接收。(被动端:ESTABLISHED->CLOSE_WAIT,主动端:FIN_WAIT_1->FIN_WAIT_2)
  3. 一段时间后,接收到这个EOF的应用进程将调用close关闭socket。这导致它的TCP也发送一个FIN包。(被动端:CLOSE_WAIT->LAST_WAIT)
  4. 接收这个最终FIN的执行主动关闭的那一端ACK这个FIN。(被动端:LAST_WAIT->CLOSED,主动端:FIN_WAIT_2->TIME_WAIT(2MSL之后,TIME_WAIT->CLOSED))

四次挥手的状态转移图

状态转换图

完整TCP时序

理解数据之间变换的关系
在这里插入图片描述

断开连接(同时关闭simultaneous close)

​ 一方(通常但不总是客户方)发送第一个FIN执行主动关闭。双方都执行主动关闭也是可能的,TCP协议也允许这样的同时关闭(simultaneous close)。

同时关闭过程图:

同时打开过程

同时关闭的状态转移图

状态转换图

断开连接(在FIN_WAIT_1状态中,接收FIN+ACK)

考虑场景:被动关闭端收到FIN包后,直接发送FIN+ACK,则主动关闭方则从FIN_WAIT_1跳过FIN_WAIT_2,直接进入TIME_WAIT。

具体流程如下:

  1. 某个应用程序首先调用close,该端发送一个FIN包,表示数据发送完毕,该应用程序再无更多数据发送给对端。(例如HTTP服务器发送Reponse数据给client后,再无多余数据发送,则Server可以执行主动关闭)(主动端:ESTABLISHED->FIN_WAIT_1)
  2. 接受到FIN的对端执行被动关闭。收到FIN包之后,被动端调用close关闭socket,则FIN+ACK同时发给主动端。(被动端:ESTABLISHED->CLOSE_WAIT->LAST_ACK,主动端:FIN_WAIT_1->TIME_WAIT)
  3. 接收这个最终FIN的执行主动关闭的那一端ACK这个FIN。(被动端:LAST_WAIT->CLOSED,主动端:FIN_WAIT_1->TIME_WAIT(2MSL之后,TIME_WAIT->CLOSED))

同时关闭的状态转移图

状态转换图

TCP连接的可靠性保证

1.应答确认

2.超时重传机制

无差错数据的交互流程:
在这里插入图片描述

出现差错数据的交互流程:
在这里插入图片描述

3.乱序重排以及对数据的去重操作

以上三点保证了TCP连接的可靠性

滑动窗口

​ TCP 协议是利用滑动窗口实现流量控制的。一般来说,我们总是希望数据传输得更快一些,不会一次只发一个字节。但是如果发送方把数据发得过快,接受方就可能来不及接收,这就会造成数据的丢失。所谓流量控制就是让发送方的发送速率不要快,要让接收方来的及接收。

​ 在 TCP 的报头中有一个字段叫做接收通告窗口,这个字段由接收端填充,是接收端告诉发送端自己还有多少缓冲区可以接收数据。于是发送端就可以根据这个接收端的处理能力来发送数据,而不会导致接收端处理不过来。所以发送端就会有一个发送窗口,这个发送窗口的大小是由接收端填充的接收通告窗口的大小决定的,并且窗口的位置会随着发送端数据的发送和接收到接收端对数据的确认而不断的向右滑动,将之称为滑动窗口。
在这里插入图片描述

(可参考《计算机网络》204页“滑动窗口”的内容)

MTU和mss

​ MTU:通信术语最大传输单元(Maximum Transmission Unit,MTU),是指一种通信协议的某一层上面所能通过的最大数据包大小(以字节为 单位)。最大传输单元这个参数通常与通信接口有关(网络接口卡、串 口等), 这个值如果设置为太大会导致丢包重传的时候重传的数据量较大, 图中的最大值是1500, 其实是一个经验值。

在这里插入图片描述

​ mss(Maximum Segment size): 最大报文长度, 只是在建立连接的时候, 告诉对方我最大能够接收多少数据, 在数据通信的过程中就没有mss了。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/正经夜光杯/article/detail/874645
推荐阅读
相关标签
  

闽ICP备14008679号