Proactor模式(三)

文中全部的Proactor模式,均指模拟Proactor模式,而不是操做系统级别的Proactor网络

先说下Erlang的check_io是作什么用的。Erlang中的check_io实质是调用系统的epoll/select/kevent/poll对IO事件进行检查。优化

那么问题就产生了,Erlang的网络模型不是Proactor模式嘛,它和scheduler有什么关系?spa

为了回答这个问题,咱们先说下Erlang的Proactor模式和常规的Proactor模式有什么样的差别。操作系统

Erlang所采用Proactor模式和常规的Proactor模式相比有两大差别。第一大差别是,Erlang的Proactor模式并无专用的IO线程,而是复用scheduler的线程。第二大差别是,Erlang的Proactor模式并无在事件发生后马上进行IO读写操做,而是将读写操做的事件放入和fd相关联的Erlang驱动中了,由Erlang的驱动来完成真正的IO操做。这样咱们就能很明显的看出来,Erlang的scheduler既是IO线程又是业务线程。线程

好了,这又产生问题了,Erlang为何选择这样作?那么Erlang是如何让scheduler线程平衡IO操做和业务处理的?队列

Erlang这么作我我的认为有如下几个缘由:进程

  1. 常规Proactor模式中,IO操做集中在IO线程上面,当其中一个Socket传输大块数据的时候,会出现IO时效性下降。由于Erlang的网络驱动自己是一个Port进程,而多个Port进程能够分散到多个Erlang的schduler中,若是将事件和fd放入驱动的队列当中,让驱动来完成真正的IO操做,将读写IO的操做分散到多个线程上,会大大的提升IO的时效性。事件

  2. 做为一个通用语言的虚拟机,Erlang不能假设某种业务场景针对Proactor模式进行优化。当出现业务并不复杂而IO吞吐又很高的状况时,会出现业务线程大量空闲而IO线程满载的场景,那么这也是一种资源浪费,因此让业务线程参与到部分IO操做上能够提升IO吞吐的量级。资源

Erlang是如何让scheduler线程平衡IO操做和业务处理的虚拟机

  1. Erlang的scheduler使用优先执行RunQueue中任务而后在进行IO检查的策略。

  2. Erlang的scheduler中有一个计数器,当RunQueue的任务执行到必定数量的时候,强制性的进行IO检查,防止过分执行RunQueue而让IO没机会进行检查。

  3. 多个scheduler共享一个pollset,当一个scheduler检查IO的时候,其它scheduler尽最大力量执行RunQueue。这里面经过使用原子性的置位操做,减小了多个scheduler去抢锁引发的开销。

相关文章
相关标签/搜索