TCP 连接建立

当我们浏览网页、发送电子邮件或者进行在线游戏时,我们常常不会想到背后复杂的网络连接过程。然而,正是这些看似不起眼的步骤,确保了我们与服务器之间的稳定通信。其中最重要的步骤之一就是TCP连接的建立,而其中的核心环节就是三次握手。

本文将详细探讨三次握手的原理、过程以及其重要性。我们将一步步解析为什么需要三次握手,它如何保证连接的稳定性和可靠性,以及它对于数据传输的重要作用。通过深入理解三次握手,我们将更好地理解网络通信的底层机制,并对TCP连接的可靠性有更清晰的认识。

TCP 三次握手过程和状态变迁

TCP是一种面向连接的传输层协议,它在进行数据传输之前需要先建立连接。这个连接的建立过程是通过三次握手来完成的。

我们根据这幅图详细讲解,每次连接中所发送的TCP报文。

在最开始,客户端和服务端都处于CLOSED状态。首先,服务端主动监听某个端口,处于LISTEN状态,即服务器必须处于启动状态。接下来,客户端准备开始访问网页,需要与服务器建立连接。第一次连接报文的格式如下:

客户端在发起连接时,会随机生成一个初始序号(client_isn),并将其放置在TCP首部的"序号"字段中。同时,客户端将SYN标志位置为1,表示发出的报文是SYN报文。客户端通过发送第一个SYN报文给服务端,表明它希望与服务端建立连接。该报文不包含应用层数据(也就是发送的数据)。此时,客户端的状态被标记为SYN-SENT。

当服务端收到客户端的SYN报文时,首先服务端会随机初始化自己的序号(server_isn),然后将该序号填入TCP首部的"序号"字段中。接着,服务端将"确认应答号"字段填入client_isn + 1,并将SYN和ACK标志位都设置为1。最后,服务端将该报文发送给客户端,该报文不包含应用层数据(此时服务器也没数据可发)。此时,服务端处于SYN-RCVD状态。

一旦客户端收到服务端的报文,它需要做以下优化来回应最后一个应答报文:首先,客户端将该应答报文的TCP首部的ACK标志位设置为1;其次,客户端在"确认应答号"字段中填入server_isn + 1的值;最后,客户端将报文发送给服务端。此次报文可以携带客户端到服务器的数据。完成这些操作后,客户端将进入ESTABLISHED状态。

一旦服务器收到客户端的应答报文,它也会切换到 ESTABLISHED 状态。

从上面的过程可以发现,在进行三次握手时,第三次握手是可以携带数据的,而前两次握手则不可以。这也是面试中经常被问到的问题。一旦完成三次握手,双方都会进入ESTABLISHED状态,表示连接已经成功建立,此时客户端和服务端就可以开始相互发送数据了。

为什么是三次握手?不是两次、四次?

相信大家通常回答的是:“因为三次握手才能保证双方具有接收和发送的能力。”这个回答没错,但它只是表面上的原因,并没有提出主要的原因。下面我将从三个方面分析三次握手的原因,加深我们对这个问题的理解。

  • 三次握手可以有效地避免历史重复连接的初始化(主要原因)
  • 三次握手可以保证双方都收到了可靠的初始序列号。
  • 三次握手可以避免资源浪费。

原因一:避免历史重复连接

简单来说,三次握手的主要原因是为了避免旧的重复连接初始化造成混乱。在复杂的网络环境中,数据包的传输并不总是按照规定时间发送到达目标主机,可能会因为网络拥堵等原因导致旧的数据包先到达目标主机。为了避免这种情况,TCP使用三次握手的方式来建立连接。

当客户端连续发送多个SYN建立连接的报文时,在网络拥堵等情况下,可能会出现以下情况:

  • 旧的SYN报文比最新的SYN报文先到达服务端。
  • 服务端收到旧的SYN报文后会回复一个SYN + ACK报文给客户端。
  • 客户端收到SYN + ACK报文后,根据自身的上下文判断这是一个历史连接(序列号过期或超时),然后发送RST报文给服务端,表示中止这次连接。

如果是两次握手的连接方式,就无法判断当前连接是否是历史连接。而三次握手可以在客户端准备发送第三次报文时,根据上下文判断当前连接是否是历史连接:

  • 如果是历史连接(序列号过期或超时),则第三次握手发送的报文是RST报文,以中止历史连接。
  • 如果不是历史连接,则第三次发送的报文是ACK报文,通信双方成功建立连接。

因此,TCP使用三次握手的主要原因是为了防止历史连接初始化了连接。

原因二:同步双方初始序列号

TCP协议的通信双方都必须维护一个序列号,这是确保可靠传输的关键因素。序列号在TCP连接中扮演了重要角色,它具有以下作用:

● 接收方可以消除重复的数据,确保数据的准确性。

● 接收方可以按照序列号的顺序接收数据包,保证数据的完整性。

● 序列号可以标识已经被对方接收的数据包,实现可靠的数据传输。

因此,在建立TCP连接时,客户端发送带有初始序列号的SYN报文,并需要服务器回复一个ACK报文,表示成功接收了客户端的SYN报文。然后,服务器发送带有初始序列号的SYN报文给客户端,并等待客户端的应答,这样一来一回,才能确保双方的初始序列号能够可靠地同步。

虽然四次握手也可以实现可靠地同步双方的初始序列号,但由于第二步和第三步可以合并为一步,所以最终演变成了三次握手。而两次握手只能保证一方的初始序列号被对方成功接收,无法保证双方的初始序列号都能被确认接收。因此,三次握手是为了确保TCP连接的稳定性和可靠性而采取的最佳选择。

原因三:避免资源浪费

如果只有"两次握手"的话,当客户端的SYN请求在网络中被阻塞时,客户端无法接收到服务器发送的ACK报文,因此会重新发送SYN。然而,由于没有第三次握手,服务器无法确定客户端是否收到了建立连接的ACK确认信号。因此,服务器只能在收到每个SYN请求后主动建立一个连接。这将导致以下情况的发生:

资源浪费:如果客户端的SYN请求被阻塞,导致重复发送多个SYN报文,服务器在收到请求后将建立多个冗余的无效连接。这将导致服务器资源的不必要浪费。

消息滞留:由于缺乏第三次握手,服务器无法知道客户端是否正确接收到了建立连接的ACK确认信号。因此,如果消息在网络中出现滞留,客户端将一直重复发送SYN请求,导致服务器不断建立新的连接。这将增加网络拥塞和延迟,并对整个网络性能产生负面影响。

因此,为了确保网络连接的稳定性和可靠性,TCP使用了三次握手来建立连接,以避免以上问题的发生。

总结

TCP连接建立是通过三次握手来完成的。在三次握手过程中,客户端首先发送一个带有SYN标志的报文给服务器,表示希望建立连接。服务器接收到客户端的请求后,回复一个带有SYN和ACK标志的报文给客户端,表示接受连接请求,并发送自己的初始序列号。最后,客户端再回复一个带有ACK标志的报文给服务器,表示连接建立成功。这样,双方就进入了ESTABLISHED状态,可以开始相互发送数据。

总的来说,TCP连接建立的三次握手过程是为了确保连接的稳定性和可靠性,避免历史连接的混乱和资源浪费,同时保证双方都具备接收和发送数据的能力。

TCP连接的关键之谜:揭秘三次握手的必要性的更多相关文章

  1. TCP连接的11种状态,三次握手四次挥手原因

    1).LISTEN:首先服务端需要打开一个socket进行监听,状态为LISTEN. /* The socket is listening for incoming connections. 侦听来自 ...

  2. 简述TCP连接的建立与释放(三次握手、四次挥手)

    在介绍TCP连接的建立与释放之前,先回顾一下相关知识. TCP是面向连接的运输层协议,它提供可靠交付的.全双工的.面向字节流的点对点服务.HTTP协议便是基于TCP协议实现的.(虽然作为应用层协议,H ...

  3. TCP具体解释(2):三次握手与四次挥手

    TCP(Transmission Control Protocol,传输控制协议)是基于连接的协议,也就是说,在正式收发数据前,必须和对方建立可靠的连接,就好像你给别人打电话.必须等线路接通了.对方拿 ...

  4. TCP报文格式和三次握手——三次握手三个tcp包(header+data),此外,TCP 报文段中的数据部分是可选的,在一个连接建立和一个连接终止时,双方交换的报文段仅有 TCP 首部。

    from:https://blog.csdn.net/mary19920410/article/details/58030147 TCP报文是TCP层传输的数据单元,也叫报文段. 1.端口号:用来标识 ...

  5. TCP的三次握手(建立连接)与 四次挥手(关闭连接)

    一.TCP报文格式 TCP/IP协议的详细信息参看<TCP/IP协议详解>三卷本.下面是TCP报文格式图: TCP报文格式上图中有几个字段需要重点介绍下: (1)序号:Seq序号,占32位 ...

  6. 为什么 TCP 建立连接需要三次握手(转载)

    为什么 TCP 建立连接需要三次握手(转载) 原文链接:https://draveness.me/whys-the-design-tcp-three-way-handshake/ TCP 协议是我们几 ...

  7. TCP的三次握手与四次挥手(个人总结)

    序列号seq:占4个字节,用来标记数据段的顺序,TCP把连接中发送的所有数据字节都编上一个序号,第一个字节的编号由本地随机产生:给字节编上序号后,就给每一个报文段指派一个序号:序列号seq就是这个报文 ...

  8. 传输层(一)TCP的三次握手和四次挥手及关闭套接字的原理

    TCP连接需三次握手才能建立,断开连接则需要四次握手. 客户端TCP状态迁移: CLOSED->SYN_SENT->ESTABLISHED->FIN_WAIT_1->FIN_W ...

  9. TCP通信三次握手的过程

    过程 编辑 第一次 第一次握手:建立连接时,客户端 发送syn包(syn=j)到服务器,并进入SYN_SENT状态,等待服务器确认:SYN:同步序列编号(Synchronize Sequence Nu ...

  10. tcp连接的3次握手

    http://www.tcpipguide.com/free/t_TCPConnectionEstablishmentProcessTheThreeWayHandsh-3.htm synchronou ...

随机推荐

  1. 强化学习从基础到进阶-常见问题和面试必知必答[1]:强化学习概述、序列决策、动作空间定义、策略价值函数、探索与利用、Gym强化学习实验

    强化学习从基础到进阶-常见问题和面试必知必答[1]:强化学习概述.序列决策.动作空间定义.策略价值函数.探索与利用.Gym强化学习实验 1.强化学习核心概念 强化学习(reinforcement le ...

  2. 4. JDK相关设置

    恐惧是本能,行动是信仰(在此感谢尚硅谷宋红康老师的教程) 1. 项目的 JDK 设置 File-->Project Structure...-->Platform Settings --& ...

  3. 一文读懂什么是AIGC?

    目录 AIGC概念 AIGC发展历史 在早期萌芽阶段(1950s~1990s) 在沉淀累积阶段(1990s~2010s) 在快速发展阶段(2010s~至今) ChatGPT AIGC能做什么? 电子商 ...

  4. CDI的概念理解

    1.CDI是什么?目的和作用是什么? 概念(是什么):是JavaEE 6标准中一个规范, 作用(干什么): 它提供了Java EE平台上服务注入的组件管理核心,简化应该是CDI的目标,让一切都可以被注 ...

  5. 让golang程序生成coredump文件并进行调试

    今天讲讲怎么让golang程序生成coredump文件,并且进行调试的. 别看我写了不少golang的博客,其实我平时写c++的时间更多,所以也算和coredump是老相识了.core dump文件实 ...

  6. 云储存选择做Hexo博客图床(腾讯云、七牛云、网易云)

    前言 博客里需要添加很多图片作为内容的补充,但是把图片放在本地博客文件夹里,上传到网上后,加载这些图片就是一个很大的问题,他们会拖累网页加载的速度,所以建议把图片放图床里,通过外链来访问和加载这些图片 ...

  7. Java开发大型互联网-架构师必须掌握的分布式技术

    Java开发大型互联网-架构师必须掌握的分布式技术 摘要:在当今互联网行业,随着用户量和业务的不断增长,大型互联网系统的设计和开发已经成为了一项头等重要的任务.作为架构师,要能够应对这样的挑战,就必须 ...

  8. JAVA小白找工作必备建议

    如果您是一名刚入门的JAVA小白,正在寻求工作机会,那么恭喜您来对地方!本文将为您提供一些建议,帮助您在求职过程中更好地展现自己的优势和准备迎接新的挑战. 1.基础知识打牢 在找工作前,务必确保您对J ...

  9. 深入Scikit-learn:掌握Python最强大的机器学习库

    本篇博客详细介绍了Python机器学习库Scikit-learn的使用方法和主要特性.内容涵盖了如何安装和配置Scikit-learn,Scikit-learn的主要特性,如何进行数据预处理,如何使用 ...

  10. npm 切换源

    切换到淘宝源 npm config set registry https://registry.npm.taobao.org 切换回官方源 npm config set registry http:/ ...