You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用poll()的多端口监听UDP服务器仅能接收单端口报文求助

问题诱因分析

以下是导致你仅能监听单个端口及其他潜在异常的所有核心原因:

  • 核心错误:poll系统调用参数错误
    你代码中的pfd是动态申请的堆内存指针,sizeof(pfd)获取的是指针本身的大小(32位系统为4字节,64位系统为8字节),而非数组总长度,因此sizeof(pfd) / sizeof(pfd[0])的计算结果恒为1(64位下struct pollfd大小为8字节,刚好8/8=1),导致poll仅监听第一个文件描述符,也就是第一个绑定的端口,这是你只能监听单个端口的直接原因。
    正确写法应该将poll的第二个参数替换为提前计算好的端口总数AmountOfPorts:
int ev_cnt = poll(pfd, AmountOfPorts, 100000);
  • 未定义变量错误
    recvfrom的返回值没有赋值给rcv变量,代码中直接判断if (rcv > 0),rcv属于未初始化的野变量,会导致接收逻辑判断异常。正确写法:
ssize_t rcv = recvfrom(s[i], buffer, sizeof(buffer), 0, (struct sockaddr *)(&addr[i]), &addrlen);
  • POLLOUT事件处理逻辑错误
  1. 初始注册POLLIN | POLLOUT事件不合理:UDP套接字只要发送缓冲区有空余就会一直触发POLLOUT事件,会导致poll立刻返回,CPU占用率100%,仅当有待发送数据时才需要注册POLLOUT事件,发送完成后取消注册即可。
  2. POLLOUT的判断逻辑被包裹在POLLIN的判断分支内,只有当前套接字有读事件时才会处理写事件,逻辑完全错误,应该将POLLOUT的判断和POLLIN的判断平级。
  3. POLLOUT处理逻辑中取客户端IP时使用了*addr,没有指定下标i,会一直取第一个端口的地址结构体内容,逻辑错误。
  • 客户端链表逻辑错误
    search函数新增节点时没有正确修改头指针,当head初始为NULL时,新增的客户端节点无法挂载到全局链表上,链表功能完全失效。
  • 其他潜在问题
    UDP是无连接协议,POLLHUP事件对UDP套接字无意义,不需要处理;非阻塞模式下的recvfrom和sendto需要处理EAGAIN/EWOULDBLOCK错误,避免异常退出。

内容的提问来源于stack exchange,提问作者Ilya

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 13:15:00