一、概述

forward retransmit相关的内容在RFC6675中有描述,可以参考RFC6675 section 4中NextSeg ()的定义。forward retransmit中文名可以叫做前向重传,我这里简单说一下linux实现上的前向重传

在快速重传(包括快速重传的各种变种)到达Recovery point之前,都会尝试重传标记为lost的数据包,当把标记为lost的数据包重传完毕后,如果同时满足下面几个条件:

1、当前拥塞控制处于Recovery状态,且在尝试重传数据包的时候,拥塞窗口允许TCP传输数据包

2、TCP连接没有待发送的数据包或者受限于window size、nagle算法等而不能发送

3、TCP连接支持SACK功能

当同时满足上面三个条件的时候,如果已经被SACK确认的最高的系列号与当前已经重传过的数据包之间存在未被SACK确认且未重传过的数据包,那么TCP就会尝试前向重传这些未进行过重传的数据包。

其实前向重传并不复杂,但是前向重传相比其他的重传方式在拥塞控制时候有自身的特殊性,后续介绍拥塞控制的时候进行介绍,下面我们通过wireshark来看一个具体示例。

二、wireshark示例

1、forward retransmit简单示例

在进行下面的测试前需要设置tcp_recovery=0,以关闭RACK重传机制,RACK重传优先于前向重传,因此当打开RACK的时候,RACK会先起作用把数据包标记为lost,并进行重传。后续文章介绍RACK。

业务场景:server端与client端建立连接休眠1000ms后,以3ms为间隔连续发送9个数据包No4-No12,每个数据包的大小为50bytes,其中只有No4和No11数据包成功到达接收端,其余数据包均在传输过程中丢失,我把传输丢失的数据包设置了高亮显示。

No1-No3:client与server端建立连接,SYN报文中协商了MSS=62,扣除TSopt选项的12bytes后,server端最多只能传输50bytes的数据,因此server端在重传的时候不会进行重组包(后续详细介绍)。

No4-No12:server端发出对应的数据包,其中只有No4和No11成功传输到client端。其实数据包传输过程中丢失。

No13:对应No4报文的ACK确认包

No14-No15:对应No11报文的ACK确认包,可以看到这是一个dup ACK,此时fackets_out=7,dupthresh=3,fackets_out-dupthresh=4。因此server端把No5、No6、No7、No8这四个数据包标记为lost。接着server端先重传No5数据包,受限于拥塞控制,其余数据包暂时还不能进行重传。

No16-No18:server端收到No16这个确认包后,拥塞控制进行更新,允许server端发出两个数据包,因此server端接着重传No6和No7数据包,即对应No17和No18。

No19-No20:server端收到No19后,拥塞控制允许发出一个数据包,因此server端重传No8数据包,即对应No20。

No21-No22:server端收到No21后,拥塞控制进行更新后允许发出一个数据包,此时被标记为lost的4个数据包都已经进行了重传,同时server端也没有新数据等待发送,因此server端进行前向重传,重传No9数据包,这里注意No9数据包并没有被标记为lost,但是同样进行了重传。

No23-No24:这组数据包的处理与No21-No22类似。

No25:server端收到No25的时候,虽然拥塞控制允许发出数据包,但是此时被SACK确认的最高系列号为401(实际上是最高系列号的下一个系列号),在系列号401之前已经没有未被SACK确认且未重传过的数据包了,因此尝试前向重传失败,没能发出数据包。这里可以看到虽然No12数据包也丢失了,但是前向重传并不会重传No12。

No26:server端收到No26后重启RTO定时器,定时时间大约为250ms

No27-No28:RTO超时后把No27标记为lost,并重传No27,接着收到No27的确认包,整个传输过程结束。

TCP系列22—重传—12、Forward Retransmit的更多相关文章

  1. TCP系列16—重传—6、基础快速重传(Fast Retransmit)

    一.快速重传介绍 按照TCP协议,RTO超时重传是一个非常重要的事件,当RTO超时的时候,TCP会同时通过两种方式非常谨慎的降低发送数据包的速率,一种是基于拥塞控制削减发送窗口的大小,另外一个是通过指 ...

  2. TCP系列11—重传—1、TCP重传概述

    在最开始介绍TCP的时候,我们就介绍了TCP的三个特点,分别是面向连接.可靠.字节流式.前面内容我们已经介绍过了TCP的连接管理,接下来的这部分内容将会介绍与TCP可靠性强关联的TCP重传. 很多网络 ...

  3. TCP系列49—拥塞控制—12、DSACK下的拥塞撤销

    一.概述 DSACK下的虚假重传的检测我们之前重传部分的文章已经介绍过了,这里简单说一下拥塞控制部分的实现. linux内部会维护一个undo_retrans状态变量,其值为已经重传的次数减掉被DSA ...

  4. TCP系列24—重传—14、F-RTO虚假重传探测

    一.虚假重传 在一些情况下,TCP可能会在没有数据丢失的情况下初始化一个重传,这种重传就叫做虚假重传(Spurious retransmission).发生虚假重传的原因可能是包传输中重排序.传输中发 ...

  5. TCP系列18—重传—8、FACK及SACK reneging下的重传

    一.介绍 FACK的全称是forward acknowledgement,FACK通过记录SACK块中系列号最大(forward-most)的SACK块来推测丢包信息,在linux中使用fackets ...

  6. TCP系列25—重传—15、DSACK虚假重传探测

    一.DSACK介绍 RFC2883通过指定使用SACK来指示接收端的重复包(duplicate packet)扩展了RFC2018对SACK选项的定义(SACK选项的介绍和示例参考前面内容).RFC2 ...

  7. TCP系列23—重传—13、RACK重传

    一.RACK概述 RACK(Recent ACKnowledgment)是一种新的基于时间的丢包探测算法,RACK的目的是取代传统的基于dupthresh门限的各种快速重传及其变种.前面介绍的各种基于 ...

  8. TCP系列20—重传—10、早期重传(ER)

    一.介绍 在前面介绍thin stream时候我们介绍过有两种场景下可能不会产生足够的dup ACK来触发快速重传,一种是游戏类响应交互式tcp传输,另外一种是传输受到拥塞控制的限制,只能发送少量TC ...

  9. TCP系列17—重传—7、SACK下的重传

    我们之前介绍SACK选项的时候说过,SACK可以把接收端系列号空间的洞反映给发送端,因此发送端可以更充分的理解接收端的情况,而进行更好的重传恢复过程.这种过程有时候也叫做advanced loss r ...

随机推荐

  1. 史上更全的 MySQL 高性能优化实战总结!

    1 前言 2 优化的哲学 3 优化思路 3.1 优化什么 3.2 优化的范围有哪些 3.3 优化维度 4 优化工具有啥? 4.1 数据库层面 4.2 数据库层面问题解决思路 4.3 系统层面 4.4 ...

  2. python3.X 安装web.py 失败的解决方法

    python2.x 安装python是非常顺利的 但是 在进行 pip3 install web.py 时提示很多错误 例如缺少模块 语法错误...... 最后试了一下web.py 的dev版本 pi ...

  3. 将图片绘制到画布上:imagecopy()

    <?php //1. 绘制图像资源(创建一个画布) $image = imagecreatetruecolor(500, 300); //2. 先分配一个绿色 $green = imagecol ...

  4. python学习笔记二:if语句及循环语句,断点,模块,pyc

    if语句 注意:语句块中的内容要强制缩进,否则出错.IndentationError,缩进错误 所有代码,如果是顶级的,必须顶格写,前面不能有空格 if … : … elif … : … else: ...

  5. go基础语法-条件语句

    1.if else 语句 if语句后面的条件不需要括号 if n > 0 { return 1 }else { return -1 } 'if'之后,条件判断之前,可以初始化变量(作用域为整个i ...

  6. mysql自动提交

    MySQL的autocommit(自动提交)默认是开启,其对mysql的性能有一定影响,举个例子来说,如果你插入了1000条数据,mysql会commit1000次的,如果我们把autocommit关 ...

  7. R语言爬虫:Rvest包函数介绍(表格)

    Rvest 包中常用函数一览: 函数 作用 read_html() 读取 html 页面 html_nodes() 提取所有符合条件的节点 html_node() 返回一个变量长度相等的list,相当 ...

  8. linux下Intellij Idea 14的安装

    一.安装配置jdk                                                         虽然很多Linux发行版现在已经自带OpenJDK,但是在开发过程中 ...

  9. 【转】odoo 10的企业微信发送程序介绍

    本文介绍的微信发送程序不是独立的模块,是某企业应用的一部分, 源码可在京津冀odoo技术交流群的群共享中下载.   [1]基本配置 在work.weixin.qq.com上注册一个企业后,会得到企业的 ...

  10. JDK核心源码(2)

    Java的基础知识有很多,但是我认为最基础的知识应该要属jdk的基础代码, jdk的基础代码里面,有分了很多基础模块,其中又属jdk包下面的lang包最为基础. 我们下面将总结和分析一下lang包下面 ...