关于处理超过1024个套接字描述符的问题

3
我使用C语言在Linux上编写了一个聊天服务器。我已经进行了测试并且性能表现良好。但是,我使用select系统调用来处理套接字描述符,这导致我的聊天服务器最多只能同时处理1024个用户,因为select的限制是1024。我知道另一种选择是使用poll,但我不确定它的性能是否与select相当。请建议我最有效的方法来解决这种情况。

2
可能是在Linux上使用C处理超过1024个文件描述符的问题的重复问题。 - Christian.K
2
绝对使用 epoll 而不是 select。 - jxh
Christian.K提供的链接绝对为此问题提供了解决方案。 - alk
在我的程序中,我应该在哪里重新定义__FD_SETSIZE?因为fdset从系统文件获取它。 - user1457812
3个回答

5

poll()可以作为几乎与select()相同的替代品,并允许您超过1024个文件描述符(您可以使传递给poll()的数组尽可能大)。

它将具有类似于select()的性能特征,因为两者都需要内核和用户空间应用程序扫描整个数组 - 但是如果select()对您有效,则poll()也应该有效。(实际上,在poll()中有轻微的性能改进 - 指定每个文件描述符所需事件的.events字段不会被poll()更改,因此您不必像传递给select()的文件描述符集一样在每次调用之前重建数组)。

如果您发现自己后来由于扫描轮询文件描述符数组而导致性能问题,则可以考虑切换到更复杂但也可扩展到非常大数量的文件描述符的epoll接口。


3
您的问题被称为C10K问题(如何处理超过10,000个同时连接)。您可以在网上找到许多资源,例如这个
您应该考虑将select作为过时的系统调用。即使只有几十个文件描述符,您也至少应该优先考虑使用poll
请注意,Qt和Gtk为您提供了事件循环机制,通常使用poll(并且QtCore或Glib可以在非图形界面中使用)。还有libevlibevent。我建议使用其中之一。

0

Linux在select()上没有1024的限制。但是:

  1. select()的性能非常差
  2. FreeBSD有 :)

您可以使用poll()。但是当活动连接数增加时,其性能会受到影响。

在Linux上使用epoll()更可取,但我建议使用libevent

libevent是实现重载服务器的快速、干净和可移植的方式,对于Linux来说,它在内部使用epoll。


这是一个糟糕的措辞。确实,在编译时重新定义FDSET宏的大小可以增加1024限制。但是这种方法在任何库中都不会很好地工作。因此最好不要这样做,否则可能会导致难以检测的错误。 - Lothar

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接