Libevent源码分析—event_init()
event_init()
struct event_base *
event_init(void)
{
struct event_base *base = event_base_new(); //event_init()调用event_base_new()
if (base != NULL)
current_base = base;
return (base);
}
我们发现event_init()工作量很少,只是调用event_base_new()函数,所以真正初始化event_base的工作是在event_base_new()函数内完成。
event_base_new()
struct event_base *
event_base_new(void) //初始化libevent的event_base
{
int i;
struct event_base *base;
if ((base = calloc(, sizeof(struct event_base))) == NULL) //在堆上分配内存存储event_base,所有字段初始化为0
event_err(, "%s: calloc", __func__);
event_sigcb = NULL;
event_gotsig = ;
detect_monotonic(); //设置use_monotonic变量
gettime(base, &base->event_tv); //base->tv_cache.tv_sec非0,则赋给base->event_tv min_heap_ctor(&base->timeheap); //初始化定时事件的小根堆base->timeheap min_heap.h
TAILQ_INIT(&base->eventqueue); //初始化注册事件链表base->eventqueue sys/queue.h
base->sig.ev_signal_pair[] = -; //初始化信号base->sig
base->sig.ev_signal_pair[] = -; base->evbase = NULL; //初始化I/O多路复用 base->evbase
//遍历全局数组eventops[],初始化libevent的I/O多路复用机制
for (i = ; eventops[i] && !base->evbase; i++) { //以NULL标志数组结尾,只选取一个I/O多路复用机制
base->evsel = eventops[i]; //初始化base->evsel
base->evbase = base->evsel->init(base); //初始化base->evbase
}
if (base->evbase == NULL) //没有I/O多路复用
event_errx(, "%s: no event mechanism available", __func__);
if (evutil_getenv("EVENT_SHOW_METHOD")) //调用getenv()获取环境变量EVENT_SHOW_METHOD evutil.c
event_msgx("libevent using: %s\n",
base->evsel->name);
/* allocate a single active event queue */
//event_base_new()内调用event_base_priority_init()
event_base_priority_init(base, ); //设置优先级base->nactivequeues;分配数组base->activequeues。数组大小和优先级相同
return (base);
}
其中由3点需要注意:
1.该函数调用calloc()在堆上分配内存来存储event_base;
2.使用全局数组eventops[]存储系统支持的I/O多路复用机制,然后遍历该数组,选取第1个I/O多路复用机制。
3.libevent支持event有优先级,所以又调用了event_base_priority_init()来完成优先级相关的设置。
event_base_priority_init()
//设置不同event的优先级,值越小,优先级越高
//返回值:0,成功;-1,出错
int
event_base_priority_init(struct event_base *base, int npriorities)
{
int i;
if (base->event_count_active) //当前base上有活跃的events则不能设置优先级,返回。
return (-);
if (npriorities == base->nactivequeues) //设置的优先级和当前优先级相同,则直接返回
return ();
if (base->nactivequeues) { //不同,则先释放原先的activequeues数组
for (i = ; i < base->nactivequeues; ++i) {
free(base->activequeues[i]);
}
free(base->activequeues);
}
/* Allocate our priority queues */
base->nactivequeues = npriorities; //设置新的优先级
base->activequeues = (struct event_list **)
calloc(base->nactivequeues, sizeof(struct event_list *)); //设置和优先级值相同大小的event_list数组
if (base->activequeues == NULL)
event_err(, "%s: calloc", __func__);
for (i = ; i < base->nactivequeues; ++i) {
base->activequeues[i] = malloc(sizeof(struct event_list)); //初始化activequeues数组中每个元素
if (base->activequeues[i] == NULL)
event_err(, "%s: malloc", __func__);
TAILQ_INIT(base->activequeues[i]);
}
return ();
}
该函数设置优先级,初始化了event_base的nactivequeues成员和activequeues成员。优先级值越小,优先级越高。在活跃事件链表中,优先级高的event先被处理。
Libevent源码分析—event_init()的更多相关文章
- 【转】libevent源码分析
libevent源码分析 转自:http://www.cnblogs.com/hustcat/archive/2010/08/31/1814022.html 这两天没事,看了一下Memcached和l ...
- Libevent源码分析 (1) hello-world
Libevent源码分析 (1) hello-world ⑨月份接触了久闻大名的libevent,当时想读读源码,可是由于事情比较多一直没有时间,现在手头的东西基本告一段落了,我准备读读libeven ...
- Libevent源码分析系列【转】
转自:https://www.cnblogs.com/zxiner/p/6919021.html 1.使用libevent库 源码那么多,该怎么分析从哪分析呢?一个好的方法就是先用起来,会用了 ...
- Libevent源码分析系列
1.使用libevent库 源码那么多,该怎么分析从哪分析呢?一个好的方法就是先用起来,会用了,然后去看底层相应的源码,这样比较有条理,自上向下掌握.下面用libevent库写个程序,每隔1秒 ...
- libevent源码分析
这两天没事,看了一下Memcached和libevent的源码,做个小总结. 1.入门 1.1.概述Libevent是一个用于开发可扩展性网络服务器的基于事件驱动(event-driven)模型的网络 ...
- Libevent源码分析—event_base_dispatch()
我们知道libevent是一个Reactor模式的事件驱动的网络库. 到目前为止,我们已经看了核心的event和event_base结构体的源码,看了初始化这两个结构体的源码,看了注册event的 ...
- libevent源码分析二--timeout事件响应
libevent不仅支持io事件,同时还支持timeout事件与signal事件,这篇文件将分析libevent是如何组织timeout事件以及如何响应timeout事件. 1. min_heap ...
- libevent源码分析一--io事件响应
这篇文章将分析libevent如何组织io事件,如何捕捉事件的发生并进行相应的响应.这里不会详细分析event与event_base的细节,仅描述io事件如何存储与如何响应. 1. select l ...
- Libevent源码分析—event, event_base
event和event_base是libevent的两个核心结构体,分别是反应堆模式中的Event和Reactor.源码分别位于event.h和event-internal.h中 1.event: s ...
随机推荐
- 源码阅读之mongoengine(0)
最近工作上用到了mongodb,之前只是草草了解了一下.对于NoSQL的了解也不是太多.所以想趁机多学习一下. 工作的项目直接用了pymongo来操作直接操作mongodb.对于用惯了Djongo O ...
- 记因PHP的内存溢出导致的事故之解决
如果对您有用记得关注,更多干货. 今天上午刚到公司,就有同事在公司群里反映某个计划任务出现问题了.我就怀着刨根问底的心,去查看了log.发现挺有意思的一个问题,PHP内存溢出导致脚本执行失败.那就一起 ...
- mvc中razor的一个bug
具体东西就不多说了,所有编译,代码都是木有问题的. 结果预览页面的时候竟然告诉我编译错误,尼玛这不科学啊. 来看看错误页面 看着问题大概应该是缺少} ,或者多了个} 倒置的编译错误才对,但是编译生成完 ...
- StringBuilder的实现
先看看MS给出的官方解释吧 (http://msdn.microsoft.com/zh-cn/library/system.text.stringbuilder(VS.80).aspx) String ...
- 【转】JDBC学习笔记(8)——数据库连接池(dbcp&C3P0)
转自:http://www.cnblogs.com/ysw-go/ JDBC数据库连接池的必要性 一.在使用开发基于数据库的web程序时,传统的模式基本是按一下步骤: 1)在主程序(如servlet/ ...
- 为linux安装xen-tools提示/dev/xvdd does not exist
看样子百度还是不如google啊.百度上找到的信息完全无用.google上却给我找到了... 1:当/dev/xvdd does not exist错误出现时,可以尝试下 mount /dev/cdr ...
- Hibernate考试试题(部分题库)含答案
Hibernate考试试题 (题库) 1. 在Hibernate中,下列说法正确的有( ABC ).[选三项] A.Hibernate是一个开放源代码的对象关系映射框架 B.Hibernate对JD ...
- 分分钟带你玩转 Web Services【2】CXF
在实践中一直在使用 JAX-WS 构建 WebService 服务,服务还是非常稳定.高效的. 但还是比较好奇其他的 WebService 开源框架,比如:CXF/Axis2/Spring WS等. ...
- 随应潮流-基于ABP+Angulsrjs现代化应用软件开发框架(2)-abp说明
前言 上周未发布完<基于ABP+Angulsrjs现代化应用软件开发框架(1)-总体介绍> 文章后,好多朋友问了我一些ABP的问题,并且希望我开源我的项目源码,向朋友们说一下,我项目的源码 ...
- bzoj4031 [HEOI2015]小Z的房间
Description 你突然有了一个大房子,房子里面有一些房间.事实上,你的房子可以看做是一个包含n*m个格子的格状矩形,每个格子是一个房间或者是一个柱子.在一开始的时候,相邻的格子之间都有墙隔着. ...