Linux:是否有超时的套接字读取或接收? [英] Linux: is there a read or recv from socket with timeout?

查看:38
本文介绍了Linux:是否有超时的套接字读取或接收?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如何尝试在超时的情况下从套接字读取数据?我知道,select、pselect、poll 有一个超时字段,但是使用它们会禁用 tcp reno 堆栈中的tcp fast-path".

How can I try to read data from socket with timeout? I know, select, pselect, poll, has a timeout field, but using of them disables "tcp fast-path" in tcp reno stack.

我唯一的想法是在循环中使用 recv(fd, ..., MSG_DONTWAIT)

The only idea I have is to use recv(fd, ..., MSG_DONTWAIT) in a loop

推荐答案

您可以使用 setsockopt 函数设置接收操作超时:

You can use the setsockopt function to set a timeout on receive operations:

SO_RCVTIMEO

设置指定的超时值输入的最长时间函数一直等到它完成.它接受一个 timeval 结构秒数和微秒数指定多长时间的限制等待输入操作完全的.如果接收操作有堵了这么长时间没有接收额外的数据,它应返回部分计数或 errno设置为 [EAGAIN] 或 [EWOULDBLOCK] 如果没有数据被接收.这个默认选项为零,这表明一个接收操作不得超时.此选项采用 timeval 结构.请注意,并非所有实现允许设置此选项.

Sets the timeout value that specifies the maximum amount of time an input function waits until it completes. It accepts a timeval structure with the number of seconds and microseconds specifying the limit on how long to wait for an input operation to complete. If a receive operation has blocked for this much time without receiving additional data, it shall return with a partial count or errno set to [EAGAIN] or [EWOULDBLOCK] if no data is received. The default for this option is zero, which indicates that a receive operation shall not time out. This option takes a timeval structure. Note that not all implementations allow this option to be set.

// LINUX
struct timeval tv;
tv.tv_sec = timeout_in_seconds;
tv.tv_usec = 0;
setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, (const char*)&tv, sizeof tv);

// WINDOWS
DWORD timeout = timeout_in_seconds * 1000;
setsockopt(socket, SOL_SOCKET, SO_RCVTIMEO, (const char*)&timeout, sizeof timeout);

// MAC OS X (identical to Linux)
struct timeval tv;
tv.tv_sec = timeout_in_seconds;
tv.tv_usec = 0;
setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, (const char*)&tv, sizeof tv);

据报道在 Windows 上这应该在调用 bind 之前完成.我已经通过实验验证,它可以在 Linux 和 OS X 上的 bind 之前或之后完成.

Reportedly on Windows this should be done before calling bind. I have verified by experiment that it can be done either before or after bind on Linux and OS X.

这篇关于Linux:是否有超时的套接字读取或接收?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆