如果套接字仍处于连接状态,EndReceive是否应返回零

本文关键字:EndReceive 状态 是否 返回 连接 套接字 于连接 如果 | 更新日期: 2023-09-27 18:29:00

我正在套接字上进行以下BeginReceive调用:

m_socket.BeginReceive(m_buffer, 0, m_buffer.Length, SocketFlags.Partial, this.ReceiveCallback, null);

在我的类ReceiveCallback函数中,我调用

try {
    int bytesReadFromSocket = m_socket.EndReceive(ar);
    if(bytesReadFromSocket > 0) {
         // Do some processing
    }
}
finally {
   if(m_socket.Connected) m_socket.BeginReceive(m_buffer, 0, m_buffer.Length, SocketFlags.Partial, this.ReceiveCallback, null);
}

我遇到的问题是EndReceive返回零,但m_socket.Connected返回true,所以我再次调用BeginReceive。这发生在一个永远不会停止的紧密循环中。文档中不清楚EndReceive何时返回零。我以为只有当套接字关闭时才会发生这种情况,但这似乎不是真的。

因此,问题仍然存在,在什么条件下EndReceive可以返回零?

如果套接字仍处于连接状态,EndReceive是否应返回零

Socket.EndReceive()在一种特定情况下返回0:远程主机已开始或确认优美的闭包序列(例如,对于基于.NET Socket的程序,使用SocketShutdown.SendSocketShutdown.Both调用Socket.Shutdown())。

但是,请注意,从技术上讲,在插座最终闭合之前,它是"连接"的。

您不应该使用Connected属性来确定是否从套接字发出另一个读取。相反,由于返回值0是专门保留的,表示将不再发送数据,因此您只需检查EndReceive()的返回值,如果该值是正数(即不是零),则应再次调用BeginReceive()

有时我们在测试TCP连接时,忘记初始化缓冲区数组。当它为null或为空时,EndReceive()将始终返回0。我在这方面有一个愚蠢的经历。