如何跳过C中连接客户端的阅读



我正在开发一个TCP客户端-服务器应用程序,该应用程序具有线程,客户端轮流向服务器发送消息(类似于回合制游戏(。服务器向客户端发送消息,但客户端有n秒的响应时间。如果客户端没有及时响应,服务器应该转到下一个客户端而不关闭连接。有没有办法跳过服务器上的read((调用?

您所说的服务器跳过read()调用是什么意思还不完全清楚,但我认为您说的是实现您所描述的响应超时。一种常见的方法是使用select()函数,该函数允许您等待指定的时间,以便文件描述符准备就绪。然后,您可以根据select()是否表示所需的文件描述符已准备就绪来选择是read()还是转到下一个客户端。

大致来说,这可能是沿着以下几条线的:

#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>
#include <assert.h>
// ...
fd_set read_fds;
FD_ZERO(&read_fds);
FD_SET(client_fd, &read_fds);
struct timeval timeout = { .tv_sec = 5, .tv_usec = 0 };
int num_ready = select(client_fd + 1, &read_fds, NULL, NULL, &timeout);
if (num_ready == -1) {
// handle error ...
} else if (num_ready == 0) {
// handle timeout ...
} else if (num_ready == 1) {
// handle client response ...
} else {
// should not happen
assert(0);
}

您还可以考虑具有类似行为的select()的替代方案,例如poll()epoll_wait()。此外,您可能会发现将客户端套接字配置为非阻塞I/O是有利的,尽管这不是使用select()的技术要求。功能。

但是,请注意,它比这更复杂。至少还有这些额外的考虑因素:

  • 您需要为客户端断开连接的情况做好准备。

  • 如果客户端的响应来得太晚,那么在处理来自同一客户端的任何后续响应之前,您将需要读取该响应并(大概(丢弃它。

  • 响应可能会在线路上分为多个部分,因此响应的开始可能会在超时内到达,但结束可能不会,也可能根本不会。

  • 为了保证健壮性,您需要处理在时间到期之前等待被信号中断的情况。在这种情况下,您可能希望恢复等待,但不希望重新启动超时。

最新更新