C语言UDP实现stop&wait停等协议 单客户端正常多客户端运行异常
问题根因
你当前的服务端是单客户端场景的逻辑,完全没有适配多客户端的状态管理,核心问题如下:
- 全局共用同一个
frame_id计数器:所有客户端的序列号都和这个全局变量匹配,第一个客户端发送sq_no=0的帧后,全局frame_id自增为1,第二个客户端首次发送sq_no=0的帧时自然匹配失败 - 匹配失败直接调用
break退出服务端循环:任意客户端发送不符合当前全局状态的帧都会直接导致整个服务端停止运行,这是多客户端场景直接失效的直接触发点 - 没有对客户端做身份区分:UDP是无连接协议,你需要通过
recvfrom返回的客户端地址(IP+端口)识别不同客户端,为每个客户端维护独立的序列号状态
修复方案
1. 新增客户端状态存储结构
在服务端代码中定义结构存储每个客户端的独立状态,示例如下:
#define MAX_CLIENTS 10 typedef struct { struct sockaddr_in addr; int frame_id; } ClientState; ClientState clients[MAX_CLIENTS]; int client_count = 0;
2. 调整客户端匹配逻辑
每次收到帧后,先遍历已存储的客户端列表,用返回的newAddr匹配对应的客户端:
- 如果是新客户端,就新增到列表,初始化其
frame_id为0 - 如果是已有客户端,就用该客户端专属的
frame_id做序列号校验
3. 移除错误的break逻辑
匹配失败不能直接退出服务端,应该只丢弃当前错误帧,或者给对应的客户端返回重传通知,不能中断整个服务的运行
4. 其他优化点
- 每次调用
recvfrom前需要重新赋值addr_size = sizeof(newAddr),否则部分系统下会出现地址读取错误 - 停等协议本身需要超时重传机制,你当前的客户端收到错误ACK就直接break退出,不符合停等协议的重传逻辑,建议调整为超时后重传上一个帧而不是直接退出
内容的提问来源于stack exchange,提问作者F.M
相关产品推荐
相关产品推荐

