◼ ACK机制 (用来确认对方到底有没有收到)
◼ 重传机制 (在协议栈不会重传)
◼ 序号机制 3 2 1 -》2 3 1 (先发的包不一定最先到达)
◼ 重排机制 2 3 1 ->3 2 1 (将收到的包进行重组)
◼ 窗口机制
Tcp不用我们管
可靠性udp 5种机制都需要用户层处理
udp场景
1)实时性要求: 音视频的通话 、 游戏(王者荣耀) 。
2)节省资源的要求: 嵌入式设备(电池供电) , 手机状态报告 、户外设备
UDP与TCP,我们如何选择
UDP在传输的时候buffer一定要小于MTU。MT大小标准是1500
sendto(user data) 运营商头 + userdata + udp头(8字节) + IP头(20字节) = 1500-8-20=1472 sento一般来讲最大1400字节
UDP如何可靠,KCP协议在哪些方面有优势
RTO(超时重传时间)
KCP精讲-名词说明
用户数据:应用层发送的数据,如一张图片2Kb的数据
MTU:最大传输单元。即每次发送的最大数据
RTO:Retransmission TimeOut,重传超时时间。
cwnd:congestion window,拥塞窗口,表示发送方可发送多少个KCP数据包。 与接收方窗口有关,与网络状况(拥塞控制)有关,与发送窗口大小有关。
rwnd:receiver window,接收方窗口大小,表示接收方还可接收多少个KCP数据包
snd_queue:待发送KCP数据包队列
snd_nxt:下一个即将发送的kcp数据包序列号
snd_una:下一个待确认的序列号
kcp使用方式
1. 创建 KCP对象:ikcpcb *kcp = ikcp_create(conv, user);
2. 设置传输回调函数(如UDP的send函数):kcp->output = udp_output; 1. 真正发送数据需要调用sendto
3. 循环调用 update:ikcp_update(kcp, millisec);
4. 输入一个应用层数据包(如UDP收到的数据包): ikcp_input(kcp,received_udp_packet,received_udp_size); 1. 我们要使用recvfrom接收,然后扔到kcp里面做解析
5. 发送数据:ikcp_send(kcp1, buffer, 8); 用户层接口
6. 接收数据:hr = ikcp_recv(kcp2, buffer, 10);
kcp源码流程图
kcp配置模式
1. 工作模式:int ikcp_nodelay(ikcpcb *kcp, int nodelay, int interval, int resend, int nc) nodelay :是否启用 nodelay模式,0不启用;1启用。 interval :协议内部工作的 interval,单位毫秒,比如 10ms或者 20ms resend :快速重传模式,默认0关闭,可以设置2(2次ACK跨越将会直接重传) nc :是否关闭流控,默认是0代表不关闭,1代表关闭。 普通模式: ikcp_nodelay(kcp, 0, 40, 0, 0); 极速模式: ikcp_nodelay(kcp, 1, 10, 2, 1) 2. 最大窗口:int ikcp_wndsize(ikcpcb *kcp, int sndwnd, int rcvwnd); 该调用将会设置协议的最大发送窗口和最大接收窗口大小,默认为32,单位为包。
3. 最大传输单元:int ikcp_setmtu(ikcpcb *kcp, int mtu); kcp协议并不负责探测 MTU,默认 mtu是1400字节
4. 最小RTO:不管是 TCP还是 KCP计算 RTO时都有最小 RTO的限制,即便计算出来RTO为 40ms,由于默认的 RTO是100ms,协议只有在100ms后才能检测到丢包,快速模式下为 30ms,可以手动更改该值: kcp->rx_minrto = 10;
kcp协议头
conv:连接号。UDP是无连接的,conv用于表示来自于哪个 客户端。对连接的一种替代
cmd:命令字。如,IKCP_CMD_ACK确认命令, IKCP_CMD_WASK接收窗口大小询问命令, IKCP_CMD_WINS接收窗口大小告知命令,
frg:分片,用户数据可能会被分成多个KCP包,发送出去
wnd:接收窗口大小,发送方的发送窗口不能超过接收方 给出的数值
ts:时间序列
sn:序列号
una:下一个可接收的序列号。其实就是确认号,收到 sn=10的包,una为11
len:数据长度
data:用户数据
kcp发送数据过程
kcp接收数据过程