TCP重传、滑动窗口、流量控制、拥塞控制机制

目录

  • 1、TCP重传机制
    • 超时重传
    • 快速重传
  • 2、滑动窗口
  • 3、流量控制
  • 4、拥塞控制
    • 1、慢启动
    • 2、拥塞避免
    • 3、拥塞发生

1、TCP重传机制

TCP 针对数据包丢失的情况,会用重传机制解决。

超时重传

就是在发送数据时,设定一个定时器,当超过指定的时间还没有收到对方的 ACK 确认应答报文,就会重发该数据。
RTT往返时延是数据包的往返时间,超时重传时间的值应该略大于报文往返 RTT 的值。

快速重传

不以时间为驱动,而是以数据驱动重传。
快速重传的工作方式是当收到三个相同的 ACK 报文时,会在定时器过期之前,重传丢失的报文段。
比如A给B发了1、2、3、4、5个报文,B收到1后应答2表示希望收到2,但是2丢失了,后面B收到3、4、5时都返回2,A收到了三个 Ack = 2 的确认,知道了 Seq2 还没有收到,就会在定时器过期之前,重传丢失的 Seq2。
【它依然面临着另外一个问题。发送方并不清楚这连续的 ACK2 是接收方收到哪个报文而回复的,是重传一个,还是重传所有的报文。】
选择性确认
在 TCP 头部「选项」字段里加一个 SACK数据,它可以将已收到的数据的信息发送给「发送方」,这样发送方就可以知道哪些数据收到了,哪些数据没收到,知道了这些信息,就可以只重传丢失的数据。

2、滑动窗口

我们都知道 TCP 是每发送一个数据,都要进行一次确认应答。当上一个数据包收到了应答了, 再发送下一个。这种方式的效率比较低。
所以TCP引入了窗口这个概念,窗口大小就是指无需等待确认应答,而可以继续发送数据的最大值。窗口实际上是操作系统开辟的一个缓存空间,发送方主机在等到确认应答返回之前,必须在缓冲区中保留已发送的数据。如果按期收到确认应答,此时数据就可以从缓存区清除。而且还会有累计应答,只要发送方收到了 ACK xx 确认应答,就意味着 xx 之前的所有数据「接收方」都收到了,这样即使之前有应答丢失了也没事。

3、流量控制

发送方不能无脑的发数据给接收方,要考虑接收方处理能力。如果一直无脑的发数据给对方,但对方处理不过来,导致网络流量的无端的浪费。TCP 提供一种机制可以让「发送方」根据「接收方」的实际接收能力控制发送的数据量。

  • TCP流量控制的主要机制是通过滑动窗口实现的。发送方根据接收方的窗口大小和网络情况动态调整自己的发送窗口大小。

4、拥塞控制

流量控制是避免「发送方」的数据填满「接收方」的缓存
拥塞控制是避免「发送方」的数据填满整个网络
拥塞窗口cwnd是发送方根据网络的拥塞程度而动态维护的一个的变量。
发送窗口的值 是拥塞窗口和接收窗口中的最小值。
拥塞控制三个阶段:慢启动-》拥塞避免-》拥塞发生

1、慢启动

有个ssthresh慢启动门限的变量
TCP 在刚建立连接完成后,首先是有个慢启动的过程,一点一点的提高发送数据包的数量,发包的个数是指数性的增长,也就是拥塞窗口1、2、4、8这样。
当 拥塞窗口cwnd 超过 ssthresh慢启动门限 时,开始「拥塞避免算法」。

2、拥塞避免

进入拥塞避免算法后,每当收到一个 ACK 时,拥塞窗口cwnd 增加 1,也就是变成了线性增长。所以还是增长阶段,只是增长速度缓慢了一些。

3、拥塞发生

一直增长后,网络就会慢慢进入拥塞的状况,于是就会出现丢包现象,需要对丢失的数据包进行重传。
我们知道,重传一般也就超时重传和快速重传。

  • 当发生了「超时重传」,则就会使用拥塞发生算法。
    ssthresh慢启动门限 设为 拥塞窗口的一半,拥塞窗口重置为 1(初始值),然后重新进入慢启动阶段。
    这种方式太激进,反应也很强烈,会造成网络卡顿。
  • 当发生了「快速重传」,使用快速恢复算法。
    快速恢复算法是认为,你还能收到 3 个重复 ACK 说明网络也不那么糟糕。此时慢启动门限和拥塞窗口都设为原拥塞窗口的一半,然后重新进入拥塞避免阶段;

TCP拥塞控制是传输控制协议(TCP)中用于防止网络拥塞的一种机制。当网络中的流量过多时,可能会导致数据包丢失和延迟增加,拥塞控制的目的是避免这种情况的发生。TCP拥塞控制主要基于以下四个算法:

慢启动(Slow Start):

慢启动是TCP开始发送数据时的初始阶段,此时拥塞窗口(Congestion Window, cwnd)从1个最大报文段(MSS)开始,每收到一个确认(ACK),cwnd 就增长1个MSS,直到达到一个阈值(ssthresh),之后切换到拥塞避免算法。
拥塞避免(Congestion Avoidance):

当cwnd超过ssthresh后,拥塞避免算法开始工作。此时,cwnd的增长速率会减慢,每经过一个往返时间(RTT),cwnd增长1个MSS。这种增长方式是线性的,而不是指数级的。
快重传(Fast Retransmit):

当接收方检测到失序的报文段时,它会立即发送重复ACK(Duplicate ACK),而不是等待自己的数据发送时才进行确认。当发送方接收到三个相同的重复ACK时,会立即重传该报文段,而不是等待重传计时器到期。
快恢复(Fast Recovery):

快恢复是与快重传配合使用的算法。当发送方接收到三个重复ACK时,会将ssthresh设置为当前cwnd的一半,并将cwnd设置为ssthresh加3个MSS,然后进入拥塞避免状态,而不是慢启动。
选择性确认(Selective Acknowledgments, SACK):

SACK是TCP的一个选项,允许接收方明确告诉发送方哪些数据已经被成功接收,哪些需要重传。这可以减少不必要的重传,提高网络效率。
延迟确认(Delayed Acknowledgments):

延迟确认是接收方为了减少发送ACK的数量而采取的一种策略,它会等待一段时间或直到收到一定数量的数据后再发送ACK。
窗口缩放(Window Scaling):

窗口缩放允许TCP窗口大小超过64KB的限制,这对于高速网络来说是非常有用的,可以显著提高传输效率。
拥塞窗口全开(Congestion Window Full, CWnd Full):

当cwnd达到最大窗口大小时,TCP会根据网络的反馈来调整数据的发送速率,以避免网络拥塞。
TCP拥塞控制的这些算法共同工作,以确保网络中的流量得到合理分配,减少数据包丢失,提高网络的整体性能和稳定性。然而,拥塞控制算法的选择和调整通常依赖于具体的网络环境和应用需求。


拥塞窗口全开(Congestion Window Full,简称CWND Full)并不是一个标准的TCP拥塞控制算法,而是对TCP拥塞窗口(Congestion Window,简称CWND)在达到最大值时行为的一种描述。在TCP拥塞控制中,CWND是一个重要的参数,用于控制发送端可以连续发送的数据量,而不受接收端接收能力的限制。

以下是CWND全开的一些概念和行为:

CWND增长:在TCP连接建立初期,CWND从1个最大报文段(MSS)开始,随着数据的成功传输,CWND会逐渐增长。

慢启动阶段:CWND按照指数方式增长,直到达到慢启动阈值(ssthresh),此时进入拥塞避免阶段。

拥塞避免阶段:CWND的增长速度会减慢,通常每经过一个往返时间(RTT),CWND增加1个MSS,增长方式为线性增长。

达到最大值:当CWND增长到一个预设的最大值(例如,由操作系统或网络环境决定的值)时,CWND就被认为是"全开"的。此时,CWND不再增长,发送端将根据这个窗口大小来控制数据的发送速率。

拥塞信号:在CWND全开的情况下,如果发生丢包或其他拥塞信号,TCP会采取措施减少CWND的大小,以避免进一步的拥塞。这通常涉及到将ssthresh设置为当前CWND的一半,并将CWND重置为1个MSS,然后重新进入慢启动阶段。

自适应调整:在某些情况下,TCP可能会使用自适应算法来调整CWND的最大值,以更好地适应网络条件。例如,使用自适应拥塞控制算法(如Vegas)的TCP变种会根据网络反馈来调整CWND的增长和减少策略。

网络环境影响:CWND全开的行为会受到网络环境的影响,例如带宽、延迟、丢包率等。在高带宽、低延迟的网络环境中,CWND可能会增长到较大值,而在拥塞严重的网络中,CWND的增长可能会受到限制。

CWND全开是一个动态的过程,它依赖于网络条件和TCP拥塞控制算法的实现。正确地管理CWND的大小对于优化网络性能和避免拥塞至关重要。

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

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

相关文章

Ctrl+C、Ctrl+V、Ctrl+X 和 Ctrl+Z 的起源

注:机翻,未校对。 The Origins of CtrlC, CtrlV, CtrlX, and CtrlZ Explained We use them dozens of times a day: The CtrlZ, CtrlX, CtrlC, and CtrlV shortcuts that trigger Undo, Cut, Copy, and Paste. But where did they come from, and why do…

文件上传接口

文章目录 开发前端接口 开发前端接口 首先这个前端的文件上传组件使用了,前端组件 首先这个接口不是一般的接口,这个接口可以提取出来,之后那里使用了,就直接放到哪里 所以这是一个万能文件上传接口 写完之后选择 头像组件 在图库中添加组件 写前端组件之后,写了前端的组件…

Bootstrap 5 加载效果

Bootstrap 5 加载效果 Bootstrap 5 是一个流行的前端框架,它提供了丰富的组件和工具,用于快速开发响应式和移动优先的网页。在本文中,我们将探讨 Bootstrap 5 中的加载效果,包括如何实现它们以及它们在网页设计中的作用。 什么是加载效果? 加载效果是在网页或应用程序中…

k8s集群创建devops项目一直等待状态,没有发现host

问题分析: kubesphere在帮我们自动化创建一些智能自动化的额时候难免会发生一些小错误,devops-jenkins是一个部署也会生成一个容器组即pod,容器组的容器服务端口是 targetPort,容器组对外暴露的端口是port,拿devops-c…

[深度学习]基于yolov10+streamlit目标检测演示系统设计

YOLOv10结合Streamlit构建的目标检测系统,不仅极大地增强了实时目标识别的能力,还通过其直观的用户界面实现了对图片、视频乃至摄像头输入的无缝支持。该系统利用YOLOv10的高效检测算法,能够快速准确地识别图像中的多个对象,并标注…

Billu_b0x靶机

信息收集 使用arp-scan 生成网络接口地址来查看ip 输入命令: arp-scan -l 可以查看到我们的目标ip为192.168.187.153 nmap扫描端口开放 输入命令: nmap -min-rate 10000 -p- 192.168.187.153 可以看到开放2个端口 nmap扫描端口信息 输入命令&…

配置PYTHONPATH环境变量

配置PYTHONPATH环境变量 前言Win系统临时配置永久配置 Linux系统临时配置永久配置 前言 在运行py脚本时不仅需要import官方库,经常会import自己编写的脚本,但此时会出现模块找不到的如下报错。解决方法是配置PYTHONPATH,下文介绍Win系统和Li…

禹神:一小时快速上手Electron,前端Electron开发教程,笔记。一篇文章入门Electron

一、Electron是什么 简单的一句话,就是用htmlcssjsnodejs(Native Api)做兼容多个系统(Windows、Linux、Mac)的软件。 官网解释如下(有点像绕口令): Electron是一个使用 JavaScript、HTML 和 CSS 构建桌面…

Resources.Load返回null

Resources.Load返回null 在unity中Resources.Load从Assets下的任意Resources目录下读取资源&#xff0c;比如从Assets\Resources下读取Cube&#xff08;预制体&#xff09;&#xff0c;当然也可以读取其他资源 代码为 GameObject prefab Resources.Load<GameObject>(…

微软Edge浏览器深度解析:性能、安全性与特色功能全面评测

一、引言 自Windows 10操作系统推出以来&#xff0c;微软Edge浏览器作为默认的网页浏览器&#xff0c;凭借其现代化的设计和出色的性能表现&#xff0c;逐渐获得了用户的认可。本文旨在对Edge浏览器进行深入分析&#xff0c;探讨其在多个方面的表现。 二、界面与操作体验 界面…

在 PostgreSQL 里如何处理数据的存储优化和数据库备份的效率平衡?

&#x1f345;关注博主&#x1f397;️ 带你畅游技术世界&#xff0c;不错过每一次成长机会&#xff01;&#x1f4da;领书&#xff1a;PostgreSQL 入门到精通.pdf 文章目录 在 PostgreSQL 里如何处理数据的存储优化和数据库备份的效率平衡&#xff1f;一、数据存储优化&#x…

HTML表格表单及框架标签

一.表格标签 1.<table></table> 创建表格 2.<caption></caption> 表格的标题 3.<tr></tr>Table Row&#xff08;表格行&#xff09; 4.<td></td>Table Data&#xff08;表格数据&#xff09;其中有属性rowspan"2&quo…

Linux操作系统——数据库

数据库 sun solaris gnu 1、分类&#xff1a; 大型 中型 小型 ORACLE MYSQL/MSSQL SQLITE DBII powdb 关系型数据库 2、名词&#xff1a; DB 数据库 select update database DBMS 数据…

Go中的defer看似很简单,实则一点都不难

Golang 中的 Defer 在Go语言中&#xff0c;defer语句用于将一个函数调用推迟到外围函数返回之后执行。它常用于确保某些操作在函数结束时一定会执行&#xff0c;例如资源释放、文件关闭等。 基本语法 defer语句的基本使用方法如下&#xff1a; func main() {defer fmt.Prin…

距离变换 Distance Transformation

以下为该学习地址的学习笔记&#xff1a;Distance transformation in image - Python OpenCV - GeeksforGeeks 其他学习资料&#xff1a;Morphology - Distance Transform 简介 距离变换是一种用于计算图像中每个像素与最近的非零像素之间距离的技术。它通常用于图像分割和物体…

51单片机5(GPIO简介)

一、序言&#xff1a;不论学习什么单片机&#xff0c;最简单的外设莫过于I口的高低电平的操作&#xff0c;接下来&#xff0c;我们将给大家介绍一下如何在创建好的工程模板上面&#xff0c;通过控制51单片机的GPIO来使我们的开发板上的LED来点亮。 二、51单片机GPIO介绍&#…

第三节SHELL脚本中的变量与运算(1.1-1.5)

一,脚本中的变量 1,1什么是变量 在编写程序是,通常会遇到被操作对象不固定的情况我们需要用一串固定的字符来的表示不固定的值,这就是变量存在的根本意义变量的实现原理就是内存存储单元的一个符合名称 1,2 变量的命名规则 变量的名称中只能包含数字,大小写字母以及下划线 …

PySide在Qt Designer中使用QTableView 显示表格数据

在 PySide6 中&#xff0c;可以使用 Qt Model View 架构中的 QTableView 部件来显示和编辑表格数据。 1、创建ui文件 在Qt Designer中新建QMainWindow&#xff0c;命名为csvShow.ui。QMainWindow上有两个部件&#xff1a;tableview和btn_exit。 2、使用pyuic工具将ui文件转换为…

Kafka(四) Consumer消费者

一&#xff0c;基础知识 1&#xff0c;消费者与消费组 每个消费者都有对应的消费组&#xff0c;不同消费组之间互不影响。 Partition的消息只能被一个消费组中的一个消费者所消费&#xff0c; 但Partition也可能被再平衡分配给新的消费者。 一个Topic的不同Partition会根据分配…

MySQL集群、Redis集群、RabbitMQ集群

一、MySQL集群 1、集群原理 MySQL-MMM 是 Master-Master Replication Manager for MySQL&#xff08;mysql 主主复制管理器&#xff09;的简称。脚本&#xff09;。MMM 基于 MySQL Replication 做的扩展架构&#xff0c;主要用来监控 mysql 主主复制并做失败转移。其原理是将真…