unix网络编程3.2——UDP(二)UDP可靠性传输1——KCP协议(上)

系列文章

阅读本文需要先阅读下面的文章:

unix网络编程1.1——TCP协议详解(一)

unix网络编程2.1——高并发服务器(一)基础——io与文件描述符、socket编程与单进程服务端客户端实现

unix网络编程2.2——高并发服务器(二)多进程与多线程实现

unix网络编程2.3——高并发服务器(三)多路IO复用之select

unix网络编程2.4——高并发服务器(四)epoll基础篇

unix网络编程2.5——高并发服务器(五)epoll进阶篇——基于epoll实现reactor

unix网络编程2.6——高并发服务器(六)基于epoll&&reactor实现http服务器

unix网络编程2.7——高并发服务器(七)基于epoll&&reactor实现web_socket服务器

unix网络编程2.8——高并发服务器(八)unix网络编程系统调用与网络协议栈

unix网络编程3.1——UDP(一)UDP入门

如何做到可靠性传输

  • ACK机制
  • 重传机制 重传策略
  • 序号机制 3 2 1 -> 2 3 1
  • 重排机制 2 3 1 -> 3 2 1
  • 窗口机制

UDP与TCP如何选择

特点比较

image

协议头比较

image

ARQ协议

  • TCP之所以能够保证传输可靠(正常 + 有序),是基于ARQ协议(Automatic Repeat-request),即自动重传请求实现的
  • ARQ协议是传输层的错误纠正协议之一,它通过使用确认和超时两个机制,在不可靠的网络上实现可靠的信息传输
  • ARQ协议主要有3种模式:
  1. 停等式(stop-and-wait)
  2. 回退n帧 (go-back-n)
  3. 选择性重传 (selective repeat)

ARQ协议——停等式(stop-and-wait)

  • 停等协议的工作原理如下:
  1. 发送方对接收方发送数据包,然后等待接收方回复 ACK 并且开始计时。
  2. 在等待过程中,发送方停止发送新的数据包。
  3. 当数据包没有成功被接收方接收,接收方不会发送 ACK. 这样发送方在等待一定时间后,重新发送数据包。
  4. 反复以上步骤直到收到从接收方发送的 ACK.
    image
  • 缺点:较长的等待时间导致低的数据传输速度

ARQ——回退n帧 (go back n)

  • 为了克服停等协议长时间等待ACK的缺陷,连续ARQ协议会连续发送一组数据包,然后再等待这些数据包的ACK 。
  • 什么是滑动窗口
  • 发送方和接收方都会维护一个数据帧的序列,这个序列被称作窗口。 发送方的窗口大小由接收方确定 ,目的在于控制发送速度,以免接收方的缓存不够大,而导致溢出,同时控制流量也可以避免网络拥塞。协议中规定,对于窗口内未经确认的分组需要重传。
  • 回退N步 (Go Back N, GBN):回退 N 步协议允许发送方在等待超时的间歇 可以继续发送分组。 所有发送的分组 都带有序号。 在GBN协议中,发送方需响应以下三种事件:
  1. 上层的调用。 上层调用相应 send() 时 发送方首先要检查发送窗口是否已满;
  2. 接收ACK。 在该协议中对序号为 n 的分组的确认采取累积确认的方式 表明接收方已正确接收到序号 n 以前 包括 n) 的所有分组;
  3. 超时。 若出现超时, 发送方将重传所有已发出但还未被确认的分组;
  • 对于接收方来说,若一个序号为n 的分组被正确接收,并且按序,则接收方会为该分组返回一个 ACK 给发送方,并将该分组中的数据交付给上层。在其他情况下,接收方都会丢弃分组。若分组 n 已接收并交付,那么所有序号比 n 小的分组也已完成了交付。因此 GBN 采用累积确认是一个很自然的选择。(当出现异常时)发送方在发完一个窗口里的所有分组后,会检查最大的有效确认,然后从最大有效确认的后一个分组开始重传。
    image
  • 如上图所示,序号为 2 的分组丢失 因此分组 2 及之后的分组都将被重传
  • 总结:GBN 采用的技术包括序号、累积确认、检验和以及计时/重传 。

ARQ协议——选择重传 (Selective repeat)

  • 虽然GBN 改善了停等协议中时间等待较长的缺陷,但它依旧存在着性能问题。 特别是当窗口长度很大的时候 会使效率大大降低 。 而 SR 协议通过让发送方仅重传在接收方丢失或损坏了的分组,从而避免了不必要的重传,提高了效率。在SR协议下,发送方需响应以下三种事件:
  1. 从上层收到数据。当从上层收到数据后 发送方需检查下一个可用于该分组的序号。若序号在窗口中则将数据发送。
  2. 接收ACK。若收到 ACK 且该分组在窗口内 则发送方将那个被确认的分组标记为已接收。若该分组序号等于基序号 则窗口序号向前移动到具有最小序号的未确认分组处。若窗口移动后并且有序号落在窗口内的未发送分组 则发送这些分组。
  3. 超时。若出现超时,发送方将重传已发出但还未确认的分组。与GBN不同的是SR协议中的每个分组都有独立的计时器。
  • 在SR 协议下 接收方需响应以下三种事件:(假设接收窗口的基序号为4,分组长度也为4)
  1. 序号在[4, 7]内的分组被正确接收。该情况下收到的分组落在接收方的窗口内,一个ACK将发送给发送方。若该分组是以前没收到的分组,则被缓存。若该分组的序号等于基序号4,则该分组以及以前缓存的序号连续的分组都交付给上层,然后接收窗口将向前移动。
  2. 序号在[0, 3]内的分组被正确接收。在该情况下,必须产生一个ACK,尽管该分组是接收方以前已确认过的分组。若接收方不确认该分组,发送方窗口将不能向前移动。
  3. 其他情况。 忽略该分组对于接收方来说若一个分组正确接收而不管其是否按序, 则接收方会为该分组返回一个ACK给发送方。失序的分组将被缓存, 直到所有丢失的分组都被收到, 这时才可以将一批分组按序交付给上层。
    image

RTT 和 RTO

  • RTO(Retransmission TimeOut) 即重传超时时间
  • RTT(Round Trip Time): 往返时延。表示从发送端发送数据开始,到发送端收到来自接收端的确(接收端收到数据后便立即发送确认) 总共经历的时延 。
  • 参考
  • 在TCP的选项内容可以插入时间戳

流量控制

  • 双方在通信的时候,发送方的速率与接收方的速率是不一定相等,如果发送方的发送速率太快,会导致接收方处理不过来,这时候接收方只能把处理不过来的数据存在缓存区里,失序的数据包也会被存放在缓存区里 。
  • 如果缓存区满了发送方还在疯狂着发送数据,接收方只能把收到的数据包丢掉,大量的丢包会极大着浪费网络资源。因此我们需要控制发送方的发送速率,让接收方与发送方处于一种动态平衡才好。
  • 对发送方发送速率的控制, 称之为流量控制。

如何进行流量控制

  • 接收方每次收到数据包可以在发送确定报文的时候,同时告诉发送方自己的缓存区还剩余多少是空闲的,我们也把缓存区的剩余大小称之为接收窗口大小 用变量 win 来表示接收窗口的大小。
  • 发送方收到之后便会调整自己的发送速率,也就是调整自己发送窗口的大小,当发送方收到接收窗口的大小为0时,发送方就会停止发送数据(窗口关闭),防止出现大量丢包情况的发生
    image

发送方何时再继续发送数据?

  • 当发送方停止发送数据后,该怎样才能知道自己可以继续发送数据
  1. 当接收方处理好数据,接收窗口win > 0 时, 接收方发个通知报文去通知发送方,告诉他可以继续发送数据了。当发送方收到窗口大于0的报文时,就继续发送数据。
  2. 当发送方收到接受窗口win = 0 时,这时发送方停止发送报文,并且同时开启一个定时器,每隔一段时间就发个测试报文去询问接收方(窗口探测),打听是否可以继续发送数据了,如果可以,接收方就告诉他此时接受窗口的大小;如果接受窗口大小还是为0,则发送方再次刷新启动定时器。
    image

拥塞控制

  • 拥塞控制和流量控制虽然采取的动作很相似,但拥塞控制与网络的拥堵情况相关联, 而流量控制与接收方的缓存状态相关联
  • 拥塞控制常见流程:慢启动(慢开始) -> 拥塞避免 -> 拥塞发生 -> 快速恢复
    image
    image
  • 参考

总结

  • 本文注意学习了ARQ协议相关的内容,这些内容主要应用于TCP协议中,进而帮助TCP实现可靠的传输,而UDP不具备这样的功能,因此需要我们先学习这些ARQ协议,进而在UDP中设计出可靠的传输协议,下文我们一起学习。
posted @ 2023-01-01 22:17  胖白白  阅读(156)  评论(0编辑  收藏  举报