-1

我正在尝试使用 C 系统调用编写一个简单的服务器,该服务器从未知客户端获取未知字节流并根据客户端输入执行特定操作。例如,客户端会发送一个命令“multiply 2 2”,服务器会将数字相乘并返回结果。

为了避免在客户端写入之前服务器读取错误,我有一个阻塞的 recv() 调用来等待使用 MSG_PEEK 的任何数据。当 recv 检测到要读取的数据时,我转到非阻塞 recv() 逐字节读取流。

除了客户端不发送数据的极端情况(即 write(socket, "", 0); )外,一切正常。我想知道如何准确检测到没有数据的消息已发送。在这种情况下, recv() 永远阻塞。

此外,这篇文章几乎总结了我的问题,但它并没有提出检测大小为 0 数据包的方法。 如果接收到有效载荷大小为 0 的有效 TCP 数据包,recv() 将返回什么值

4

3 回答 3

1

send/recv级别使用 TCP 时,您不知道进入流的数据包流量。当您通过 TCP 流发送非零字节数时,序列号会增加字节数。这就是双方在成功交换数据方面知道对方在哪里的方式。发送具有相同序列号的多个数据包并不意味着客户端做了任何事情(例如您的write(s, "", 0)示例),它只是意味着客户端想要传达一些其他信息(例如,以另一种方式流动的数据的 ACK )。在流级别操作时,您无法直接看到重传、重复 ACK 或其他类似的异常情况。

您链接的答案说的差不多。

于 2013-04-10T23:27:00.483 回答
0

除了客户端不发送数据的极端情况(即 write(socket, "", 0); )外,一切正常。

write(socket, "", 0)一开始甚至不是发送。它只是一个本地 API 调用,在网络上什么都不做。

我想知道如何准确检测到没有数据的消息已发送。

没有消息被发送,所以没有什么可检测的。

在这种情况下, recv() 永远阻塞。

我同意。

于 2013-04-11T01:12:21.997 回答
-1

我有一个阻塞的 recv() 调用来等待使用 MSG_PEEK 的任何数据。当 recv 检测到要读取的数据时,我转到非阻塞 recv() 逐字节读取流。

而不是使用recv(MSG_PEEK),您应该使用select(),poll()epoll()来检测数据何时到达,然后调用recv()以读取它。

于 2013-04-11T03:59:09.853 回答