KCP简介
KCP是一个快速可靠协议,纯算法实现,并不负责底层协议的收发,需要使用者自己定义下层数据包的发送方式,以callback的方式提供给KCP。
KCP存在的价值
TCP的可靠和无私让TCP开发变得简单,同时它的设计也导致了慢的特点。UDP简单,所以它更快,但是UDP是不可靠的,收到的数据可能是乱序、丢失的。KCP就是在保留UDP快的基础上,提供可靠的传输,应用层使用也更为简单。
KCP数据发送过程
KCP是一个可靠的传输协议,UDP本身是不可靠的,所以需要额外信息来保证传输数据的可靠性。因此,我们需要在传输的数据上增加一个包头。用于确保数据的可靠、有序。
步骤1:待发送队列移至发送队列
步骤2:发送发送队列的数据
发送队列中包含两种类型的数据,已发送但是尚未被接收方确认的数据,没被发送过的数据。没发送过的数据比较好处理,直接发送即可。重点在于已经发送了但是还没被接收方确认的数据,该部分的策略直接决定着协议快速、高效与否。KCP主要使用两种策略来决定是否需要重传KCP数据包,超时重传、快速重传、选择重传。
超时重传
TCP超时计算是RTOx2,这样连续丢三次包就变成RTOx8了,而KCP非快速模式下每次+RTO,急速模式下+0.5RTO(实验证明1.5这个值相对比较好),提高了传输速度。
快速重传
发送端发送了1,2,3,4,5几个包,然后收到远端的ACK: 1, 3, 4,
5,当收到ACK3时,KCP知道2被跳过1次,收到ACK4时,知道2被跳过了2次,此时可以认为2号丢失,不用等超时,直接重传2号包,大大改善了丢包时的传输速度。TCP有快速重传算法,TCP包被跳过3次之后会进行重传。
注:可以通过统计错误重传(重传的包实际没丢,仅乱序),优化该设置。
选择重传
老的TCP丢包时会全部重传从丢的那个包开始以后的数据,KCP是选择性重传,只重传真正丢失的数据包。但是,目前大部分的操作系统,linux与android手机均是支持SACK选择重传的。
步骤3:数据发送
把较小的kcp包进行合并,一次性发送提高效率。
KCP流量控制
KCP的发送机制采用TCP的滑动窗口方式,可以非常容易的控制流量。KCP的主要特色在于实时性高,对于实时性高的应用,如果发生数据堆积会造成延迟的持续增大。建议从应用侧更好的控制发送流量与网络速度持平,避免缓存堆积延迟。
KCP拥塞控制(可关闭)
KCP的优势在于可以完全关闭拥塞控制,非常自私的进行发送。KCP采用的拥塞控制策略为TCP最古老的策略,无任何优势。完全关闭拥塞控制,也不是一个最优策略,它全是会造成更为拥堵的情况。