3

我在用 Python 编写 TCP 服务器时注意到,当一端或另一端意外停止时,在不同的条件下会发生一些错误。

例如,有时我得到“管道损坏”(errno.EPIPE),有时是“连接中止”(errno.CONNABORTEDerrno.WSAECONNABORTED)。还有一个问题是跨操作系统的代码是不一样的,但我猜 Python 的errno模块可以处理这个问题。

我搜索了很多套接字连接错误代码含义的列表,但没有找到我要查找的内容。

到目前为止,我所拥有的是:

try:
    # write or read operation
except socket.error as e:
    if e.errno in (errno.EPIPE, errno.ECONNABORTED, errno.WSAECONNABORTED):
         print 'Connection lost with server...'

到现在为止,一切都很顺利,甚至在添加最后一个之前,我在Windows上遇到了问题,并添加了它,所以我担心可能有一些我没有处理的情况。此外,有时,它只是没有抛出错误并继续读取空行(带有recv)和错误的文件描述符等。

SocketServer类提供这样的东西吗?还是一般的 TCP 连接?

4

2 回答 2

1

当您尝试从 python 中的关闭套接字读取时,通常不会引发异常。您应该只阅读直到recv返回空字符串。

写入关闭的套接字当然会引发一个 Execption ( socket.error),它包含操作系统引发的错误号。

但是你不应该太关心错误代码。Python 不是 C,或者正如教程在谈论非阻塞套接字时所说的那样:

您可以检查返回码和错误码,通常会让自己发疯。如果你不相信我,有时间试试。你的应用程序会变得很大、有问题并且会占用 CPU。所以让我们跳过脑死亡的解决方案,把它做好。

...

于 2012-11-10T22:26:53.977 回答
1

Python 套接字模块主要是围绕 BSD 套接字 API 的精简包装器。通常,您可以通过查看 C BSD 套接字 API 的手册页找到可能的错误代码(errno 值)的文档。例如man 2 recv

ERRORS
   These are some standard errors generated by the socket layer.  Additional errors
   may be generated and returned from the underlying protocol modules; see their
   manual pages.

   EAGAIN or EWOULDBLOCK
          The  socket  is  marked  nonblocking  and  the receive operation would
          block, or a receive timeout had been set and the timeout expired before
          data was received.  POSIX.1-2001 allows either error to be returned for
          this case, and does not require these constants to have the same value,
          so a portable application should check for both possibilities.

   EBADF  The argument sockfd is an invalid descriptor.

   ECONNREFUSED
          A remote host refused to allow the network connection (typically because
          it is not running the requested service).

   EFAULT The receive buffer pointer(s) point outside the process's address space.

   EINTR  The receive was interrupted by delivery of a signal before any data were
          available; see signal(7).

   EINVAL Invalid argument passed.

   ENOMEM Could not allocate memory for recvmsg().

   ENOTCONN
          The socket is associated with a connection-oriented protocol and has not
          been connected (see connect(2) and accept(2)).

   ENOTSOCK
          The argument sockfd does not refer to a socket.

手动页面本身通常不完整,但它们涵盖的案例比任何 Python 文档都多。

于 2012-11-18T13:20:12.860 回答