一、概述

DSACK下的虚假重传的检测我们之前重传部分的文章已经介绍过了,这里简单说一下拥塞控制部分的实现。

linux内部会维护一个undo_retrans状态变量,其值为已经重传的次数减掉被DSACK检测到的虚假重传的次数,例如当前总共重传了5个数据包,DSACK检测到3个虚假重传,那么undo_retrans即为2。undo_retrans初始化为-1,当发生重传的时候,如果undo_retrans为-1那么就更新undo_retrans=1,否则更新undo_retrans=undo_retrans+1。这样当undo_retrans=0的时候,就表示DSACK已经检测到之前的重传都是虚假重传,可以进行拥塞撤销过程了。DSACK块只能在ACK报文中传输一次,因此当传输DSACK信息的ACK报文丢失的时候,DSACK下的拥塞撤销就不能生效了。下面我们通过DSACK下的拥塞撤销实例来看一下DSACK下的拥塞撤销过程。

二、wireshark示例

1、Open状态下DSACK的拥塞撤销
在这个示例中我们除了观察DSACK的拥塞撤销外还要看一下TSopt的协商问题。我们之前介绍TSopt选项的时候介绍过,如果server与client端协商好TSopt选项后,但随后接收到不带有TSopt选项的数据的时候,协议说TCP应该静默的丢弃这个报文(注意协议描述是应该should而不是必须must),我们提到过linux则会正常接收这个报文,通过这个示例顺便来演示一下。在运行示例前如下设置相关参数。

  1. ******@Inspiron:~$ sudo ip route add local 127.0.0.2 dev lo congctl reno initcwnd 4    #参考本系列destination metric文章
  2. ******@Inspiron:~$ sudo ethtool -K lo tso off gso off  #关闭tso gso以方便观察cwnd变化

业务场景:server端在与client端建立连接后,休眠1002ms,然后连续进行17次write写入操作,每次写入50bytes数据,每次写入间隔5ms。其中高亮的No6数据包发生了乱序传输,在No11之后到达client端,client对每个收到的数据包都会回复一个ACK确认包。注意下面的示例中,server端的TCP在Open状态下,通过拥塞撤销,从拥塞避免切换到了慢启动。

No1-No3:client与server端通过三次握手建立连接,注意三次握手这里协商了TSopt,其余的废话不多说了

No4-No24:这里前面也解释过很多类似场景了,这里可以看到No4数据包没有TSopt选项,但是server端TCP依然正常接收了,另外需要补充说明的一点是server收到No17后,从Disorder模式切换到Recovery模式时候,会初始化undo_retrans=-1,然后在重传了No18后,设置undo_retrans=1。最终在发出No24后,server端处于Open状态,正在进行拥塞避免过程,prior_ssthresh=0x7fffffff, ssthresh=2, cwnd=2, cwnd_cnt=1, packets_out=2, sacked_out=0, lost_out=0, retrans_out=0, fackets_out=0,undo_retrans=1,undo_marker非0表示允许进行拥塞撤销。

No25-No27:可以看到No25带有一个DSACK块,通知server端重复收到了系列号为(51,101)的报文,server端在收到这个DSACK块的时候,更新undo_retrans=undo_retrans-1=0,接着server端发现当前undo_marker非0,即上次快速重传还没有进行过拥塞撤销,同时undo_retrans=0,因此判断之前的快速重传为虚假重传,接着进行拥塞撤销的过程,更新cwnd=max(cwnd,2*ssthresh)=4,ssthresh=max(ssthresh,prior_ssthresh)=0x7fffffff,此时in_flight=2-(0+0)+0=2,拥塞窗口允许TCP发出两个新数据包,即No26、No27,然后更新packets_out=4。这里要注意No25的SACK选项中带有的是一个DSACK块,因此并不会更新sacked_out,也不会触发server从Open状态切换到Disorder状态了。

No28-No41:server端在收到No25进行拥塞撤销后,又进入慢启动阶段,随后进入application-limited状态,这个过程不再重复叙述,最终server端在收到No41后,ssthresh=0x7fffffff,cwnd=12。

TCP系列49—拥塞控制—12、DSACK下的拥塞撤销的更多相关文章

  1. TCP系列50—拥塞控制—13、Eifel探测下的拥塞撤销

    一.概述 我们之前在SACK关闭场景下的拥塞撤销那篇文章中提到过Eifel探测算法(Eifel Detection Algorithm),最早在介绍DSACK和FRTO的时候我们就有提到过Eifel探 ...

  2. TCP系列46—拥塞控制—9、SACK下的快速恢复与Limited transmit

    一.概述 1.SACK下的特殊处理过程 SACK下的拥塞控制处理是linux中拥塞控制的实现依据,再次强调一遍RFC6675的重要性,linux中拥塞控制主体框架的实现是与RFC6675一致的,所以如 ...

  3. TCP系列45—拥塞控制—8、SACK关闭的拥塞撤销与虚假快速重传

    一.概述 这篇文章介绍一下TCP从Recovery状态恢复到Open状态的时候cwnd的更新.我们在tcp重传部分的文章中曾经介绍过虚假重传的概念,Linux在探测到虚假重传的时候就会执行拥塞撤销操作 ...

  4. TCP系列48—拥塞控制—11、FRTO拥塞撤销

    一.概述 FRTO虚假超时重传检测我们之前重传章节的文章已经介绍过了,这里不再重复介绍,针对后面的示例在说明两点 1.FRTO只能用于虚假超时重传的探测,不能用于虚假快速重传的探测. 2.延迟ER重传 ...

  5. TCP系列51—拥塞控制—14、TLP、ER与拥塞控制

    一.概述 这里的重点是介绍TLP.ER与拥塞控制并不是介绍TLP和ER本身,因此TLP和ER的详细内容请翻前文. 在TLP与拥塞控制的交互中有几个点需要注意 1.TLP触发的重传后,TCP仍然处于Op ...

  6. TCP系列40—拥塞控制—3、慢启动和拥塞避免概述

    本篇中先介绍一下慢启动和拥塞避免的大概过程,下一篇中将会给出多个linux下reno拥塞控制算法的wireshark示例,并详细解释慢启动和拥塞避免的过程. 一.慢启动(slow start) 一个T ...

  7. TCP系列55—拥塞控制—18、其他拥塞控制算法及相关内容概述

    前面我们演示分析了100+个wireshark TCP实例,拥塞控制部分也介绍常见的拥塞处理场景以及4种拥塞撤销机制,但是我们一直使用的都是reno拥塞控制算法.实际上拥塞控制发展到今天已经有了各种各 ...

  8. TCP系列54—拥塞控制—17、AQM及ECN

    一.概述 ECN的相关内容是在RFC3168中定义的,这里我简单描述一下RFC3168涉及的主要内容. 1.AQM和RED 目前TCP中多数的拥塞控制算法都是通过缓慢增加拥塞窗口直到检测到丢包来进行慢 ...

  9. TCP系列41—拥塞控制—4、Linux中的慢启动和拥塞避免(一)

    一.Linux中的慢启动和拥塞避免 Linux中采用了Google论文的建议把IW初始化成了10了.在linux中一般有三种场景会触发慢启动过程 1.连接初始建立发送数据的时候,此时cwnd初始化为1 ...

随机推荐

  1. Python学习 :反射 & 单例模式

    反射 什么是反射? - 反射主要是指程序可以访问.检测和修改它本身状态或行为的一种能力(自省) 面向对象中的反射 - 通过字符串的形式来操作(获取.检查.增加.删除)对象中的成员 - python中的 ...

  2. 改脚本之dbscaner

    默认的DBscaner只是用了ipy模块支持一个段的解析,但是我想让他加载脚本进行检测 所以,直接看 def __init__(self, target, thread): self.target = ...

  3. R语言学习笔记(二十一五):如何如何提升R语言运算的性能以及速度

    在R中获得快速运行代码的方法 使用向量化运算 R语言的并行计算可以用parallel和foreach包 加快R运行速度还可以使用cmpfun()函数即字节码编译器 再者就是在R中调用C或C++ 同时还 ...

  4. ubuntu配置机器学习环境(二) cuda 和cudnn 安装

    Nvidia CUDA Toolkit的安装(cuda) PS:特别推荐*.deb的方法,目前已提供离线版的deb文件,该方法比较简单,不需要切换到tty模式,因此不再提供原来的*.run安装方法,这 ...

  5. 初识Symbol

    Symbol作用域 Symbol,是ES6语法中新增的,值是由Symbol函数调用产生的. var s1 = Symbol(); console.log(s1); // Symbol console. ...

  6. vue手脚架安装和项目创建

    一 node安装 1 如果不确定自己是否安装了node,可以在命令行工具内执行:node -v: 2如果执行结果显示:xx不是内部命令,说明你还没有安装node,node按爪给你地址 : http:/ ...

  7. 罗佳琪的第三次预备作业——虚拟机的安装及Linux的初步学习

    虚拟机的安装及Linux的初步学习 坎坷的安装过程 首先我按照老师给的基于VirtualBox虚拟机安装Ubuntu图文教程进行了下载,下载很顺利但是安装时出现了问题. 起初我以为是电脑位数问题,但我 ...

  8. 【LOJ4632】[PKUSC2018]真实排名

    [LOJ4632][PKUSC2018]真实排名 题面 终于有题面啦!!! 题目描述 小 C 是某知名比赛的组织者,该比赛一共有 \(n\) 名选手参加,每个选手的成绩是一个非负整数,定义一个选手的排 ...

  9. kali安装后相关软件的配置

    更新软件apt-get updateapt-get upgrade安装输入法apt-get install ibus-pinyin apt-get install netspeed安装GNOMEapt ...

  10. JS基础,课堂作业,相亲问答

    相亲问答 <script> var a = prompt("你有房子么?"); var b = prompt("你有钱么?"); var c = p ...