使用 libevent 和 libev 提高网络应用性能【转】
许多服务器部署(尤其是 web 服务器部署)面对的最大问题之一是必须能够处理大量连接。无论是通过构建基于云的服务来处理网络通信流,还是把应用程序分布在 IBM Amazon EC 实例上,还是为网站提供高性能组件,都需要能够处理大量并发连接。
一个好例子是,web 应用程序最近越来越动态了,尤其是使用 AJAX 技术的应用程序。如果要部署的系统允许数千客户端直接在网页中更新信息,比如提供事件或问题实时监视的系统,那么提供信息的速度就非常重要了。在网格或云环境中,可能有来自数千客户端的持久连接同时打开着,必须能够处理每个客户端的请求并做出响应。
在讨论 libevent 和 libev 如何处理多个网络连接之前,我们先简要回顾一下处理这类连接的传统解决方案。
处理多个连接有许多不同的传统方法,但是在处理大量连接时它们往往会产生问题,因为它们使用的内存或 CPU 太多,或者达到了某个操作系统限制。
使用的主要方法如下:
- 循环:早期系统使用简单的循环选择解决方案,即循环遍历打开的网络连接的列表,判断是否有要读取的数据。这种方法既缓慢(尤其是随着连接数量增加越来越慢),又低效(因为在处理当前连接时其他连接可能正在发送请求并等待响应)。在系统循环遍历每个连接时,其他连接不得不等待。如果有 100 个连接,其中只有一个有数据,那么仍然必须处理其他 99 个连接,才能轮到真正需要处理的连接。
- poll、epoll 和变体:这是对循环方法的改进,它用一个结构保存要监视的每个连接的数组,当在网络套接字上发现数据时,通过回调机制调用处理函数。poll 的问题是这个结构会非常大,在列表中添加新的网络连接时,修改结构会增加负载并影响性能。
- 选择:
select()
函数调用使用一个静态结构,它事先被硬编码为相当小的数量(1024 个连接),因此不适用于非常大的部署。
在各种平台上还有其他实现(比如 Solaris 上的 /dev/poll 或 FreeBSD/NetBSD 上的 kqueue),它们在各自的 OS 上性能可能更好,但是无法移植,也不一定能够解决处理请求的高层问题。
上面的所有解决方案都用简单的循环等待并处理请求,然后把请求分派给另一个函数以处理实际的网络交互。关键在于循环和网络套接字需要大量管理代码,这样才能监听、更新和控制不同的连接和接口。
处理许多连接的另一种方法是,利用现代内核中的多线程支持监听和处理连接,为每个连接启动一个新线程。这把责任直接交给操作系统,但是会在 RAM 和 CPU 方面增加相当大的开销,因为每个线程都需要自己的执行空间。另外,如果每个线程都忙于处理网络连接,线程之间的上下文切换会很频繁。最后,许多内核并不适于处理如此大量的活跃线程。
继续阅读,有具体的实现
http://www.ibm.com/developerworks/cn/aix/library/au-libev/index.html?ca=drs-
相关推荐
- 《构建高性能web站点》–服务器并发处理能力–I/O
- Posted on 04月09日
- 何跃的第一篇正式的博客
- Posted on 08月29日
- 阅读IT大牛的博客
- Posted on 04月25日
- 我们说自己不行,其实就是在逃避自己的弱点和欲望
- Posted on 09月14日
magnet:?xt=urn:btih:82E2AB7C10287F65C60BBA4CA2CD88ABC934775D
更吧更吧 ?????
原来盖二十层楼就可以进排行榜了。我看我平时只浏览,不发言真亏。还得多留言。