Redis的事件管理和定时器的管理都是自己来实现的,Redis的事件管理分为两部分,一部分是封装了系统的异步事件API,还有一部分是在这基础上封装了一个通用的事件管理器,根据具体的系统来决定具体使用哪个异步管理API。

先来说说Redis支持哪些异步的系统API。Redis内部封装了epoll,evport,kqueue,select这四个原始的事件管理器。

那epoll举个例子解析一下吧。

 typedef struct aeApiState
{
int epfd; //文件描述符
struct epoll_event *events;//epoll实例
} aeApiState;

这个结构体封装了一个具体的事件实例。

封装的接口函数:

 static int aeApiCreate(aeEventLoop *eventLoop) //创建一个事件管理器
static int aeApiResize(aeEventLoop *eventLoop, int setsize) //重置事件管理器管理事件的个数
static void aeApiFree(aeEventLoop *eventLoop) //删除一个事件管理器
static int aeApiAddEvent(aeEventLoop *eventLoop, int fd, int mask)//向事件管理器中添加一个事件
static void aeApiDelEvent(aeEventLoop *eventLoop, int fd, int delmask) //从时间管理器中删除一个事件
static int aeApiPoll(aeEventLoop *eventLoop, struct timeval *tvp)//激活事件管理器,返回已经触发的事件的个数
static char *aeApiName(void) //获取当前使用的是什么事件模型
1 static int aeApiCreate(aeEventLoop *eventLoop) //创建一个事件管理器
 /*创建成功返回0,否则返回-1*/
static int aeApiCreate(aeEventLoop *eventLoop)
{
aeApiState *state = zmalloc(sizeof(aeApiState)); if (!state) return -;
/*直接按size申请内存*/
state->events = zmalloc(sizeof(struct epoll_event) * eventLoop->setsize);
/*事件内存失败时要释放结构体的内存,防止出现内存泄露*/
if (!state->events)
{
zfree(state);
return -;
}
/*创建epoll描述符,如果创建失败,记得把上面申请的内存释放掉*/
state->epfd = epoll_create(); /* 1024 is just a hint for the kernel */
if (state->epfd == -)
{
zfree(state->events);
zfree(state);
return -;
}
eventLoop->apidata = state;
return ;
}
2 static int aeApiResize(aeEventLoop *eventLoop, int setsize) //重置事件管理器管理事件的个数
/*重置可接受事件的个数,这个函数不能直接调用,因为没有检查新size和旧size的大小关系,如果小了,直接重置会出问题*/
static int aeApiResize(aeEventLoop *eventLoop, int setsize)
{
aeApiState *state = eventLoop->apidata; state->events = zrealloc(state->events, sizeof(struct epoll_event)*setsize);
return ;
}
4 static int aeApiAddEvent(aeEventLoop *eventLoop, int fd, int mask)//向事件管理器中添加一个事件
 /*向epoll中增加事件,需要注册新的文件描述符和需要监控的事件类型*/
static int aeApiAddEvent(aeEventLoop *eventLoop, int fd, int mask)
{
aeApiState *state = eventLoop->apidata;
struct epoll_event ee;
/*因为epoll的维护是用数组维护的,通过下标的方式可以直接访问,省时省力。如果这个节点已经激活了,那新事件添加就好了*/
int op = eventLoop->events[fd].mask == AE_NONE ? EPOLL_CTL_ADD : EPOLL_CTL_MOD; ee.events = ;
mask |= eventLoop->events[fd].mask; /* Merge old events */
if (mask & AE_READABLE) ee.events |= EPOLLIN;
if (mask & AE_WRITABLE) ee.events |= EPOLLOUT;
ee.data.u64 = ; /* avoid valgrind warning */
ee.data.fd = fd;
if (epoll_ctl(state->epfd,op,fd,&ee) == -) return -;
return ;
}
6 static int aeApiPoll(aeEventLoop *eventLoop, struct timeval *tvp)//激活事件管理器,返回已经触发的事件的个数
/*获取事件队列*/
static int aeApiPoll(aeEventLoop *eventLoop, struct timeval *tvp)
{
aeApiState *state = eventLoop->apidata;
int retval, numevents = ; retval = epoll_wait(state->epfd,state->events,eventLoop->setsize,tvp ? (tvp->tv_sec* + tvp->tv_usec/) : -);
if (retval > )
{
int j; numevents = retval;
/*将满足条件的文件描述符和状态保存到fired中,后期逐个处理*/
for (j = ; j < numevents; j++)
{
int mask = ;
struct epoll_event *e = state->events+j; if (e->events & EPOLLIN) mask |= AE_READABLE;
if (e->events & EPOLLOUT) mask |= AE_WRITABLE;
if (e->events & EPOLLERR) mask |= AE_WRITABLE;
if (e->events & EPOLLHUP) mask |= AE_WRITABLE;
eventLoop->fired[j].fd = e->data.fd;
eventLoop->fired[j].mask = mask;
}
}
return numevents;
}

Redis事件管理(三)的更多相关文章

  1. Redis事件管理(二)

    Redis的定时器是自己实现的,不是很复杂.说说具体的实现吧. 定时器的存储维护采用的是普通的单向链表结构,具体节点定义为: /*时间定时器结构体*/ typedef struct aeTimeEve ...

  2. Redis事件管理(一)

    Redis统一的时间管理器,同时管理文件事件和定时器, 这个管理器的定义: #if defined(__APPLE__) #define HAVE_TASKINFO 1 #endif /* Test ...

  3. 服务器文档下载zip格式 SQL Server SQL分页查询 C#过滤html标签 EF 延时加载与死锁 在JS方法中返回多个值的三种方法(转载) IEnumerable,ICollection,IList接口问题 不吹不擂,你想要的Python面试都在这里了【315+道题】 基于mvc三层架构和ajax技术实现最简单的文件上传 事件管理

    服务器文档下载zip格式   刚好这次项目中遇到了这个东西,就来弄一下,挺简单的,但是前台调用的时候弄错了,浪费了大半天的时间,本人也是菜鸟一枚.开始吧.(MVC的) @using Rattan.Co ...

  4. redis的管理工具

    phpredisadmin工具 rdbtools管理工具 saltstack管理redis 通过codis完成redis管理 一:phpredisadmin工具:类似于mysqladmin管理mysq ...

  5. 详解 Redis 内存管理机制和实现

    Redis是一个基于内存的键值数据库,其内存管理是非常重要的.本文内存管理的内容包括:过期键的懒性删除和过期删除以及内存溢出控制策略. 最大内存限制 Redis使用 maxmemory 参数限制最大可 ...

  6. zendframework 事件管理(一)

    zend里的事件管理器主要是为了实现: 1.观察者模式 2.面向切面设计 3.事件驱动构架 事件管理最基本的功能是将监听器与事件连接或断开.不论时连接还是断开都是通过shared collection ...

  7. Redis 内存管理与事件处理

    1 Redis内存管理 Redis内存管理相关文件为zmalloc.c/zmalloc.h,其只是对C中内存管理函数做了简单的封装,屏蔽了底层平台的差异,并增加了内存使用情况统计的功能. void * ...

  8. 安装window下的redis,redis可视化管理工具(Redis Desktop Manager)安装,基础使用,实例化项目

    以下包括内容: 一.redis下载安装,启动 二.Redis可视化管理工具(Redis Desktop Manager)安装 三.实例化项目 一.redis下载安装,启动 1,redis官方下载地址: ...

  9. redis : 桌面管理工具 redis-desktop-manager使用指南

    概要:一款好用的Redis桌面管理工具,支持命令控制台操作,以及常用,查询key,rename,delete等操作. 下载软件,请点击下面链接,进入下载页,选择对应版本: https://redisd ...

随机推荐

  1. Mac OS 中的 Python(和 NumPy)开发环境设置

    http://www.python()tab.com/html/2013/pythonjichu_1010/582.html ()需要删除

  2. JS获取/设置iframe内对象元素、文档的几种方法

    1.IE专用(通过frames索引形象定位): document.frames[i].document.getElementById('元素的ID'); 2.IE专用(通过iframe名称形象定位): ...

  3. maven 工程启动找不到 Spring ContextLoaderListener 的解决办法

    1.错误:  Error configuring application listener of class org.springframework.web.context.ContextLoader ...

  4. YC大牛的判题任务-想法

    YC大牛的判题任务 Time Limit: 1000ms Memory Limit: 65536KB   64-bit integer IO format: %lld      Java class ...

  5. opencv删除二值图中较小的噪点色块

    CvSeq* contour = NULL; double minarea = 100.0; double tmparea = 0.0; CFileDialog dlg(true); if (dlg. ...

  6. OpenCv椭圆皮肤模型

    Mat input_image; Mat output_mask; Mat output_image; void main() { VideoCapture cam(); if (!cam.isOpe ...

  7. PDU与SDU理解

    惯例:首先标注定义,而后是形象的解释. PDU(Protocol Data Unit)协议数据单元 SDU(service data unit)服务数据单元 什么是协议数据单元?就是按照协议的要求来传 ...

  8. nested exception is java.lang.RuntimeException: Error parsing Mapper XML. Cause: java.lang.IllegalArgumentException: Result Maps collection already contains value for

    org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'daoSupport': ...

  9. Servlet的使用方法详细说明

    Servlet的生命周期方法: init() destroy() doGet(HttpServletRequest request,HttpServletResponse response) 客户端请 ...

  10. oracle数据库备份

    --数据库备份--导出 exp userid=shoppingsys/shoppingsys@orcl file=/home/oracle/shoppingsys.dmp log=/home/orac ...