1:添加信号

  1.1 原型:sloop_handle sloop_register_signal(int sig, sloop_signal_handler handler, void * param)

 /* register a signal handler */
sloop_handle sloop_register_signal(int sig, sloop_signal_handler handler, void * param)
{
struct sloop_signal * entry;
struct sigaction sa; sa.sa_handler = sloop_signals_handler;
sigemptyset(&sa.sa_mask);
sa.sa_flags = SA_RESTART; /* allocate a new structure sloop_signal */
entry = get_signal();
if (entry == NULL)
return NULL; /* setup structure and insert into list. */
entry->sig = sig;
entry->param = param;
entry->handler = handler;
dlist_add(&entry->list, &sloop.signals);
SLOOPDBG(d_dbg("sloop: sloop_register_signal(%d)\n", sig));
if (sigaction(sig, &sa, NULL) < ) {
dlist_del(&entry->list);
free_signal(entry);
d_error("sigaction %d error %s\n", sig, strerror(errno));
return NULL;
} return entry;
}

  这个函数提供给使用sloop模块的第三方,只需要传入要监听的信号、信号处理函数、参数,就可以将此信号登记到sloop_data结构体中的struct dlist_head signals链表中,在sloop_run函数中进行监听。get_signal函数是从初始化时的struct dlist_head free_signals链表中取出一个可用的节点挂在struct dlist_head signals链表中。具体实现如下:

 /* get signal from pool */
static struct sloop_signal * get_signal(void)
{
struct dlist_head * entry;
struct sloop_signal * target; if (dlist_empty(&sloop.free_signals)) {
d_error("sloop: no sloop_signal available !!!\n");
return NULL;
}
entry = sloop.free_signals.next;
dlist_del(entry);
target = dlist_entry(entry, struct sloop_signal, list);
target->flags = SLOOP_INUSED | SLOOP_TYPE_SIGNAL;
return target;
}

  flags参数主要是为了标识此节点的类型,有三种类型,SLOOP_TYPE_SOCKETSLOOP_TYPE_TIMEOUTSLOOP_TYPE_SIGNAL

  1.2 一般使用方法

      sloop_register_signal(SIGTERM, sig_term,    NULL);登记SIGTERM信号的处理函数是sig_term,没有要传递的参数。

2:添加定时器

  2.1 原型:sloop_handle sloop_register_timeout(unsigned int secs, unsigned int usecs, sloop_timeout_handler handler, void * param)

  同添加信号的实现思路是一样的,需要传递的参数是定时器的秒和微妙参数。

 /* register a timer  */
sloop_handle sloop_register_timeout(unsigned int secs, unsigned int usecs, sloop_timeout_handler handler, void * param)
{
struct sloop_timeout * timeout, * tmp;
struct dlist_head * entry; /* allocate a new struct sloop_timeout. */
timeout = get_timeout();
if (timeout == NULL) return NULL; /* get current time */
gettimeofday(&timeout->time, NULL);
timeout->time.tv_sec += secs;
timeout->time.tv_usec += usecs; while (timeout->time.tv_usec >= ) {
timeout->time.tv_sec++;
timeout->time.tv_usec -= ;
}
timeout->handler = handler;
timeout->param = param;
INIT_DLIST_HEAD(&timeout->list); /* put into the list */
if (dlist_empty(&sloop.timeout)) {
dlist_add(&timeout->list, &sloop.timeout);
SLOOPDBG(d_dbg("sloop: timeout(0x%x) added !\n", timeout));
return timeout;
} entry = sloop.timeout.next;
while (entry != &sloop.timeout) {
tmp = dlist_entry(entry, struct sloop_timeout, list);
if (timercmp(&timeout->time, &tmp->time, < )) break;
entry = entry->next;
}
dlist_add_tail(&timeout->list, entry);
SLOOPDBG(d_dbg("sloop: timeout(0x%x) added !!\n", timeout));
return timeout;
}

  2.2 一般使用方法

  sloop_register_timeout(1, 0, wan_handler, param);在登记之后的1秒执行函数wan_handler。

3:添加套接字

  3.1 原型:套接字分为监听可读或可写两种

/* register a read socket */
sloop_handle sloop_register_read_sock(int sock, sloop_socket_handler handler, void * param)
{
return register_socket(sock, handler, param, &sloop.readers);
} /* register a write socket */
sloop_handle sloop_register_write_sock(int sock, sloop_socket_handler handler, void * param)
{
return register_socket(sock, handler, param, &sloop.writers);
}

   分别挂载到sloop.readers和sloop.writers链表上。

 static struct sloop_socket * register_socket(int sock,
sloop_socket_handler handler, void * param, struct dlist_head * head)
{
struct sloop_socket * entry; /* allocate a new structure sloop_socket */
entry = get_socket();
if (entry == NULL) return NULL; /* setup structure and insert into list. */
entry->sock = sock;
entry->param = param;
entry->handler = handler;
dlist_add(&entry->list, head);
SLOOPDBG(d_dbg("sloop: new socket : 0x%x (fd=%d)\n", (unsigned int)entry, entry->sock));
return entry;
}

  get_socket实现:

 /* get socket from pool */
static struct sloop_socket * get_socket(void)
{
struct dlist_head * entry;
struct sloop_socket * target; if (dlist_empty(&sloop.free_sockets)) {
d_error("sloop: no sloop_socket available !!!\n");
return NULL;
}
entry = sloop.free_sockets.next;
SLOOPDBG(daig_printf("%s: get socket sd=[%x],\n", __FILE__, entry));
dlist_del(entry);
target = dlist_entry(entry, struct sloop_socket, list);
target->flags = SLOOP_INUSED | SLOOP_TYPE_SOCKET;
return target;
}

综上:

  这就是这四种功能的实现思路及使用方式。

sloop公共函数之添加信号,定时器及socket的更多相关文章

  1. sloop公共程序之初始过程及启动

    1:sloop_init() 初始化主要是初始化静态sloop_*** 结构体和填充struct sloop_data 结构体中的成员. //初始化静态存储区给sloop_***结构体 static ...

  2. 除了信号触发线程与接收者线程相同的情况能直接调用到slot,其它情况都依赖事件机制(解决上面代码收不到信号的问题其实很简单,在线程的run();函数中添加一个事件循环就可以了,即加入一句exec();),信号槽不就是一个回调函数嘛

    MainWindow::MainWindow(QWidget *parent) :   QMainWindow(parent)   {   pThreadCon = new CSerialThread ...

  3. sloop公共程序之总体描述

    1:功能需求 开发一个公共库文件sloop.c,实现三个常用功能以供其它模块调用.三个功能如下: 功能一:实现一般的信号监听,调用模块只需传入要监听的信号和相应的回调函数就可以在信号到时调用回调函数处 ...

  4. 在Qt Creator 和在 vs2012 里添加信号和槽

    原文地址:http://www.cnblogs.com/li-peng/p/3644812.html 作者:李鹏 出处:http://www.cnblogs.com/li-peng/ 本文版权归作者和 ...

  5. Postman高级应用——流程控制、调试、公共函数、外部数据文件

    postman客户端下载地址:https://www.getpostman.com/apps 目录 流程控制 调试 公共函数 外部数据文件 流程控制 流程控制简言之就是设置接口的执行顺序,流程控制只有 ...

  6. VS2005 添加onTimer定时器

    SetTimer(1,300,NULL); void CchangeDisplayDlg::OnTimer(UINT_PTR nIDEvent) { // TODO: 在此添加消息处理程序代码和/或调 ...

  7. phpcms公共函数库 总结

    *  global.func.php 公共函数库 /** * 返回经addslashes处理过的字符串或数组 * @param $string 需要处理的字符串或数组 * @return mixed ...

  8. cmf公共函数解析

    cmf公共函数解析-common.php 路径:thinkcmf\simplewind\cmf\common.php方法: 方法 作用 返回值 cmf_get_current_admin_id    ...

  9. ThinkPHP 3.2.3 自动加载公共函数文件的方法

    方法一.加载默认的公共函数文件 在 ThinkPHP 3.2.3 中,默认的公共函数文件位于公共模块 ./Application/Common 下,访问所有的模块之前都会首先加载公共模块下面的配置文件 ...

随机推荐

  1. Jenkins之Sonar 代码检查

    一.简介 SonarQube 是一个用于代码质量管理的开放平台.通过插件机制,Sonar 可以集成不同的测试工具,代码分析工具,以及持续集成工具.与持续集成工具(例如 Hudson/Jenkins 等 ...

  2. CS231n assignment2

    preparation: solve the problem of `from builtins import rang` pip install future  update_rule

  3. 用js两张图片合并成一张图片

    JS和canvas的合成方式 function drawAndShareImage(){ var canvas = document.createElement("canvas") ...

  4. 《构建之法》6-7章读后感、问题及对Scrum的理解

    第6章读后感: 看完第六章后了解什么是敏捷流程.“敏捷流程”在软件工程的语境中是一系列价值观和方法论的集合.我觉得敏捷是比较人性化而且让人比较轻松的的一种团队做项目的方法吧,它会比较注重交流,而不是硬 ...

  5. 基于spec探路者团队贪吃蛇作品的评论

    1 运动功能 由以上两图贪吃蛇的位置不同可知,运动功能实现.并且我能够通过使用键盘上的上下左右方位键控制蛇的移动方向,蛇在控制的方向上进行直线前进. 2 吃食物功能 以上两图可知吃食物功能实现.当界面 ...

  6. Nodejs学习笔记(一)--- 操作Mysql数据库

    对于一门语言的学习,我个人觉得最好的方式就是通过一个项目来展示,所以从基本的一些模块去了解是最好的方式对于Mysql怎么去链接数据库这个我是在网上找到的(其实一直想找官方文档的,发现没有它的踪迹,(后 ...

  7. 使用rand替换random模块

    random模块使用相同的种子,在不同的进程中会出现相同的结果. rand的模块使用不同的种子,在不同的进程中不会出现相同的结果. 2个模块都是erlang自带的. 然后erlang在文档里面注明推荐 ...

  8. (十二)Jmeter之Bean Shell的使用(一)

    一.什么是Bean Shell BeanShell是一种完全符合Java语法规范的脚本语言,并且又拥有自己的一些语法和方法; BeanShell是一种松散类型的脚本语言(这点和JS类似); BeanS ...

  9. Ubuntu 16.04 LTS安装sogou输入法详解

    http://blog.csdn.net/qq_21792169/article/details/53152700 最近开始学习linux 在安装输入法中遇到的一些问题,最终成功安装,也得益于网络上的 ...

  10. phaser2 微信小游戏入手

    phaser2小游戏基本没什么什么问题,可以下常开发游戏.如果遇到什么问题, 可以提出来共同讨论. 下面来个例子 import './lib/weapp-adapter'; import Phaser ...