EventLoop相当于reactor模型的reactor反应堆的角色
poller和epollpoller相当于是多路分发器的角色,掌控epoll的所有操作


最起码得有一个线程来支撑。
如果我们设置了setthreadnumber的多线程的反应堆类型,mainreactor就是处理新用户的连接,accept,拿到新用户通信的fd,把fd感兴趣的事件打包成channel,然后唤醒某个工作线程workreactor(subreactor)(轮询的方式),代表eventloop。每个工作线程subreactor都监听一组channel,每一组channel都得在自己的eventloop去执行。
mainreactor和subreactor
如果没有事件发生的话,他们loop所在的线程都是阻塞的。
假如现在mainreactor监听到一个新用户的连接,得到了表示新用户连接的fd,以及感兴趣的事件的channel,它把这个channel怎么扔给subreactor呢?
如何叫醒???

统一事件源的原理。
在libevent库中,采用的是socketpair

创建了一个本地socket的数组,这2个socket都是可读可写的。
在muduo库中,采用的是linux提供的eventfd

这就是线程间的通信机制。这个线程可以notify通知其他线程起来做事情。eventfd是系统API,在内核可以直接notify应用空间的应用程序,让它的线程起来做事情,效率高。
EventLoop.h
#pragma once
#include <functional>
#include <vector>
#include <atomic>//C++ 11
#include <memory>
#include <mutex>
#include "noncopyable.h"
#include "Timestamp.h"
#include "CurrentThread.h"
class Channel;
class Poller;
//时间循环类 主要包含了两个大模块 Channel Poller(epoll的抽象)
class EventLoop : noncopyable
{
public:
using Functor = std::function<void()>;//定义一个回调的类型
//using代替typedef,进行类型的重命名
EventLoop();
~EventLoop();
//开启事件循环
void loop();
//退出事件循环
void quit();
Timestamp pollReturnTime() const {
return pollReturnTime_; }
//在当前loop中执行cb
void runInLoop(Functor cb);
//把cb放入队列中,唤醒loop所在的线程,执行cb
void queueInLoop(Functor cb);
//用来唤醒loop所在的线程的
void wakeup();
//EventLoop的方法 =》 Poller的方法
void updateChannel(Channel *channel);
void removeChannel(Channel *channel);
bool hasChannel(Channel *channel);
//判断EventLoop对象是否在自己的线程里面
bool isInLoopThread() const

2729

被折叠的 条评论
为什么被折叠?



