网络原理(二)TCP的可靠传输

news2025/2/25 21:08:13

网络原理(一)目录

  • 网络原理
    • 应用层
    • 传输层
      • 先说UDP(不可靠传输)
      • 重点说明TCP(可靠传输)
        • 一、确认应答
        • 二、超时重传
        • 三、链接管理
          • 建立连接
          • 断开链接
        • 四、滑动窗口
        • 五、流量控制(也是保证可靠性的机制)
        • 六、阻塞控制
        • 七、延迟应答(效率机制)
        • 八、捎带应答(效率机制)
        • 九、面向字节流(粘包问题)
        • 十、异常情况(心跳包)

网络原理

网络协议的在实际运用是分为5层协议及:

  1. 应用层
  2. 传输层
  3. 网络层
  4. 数据链路层
  5. 物理层

这五层结构在,java 网络编程中已经有所现,具体用法具体实现的功能,都有。

应用层

这里主要的一个协议也是目前网络上最常用的一个协议,HTTP协议。

这层结构,决定数据要传输什么,拿到数据后如何使用。HTTP为什么是最长用的一个应用层协议,其本质就是在确定框架后,程序员可以在自定义一些协议,可控性和操控大大提升。

及约定数据报的数据格式,就是在自定义协议。

而如何约定?

  1. 确定要传输那些信息(根据需求走)
  2. 确定数据按照啥样的格式来组织。
  • 网络上传输的,本质都是二进制字符串,就需要将上述的穿输的信息整合为一个字符串。但是在传输内容的时候,一个我们需要的数据,其实和其他数据是合在一起的。我们要如何拿到所需要的数据。很简单,我们在传输数据的时候,设定一个符号,或者距离单位。锁定所需要的数据。

  • 比如我规定,属性之间用 ’,‘ 隔开 ,每个对象用 ‘\n’ 隔开,结束标志用 ’;‘ 隔开 。

  • 只要发送方发送数据按照这个格式传输,然后接收方,在解析数据的时候,用这个格式解析就好;

  • 在开发中,有一些特定的现成的格式。可以直接拿来使用。比如之前的一种典型的格式,xml ,还有现在用的比较多的一种格式。json,
    什么是json。
    {
    userId:100
    userPos:10-100
    }
    使用{}作为标识,{}里面的诺干个键值对,每个键值对用 ’,‘ ,分割,键值对,用 ’:‘ 分割。 键必须是字符串,值就可以是一个object。

传输层

先说UDP(不可靠传输)

这个就是UDP 的报文格式。
在这里插入图片描述
在这里插入图片描述

  • 端口是2个字节,所以端口可以取:0-- > 65535
  • 报文长度就局限了正文最大能装多少的内容。64KB。所以如果用UDP进行传输一个很长的数据,就需要包一个较大的数据,拆成很多分,用UDP传输。(很复杂)
    所以用UDP传输数据,不能太大,否则就会出现问题。
  • 校验和,是为了校验数据的准确的。在真实的网络传输中就会遇到很多问题。磁场,太阳风暴,等等。这些都会干扰数据的稳定。而校验和就是用来判定,当前的数据是否出错。(通常是设定一种特殊的算法,比如取正文中的一些字符,然后算出一个数据,然后传输完毕后在验证一次)

重点说明TCP(可靠传输)

TCP如何实现可靠传输?

一、确认应答

什么是确认应答呢?其实就很简单,比如网上购物,商家发货,货物根据你的信息发送货物,然后送到哪里并且,你确认了收货,然后平台就会将钱给商家,这就是一个很简单的应答模式。

在这里插入图片描述
这个模型有一个问题,就是网络的状况有很多种,会出现后发先至的问题。对应到上述的例子就是,遇到强降雨,但是后边的货车走了另一条路。走的就比之前的车要快。

异常状态
在这里插入图片描述
正常状态
在这里插入图片描述
如何解决这个问题?
此时就需要对消息进行编号。

  • 给发送的消息分配一个需要
  • 同时应答报文,给出一个确认顺序

在这里插入图片描述

协议格式:

在这里插入图片描述

TCP将每个字节的数据都进行了编号,基序列号。


在这里插入图片描述

  • 源/目的端口号:表示数据是从哪个进程来,到哪个进程去;
  • 32位序号/32位确认号:后面详细讲;
  • 4位TCP报头长度:表示该TCP头部有多少个32位bit(有多少个4字节);所以TCP头部最大长度是15 * 4 = 60
  • 6位标志位:
    • URG:紧急指针是否有效
    • ACK:确认号是否有效
    • PSH:提示接收端应用程序立刻从TCP缓冲区把数据读走
    • RST:对方要求重新建立连接;我们把携带RST标识的称为复位报文段
    • SYN:请求建立连接;我们把携带SYN标识的称为同步报文段
    • FIN:通知对方,本端要关闭了,我们称携带FIN标识的为结束报文段
  • 16位窗口大小:后面再说
  • 16位校验和:发送端填充,CRC校验。接收端校验不通过,则认为数据有问题。此处的检验和不光
  • 包含TCP首部,也包含TCP数据部分。
  • 16位紧急指针:标识哪部分数据是紧急数据;
  • 40字节头部选项:暂时忽略;

在这里插入图片描述
首先接送方的序号和发送方的序号无关
确认序号 1001 的含义。

  1. 小于1001的数据,我已经收到
  2. 我接下来想要发送方从1001开始的数据

在之前说过,网络传输的时候,会有后发先至的情况,同样的这个也是。但是能,TCP在传输时会有序号,序号天然就有顺序,所以对于这种情况,只要在接收方接收前排序就好了。(优先级队列就能完成这个)、

对于TCP来说,自身也承担了这个整队的任务,TCP会有一个缓冲区(内核中的一个区域),每个socket都有自己的缓冲区。然后TCP就可以按照序号针对收到的消息进行针对。

如果一切顺利就可以应答了。可问题就是,现实并不顺利。比如丢包。

二、超时重传

那么什么是丢包呢?
传输数据的时候要经过各个节点,可是问题来了,一台机器节点的转发能力是有极限的,也就是说到达极限的机器,就可能会引起丢包的问题。(实时性的APP或者应用对于丢包的问题非常的敏感),如果丢包了接收方就收不到了。自然就不会返回ACK。

如何解决?

之前的逻辑,就是发送方发送消息会受到一个接收者的反馈的接收信息。但是丢包了,数据就不完整了。在队列里之前排好序的数据,因为丢包使得,序列并不完整。

此时因为序列并不完整,就不会交给接收者。然后序列就会等待,如果此时的序列等待时间长了,发送方迟迟拿不到应答。那么发送方就知道,传输出了问题,那么就会重新再发一次。直到拿到应答。(这个就叫超时重传)

有一个细节:

  • 数据直接丢失,接收方没收到,自然不会发 ack
  • 接收方接收到数据了,但是返回的ack 却丢了。

此时发送方分不清这些情况,只能重传。

可是此时,接收方已经在缓冲区中有了数据,再传一个,就重复了。此时接收方的缓冲区,会根据数据的序列,自动去重。保证应用程序中读到的数据任然只有一份

如果多次重复发送还没有收到ack 那么多半网络出了问题。主要是假设丢包率为10%,那么连续两次丢包,概率就是10% * 10%=1%

而以上这两种机制就是,TCP的可靠性保障。及:

  1. 确认应答
  2. 超时重传

三、链接管理

TCP创建链接:三次握手
TCP断开链接:四次挥手

建立连接

什么是三次握手?
握手是指通信双方,进行一次网络交互。相当于客户端和服务器之间,通过三次交互,建立连接关系(双方各自记录了对方的信息)
在这里插入图片描述
互相应答,确保双方的网络是完整的。并建立连接(有那么一滴滴可靠性的说法,但并不是)

等建立连接完毕,服务器 accept 把建立好的链接从内核拿到应用程序中。
在这里插入图片描述

  • 此时如果ACK 为 1 ,则表示当前的TCP数据报为一个应答报文
  • 此时如果SYN为 1 ,则表示当前的TCP数据报为一个同步报文
  • 如果ACK和SYN都是 1 ,则这个报文就是 SYN + ACK

做这么多。其实就是验证自己的发送能力和接收能力是否正常。

断开链接

什么是四次挥手?
通信的双方,各自给对方发一个FIN(结束报文),在各自给对方放回ACK

在这里插入图片描述
建立连接,一定是客户端发起,但是断开链接客户端和服务器都有可能。(并且通常ACK与FIN并不能重合)(FIN比特位位1的时候)

注意:
三次握手:ack与syn是同一个时机触发的(都是由内核完成)
四次握手:ack与fin内是不同时机出发的。前者由内核完成,而后者需要程序中 socke t的 close 方法才会触发fin、

在这里插入图片描述

四、滑动窗口

是为了解决,数据传输的效率问题。

对每一个发送的数据段,都要给一个ACK确认应答。收到ACK后再发送下一个数据段。这样做有一个比较大的缺点,就是性能较差。尤其是数据往返的时间较长的时候。

可靠性的提升,往往代表,效率的损失。

在这里插入图片描述
可以看到,客户端A这边传输5000个字节,要应答四次。此时A就用了大量的时间去等待ACK

既然这样一发一收的方式性能较低,那么我们一次发送多条数据,就可以大大的提高性能(其实是将多个段的等待时间重叠在一起了)

在这里插入图片描述
此时将数据进行批量发送。统一发送后,一起等待ACK的返回。这个批量传输的过程就是滑动窗口

等待的传输数据到达一定的数量,而这个批量等待的数据称为————》窗口大小

在这里插入图片描述
白色区域,相当于等待的窗口~~

批量发送了四个数据,就等待四个ACK。

这个批量发送也会出现问题。
比如:

  • 数据包以抵达,而ACK却丢了
    在这里插入图片描述
    这种情况,即使丢了这么多的ack,对于可靠性也没有任何影响。

确认序号的意思是指,该序号之前的数据都已经收到了,后一个 ACK 能表示前面的 ACK。(覆盖了)

  • 数据包就直接丢了
    在这里插入图片描述

解释:由于刚才1001 - 2000 这个数据丢了,所以接收方任然要索要1001,不会说因为收到的是2001-3000,就返回3001。接下来几次的数据 ack ,确认序号都是1001, B 再次向 A 反复索要 1001 这个数据,A这边识别到多个 1001 的请求,就知道 1001-2000丢了。于是 A 就重传了 1001-2000 这个数据。

当 A 1001-2000 这个数据重传后,B 收到了就会 传一个7001这个ACK,因为,数据只是缺了1001-2000这一段,补上之后,不用传关于这个段的 ACK,根据滑动窗口特点,后一个 ACK 就能表示他前面的数据已经到达 B。也就是,虽然1001-2000这一段没收到,但是其他的还在收啊。只是没有应答。补上了之后就开始应答。

这个重传的过程也叫:快速重传。

五、流量控制(也是保证可靠性的机制)

按道理来说,窗口越大,意味着,批量传输数据越多,也就意味着整体速度越快。但是数据多,就不意味着安全可靠。

数据一次性发的多,而快,一下子就把接收缓冲区给充满了。如果继续发送数据,此时就会丢包。这个时候,就需要控制一下流量

在这里插入图片描述
当ACK为1的时候,窗口大小字段就会生效。这里16位窗口是建议。

重要:发送方的窗口大小 = 流量控制 + 拥塞控制
在这里插入图片描述
如此就达成了阻塞的效果。

六、阻塞控制

滑动窗口大小 = 流量控制 + 拥塞控制

流量控制:平衡了接收方的处理能力
阻塞控制:衡量了传输路劲的处理能力

在java网络编程的哪一章中网络的传输是需要经过很多个节点的。如果任何一个设备,处理能力达到瓶颈,都会对整体的传输塑料产生明显影响。

而阻塞控制,就需要找到,衡量中间节点,传输的能力。怎么找?通过一次次实验,找到一个合适的发送速率

  1. 开始的时候,按照一个小的速率发送
  2. 如果不丢包,就可以扩大窗口的大小
  3. 如果丢包,就可以缩小窗口的大小

在这里插入图片描述
慢开始:刚开始传输会给一个非常小的窗口
指数规律增长:每一次扩大窗口,是翻倍成长。快速接近网络传输路径的能力瓶颈。
传输轮次:第一次发送,第二次发送。。。。
拥塞避免,“加法增大” :指数增长懂啊一定的阈值,就变成线性增长。避免一次性增加很多突然超出上限。
网络拥塞:增长到一定程度,出现丢包,认为当前的窗口大小,已经是传输的极限了。

七、延迟应答(效率机制)

TCP 可靠性的核心,是确认应答,ACK要发,但是不是立即发,而是稍微磨蹭一会再发,TCP中决定传输效率的关键元素就是,窗口大小。

在这里插入图片描述
此时服务器并不会立即返回一个ACK,也不一定要等到服务器将缓冲区里的数据全部拿出来,等待一下,然后偷偷的拿数据,悄悄的消耗缓冲区的数据,这样就相当于增大了窗口的大小。然后等到合适的时机服务器在返回ACK应答。

这样使得窗口大小似乎变大了,然后效率相应的变大了。

但是也并不是所有的报都延迟。

  • 数量限制:每隔N个包就应答一次;
  • 时间限制:超过最大延迟时间就应答一次;

八、捎带应答(效率机制)

是基于延迟应答的。
适用于:客户端,服务器,之间的通信模型,通常是“一问一答”这用模式

通信模型:

  1. 一问一答:绝大部分服务器都是这样
  2. 多问一答:上传大文件
  3. 一问多答:下载大文件
  4. 多问多答:游戏串流

原则是,客户端发送一个消息,需要等待服务器的ACK,但是因为延迟等待,数据实际上已经上传了,并且也处理好了,按照一般逻辑就是,将处理好的数据,返回给客户端,之前 ACK 还没有返回给客户端,那么此时 ACK 就会捎带着服务器处理好的数据返回给客户端。(原本分两次的返回,现在一次就可以)

九、面向字节流(粘包问题)

这个有一个巨大的问题,就是粘包问题。
根据上面的说法综合一下就知道,我们发送方传输的数据,是多个数据放在一起传输的。然后在缓冲区上集结排列,然后接收方如何将数据分离,读出一个完整的数据报,此时造成的结果就是,容易读出半个包,或者一个半的包,反正就是不是我们想要的。

如何解决?

提前约定好,数据的格式。比如:

  1. 约定结尾符号,接收方收到后,通过结尾符号知道一个完整的数据。
  2. 约定长度,约定数据的前几个字节,表示整个数据包的长度,通过光标读取字节长度。读取完整数据。

十、异常情况(心跳包)

  1. 进程关闭 / 进程崩溃
  • 进程没有了,socket是文件,随之关闭,虽然进程没有了,但是连接还在,仍然可以继续关闭连接(四次挥手)
  1. 主机关机
  • 先杀死所有的用户进程,也会触发四次挥手,如果没有挥完,比如 对方发了一个fin,咱们没来得及 ack 就关机了,姿势对端,就会重传fin ,重传几次后,发现没有 ACK ,尝试重置连接,如果还不行,就直接释放链接。
  1. 主机掉电
    主机瞬间关闭,来不及任何挥手操作。
  • 对方是发送方 :接收方收不到ACK =》超时重传 =》重置链接 =》释放链接
  • 对方是接收方:发送方,没办法立即知道,接收方死机了,这边还没有来得及发新数据,就没了。
    • TCP为了防止这种情况,内置了一个机制,心跳机制(周期性的,如果没有心跳,就代表挂了),也就是接收方会给发送方定期发一个心跳包(ping),然后发送方会给接收方发送一个返回(pong)
    • 如果每个ping都有一个pong返回,就说明接收方是好的。如果bing了很多次,还没反应,就知道就收方挂了。
  1. 网线断开
  • 同上,与主机掉电原理一样

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/990807.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

性能指标都不了解,如何做性能测试?

1、性能指标在性能测试的作用? 性能指标在性能测试中起着非常重要的作用,它们帮助我们评估和了解系统的性能表现。下面用通俗易懂的话来解释性能指标的作用和意义: 帮助我们了解系统的处理能力:性能指标可以告诉我们系统在给定负…

目标检测评估指标mAP:从Precision,Recall,PR曲线到AP

1. TP, FP, FN, TN True Positive 满足以下三个条件被看做是TP 1. 置信度大于阈值(类别有阈值,IoU判断这个bouding box是否合适也有阈值) 2. 预测类型与标签类型相匹配(类别预测对了) 3. 预测的Bouding Box和Ground …

[react基础]关于v6版本route的变化,以及常见应用模式

该说不说,在做这些之前,你要记得一件事 route不是react或者vue等原本就有的组件!需要你手动下载!然后导入! 原本的框架只是最终挂载到一个html界面上!!! 别再问我为啥你扒下来的代码为啥不好使了! 讨厌 > _< 下载指令去看我另一篇推文 今天复盘了一下自己的实训…

pyCharm远程DEBUG

第一步&#xff0c;添加一个远程机器的解释器 ssh 远程机器解释器添加&#xff0c; 我本地ssh有配置目标机器。 如果没配置&#xff0c;那就选着new server configuration 新增一个。 interpreter 指定远程机器python&#xff0c; &#xff08;机器上有多个版本python里尤其要…

【LeetCode-中等题】22. 括号生成

文章目录 题目方法一&#xff1a;递归&#xff1a;方法二&#xff1a;递归回溯 题目 方法一&#xff1a;递归&#xff1a; 递归入口 空子结果集&#xff0c;左括号数目&#xff08;初始为0&#xff09;&#xff0c;右括号数目&#xff08;初始为0&#xff09; 递归出口 若左括…

Eviews用向量自回归模型VAR实证分析公路交通通车里程与经济发展GDP协整关系时间序列数据和脉冲响应可视化...

全文下载链接&#xff1a;http://tecdat.cn/?p27784 河源市是国务院1988年1月7日批准设立的地级市&#xff0c;为了深入研究河源市公路交通与经济发展的关系&#xff0c;本文选取了1988&#xff0d;2014年河源市建市以来24年的地区生产总值&#xff08;GDP&#xff09;和公路通…

vue 子组件向父组件传递参数 子传父

子组件中写&#xff1a; this.$emit(RowCount,res.data.RowCount); 父组件中写&#xff1a; getMFGLRowCount(val){ //父组件中的方法: 接收子组件传过来的参数值赋值给父组件的变量 //this.totalCount val; alert("这…

CSS整理

目录 CSS中的& 弹性&#xff08;display:flex&#xff09;布局 flex的属性 justify-content align-items flex:1 flex属性 flex-grow&#xff1a;项目的放大比例 flex-shrink&#xff1a;收缩 flex-basis&#xff1a;初始值&#xff0c;项目占据的主轴空间&…

javascript | 变量、函数、属性的命名规则

javascript标识符的命名规则 变量、函数、属性的名字、或者函数的参数&#xff0c;都可称为标识符。标识符可以是按照下列格式规则组合起来的一个或者多个字符。 第一个字符必须是一个字母、下划线_、或美元符号$。数字不可以作为标识符的首字符。其他字符可以是数字、字母、…

华为云云耀云服务器L实例评测|在 Centos Docker 中使用Nginx部署Vue项目

目录 前言 项目构建 使用CentOS部署 安装Nginx 配置Nginx 项目启动 访问重定向 使用Docker部署 编写docker文件 dockerfile nginx dockercompose 项目启动 前言 本期我们测试在云耀云服务器L实例中分别演示如何在 系统镜像Centos 与 应用镜像 Docker 中使用Nginx…

Java多线程(三)多线程的模式--(阻塞队列,定时器,线程池)

多线程的模式--&#xff08;阻塞队列&#xff0c;定时器&#xff0c;线程池&#xff09; 多线程模式&#xff1a; 阻塞队列&#xff08;线程安全&#xff09; 重点是如何自己去实现这种数据结构&#xff1a; ​编辑 定时器&#xff1a; 实现一个定时器&#xff1a; 线程…

两种解法解决LCR 008. 长度最小的子数组【C++】

文章目录 [LCR 008. 长度最小的子数组](https://leetcode.cn/problems/2VG8Kg/description/)解法暴力解法滑动窗口&#xff08;双指针法&#xff09; LCR 008. 长度最小的子数组 解法 暴力解法 //暴力解法&#xff1a; //使用双for循环依次遍历数组&#xff0c;罗列出所有情况…

HTML的段落中怎么样显示出标签要使用的尖括号<>?

很简单&#xff1a; 符号 < 用 < 替代&#xff1b; 符号 > 用 > 替代。 示例代码如下&#xff1a; <!DOCTYPE html> <html> <head><meta charset"UTF-8"><title>HTML中怎样打出尖括号</title> </head> <b…

AI图片生成 discord 使用midjourney

参考: 不用找咒语了&#xff01;Midjourney图生文功能特征解析&#xff0c;玩转Describe命令&#xff0c;快速搞定AI绘画_哔哩哔哩_bilibili 1 登录 discord 2 点发现 找 midjourney 3 创建 服务器 -> 亲自创建 4 选 仅供我和我的朋友使用 5 起个 服务器名字 6 加bot 由于…

常见的旅游类软文类型分享

假期将至&#xff0c;越来越多人选择出门旅游度过假期&#xff0c;那么各大旅游品牌应该怎么让自己的旅游软文在众多品牌中脱颖而出呢&#xff1f;接下来媒介盒子就给大家分享几个最能吸引受众的旅游类型软文。 一、攻略类软文 和普通的攻略不一样&#xff0c;普通的攻略以用户…

Element--生成不定列的表格

1、对于一些场景&#xff0c;前端可能需要展示不定列数的数据&#xff1b;譬如考勤&#xff0c;可能有的人是一天一次上下班打卡&#xff0c;有的人是一天两次上下班打卡。这个时候统计就需要更具人员做不同的展示&#xff0c;不能固定在前端写死列的属性。 2、代码示例 &…

Linux命令200例:nohup用于在后台运行命令

&#x1f3c6;作者简介&#xff0c;黑夜开发者&#xff0c;CSDN领军人物&#xff0c;全栈领域优质创作者✌。CSDN专家博主&#xff0c;阿里云社区专家博主&#xff0c;2023年6月csdn上海赛道top4。 &#x1f3c6;数年电商行业从业经验&#xff0c;历任核心研发工程师&#xff0…

直播APP源码搭建:核心的服务器系统

在现代科技的推动下&#xff0c;网络衍生出了各种各样的技术&#xff0c;每个技术都被应用到需要的APP上&#xff0c;直播APP源码搭建出来的APP就是其中的一个&#xff0c;然而&#xff0c;这些技术能够成功的在直播APP源码搭建的APP中稳定的为用户们提供功能与服务&#xff0c…

内网穿透实现Windows远程桌面访问Ubuntu,简单高效的远程桌面解决方案

文章目录 前言1. ubuntu安装XRDP2.局域网测试连接3.安装cpolar内网穿透4.cpolar公网地址测试访问5.固定域名公网地址 前言 XRDP是一种开源工具&#xff0c;它允许用户通过Windows RDP访问Linux远程桌面。 除了Windows RDP外&#xff0c;xrdp工具还接受来自其他RDP客户端(如Fre…

Windows环境下Springboot3+Graalvm+Idea 打包成原生镜像 踩坑

https://github.com/oracle/graal/https://github.com/graalvm/graalvm-ce-builds/releases/对应关系graalvm-ce-java17-windows-amd64-X.X.X.zipnative-image-installable-svm-java17-windows-amd64-X.X.X.jar本人使用:graalvm-ce-java17-windows-amd64-23.0.1.zipnative-imag…