【问题标题】:What is SOCKET accept() error errno 316?什么是 SOCKET accept() 错误 errno 316?
【发布时间】:2015-05-15 10:54:01
【问题描述】:

在 OSX 上,在绑定和侦听套接字上调用 accept() 后,我不断收到 316 的套接字错误。 我得到了一个有效的套接字返回,我相信我可以很好地使用它,(虽然我可能不是,我需要仔细检查,因为我随时接受数百个连接)但 errno 已设置。

我试图了解 the documentation on the unix accept(2) man pages 的哪些注释(顺便说一下,apple's accept() documentation 中缺少这些注释)

Linux accept()(和 accept4())传递已经挂起的网络错误 在新套接字上作为来自 accept() 的错误代码。这种行为 不同于其他 BSD 套接字实现。可靠运行 应用程序应检测为 accept() 之后的协议,并通过重试将它们视为 EAGAIN。

现在,316 与 ETIMEDOUT(60) 的结果为 256 OR'd。所以,我很好奇我应该如何处理这个问题;

  1. 如果在accept() 之后设置了任何错误,我应该再次accept() 吗?
  2. 我应该 close() 接受 DID 返回的 SOCKET 吗?
  3. 是 unix errno 代码的 8 位? (我看到的所有代码都
  4. 这个错误是否意味着我刚刚从堆栈中弹出的连接超时...本身和操作系统断开了它们,或者我没有足够快地接受()?

【问题讨论】:

  • 这个“...如何在绑定和侦听套接字上调用accept() 后继续收到316 的套接字错误。我得到一个有效的套接字返回,”工作?如果accept() 返回了-1,您只想检查errno,而这又不是有效的套接字描述符。
  • 这是我最初的想法,但引用的文档说“在新套接字上传递已经挂起的网络错误”。这里的新插座意味着......我现有的插座?还是它生成的新套接字?
  • 不过,我在调用accept() 之前刚刚弹出了所有错误,而且我觉得这毕竟只是一个旧的错误代码,所以在其他一些调用之后我不会检查错误...
  • Hmhmja,Linux 手册页还继续列出检查 TCP/IP 的代码。所以我要做的(对于Linux)是在调用accpet()之前将errno设置为0,然后在accept()返回一个值>=0之后只测试errnoENETDOWN,@987654334 @、ENOPROTOOPTEHOSTDOWNENONETEHOSTUNREACHEOPNOTSUPPENETUNREACH,如所列。请注意,此行为记录在案。在 OSX 上不需要这样做。
  • OS X 网络基于 BSD,因此不会表现出 Linux 的怪异。在 OSX 上,ELAST 是最大的 errno,在 10.9 上是 106。正如@alk 所说,不要检查errno,除非accept() 返回-1。

标签: c linux macos sockets


【解决方案1】:

除非accept() 返回-1,否则不要检查errno。如果accept() 返回一个有效的文件描述符,那么errno 的值为undefined

【讨论】:

  • 我已经接受了这个作为答案。真正的解决方案是这个错误是由我的成功 socket() 创建(我在UDP 和TCP 中得到它)触发的,事实上我正在检查那个错误,而不是接受。至于奇怪的错误本身,那可能是一个单独的问题
  • meta:我应该像“不是一个真正的问题”那样“解决”这个问题吗?
  • 我不知道如何更明确地说:永远不要检查errno 除非最近的函数返回了一个指示发生实际错误!它没有任何意义,并且在最近的函数成功的任何情况下,它的值都是未定义的。
  • 啊,是的,抱歉,没有将该逻辑应用于socket() :) 假设 316 只是一些错误值,谢谢
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-06-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-04-20
相关资源
最近更新 更多