持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第33天,点击查看活动详情
大家好,我是bug郭,一名双非科班的在校大学生。对C/JAVA、数据结构、Spring系列框架、Linux及MySql、算法等领域感兴趣,喜欢将所学知识写成博客记录下来。 希望该文章对你有所帮助!如果有错误请大佬们指正!共同学习交流
作者简介:
- CSDN java领域新星创作者blog.csdn.net/bug..
- 掘金LV3用户 juejin.cn/user/bug..
- 阿里云社区专家博主,星级博主,developer.aliyun.com/bug..
- 华为云云享专家 bbs.huaweicloud.com/bug..
滑动窗口
上述的机制都是针对TCP的可靠的传输设计的!
而在可靠传输的基础上还要保证传输效率!
滑动窗口机制就是提高TCP网络协议的传输效率!
我们可以看到,如果
TCP每次传输一次数据就要等待一个ACK确认序号后再进行传输数据,显然这样每次等待ACK这就使得TCP的传输效率很慢,而滑动窗口就解决了这个问题!
我们可以一次发送多组数据,每组数据都会有一个
ACK我们同一发送完一组数据后,再一次等待ACK保证传输的可靠性同时又保证了传输效率!
- 这里的一组数据的数据条数就是窗口大小,在窗口大小的范围内,我们无效等待
ACK可以继续发送数据! - 滑动,就是我们接收到
ACK后,我们的窗口位置就可以往后滑动,又可以进行数据发送!
这张图就很好的诠释了滑动窗口!
这里一组数据有4条数据,就是窗口大小为4!
当我们已经接收到了
ACK2001时,我们就知道1001-200数据已经发送成功,窗口向下滑动!
一起发这么多ACK,如果出现丢包问题,该如何解决呢?
-
ACK包丢失,数据到达!
这种情况,我们并不需要处理,就如上图,虽然ACK1001丢失了,但是后面的2001接收到了,我们知道,接收到了ACK2001说明前2000个字节数据传输成功,也就是ACK2001涵盖了ACK1001的功能!后面的4001丢失也是如此,我们已经接收到了5001,就保证了1-4000数据已经发送成功!
-
数据丢失
数据丢失,就需要进行处理,可以看到当
1001-2000数据丢失后,虽然这一组数据的发送并没有结束,但是每次的ACK1001确认序号都是一样的,服务器向客户端索要1001-2000数据,在进行这一组数据的发送后,客户端会将数据重发! 我们知道主机B会将数据保存到接收缓冲区,在没有接收到1001-2000的数据,接收缓冲区会留有一块空间!直到接收到
1001-2000的数据将其补上! 这种机制叫做高数重发机制(也叫快重传)
流量控制
流量控制是在滑动窗口机制上对其补充!保证了传输的可靠性! 我们了解到在主机A和主机B进行通信时,主机A的数据先保存到主机B操作系统中的接收缓冲区当中! 我们又说过,接收缓冲区是一个阻塞队列,那么当主机A的传输数据过快时,那么数据就会在主机B中的接收缓冲区阻塞,如果主机A继续发送数据就会导致丢包问题!
因此TCP根据接收方的处理能力,来决定发送速度,这个机制就叫做流量控制! TCP如何得知接收方的处理能力呢?
- 接收方通过将接收缓冲区剩余空间大小放在
TCP报文中的16位窗口大小中,然后通过ACK报文告知发送方! - 窗口大小越大说明,接收方的处理能力越强!
- 当接收缓冲区将要满时,发送方会减小发送速率,避免产生丢包!
- 如果接收缓冲区满了,那接收方就会回将0保存在16位窗口中!发送方收到ACK后就会停止数据传输,会过会时间定期发送一个窗口探测报文,接收方会将窗口大小返回给发送方!
我们知道16位窗口大小只能保存最大数据为65535字节,那么一个TCP数据报超过65535字节呢?
我们TCP报文中还有一个40字节的选项,这里面包含了一个窗口扩大因子M,实际的窗口大小可以是16位窗口大小+M左移因子!