强制断开连接后,数据在套接字输入缓冲区中排队

时间:2019-04-14 15:47:25

标签: c windows sockets networking gtk

两台完全不同的计算机,其中一台运行Windows 7 Ultimate和一台运行Windows Server,它们运行相同的程序。该程序使用GSocket在它们之间建立P2P网络体系结构,这表明底层套接字类型是特定于平台的,因此是窗口SOCKET

类似于select()的函数用作检测输入队列中是否有数据的一种形式,它可以完美地工作。 Windows 7客户端强制断开连接时,什么也没有发生,类似于select()的函数超时,这是预期的行为(因为它只能返回取消或超时错误,并且返回TRUE / FALSE值)

但是,如果Windows服务器对等方以相同的方式断开连接,则会导致类似select()的函数返回输入队列中存在数据,这反过来又调用recv(),该失败会失败。 (-1)。在这种情况下,g_socket_get_available_bytes(socket)将返回0,因为没有字节,这说明recv()失败。

现在这不是客户端/服务器之间的问题,因为如果我交换计算机以使另一台计算机成为连接的计算机,则会发生相同的情况。 而且我不知道当两台计算机都是Windows并且都运行相同的GTK +版本运行时时,这是特定于平台的问题。


是什么原因导致这种严重的不良行为? 在Windows发行版中,类似select()的函数行为(g_socket_condition_timed_wait())是否有很大差异。


基本上,此问题已通过替换解决 g_socket_condition_timed_wait(socket, G_IO_IN, 32 * MS_SECOND, NULL, NULL);

gboolean cnp_receive_wait_for_available_bytes (GSocket* socket/*, gint64 timeout*/)
{
    return (g_socket_get_available_bytes(socket) > 0);
}

在这种情况下,如果在强行断开连接时未通过检查,但老实说,我更喜欢另一种方式,如果强行断开连接,g_socket_condition_timed_wait返回TRUE并导致{{1} }失败,因此我无需执行任何其他类型的ping操作即可检测到对等方已强制断开连接。


更新这不是recv的错,我才发现

g_socket_condition_timed_wait()

类似于gboolean cnp_send_failed (GSocket* socket) { /* Probably unspecified how recv() and send() tolerates a zero-length message. */ return(g_socket_send_with_blocking(socket, "", 0, TRUE, NULL, NULL) == (-1)); } 的操作仅在Windows Server对等方断开连接时才对Windows 7计算机失败,这只会使问题更严重,因为它使我无法检测到Windows Server计算机通过上述功能强行断开连接。我不知道OS是否能正确处理关闭输入/输出通道。

0 个答案:

没有答案