C10K问题


网络服务在处理数以 万计的客户端 连接时,往往出现效率底下甚至完全瘫痪,这被成为 C10K问题 。

select和poll在连接数增加时,性能急剧下降。这有两方面的原因:

(1)操作系统面对每次的select/poll操作,都需要 重新建立 一个当前线程的关心事件链表,并把线程挂在这个复杂的等待队列上,这是相当耗时的。

(2)应用软件在select/poll返回后需要对传入的句柄链表做一次 循环扫描 来dispatch,这也是很耗时的。

基于以上原因,unix系列的hacker们开发了epoll, kqueue, /dev/poll这3套利器。

epoll 是Linux的方案

kqueue 是freebsd的方案

/dev/poll 是solaris的方案

wfmo (WaitForMultipleObjects)是windows的方案  --- 同时最多64个连接,windows中FD_SETSIZE的缺省大小为64

iocp (I/O Completion Port,I/O完成端口) 是Windows 异步通讯机制

由于epoll、poll和select都使用文件描述符fd作为数组的索引,

select内核使用fd_set[OPEN_MAX=1024]

poll内核使用fd_set[0x8000=32768]

epoll内核会根据用户提供的size动态开辟和初始化fd_set,如果后面超过了当前fd_set的最大尺寸就会动态重新分配fd_set

解决这个问题的一种途径是线程池(Thread Pool),并在各个线程中运行单独的select/poll以实现对网络事件的多路分离。

提高单io复用api的socket处理容量,需要关注下面的系统资源设置:

(1) 单一进程允许打开的最大文件数

ulimit -n

(2) 查看Linux系统的最大打开文件数限制(所有进程)

通常这个系统级硬限制是Linux系统在启动时根据系统硬件资源状况计算出来的最佳的最大同时打开文件数限制,如果没有特殊需要,不应该修改此限制,除非想为用户级打开文件数限制设置超过此限制的值。

cat /proc/sys/fs/file-max

echo 22158 > /proc/sys/fs/file-max


你可能感兴趣的:(计算机网络)