我正在尝试测试一个已关闭的套接字,该套接字已被对等方正常关闭,而不会产生双重发送的延迟影响以引发SIGPIPE
.
这里的假设之一是,如果关闭的套接字在上次写入/发送后立即被对等方正常关闭。诸如过早关闭之类的实际错误将在代码中的其他位置进行处理。
如果套接字仍然打开,将会有 0 或更多字节的数据,我实际上还不想从套接字缓冲区中取出这些数据。
我想我可以打电话int ret = recv(sockfd, buf, 1, MSG_DONTWAIT | MSG_PEEK);
确定套接字是否仍处于连接状态。如果已连接但缓冲区中没有数据,我将得到以下返回-1
with errno == EAGAIN
并返回 sockfd 以供重用。如果它被同行优雅地关闭,我会得到ret == 0
并打开一个新连接。
我已经测试过这个和它seems上班。但是,我怀疑在我接收数据的最后一位和对等方之间存在一个小窗口FIN
到达时我可能会得到假阳性EAGAIN
从我的测试来看recv
.
这会咬我吗,还是有更好的方法吗?
好的,所以我又进行了一些测试,这就是我发现的结果。
我设置我的客户发送HTTP/1.1 Connection: close
发送到服务器的消息导致服务器在最后一次写入数据后调用 close。当我的客户端完成从 GET 事务读取数据时,它将使用上述方法测试套接字以查看它是否仍然打开,然后尝试发出另一个 GET。
我发现大约 30% 的时间我的测试发生在服务器之前FIN
到达导致误报和操作失败。
可能要使其相当可靠(比如说接近 99%)的唯一方法是引入与上次读取和尝试套接字重用之间的连接延迟相关的人为延迟 - 然而,这几乎会扼杀性能。
因此,我必须得出结论,虽然这个工具很有用,但作用有限。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)