嗨,老铁,欢迎来到我的博客!

如果觉得我的内容还不错的话,可以关注下我在 segmentfault.com 上的直播。我主要从事 PHP 和 Java 方面的开发,《深入 PHP 内核》作者之一。

[视频直播] PHP 进阶之路 - 亿级 pv 网站架构的技术细节与套路 直播中我将毫无保留的分享我这六年的全部工作经验和踩坑的故事,以及会穿插着一些面试中的 考点难点加分点

周梦康 发表于 2015-06-16 20235 次浏览 标签 : NginxLinux

参考链接

http://blog.chinaunix.net/uid-22312037-id-3974068.html

http://tengine.taobao.org/book/chapter_2.html

如果采用阻塞调用,当读写事件没有准备好,阻塞调用就会进入内核等待,CPU就会让出去给别人使用了.这样对于单线程的 worker 来说,显然不合适,请求一多,都卡在了IO上,CPU 空闲下来没人用,CPU 的利用率就上不去. 如果增加进程数,就会增加无谓的上下文切换.如果只是非阻塞,当读写事件还没准备好,就马上返回 EAGAIN,告诉你,事件还没准备好呢,你慌什么,过会再来吧。好吧,你过一会,再来检查一下事件,直到事件准备好了为止,在这期间,你就可以先去做其它事情,然后再来看看事件好了没。虽然不阻塞了,但你得不时地过来检查一下事件的状态,你可以做更多的事情了,但带来的开销也是不小的。

epoll/kqueue这样的系统调用,它们提供了一种机制,让你可以同时监控多个事件,调用他们是阻塞的但可以设置超时时间,在超时时间之内,如果有事件准备好了,就返回。这种机制正好解决了我们上面的两个问题,拿epoll为例(epoll 的简单使用 https://mengkang.net/726.html),当事件没准备好时,放到epoll里面,事件准备好了,我们就去读写。注意这里我们采用的时非阻塞的方式,我们知道非阻塞的方式实际非常低效的,因为需要不停地执行上下文切换去检查I/O结果(具体可以看IBM得这篇文章 http://www.ibm.com/developerworks/cn/linux/l-async/)。如果当读写返回EAGAIN时,我们将它再次加入到epoll里面。这样,只有当事件准备好了,我们才去处理它,这样就是现了异步非阻塞。


嗨,老铁,欢迎来到我的博客!

如果觉得我的内容还不错的话,可以关注下我在 segmentfault.com 上的直播。我主要从事 PHP 和 Java 方面的开发,《深入 PHP 内核》作者之一。

[视频直播] PHP 进阶之路 - 亿级 pv 网站架构的技术细节与套路 直播中我将毫无保留的分享我这六年的全部工作经验和踩坑的故事,以及会穿插着一些面试中的 考点难点加分点

评论列表