继续画图带你学习TCP 其他 7 大特性

四、滑动窗口机制

五、流量控制

六、拥塞控制 (安全机制)

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

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

九、粘包问题

十、保活机制

TCP总结

四、滑动窗口机制

滑动窗口机制,是在可靠性的前提下,进一步地提高传输效率

认识滑动窗口

一发一收的方式:TCP 协议需要对数据进行确认后,才可以发送下一个数据包,如图:

图片

如上图,发送端每发送一个数据包,都需要得到接收端的确认应答以后,才可以发送下一个数据包,是一问一答的串行过程;即每次传输数据都需要等待一个对应的等待时间,那么传输 N 份数据,就需要等待 N 次应答时间,总的传输时间:N 份数据传输时间 + N 份应答传输时间

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

图片

滑动窗口本质上是批量传输数据

总的传输时间:N 份数据传输时间重叠成了一份时间,N 份应答传输时间重叠成了一份时间,相当于把多份数据的传输时间和等待 ACK 的时间压缩成一份了,总的等待时间少了,传输效率也就高了

a. 窗口

窗口大小: 不等待 ACK 的情况下,批量发送的最大数据量,就叫"窗口大小" (如上图,就是4000个字节,4个字段)

  • 发送前四个字段的时候,不需要等待任何 ACK,直接发送;

  • 收到第一个ACK后,滑动窗口向后移动,继续发送第五个字段的数据,依次类推;

  • 操作系统内核为了维护这个滑动窗口;需要开辟 发送缓冲区 来记录当前还有哪些数据没有应答;只有确认应答过的数据,才能从缓冲区删掉;

  • 窗口越大, 则网络的吞吐率就越高

b. 滑动

窗口范围内的数据是在等待这些数据的 ACK (已经被发送出去)

图片

如上图,当发送方收到 2001 的 ACK,意味着 1001 - 2000 的数据对方已经接收,此时立刻继续传输 5001 - 6000 的数据,则等待 ACK 的数据包的序号就是 2001,3001,4001,5001

丢包问题处理

丢包的两种情况如图:

图片

情况1: 确认应答 (ACK) 丢包

不需要进行额外的处理;在这种情况下,部分 ACK 丢了并不要紧,因为可以通过后续的 ACK进 行确认

理解"确认序号"的含义

从当前序号开始,前面的数据都已经正确到了

如上图,是 1001 的 ACK 丢失,2001 的 ACK 没丢,此时,发送方收到 2001 之后,就会认为 1 - 1000 这个数据也是顺利到达的,1001 丢了无所谓,2001 的 ACK 能够包含 1001 ACK 中的信息

情况2: 数据包丢失

如下图,若是 1001-2000 丢失,然后 2001-3000,3001-4000 等后边的几个数据都顺利到达,此时主机 B 反馈的 ACK 的确认序号始终是 1001;

此时若主机 A 发现连续几个 ACK 都是1001,主机 A 就知道,1001 这个数据丢失,就会重传 1001;

在重传 1001 之前,收到的确认序号都是 1001;

当主机 B 收到 1001 这个数据的时候,由于 2001-7000 这些数据前边已经收到过,接下来的 ACK 就从 7001 开始;

此处的重传,只是重传丢了的数据,其他数据不需要额外重传—— 快速重传(搭配滑动窗口下的超时重传)

图片

"乱序"传输:

图片

图片

五、流量控制

流量控制: 根据接收方的处理能力来反向制衡发送方的发送效率(窗口大小) (通过接收缓冲区的 “剩余空间大小” 来决定发送方的速率)

窗口大小不能无限大,传输速率太快,接收方可能处理不过来

在使用滑动窗口机制进行数据传输时,发送方根据实际情况发送数据包,接收端接收数据包;由于接收端处理数据包的能力是不同的,因此可能出现两种情况:

  • 若窗口过小,发送端发送少量的数据包,接收端很快就处理了,并且还能处理更多的数据包;当传输比较大的数据时需要不停地等待发送方,就会造成很大的延迟

  • 若窗口过大,发送端发送大量的数据包,而接收端处理不了这么多的数据包,就会堵塞链路;若丢弃这些本应该接收的数据包,又会触发重发机制

(第一次的窗口大小是根据链路带宽的大小来决定的) ,发送数据包,接收端接收这些数据包,并返回确认应答包,告诉发送端自己下次希望收到的数据包是多少(新的窗口大小),发送端收到确认应答包以后,将以该窗口大小进行发送数据包

  • 接收端将自己可以接收的缓冲区大小放入 TCP 首部中的 “窗口大小” 字段,通过 ACK 端通知发送端

  • 窗口大小字段越大,说明网络的吞吐量越高

  • 接收端一旦发现自己的缓冲区快满了,就会将窗口大小设置成一个更小的值通知给发送端

  • 发送端接受到这个窗口之后,就会减慢自己的发送速度

  • 如果接收端缓冲区满了,就会将窗口置为0;这时发送方不再发送数据,但是需要定期发送一个窗口探测数据段,使接收端把窗口大小告诉发送端

如下图:

图片

图解:

  • 假设初始窗口大小为4000,发送端发送 4 个数据包,分别为 1-1000,1001-2000,2001-3000 和 3001-4000

  • 接收端接收数据包,接收到 1-1000 数据包之后,设置窗口大小为 3000,告诉发送端自己现在只能处理 3 个数据包,下一次请发送 3 个数据包

  • 发送端接收到确认应答包,查看到接收端返回窗口大小为 3000,知道接收端处理了 1 个数据包;接着继续发送: 1001-2000,2001-3000 和 3001-4000

  • 接收方收到之后,缓冲区只能处理 2 个数据包,发过去的第 3 个数据包 3001-4000 没有被处理;这说明此时接收端只能处理 2 个数据包,第 3 个数据包还需要重新发送

  • 当窗口为 0 时,发送方会暂停发送,也会定时发送一个探测报文;因为接收缓冲区的数据随时可能被取走,一旦取走,就可以接收新的数据(滑动窗口大小是动态变化的

六、拥塞控制 (安全机制)

拥塞控制是考虑网络传输路径上的拥堵程度

虽然TCP有了滑动窗口这个大杀器,能够高效可靠的发送大量的数据;但是如果在刚开始阶段就发送大量的数据,仍然可能引发问题;因为网络上有很多的计算机,可能当前的网络状态就已经比较拥堵,在不清楚当前网络状态下,贸然发送大量的数据,是很有可能雪上加霜,因此,TCP引入 慢启动 机制,先发少量的数据,探探路,摸清当前的网络拥堵状态,再决定按照多大的速度传输数据

图片

线增积减 (和式增加,积式减少)

像上面这样的拥塞窗口增长速度,是指数级别的,“慢启动” 只是指初使时慢,但是增长速度非常快,具体的增长如下图:

图片

图片

刚开始的时候从1指数增长,到达阈值后开始线性增长,如果出现网络阻塞,直接减小到初始值,然后再次指数增长到达新的阈值(新阈值为上次阻塞窗口大小的一半),再次线性增长直到网络阻塞,一直这样动态变换循环

为啥要动态变化??

网络的拥堵情况是瞬息万变的,我们要随时根据网络的实际情况进行动态调整 (随时适应网络的变化过程)

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

目的是为了提高效率,在流量控制的基础上,尽量返回一个合理但又比较大的窗口

在前面我们提到,在发送端发送数据后,接收数据的主机需要返回 ACK应答,此时若立刻返回,窗口可能比较小 (因为缓冲区的数据只处理了一部分),所以 TCP 采用了延迟应答机制,举例:

不带延迟应答:

有一个超市,假设泡面库存最多存放100箱,当前已经存了80箱,空余20箱;

第二天一早,送货小哥来问:“老板,你明天需要多少面?”

老板:“你最多送20箱就行。”

带延迟应答:

第二天一早,送货小哥来问:“老板,你明天需要多少面?”

老板:“我晚上的时候打电话告诉你需要多少。”

(可能白天又卖出了10箱,第二天最多送10箱即可)

延时应答其实就是让 ACK 的发送时间晚一会儿 (不影响可靠性的前提下);

延迟的时间中就会给应用程序提供更多的消费数据的机会,此时时间到了,再发送 ACK 的时候,得到的窗口大小(接收缓冲区的剩余空间就会更大一些)

窗口越大,网络吞吐量就越大,传输效率就越高;我们的目标是在保证网络不拥塞的情况下尽量提高传输效率

问:所有的包都可以延迟应答么?

肯定不是

  • 数量限制: 每隔 N 个包就应答一次 (N一般为2)

  • 时间限制: 超过最大延迟时间就应答一次 (时间一般取200 ms,延迟应答的等待时间不能超过超时重传的时间,不然就重传了)

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

在延迟应答的基础上,为了进一步提高程序运行效率而引入的机制

在很多情况下,客户端和服务器的通信模式一般都是 Request - Response 模式,即 “一问一答”

如图:

图片

注意:

三次握手中间的 SYN 和 ACK 都是由内核决定的,不涉及不同的时机

上述提到的四次挥手的过程,ACK 是内核决定的,发的 FIN (close方法) 是应用程序代码决定的

九、粘包问题

严格说,粘包问题不是 TCP 自身的机制,而是面向字节流传输所具备的共性问题

粘包,指粘的是应用层数据包,导致数据在处理的时候,容易读取半个应用层数据包

面向字节流: 指的是一次读一个字节,或者一次读两个字节,或者一次读 N 个字节都行

举例:双方建立连接,需要在连接后一段时间内发送不同结构数据,如连接后,有好几种结构

  • “你好不好”

  • “好个P”

读多少个字节才是一个完整的应用层数据包,这个是不清楚的

若一次读一个汉字,读出来就是 “好”;若一次读三个汉字,读出来就是 “好个P”

读法不一样,最终的含义差异也很大;读取应用层数据,就不应该只读半个包

如何避免粘包问题?

归根结底就是一句话,明确两个包之间的边界

TCP 协议本身不帮你区分应用层数据包,相对而言,UDP 协议没这个问题 (UDP 协议就是按照数据包为单位进行收发的)

  • 方式1 - 使用分隔符

比如,上述回答改为 “好个P;”

用分号 ;当做两个包的分隔符,读数据,一直读到分号;才认为是一个完整的应用层数据包

应用层协议,是程序猿自己来定的,只要保证分隔符不和正文冲突即可**

  • 方式2 - 明确包的长度

比如,上述用例改为 “4你好不好3好个P”

先读取最开始的四个字节,得到包的长度3;继续读取3个汉字,于是就读取一个完整的包

HTTP 协议基于 TCP 的应用层协议,自己就会处理好粘包问题,上述两种方式都使用到了:

对于 GET 请求,分隔符就是空行

对于 POST 请求,Content-length 来指定包的长度

思考:对于UDP协议来说,是否也存在 “粘包问题” 呢?

  • 对于UDP,如果还没有上层交付数据,UDP的报文长度仍然在。同时,UDP是一个一个把数据交付给应用层;就有很明确的数据边界

  • 站在应用层的站在应用层的角度,使用UDP的时候,要么收到完整的UDP报文,要么不收;不会出现"半个"的情况

十、保活机制

双方建立交互的连接,并不是一直存在数据交互,有些连接会在数据交互完毕后,主动释放连接,而有些不会,那么在长时间无数据交互的时间段内,交互双方都有可能出现掉电、死机、异常重启,还是中间路由网络无故断开、NAT超时等各种意外

在这些 “异常情况” 下,TCP 对于连接会有一些特殊的处理

举例:

1.进程崩溃: 这种情况,TCP 连接会正常四次挥手 (只要是进程退出,都会自动关闭相关的文件)

2.主机关机(按照流程关机):关机的时候会强制先杀进程,杀进程过程之中就要进行四次挥手了

3.主机断电 / 网线断开:

  • a) 接收方断电。 对端尝试发送消息的时候,就会出现没有 ACK 的情况 — 于是就会触发超时重传 — 重传一定次数,就会重置连接 — 放弃连接

  • b) 发送方断电。对端尝试接收消息,对于接收端来说,本来也不知道发送方什么时候发送,难道就一直等吗?

    解决方案 — 心跳包 TCP 的通信双方,即使在没有数据交互的过程中,也会定时相互传输一个没有数据业务意义的 “心跳包”,只是为了证明 “我活着”,一旦隔了一段时间都没有收到对方的心跳包,就可以认为对端"挂"了

TCP总结

TCP 之所以复杂,是因为它既要保证可靠性,同时又尽可能地提高性能

图片

可靠性:

校验和,序列号

确认应答,超时重传

连接管理,流量控制,拥塞控制

提高性能:

滑动窗口,快速重传

延迟应答,捎带应答

其他:

定时器(超时重传定时器,保活定时器,TIME_WAIT定时器等)

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

LLM-Intro to Large Language Models

LLM some LLM’s model and weight are not opened to user what is? Llama 270b model 2 files parameters file parameter or weight of neural networkparameter – 2bytes, float number code run parameters(inference) c or python, etcfor c, 500 lines code withou…

Matlab和python详解数独谜题问题

🔗 运行环境:Matlab、Python 🚩 撰写作者:左手の明天 🥇 精选专栏:《python》 🔥 推荐专栏:《算法研究》 🔐#### 防伪水印——左手の明天 ####🔐 &#x1f4…

爱德华|书客|飞利浦护眼台灯好不好用?多方位测评对比爆料!

说到护眼台灯相信大家都不陌生,很多办公族、学生党都会备上一台用于工作、学习。因为长时间的工作或者学习,会明显的感觉到眼睛疲劳和不适。而护眼台灯可以很好的解决这个难题,因为护眼台灯是经过科学的设计和研发的,护眼台灯可以…

苹果录屏功能在哪?提升你的使用体验

屏幕录制已成为人们日常生活中不可或缺的一部分,苹果设备内置了强大的录屏功能,允许用户捕捉屏幕上的活动,可是很多用户不知道苹果录屏功能在哪。本文将详细介绍如何使用苹果内置录屏功能,为用户提供全面的录屏解决方案。 苹果录屏…

ESP32 LVGL Gui-Guider的移植

使用参考: ESP32系列之LVGL(三):Gui-Guider的使用_esp32 lvgl-CSDN博客 1、拷贝文件: 按照上面的文章,使用Gui-Guider软件生成C代码之后,custom和generated是我们要使用到的文件,…

36、红外遥控(外部中断)

红外遥控简介 红外遥控是利用红外光进行通信的设备,由红外LED将调制后的信号发出,由专用的红外接收头进行解调输出 通信方式:单工,异步 红外LED波长:940nm 通信协议标准:NEC标准 硬件电路 基本发送与接收…

海云安参与制定《信息安全技术 移动互联网应用程序(App)软件开发工具包(SDK)安全要求》标准正式发布

近日,由TC260(全国信息安全标准化技术委员会)归口 ,主管部门为国家标准化管理委员会,深圳海云安网络安全技术有限公司(以下简称“海云安”)等多家相关企事业单位共同参与编制的GB/T 43435-2023《…

鸿蒙Watch 页面跳转

新建页面 config.json 回自动注册 添加跳转 <button type"capsule" onclick"toStatusMonitor">状态检测</button>写跳转方法 import router from system.router;export default {data: {},onInit() {},onShow() {},toStatusMonitor() {rou…

GraphPad Prism 9:最强大的数据分析软件,助您轻松解析复杂数据!

您是否正在寻找一个功能强大、易于使用的数据分析软件&#xff1f;GraphPad Prism 9是您的最佳选择&#xff01;作为全球领先的科学数据分析工具&#xff0c;Prism 9提供了广泛的功能和先进的统计分析方法&#xff0c;帮助您轻松解析和可视化复杂的数据。 Prism 9不仅具备直观…

linux作业管理_jobs

4.2 作业管理 是指控制当前正在运行的进程的行为&#xff0c;也称为进程控制。 是shell的一个特性&#xff0c;使用户能在多个独立进程间进行切换。 例如&#xff0c;用户可以挂起一个正在运行的进程&#xff0c;稍后再恢复其运行。当用户使用vim编辑一个文本文件&#xff0c…

Android把宽高均小于给定值的Bitmap放大到给定值,Kotlin

Android把宽高均小于给定值的Bitmap放大到给定值&#xff0c;Kotlin 假设拉伸放大到SIZE2048 fun scaleSize(image: Bitmap): Bitmap {val w image.widthval h image.heightvar newW: Intvar newH: Intif (w > h) {newW SIZEnewH (SIZE / w.toFloat()) * h} else {newW …

【Springboot+vue】如何运行springboot+vue项目

从github 或者 gitee 下载源码后&#xff0c;解压&#xff0c;再从idea打开项目 后端代码处理 这是我在gitee下载下来的源码 打开之后&#xff0c;先处理后端代码 该配置的配置&#xff0c;该部署的部署 比如将sql文件导入数据库 然后去配置文件更改配置 然后启动项目 确保…

极米Z系列双十一销量超10万台 极米Z7X成轻薄投影首选

近期&#xff0c;极米2023双十一战报公布&#xff0c;双十一全周期&#xff08;10月19日00:00-11月11日23:59&#xff09;极米夺得京东/天猫/抖音投影品类销量&GMV双第一&#xff0c;全网单品总销量超190,000台。按照产品系列来看&#xff0c;极米家用旗舰H系列全网销量超4…

在项目根目录未找到 app.json

这个问题就是我们在编译后的app.json文件找不到&#xff0c;路径出现了问题 首先看dist下我们该文件的路径 所以我们需要将该路径配置到我们project.config.json文件中去 在这里新加下面这行代码就可以了&#xff0c; "miniprogramRoot": "dist/dev/mp-weixi…

【蓝桥杯选拔赛真题73】Scratch烟花特效 少儿编程scratch图形化编程 蓝桥杯创意编程选拔赛真题解析

目录 scratch烟花特效 一、题目要求 编程实现 二、案例分析 1、角色分析

16种数据分解方法任意挑选,MATLAB代码,实现数据分解自由,一次性全部带走,速看!...

目录 16种常用的数据分解方法 EMD(经验模态分解) EEMD(集合经验模态分解) CEEMD(互补集合经验模态分解) FEEMD(快速EEMD分解) CEEMDAN(完全自适应噪声集合经验模态分解) ICEEMDAN(改进的自适应噪声完备EEMD) LMD(局域均值分解) RLMD(鲁棒性局部均值分解) EWT(经验小波分解) VMD…

Kubernetes(K8s) Ingress介绍-08

Ingress介绍 在前面课程中已经提到&#xff0c;Service对集群之外暴露服务的主要方式有两种&#xff1a;NotePort和LoadBalancer&#xff0c;但是这两种方式&#xff0c;都有一定的缺点&#xff1a; NodePort方式的缺点是会占用很多集群机器的端口&#xff0c;那么当集群服务…

docker、docker-component安装

1.docker安装 #安装c环境 yum -y install gcc-c yum install -y yum-utils device-mapper-persistent-data lvm2 #添加yum的镜像地址 yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo yum makecache fast #下载docker yum -y…

打印机文档被挂起无法打印怎么办?分享5个常见解决方法!

“我需要打印一份比较紧急的文件&#xff0c;但是当我需要用到打印机时&#xff0c;却发现打印机显示文档被挂起&#xff0c;根本就无法打印。这是为什么呢&#xff1f;我怎么解决打印机文档被挂起的问题呢&#xff1f;” 在我们的工作和学习中&#xff0c;可能经常需要使用打印…

宝宝洗衣机哪个牌子质量好?婴儿专用洗衣机推荐

对于宝妈来说有一款小型可以自动杀菌的洗衣机真的非常重要。我们日常生活中一般会把一些贴身衣物和较特殊的面料的衣物用于手洗&#xff0c;而手洗的过程会相对来说比较麻烦&#xff0c;而且还可能洗不干净&#xff0c;而传统的洗衣机采用了双缸式容易滋生霉菌&#xff0c;容易…