c++ - 处理超过 1024 个套接字?

标签 c++ c sockets networking select

我正在从事 MMO 游戏服务器项目,但遇到了问题。这是 select() 方法的限制。我想用一个线程处理超过 1024 个套接字 I/O。我想用单线程做这个,因为我试图做一个多线程处理系统。该系统创建了 3 个线程(例如在 4 核处理器中;1 个是主线程,3 个是 select() 处理程序)来处理 select() 方法,但又出现了另一个问题,现在我们的限制已经达到 3072 (1024 * 3)那不是解决方案!有了这个想法之后,我想制作一个非阻塞套接字系统,在这个系统中,我在 1 个单线程中调用了 2 个不同的 select 方法; “选择()选择()”。他们按顺序返回,我可以按顺序处理它们。但我认为还有一个问题。如果我想实现像“while(true){ select() select()}”这样的线程和 select() 方法(非阻塞)重新调整,我将像一个空的“while(true)” block 一样使 CPU 过载。如果我想使 select() 超时,我无法实时处理底部 select()。现在我无法为此制定算法。有人可以帮我解决这个问题吗?

注意:我不想使用 poll-epoll-wsapoll 等。(poll 不能处理微秒,它没有 select 快!) 和 libevent 就像 3rd 方库(我想自己做!)

最终解决方案(我认为):我不需要为 I/O 操作处理纳秒,因为处理它没有任何意义。轮询是处理超过 1024 个套接字 I/O 的好方法。我会研究一些东西来理解 MMO 系统。最后一个是我会做一些测试,在我问问题之前我会尝试一些事情 :) 谢谢!

编辑:我是这个问答平台的新手。给负分后能不能告诉我我的问题有什么问题? :)

最佳答案

使用 select 对于如此多(数千)的连接从根本上来说是错误的。虽然 select 通常在您只有很少数量的套接字(可能是十个)时更快,但它会可怕地扩展到数千甚至更多。在我所知道的任何地方,select 都会随着连接数线性减慢(甚至比这更糟,但我不会详细介绍。)

即使 poll 在扩展到数千个连接时也没有比 select 好多少。它没有 select 对您可以轮询的文件描述符数量的(低)限制,但它仍然与连接数量成线性比例。

您真正应该使用的是特定于平台的工具,例如 epollkqueue。它们的扩展性非常好(通常是 O(1)),但显然它们不可移植。

我强烈建议您考虑像 libev 这样的东西这是一个可移植的、经过严格测试的、围绕特定于平台的设施和服务的薄包装。

这是因为特定于平台的方法(例如selectpollepollkqueue、我/O 完成端口、事件端口等)彼此形式不同,并且它们都不能在超过一个或两个平台上使用,或者它们的限制和行为细节略有不同。这些设施甚至可能从操作系统的一个版本更改为下一个版本(例如 Linux 2.6.9 上的 epoll,IIRC。)

即使您不关心可移植性或面向 future 的代码,这样的库也可以为您提供更多功能和更好的界面。

您可以尝试的另外两个库是 libevent (更大更慢,但功能更多)和 libuv (如果您需要 Windows 的可移植性。)

关于c++ - 处理超过 1024 个套接字?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17460072/

相关文章:

c++ - LLDB 为局部变量给出 "use of undeclared identifier"错误

将 OPC-UA-AnsiC 编译为 DLL

c++ - 如何找到 C 中可执行文件的位置?

MongoLab 上的 Node.js 和 MongoDB : "Sockets Closed" On Every Insert

java - android套接字等待传入数据的指定时间

c++ 当你在双端队列中 push_back 或 push_front 时真正发生了什么

c++ - 计算满足给定条件的三元组

c++ - 从模板分配空指针

c - scanf() 将换行符保留在缓冲区中

C++ 套接字客户端断开连接