我试图打开已经打开的 UDP 端口并且 ACE_SOCK_Dgram::open() 失败。正如预期的那样,strace 显示 bind() 失败并且 errno 设置为 EADDRINUSE。
为了查看发生了什么错误,我使用了 ACE_OS::last_error(),但它没有更新。
我想向用户提供端口已在使用中的信息性错误,而不是一些一般性错误。
额外的问题 - 什么时候可以使用 ACE_OS::last_error()?
肿瘤坏死因子
我试图打开已经打开的 UDP 端口并且 ACE_SOCK_Dgram::open() 失败。正如预期的那样,strace 显示 bind() 失败并且 errno 设置为 EADDRINUSE。
为了查看发生了什么错误,我使用了 ACE_OS::last_error(),但它没有更新。
我想向用户提供端口已在使用中的信息性错误,而不是一些一般性错误。
额外的问题 - 什么时候可以使用 ACE_OS::last_error()?
肿瘤坏死因子
如果您提供更多详细信息,将会有所帮助。您在哪个平台上运行您的应用程序?您使用的是什么版本的 ACE 库?它是 1-1024 范围内的 UDP 端口吗?你使用广播UDP套接字吗?
假设由于您检查的是“errno”而不是 GetLastError(),因此您在 UNIX 风格(如 Linux)上运行。查看 OS_S_errno.inl,您可以找到描述不同操作系统之间行为差异的注释。
您不是在问为什么首先获得 EADDRINUSE 用于 UDP 套接字。你使用 SO_REUSEADDR 选项吗?如果你这样做,你应该知道只有绑定到套接字的最后一个进程会被通知,并且行为可能因操作系统而异。
是否有可能在 bind() 之后发出另一个系统函数调用?在这种情况下,bind() 返回的错误可能会被随后的系统调用重置。正如您从 last_error() 的实现中看到的,它只是在 Windows 上设置“errno = ::GetLastError()”,并在 UNIX 上直接返回 errno。
我发现了问题。我使用 ACE_OS::last_error() 来宏(是的,宏不好),它扩展到了几个链接。其中一行执行了系统调用,因此 errno 的值发生了变化
你有没有试过errno
在打开电话后检查自己?在我看来,如果errno == EADDRINUSE
你可以从那里随心所欲地处理它,而不需要 ACE 的帮助。