UDP协议进阶

UDP协议

什么时候UDP比TCP通信更好?

1. UDP协议有更加好的通讯速度
2. 在一问一答的情况之下,包的次序无关 =>DNS
3. 在网络状况不好情况之下,短连接可能比长连接有更好的体验,一问一答式的小数据量通讯,正是 TCP 的弱项
我的思考:在UDP上实现一个带超时的请求回应机制,让业务层负责超时重发,可能比TCP效果更好,前提:单个请求或回应的包不应该过大,最好不要超过一个MTU,大概在互联网上500多字节,
在国内是最大不超过521个字节,在跨网(电信和联通)UDP是比TCP快120倍

一个可靠的UDP通讯模块的API接口应该怎样设计?

1. 在一定的情况之下,TCP的设计已经很复杂了,利用UDP来进行封装成可靠的协议,只能表现在部分方面的优势。其实有一个更加好的协议 SCTP
2. 建立一个可靠通讯协议,最主要解决的问题还是如果利用不可靠的数据传输,实现一个协议来达到可靠传输(保证次序不丢包)的问题。
`struct rudp_package 
{
    struct rudp_package *next;
    char *buffer; 
    int sz; 
}; 
    rudp_new 创建 rudp 对象时,有两个参数可配置。send delay 表示数据累积多少个时间周期 tick 数才打包在一起发送。expired time 表示已发送的包至少保留多少个时间周期。
    和 TCP 不同,我们既然使用 udp 通讯,就是希望高响应速度,所以即使数据抱迟迟没有送达,它们也不必保留太长时间,而只需要通知业务层异常即可。
struct rudp * rudp_new(int send_delay, int expired_time); 

void rudp_delete(struct rudp *); // return the size of new package, 0 where no new package // -1 corrupt connection 

    而业务层的数据收发只需要调用 rudp_send 和 rudp_recv 即可。其中,rudp_recv 保证数据包按次序输出;rudp_send 也并不真正发送这些数据包,
    而是堆积在 rudp 对象内,等待下一个时间片。
int rudp_recv(struct rudp *U, char buffer[MAX_PACKAGE]); // send a new package out 

// should call every frame with the time tick, or a new package is coming. 
// return the package should be send out. 
void rudp_send(struct rudp *U, const char *buffer, int sz); 
    这里提供了一个 rudp_update 的 api 要求业务层按时间周期调用,当然也可以在同一时间片内调用多次,用传入的参数 tick 做区分。如果 tick 为 0 表示是在同一时间片内,不用急着处理数据,
    当 tick 大于 0 时,才表示时间流逝,这时可以合并上个时间周期内的数据集中处理。 rudp_update 的每次调用均可以传入一个实际收到的 UDP 包(可以是一个完整的 UDP 包,也可以是一部分),
    这个包数据是一个黑盒子,业务层不必了解细节。它的编码依赖对端采用的相同的 rudp 模块。每次调用都有可能输出一系列需要发送出去的 UDP 包。这些数据包是由过去的 rudp_send 调用压入的数
    据产生的,同时也包含了最近接收到的数据包中发现的,对端可能需要重传的数据,以及在没有通讯数据时插入的心跳包等。总的来说,rudp_update 内部做了所有的可靠化通讯需要的数据组织工作。
    使用的人传入从 UDP socket 上收到的数据(不包括数据加密或其它数据组织工作),并从中获取需要发送到 UDP socekt 的数据。
struct rudp_package * rudp_update(struct rudp *U, const void * buffer, int sz, int tick);`

设计一个可靠的UDP

无非是在udp的模式上我们拿了2样东西回来。
1. 顺序,同时是流控方式:基于状态的代码模式决定的数据顺序。 tcp把数据确保数据序列的工作在网络传输时,层层 包包,顺序保证,用起来确实方便。但也消除了数据并发传输的可能。
这很大程度上直接形成了tcp的流控模式,从编程的形式上tcp无需流控,你不拿走对方就丢不出来。代码的顺序化,和收发的顺序在影响传输性能。但udp模式在这方面有本质的不同,数据传
送时没有前后这一说,你拿到的数据也是如此。交换机,网卡根本不考虑序列的要求,从传输上这很牛叉,但这种模式与Coding的顺序式思维不相符,偶尔有无状态的数据可以直接套用这个思
维,但对于具备时间和序列要求的场景,这就显得十分难用。因此大多情况下udp fake tcp必须要做数据序列重整。端对端的序列重建和步步紧等的局部重整,在整体行为上确实可以减少延迟。

2. 链路特性,更是流控方式。 一旦转入udp,链路的管理就从路由器的问题变成你的问题了。还要不要等ack,对方是否还在,我能发送多快这一系列的问题在你建立socket的第一个瞬间
    就变坑了。貌似少了connect的动作,但实际需要考虑的问题变得更多了起来,但此时你具备的信息也是路由器不具备的例如带宽,端对端延迟,实际的丢包率,如果这些都用来作为
    链路可靠性和流控的参数,你或许能'预测',发送速率,ack的时间,重发的速度。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值