Linux 增加 FD_SETSIZE 的限制并选择

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/7976388/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-05 06:57:01  来源:igfitidea点击:

Increasing limit of FD_SETSIZE and select

clinuxfile-descriptor

提问by Vivek Goel

I want to increase FD_SETSIZE macro value for my system. Is there any way to increase FD_SETSIZE so select will not fail

我想为我的系统增加 FD_SETSIZE 宏值。有什么办法可以增加 FD_SETSIZE 这样选择就不会失败

采纳答案by R.. GitHub STOP HELPING ICE

Per the standards, there is no way to increase FD_SETSIZE. Some programs and libraries (libevent comes to mind) try to work around this by allocating additional space for the fd_setobject and passing values larger than FD_SETSIZEto the FD_*macros, but this is a very bad idea since robust implementations may perform bounds-checking on the argument and abort if it's out of range.

根据标准,没有办法增加FD_SETSIZE。一些程序和库(想到 libevent)试图通过为fd_set对象分配额外的空间并传递大于宏的值FD_SETSIZE来解决这个问题FD_*,但这是一个非常糟糕的主意,因为健壮的实现可能会对参数执行边界检查和如果超出范围则中止。

I have an alternate solution that should always work (even though it's not required to by the standards). Instead of a single fd_setobject, allocate an array of them large enough to hold the max fd you'll need, then use FD_SET(fd%FD_SETSIZE, &fds_array[fd/FD_SETSIZE])etc. to access the set.

我有一个应该始终有效的替代解决方案(即使标准没有要求)。不是单个fd_set对象,而是分配一个足够大的数组来容纳您需要的最大 fd,然后使用FD_SET(fd%FD_SETSIZE, &fds_array[fd/FD_SETSIZE])etc. 来访问该集合。

回答by Basile Starynkevitch

I also suggest using pollif possible. And there exist several "event" processing libraries like libeventor libev(or the event abilities of Glibfrom GTK, or QtCore, etc) which should help you. There are also things like epoll. And your problem is related to C10k

poll如果可能的话,我也建议使用。并且存在几个“事件”处理库,如libeventlibev(或来自 GTK的GlibQtCore等的事件能力)应该对您有所帮助。还有像epoll这样的东西。而你的问题与C10k有关

回答by BrierMay

actually there ISa way to increase FD_SETSIZE on windows. its defined in winsock.h and per microsoft themselves you can increase it by simply defining it BEFORE you include winsock.h

居然还有IS加大对窗口FD_SETSIZE的方式。它在 winsock.h 和每个 microsoft 中定义,您可以通过在包含 winsock.h 之前简单地定义它来增加它

http://support.microsoft.com/kb/111855

http://support.microsoft.com/kb/111855

I do it all the time and have had no problems largest value I have used was around 5000 for a server I was developing

我一直这样做并且没有任何问题我使用的最大价值是我正在开发的服务器的大约 5000

回答by Simon Gymer

It would be better (and easy) to replace with poll. Generally poll() is a simple drop-in replacement for select() and isn't limited by the 1024 of FD_SETSIZE...

用 poll 替换会更好(也很容易)。通常 poll() 是 select() 的简单替代品,不受 FD_SETSIZE 的 1024 限制...

fd_set fd_read;
int id = 42;
FD_ZERO(fd_read);
FD_SET(id, &fd_read);
struct timeval tv;
tv.tv_sec = 5;
tv.tv_usec = 0;
if (select(id + 1, &fd_read, NULL, NULL, &tv) != 1) {
   // Error.
}

becomes:

变成:

struct pollfd pfd_read;
int id = 42;
int timeout = 5000;
pfd_read.fd = id;
pfd_read.events = POLLIN;
if (poll(&pfd_read, 1, timeout) != 1) {
   // Error
}

You need to include poll.h for the pollfd structure.

您需要为 pollfd 结构包含 poll.h。

If you need to write as well as read then set the events flag as POLLIN | POLLOUT.

如果您需要写入和读取,则将事件标志设置为 POLLIN | 污染。

回答by mpromonet

In order to use a fd_setlarger than FD_SETSIZE, it is possible to define an extended one like this :

为了使用fd_set大于 FD_SETSIZE 的值,可以像这样定义一个扩展:

#include <sys/select.h>
#include <stdio.h>

#define EXT_FD_SETSIZE 2048
typedef struct
{
    long __fds_bits[EXT_FD_SETSIZE / 8 / sizeof(long)];
} ext_fd_set;

int main()
{
    ext_fd_set fd;
    int s;
    printf("FD_SETSIZE:%d sizeof(fd):%ld\n", EXT_FD_SETSIZE, sizeof(fd));
    FD_ZERO(&fd);
    while ( ((s=dup(0)) != -1) && (s < EXT_FD_SETSIZE) )
    {
        FD_SET(s, &fd);
    }
    printf("select:%d\n", select(EXT_FD_SETSIZE,(fd_set*)&fd, NULL, NULL, NULL));
    return 0;
}

This prints :

这打印:

FD_SETSIZE:2048 sizeof(fd):256

select:2045

FD_SETSIZE:2048 sizeof(fd):256

选择:2045



为了打开超过 1024 个文件描述符,需要使用例如ulimit -n 2048ulimit -n 2048.