事件处理框架-event_base
来源:互联网 发布:和俄罗斯女人啪啪知乎 编辑:程序博客网 时间:2024/05/17 00:19
分析libevent的事件处理框架event_base和libevent注册,删除事件的具体流程,这就表现为event_base结构体.
由于源代码的event_base定义的变量太多就先放上书中精简过的有价值的
struct event_base{const struct eventop* evsel;void* evbase;int event_count;int event_gotterm;int event_break;struct event_list **activequeues;int nactivequeues;struct evsignal_info sig;struct event_list eventqueue;struct timeval event_tv;struct min_heap timeheap;struct timeval tv_cache;}
关于结构体中各个字段的含义:
1
evsel和evbase这两个字段
这两个要一起看,你可以把evsel看成是一个类,然后evbase看成是一个被类调用的静态函数
evsel->add(evbase,ev),实际的操作是evbase,也就相当于class::add(instance,ev),instance就是class的一个对象实例。
evsel指向了全局变量static const struct eventop* eventops[];中的一个。
libevent将系统提供的I/O demultiplex机制同一封装成了eventop结构:因此,eventops[]包含了select,poll,kqueue和epoll等等其中的若干个全局实例对象
evbase就是一个eventop实例对象:
先看看eventop结构体
struct eventop { const char *name; void *(*init)(struct event_base *); int (*add)(struct event_base *, evutil_socket_t fd, short old, short events, void *fdinfo); int (*del)(struct event_base *, evutil_socket_t fd, short old, short events, void *fdinfo); int (*dispatch)(struct event_base *, struct timeval *); void (*dealloc)(struct event_base *); int need_reinit; enum event_method_feature features; size_t fdinfo_len;};
也就是说在libevent中多路复用机智的实现都必须提供这五个函数接口
1)完成自身的初始化
2)销毁释放
3)对事件的注册
4)注销
5)分发
2
activequeues是一个二级指针,你可以把它看做是数组,其中activequeues[priority]是一个链表,链表的每个节点指向一个优先级为priority的就绪事件event
3
eventqueue
链表,保存了所有的注册事件event的指针。
4
sig是用来管理信号的结构体
5
timeheap是管理定时事件的小根堆,将在后面定时事件处理时专门讲解
6
event_tv和tv_cache是libevent用于时间管理的变量,将在后面讲到
总体结合event来看,event_base就相当于是一个整体,其内的变量可以用来管理和统计所有的event。
接下来来看看关于event_base的操作函数
创建和初始化event_base
event_init()
struct event_base *event_init(void){ struct event_base *base = event_base_new_with_config(NULL); if (base == NULL) { event_errx(1, "%s: Unable to construct event_base", __func__); return NULL; } current_base = base; return (base);}
创建一个event_base对象也就是创建了一个新的libevent实例
该函数首先为event_base实例申请空间,其中调用了event_base_new_with_config函数,然后其实主要操作都在event_base_new_with_config中,在event.c文件中可以找到定义
接口函数
首先要理解Reactor框架的作用:
提供事件的注册,注销接口;
根据系统提供的事件多路分发机制执行事件循环,
当有事件进入”就绪”状态时,调用注册事件的回调函数来处理事件
libevent中对应接口函数
int event_add(struct event *ev,const struct timeval* timeout);int event_del(struct event* ev);int event_base_loop(struct event_base* base,int loops);void event_active(struct event *event,int res,short events);void event_process_active(struct event_base *base);
关于事件的注册
int event_add(struct event* ev,const struct timeval* tv);
ev指向要注册的事件
tv超过时间
函数应用过程:
函数将ev注册到ev->ev_base上,事件类型由ev->ev_events指明,如果注册成功,ev将被插入到已注册链表中;如果tv不是空,则会同时注册定时事件,将ev添加到timer堆上。
在操作过程中有一步失败,那么函数保证没有事件会被注册,可以讲这相当于一个原子操作
函数的关键思想是调用timer heap接口在堆上预留一个位置,这样做的目的是保证操作的原子性:
向系统I/O机制注册可能会失败,而当在堆上预留成功后,定时事件的添加将肯定不会失败;而预留位置的可能结果是堆扩充,但是内部元素并不会改变
int event_del(struct event* ev);
同样的删除操作不一定是原子的,例如删除时间事件之后,有可能从系统I/O机制中注销会失败。
- 事件处理框架-event_base
- Libevent之事件处理框架-event_base结构体学习
- libevent源码学习-----event_base事件循环
- 事件处理框架
- SDL事件处理框架
- QGraphicsView框架事件处理
- 事件监听处理小框架
- 事件监听处理小框架
- libevent事件处理框架分析
- libevent事件处理框架分析
- libevent事件处理框架分析
- Actor事件处理框架介绍
- libevent源码学习(二)事件循环event_base
- bbossgroups 分布式事件处理框架特性
- 使用DXUT框架简单处理鼠标事件
- libevent源码浅析: 事件处理框架
- libevent源码分析--事件处理框架
- libevent源码分析--事件处理框架
- Functions of Protocols and Transmission Speed
- 高精度加法
- WFE
- windows上安装Anaconda
- LeetCode 46. Permutations
- 事件处理框架-event_base
- 没有微信小小程序内测资格的小伙伴们有福了,IED被破解!!!
- C
- 第四周项目4——建设双链表算法库
- Python - 格式化(format())输出字符串 详解 及 代码
- Jsonschema2pojo中json schema规范写法
- C++编程题之将功赎过和约德尔测试
- Java编程思想
- 百位数分解