如果POSIX socket "read" 函数returns 0,是否表示发生了错误?
If the POSIX socket "read" function returns 0, does that indicate an error occurred?
我正在使用遗留代码。此代码在套接字上调用“读取”。如果读取函数 return 为 0 或以下,调用函数将抛出错误。
n = read(sock, &buff[bytesRead], bytesToRead - bytesRead);
if (n <= 0) {
syslog(LOG_CRIT, "ReadFromSocket: read() failed, errno=%d\n", errno);
return FALSE;
}
但是,我注意到此函数抛出错误,其中“errno”= 0。
我很好奇我是否 运行 进入读取函数 return 为 0 的边缘情况,这被错误地解释为错误。
return 值为 0 是否表示实际错误?
不,return 值为零并不表示错误。 documentation for read() 表示:
Upon successful completion, these functions shall return a non-negative integer indicating the number of bytes actually read. Otherwise, the functions shall return -1 and set errno to indicate the error.
即:return 值为零仅表示已实际读取零字节。这不是错误。 return 值 -1
指示错误。 errno
仍然为零的事实也表明没有发生错误。
关于阻塞/非阻塞部分:
If fildes [i.e.: first parameter] refers to a socket, read() shall be equivalent to recv() with no flags set.
上面写着:
If no messages are available at the socket and O_NONBLOCK is not set on the socket's file descriptor, recv() shall block until a message arrives. If no messages are available at the socket and O_NONBLOCK is set on the socket's file descriptor, recv() shall fail and set errno to [EAGAIN] or [EWOULDBLOCK].
记住文件是一个套接字,转换为:
- 在阻塞模式下,
read()
/recv()
调用将等待直到有更多数据可用。因此,return 值为零应该表示套接字已关闭并且不会再接收到更多数据。可以争论这是否是一个错误,但它表示正常关闭,所以我不会将其视为错误,而只是 “这里没有更多数据可读,继续!” 相反。
- 在非阻塞模式下,
read()
/recv()
调用将 return 与 -1
和 errno
可以是 EAGAIN
或 EWOULDBLOCK
。如果套接字已正确关闭,零仍然可以在非阻塞模式下作为 return 值出现。
总结:
零不表示错误。零可以 returned,如果:
- 套接字已有序关闭且无法接收更多数据(在阻塞和非阻塞模式下),或者
- 已收到大小为零的数据报,或者
- 已通过
read()
. 的第三个参数请求了完全零字节
根据手册,read
return -1 错误的情况下,或读取的字节数。所以 0 return 值表示没有错误,只是没有读取任何字节。
你的代码应该是
n = read(sock, &buff[bytesRead], bytesToRead - bytesRead);
if (n < 0) {
syslog(LOG_CRIT, "ReadFromSocket: read() failed, errno=%d\n", errno);
return FALSE;
}
这取决于套接字是否处于阻塞模式。在非阻塞模式下,0 读取仅表示当前没有可用数据,但稍后可能会有更多数据。在阻塞模式下,0 读取是流结束条件。这不是错误,但在那之后将永远没有数据可用。一般是对端调用shutdown
或者close
.
造成的
If fildes refers to a socket, read() shall be equivalent to recv() with no flags set.
If no messages are available at the socket and O_NONBLOCK is not set on the socket's file descriptor, recv() shall block until a message arrives. If no messages are available at the socket and O_NONBLOCK is set on the socket's file descriptor, recv() shall fail and set errno to [EAGAIN] or [EWOULDBLOCK].
Upon successful completion, recv() shall return the length of the message in bytes. If no messages are available to be received and the peer has performed an orderly shutdown, recv() shall return 0. Otherwise, -1 shall be returned and errno set to indicate the error.
Linux man page for recv*()
对此进行了扩展:
These calls return the number of bytes received, or -1 if an error occurred. In the event of an error, errno is set to indicate the error.
When a stream socket peer has performed an orderly shutdown, the return value will be 0 (the traditional "end-of-file" return).
Datagram sockets in various domains (e.g., the UNIX and Internet domains) permit zero-length datagrams. When such a datagram is received, the return
value is 0.
> The value 0 may also be returned if the requested number of bytes to receive from a stream socket was 0.
所以,不,return 值为零并不表示错误,但是
- 你要求零字节并得到它
- 连接已关闭,或者
- 这是一个数据报套接字,而你只是读取了一个零长度的数据报。
我正在使用遗留代码。此代码在套接字上调用“读取”。如果读取函数 return 为 0 或以下,调用函数将抛出错误。
n = read(sock, &buff[bytesRead], bytesToRead - bytesRead);
if (n <= 0) {
syslog(LOG_CRIT, "ReadFromSocket: read() failed, errno=%d\n", errno);
return FALSE;
}
但是,我注意到此函数抛出错误,其中“errno”= 0。
我很好奇我是否 运行 进入读取函数 return 为 0 的边缘情况,这被错误地解释为错误。
return 值为 0 是否表示实际错误?
不,return 值为零并不表示错误。 documentation for read() 表示:
Upon successful completion, these functions shall return a non-negative integer indicating the number of bytes actually read. Otherwise, the functions shall return -1 and set errno to indicate the error.
即:return 值为零仅表示已实际读取零字节。这不是错误。 return 值 -1
指示错误。 errno
仍然为零的事实也表明没有发生错误。
关于阻塞/非阻塞部分:
If fildes [i.e.: first parameter] refers to a socket, read() shall be equivalent to recv() with no flags set.
上面写着:
If no messages are available at the socket and O_NONBLOCK is not set on the socket's file descriptor, recv() shall block until a message arrives. If no messages are available at the socket and O_NONBLOCK is set on the socket's file descriptor, recv() shall fail and set errno to [EAGAIN] or [EWOULDBLOCK].
记住文件是一个套接字,转换为:
- 在阻塞模式下,
read()
/recv()
调用将等待直到有更多数据可用。因此,return 值为零应该表示套接字已关闭并且不会再接收到更多数据。可以争论这是否是一个错误,但它表示正常关闭,所以我不会将其视为错误,而只是 “这里没有更多数据可读,继续!” 相反。 - 在非阻塞模式下,
read()
/recv()
调用将 return 与-1
和errno
可以是EAGAIN
或EWOULDBLOCK
。如果套接字已正确关闭,零仍然可以在非阻塞模式下作为 return 值出现。
总结:
零不表示错误。零可以 returned,如果:
- 套接字已有序关闭且无法接收更多数据(在阻塞和非阻塞模式下),或者
- 已收到大小为零的数据报,或者
- 已通过
read()
. 的第三个参数请求了完全零字节
根据手册,read
return -1 错误的情况下,或读取的字节数。所以 0 return 值表示没有错误,只是没有读取任何字节。
你的代码应该是
n = read(sock, &buff[bytesRead], bytesToRead - bytesRead);
if (n < 0) {
syslog(LOG_CRIT, "ReadFromSocket: read() failed, errno=%d\n", errno);
return FALSE;
}
这取决于套接字是否处于阻塞模式。在非阻塞模式下,0 读取仅表示当前没有可用数据,但稍后可能会有更多数据。在阻塞模式下,0 读取是流结束条件。这不是错误,但在那之后将永远没有数据可用。一般是对端调用shutdown
或者close
.
If fildes refers to a socket, read() shall be equivalent to recv() with no flags set.
If no messages are available at the socket and O_NONBLOCK is not set on the socket's file descriptor, recv() shall block until a message arrives. If no messages are available at the socket and O_NONBLOCK is set on the socket's file descriptor, recv() shall fail and set errno to [EAGAIN] or [EWOULDBLOCK].
Upon successful completion, recv() shall return the length of the message in bytes. If no messages are available to be received and the peer has performed an orderly shutdown, recv() shall return 0. Otherwise, -1 shall be returned and errno set to indicate the error.
Linux man page for recv*()
对此进行了扩展:
These calls return the number of bytes received, or -1 if an error occurred. In the event of an error, errno is set to indicate the error.
When a stream socket peer has performed an orderly shutdown, the return value will be 0 (the traditional "end-of-file" return).
Datagram sockets in various domains (e.g., the UNIX and Internet domains) permit zero-length datagrams. When such a datagram is received, the return value is 0. > The value 0 may also be returned if the requested number of bytes to receive from a stream socket was 0.
所以,不,return 值为零并不表示错误,但是
- 你要求零字节并得到它
- 连接已关闭,或者
- 这是一个数据报套接字,而你只是读取了一个零长度的数据报。