https://blog.csdn.net/q1007729991/article/details/70142341

相信大家都遇到过这样的场景:

同学 Luffy 给你打电话,让你记下一串手机号码,可是你记忆力不太好,你跟 Luffy 约定,一次只最多只能报 4 个数字,Luffy 念一遍,如果你听到了就把他说的话重复一遍。接下来:

  • 你:你一次最多报 4 个数字,多了我记不住啊!
  • Luffy:139
  • 你:139 (Luffy 知道你听到了)
  • Luffy:7548
  • 你:7538 (很明显你听错了)
  • Luffy:不对,是7548
  • 你:7548
  • Luffy : 2669
  • 你:2669

最后,你接收到的完整的号码就是 139-7548-2669.

1. 滑动窗口

上面的场景,你一次最多只能接受 4 个数字,表示你的滑动窗口大小就是 4. 在 TCP 协议中,也有这样的滑动窗口,它的大小表示目前还能接收多少字节的数据。

TCP 每次收到对方发来的报文,都会检查窗口大小字段,见图 1.

 
图1 TCP 首部中有一个字段——16 位窗口大小

知道了对方的窗口大小后,就知道对方目前还能接收多少数据,接收的数据字节序号是 TCP 段中的 ACK 的值到 ACK + 窗口大小,即 [ACK,ACK+窗口大小)[ACK,ACK+窗口大小).

比如,你给对方发送了一个段携带字节序号为 [400, 500) 的数据。对方回送了一个 TCP 段,ack = 500, win = 100,就表示,我已经收到 [400, 500) 的数据我还能接收字节序号为 [500, 600) 之间的数据,见图 2。

 
图2 滑动窗口

如果对方回送了一个 TCP 段,ack = 500, win = 0,就表示,我已经收到了 [400, 500) 的数据,但是我现在不能再接收数据了,你待会再发。

 
图3 对方回送 0 大小的窗口,接收端的反应

2. 滑动窗口的目的

回顾本文开头给出的打电话的例子,为什么你要告诉对方一次最多只能报 4 个数字?原因在于你的接受能力有限,不是说你无法记忆很多数字,只是在短期内,你记不住,你需要一段一段的记忆(一段一段的将数据放入缓冲区)。

所以,在 TCP 中,滑动窗口是为了实现流量控制。如果对方发送数据过快,接收方就来不及接收(你来不急记住),接收方就需要通告对方,减慢数据的发送(图 3)。

需要特别注意的是,在学习滑动窗口的时候,我们假设网络无限好,不拥塞。只要你发送了数据,对方一定可以收到。

再解释一下网络拥塞的含义,它是指你发送的数据滞留在网络中,迟迟未到达接收方。

3. 滑动窗口模拟

 
图4 滑动窗口模拟

修正:图4 中最后一个小图修正一下文字,应该为『发送方收到 ack=41, win=10, 知道对方希望接收序号为 [41, 51) 的数据』

  • 发送方接收到了对方发来的报文 ack = 33, win = 10,知道对方收到了 33 号前的数据,现在期望接收 [33, 43) 号数据。发送方连续发送了 4 个报文段假设为 A, B, C, D, 分别携带 [33, 35), [35, 36), [36, 38), [38, 41) 号数据。
  • 接收方接收到了报文段 A, C,但是没收到 B 和 D,也就是只收到了 [33, 35) 和 [36, 38) 号数据。接收方发送回对报文段 A 的确认:ack = 35, win = 10。
  • 发送方收到了 ack = 35, win = 10,对方期望接收 [35, 45) 号数据。接着发送了一个报文段 E,它携带了 [41, 44) 号数据。
  • 接收方接收到了报文段 B: [35, 36), D:[38, 41),接收方发送对 D 的确认:ack = 41, win = 10. (这是一个累积确认)
  • 发送方收到了 ack = 41, win = 10,对方期望接收 [41, 51) 号数据。
  • ……

需要注意的是,接收方接收 tcp 报文的顺序是不确定的,并非是一定先收到 35 再收到 36,也可能是先收到 36,37,再收到 35.

4. 总结

  • 理解滑动窗口的工作过程
  • 滑动窗口的目的是什么?

下一篇文章,我们得抓个包来分析一下。

【转】20-TCP 协议(滑动窗口——基础)的更多相关文章

  1. TCP协议滑动窗口(一)——控制数据传输速率

    窗口大小:TCP头中一个16位的域,表示当前可用接受缓冲区大小.在每个TCP对等段连接初始化时,告诉对方自己的窗口大小(不一定是满额,假如满额65201字节,可能暂时通告5840字节).若客户端接受数 ...

  2. TCP协议滑动窗口(一)——控制大批量数据传输速率

    窗口大小:TCP头中一个16位的域,表示当前可用接受缓冲区大小.在每个TCP对等段连接初始化时,告诉对方自己的窗口大小(不一定是满额,假如满额65201字节,可能暂时通告5840字节).若客户端接受数 ...

  3. tcp协议头窗口,滑动窗口,流控制,拥塞控制关系

    参考文章 TCP 的那些事儿(下) http://coolshell.cn/articles/11609.html tcp/ip详解--拥塞控制 & 慢启动 快恢复 拥塞避免 http://b ...

  4. 面试连环炮系列(二十):TCP的滑动窗口协议是什么

    TCP的滑动窗口协议是什么 滑动窗口协议,用于网络数据传输时的流量控制,以避免拥塞的发生.该协议允许发送方在停止并等待确认前发送多个数据分组.由于发送方不必每发一个分组就停下来等待确认,因此该协议可以 ...

  5. TCP的滑动窗口机制【转】

    原文链接:http://www.cnblogs.com/luoquan/p/4886345.html      TCP这个协议是网络中使用的比较广泛,他是一个面向连接的可靠的传输协议.既然是一个可靠的 ...

  6. 计算机网络(八),TCP的滑动窗口

    目录 1.RTT和RTO 2.TCP使用滑动窗口做流量控制与乱序重排 3.滑动窗口的基本原理 八.TCP的滑动窗口 TCP头部中的窗口字段:滑动窗口大小,用来告知发送端接受端的缓存大小,以此控制发送端 ...

  7. TCP协议总结--停止等待协议,连续ARQ协议,滑动窗口协议

    前言:在学习tcp三次握手的过程之中,由于一直无法解释tcpdump命令抓的包中seq和ack的含义,就将tcp协议往深入的了解了一下,了解到了几个协议,做一个小结. 先来看看我的问题: 这是用tcp ...

  8. 一篇带你读懂TCP之“滑动窗口”协议

    前言 你现在的努力,是为了以后有更多的选择. 在上一篇文章通过"表白"方式,让我们快速了解网络七层协议了解了网络七层协议. 接下来我们要把重心放在网络传输的可靠性上面.一起来看TC ...

  9. TCP通过滑动窗口和拥塞窗口实现限流,能抵御ddos攻击吗

    tcp可以通过滑动窗口和拥塞算法实现流量控制,限制上行和下行的流量,但是却不能抵御ddos攻击. 限流只是限制访问流量的大小,是无法区分正常流量和异常攻击流量的. 限流可以控制本软件或者应用的流量大小 ...

随机推荐

  1. JavaScript Dom 事件

    JavaScript  Dom 事件 对于事件需要注意的要点: // this标签当前正在操作的标签. this // event封装了当前事件的内容. even 常用事件 // 鼠标单击.触发事件 ...

  2. vue_elementUI_ tree树形控件 获取选中的父节点ID

    el-tree 的 this.$refs.tree.getCheckedKeys() 只可以获取选中的id 无法获取选中的父节点ID想要获取选中父节点的id;需要如下操作1. 找到工程下的node_m ...

  3. Python3 tkinter基础 Menubutton 点击按钮出现下拉菜单

             Python : 3.7.0          OS : Ubuntu 18.04.1 LTS         IDE : PyCharm 2018.2.4       Conda ...

  4. react中使用antd遇到的问题

    1.less使用报错 less配置修改一般都是1个修改1个增加 test: /\.(css|less)$/, // 修改 // 增加 { loader: require.resolve('less-l ...

  5. CSS基础学习(一) 之 line-height 与 height 属性区别

    官方定义: height:定义了了元素的高度.默认情况下,该属性订了 content area(内容区域) 的高度.如果box-sizing属性设置为 border-box,那么height就表示bo ...

  6. MySQL简单查询语句练习

    数据查询语法(DQL) DQL就是数据查询语言,数据库执行DQL语句不会对数据进行改变,而是让数据库发送结果集给客户端. 语法: SELECT selection_list /*要查询的列名称*/ F ...

  7. [python]python2与python3版本的区别

    python2和python3的区别 区别: print函数 整数相除 Unicode 异常处理 xrange map函数 不支持has_key print函数: Python 2: print是语句 ...

  8. LeetCode--023--合并K个排序链表

    合并 k 个排序链表,返回合并后的排序链表.请分析和描述算法的复杂度. 示例: 输入: [   1->4->5,   1->3->4,   2->6 ] 输出: 1-&g ...

  9. MySql 8.0 版本使用navicat连不上解决

    先通过命令行进入mysql的root账户: 更改加密方式 ALTER USER 'root'@'localhost' IDENTIFIED BY 'password' PASSWORD EXPIRE ...

  10. 【XAF问题】不能将值NULL插入列"Oid"

    一.问题 1. 不能将值NULL插入列"Oid" 二.解决方法 解决方法:删表,oid不能为空,继承的对象变了