UDP 套接字上的 recvfrom() 返回 -1 但 WSAGetLastError() 返回 0
Posted
技术标签:
【中文标题】UDP 套接字上的 recvfrom() 返回 -1 但 WSAGetLastError() 返回 0【英文标题】:recvfrom() on a UDP socket returns -1 but WSAGetLastError() returns 0 【发布时间】:2011-05-17 15:41:55 【问题描述】:我似乎无法弄清楚为什么会这样。我没有使用任何可能调用 WSAGetLastError() 的套接字库,因为我只在 Windows 平台上使用 C 套接字函数。我正在使用 select() 来管理多个 UDP 套接字,所以这可能与它有关。这是发生了什么:
我有许多 UDP 套接字,我使用 fd_set 注册并使用 select() 仅在读取操作可用时进行检查。我遍历所有套接字并检查 FD_ISSET() 以确保读取操作可用。然后我调用 recvfrom(),这似乎在大多数情况下都有效,但偶尔当其中一个套接字上有大量活动时,recvfrom() 将返回 -1。当我对 WSAGetLastError() 进行后续调用时,它返回 0(这是我整个应用程序中对 WSAGetLastError 的唯一调用)。如果我忽略该错误,套接字将继续正常运行。它仍然能够接收数据并做它的事情。这很奇怪。
我知道 UDP 套接字有可能返回 0(一个有效的空 UDP 数据包),而 TCP 不是这种情况(干净关闭),但 -1 也可能是正常的吗?我认为这可能是由某种并发问题引起的,其中一个线程可能正在套接字上执行 sendto() 而 recvfrom() 正在被调用,所以我添加了一个互斥锁以防止这种情况发生(但行为仍然存在)。
我对整个问题感到很困惑,所以任何建议或帮助将不胜感激。也许 select() 为实际上不是读取操作的读取操作添加了套接字?我很确定 TCP 会为侦听套接字上的连接请求执行此操作。
我在 Visual Studio 2010 中使用 C++ 作为我的编译器和 IDE。这是一个没有 MFC 或任何废话的控制台应用程序。
谢谢!
【问题讨论】:
【参考方案1】:嗯,-1 是SOCKET_ERROR
,所以不:-1 绝不是正常值。我唯一一次看到此错误是当您在 TCP 套接字上使用 accept
但然后在您调用 accept
的同一个套接字上调用 recv
时,而不是 accept
调用的返回值。你确定你失败的recvfrom
是在正确的套接字上调用的吗?
【讨论】:
哦。您使用的是 Windows 2000?以上是关于UDP 套接字上的 recvfrom() 返回 -1 但 WSAGetLastError() 返回 0的主要内容,如果未能解决你的问题,请参考以下文章
在 UDP 套接字上使用 sendto()/recvfrom() 而不是 connect()/send()/recv() 的目的是啥?