zoukankan      html  css  js  c++  java
  • 浅谈三握四挥

    三次握手

     - 第一次握手

    客户端向服务端发送一个 SYN 报文,并指明客户端初始序列号 ISN。假设客户端的初始序列号为1000,以该序列号为原点,将自己要发送的每个字节的数据进行编号,1001,1002,1003....,服务端收到初始序列号后,就可以知道什么样的序列号是合法的。同时服务端还可以对客户端发送的字节数据进行确认,

    - 第二次握手

    服务端收到 SYN 报文后,会将自己的 SYN 报文作为应答,并且也指定自己的序列号 ISN。同时会把客户端的 ISN + 1 作为ACK 的值,表示自己已经收到了客户端的 SYN。确认号 ack=客户端序列号+1,如果客户端收到服务端的确认号为2001,则意味着字节编号为1001-2000,共1000个字节已近安全到达。

    - 第三次握手

    第三次握手和第二次握手基本相同,只不过变为客户端,客户端收到 SYN 报文后,会发送一个 ACK 报文,表示已经收到了服务端的 SYN 报文。此时客户端处于 ESTABLISHED 状态。服务器收到 ACK 报文之后,也处于 ESTABLISHED 状态,此时,双方已建立起了连接。双方就可以愉快的玩耍了。

    这里需要重点留意的是,TCP 连接握手,主要目的就是为了获取双方数据原点的序列号。

    重点来了,这里画下来,考试要考的。

    TCP的比较突出的特点大家都知道:保证数据可靠传输。那如何保证数据可靠传输呢?前提就要确认通信双方收发数据的能力。

    - 首先,我让信使运输一份信件给对方,对方收到了,那么他就知道了我的发件能力和他的收件能力是可以的。

    - 于是他给我回信,我若收到了,我便知我的发件能力和他的收件能力是可以的,并且他的发件能力和我的收件能力是可以。

    - 然而此时他还不知道他的发件能力和我的收件能力到底可不可以,于是我最后回馈一次,他若收到了,他便清楚了他的发件能力和我的收件能力是可以的。

    显然,三次是最优选择。两次不足以确认双发收发数据的能力,超过三次又浪费。

    四次挥手

     - 第一次挥手

    客户端发送一个 FIN 报文,报文中会指定一个序列号。此时客户端处于 FIN_WAIT1 状态。

    即发出连接释放报文段(FIN=1,序号seq=u),并停止再发送数据,主动关闭TCP连接,进入FIN_WAIT1(终止等待1)状态,等待服务端的确认。

    - 第二次挥手

    服务端收到 FIN 之后,会发送 ACK 报文,且把客户端的序列号值 +1 作为 ACK 报文的序列号值,表明已经收到客户端的报文了,此时服务端处于 CLOSE_WAIT 状态。

    即服务端收到连接释放报文段后即发出确认报文段(ACK=1,确认号ack=u+1,序号seq=v),服务端进入CLOSE_WAIT(关闭等待)状态,此时的TCP处于半关闭状态,客户端到服务端的连接释放。客户端收到服务端的确认后,进入FIN_WAIT2(终止等待2)状态,等待服务端发出的连接释放报文段。

    - 第三次挥手

    如果服务端也想断开连接了,和客户端的第一次挥手一样,发给 FIN 报文,且指定一个序列号。此时服务端处于 LAST_ACK 的状态。

    即服务端没有要向客户端发出的数据,服务端发出连接释放报文段(FIN=1,ACK=1,序号seq=w,确认号ack=u+1),服务端进入LAST_ACK(最后确认)状态,等待客户端的确认。

    - 第四次挥手

    客户端收到 FIN 之后,一样发送一个 ACK 报文作为应答,且把服务端的序列号值 +1 作为自己 ACK 报文的序列号值,此时客户端处于 TIME_WAIT 状态。需要过一阵子以确保服务端收到自己的 ACK 报文之后才会进入 CLOSED 状态,服务端收到 ACK 报文之后,就处于关闭连接了,处于 CLOSED 状态。

    即客户端收到服务端的连接释放报文段后,对此发出确认报文段(ACK=1,seq=u+1,ack=w+1),客户端进入TIME_WAIT(时间等待)状态。此时TCP未释放掉,需要经过时间等待计时器设置的时间2MSL后,客户端才进入CLOSED状态。

    好文章要分享:

    TCP为什么是三次握手,而不是两次或四次?

    面试官,不要再问我三次握手和四次挥手

    卧槽!牛皮了,头一次见有大佬把TCP/IP三次握手四次挥手解释的这么明白

  • 相关阅读:
    Linux 学习之DNS服务器
    Windows系统镜像自动添加驱动程序
    Linux下集群的搭建
    Heartbeat+LVS构建高可用负载均衡集群
    Keepalived高可用集群搭建(转载linuxIDC)
    CentOS 7.x设置自定义开机启动,添加自定义系统服务
    代码改变世界
    Vim食用指南
    Hibernate三种状态详解
    MySQL服务器的安装与配置
  • 原文地址:https://www.cnblogs.com/suojian/p/14108699.html
Copyright © 2011-2022 走看看