- signal函数
1.1 函数指针
上述的func是一个函数指针,可以指定所有返回类型为void,参数类型为int的所有函数,和指针本质上并没有什么区别,在内存空间上都是指向一个特定的地址。函数指针的意义类似于C++语言当中的类,类是具有同一种性质事物的集合,现实生活中的许多事物我们都可以抽象成对应的类,C++相较于C语言而言,扩展了面向对象的部分,面向对象的主要功能就是为了更好地将事物进行模块化,从这个角度上出发,函数指针出现的意义应该也差不多(扯远啦~,以后有时间我再具体讨论这两门语言)void (*func)(int)
例如:void catNum(int num){ cout << "the count of cat is" << num << endl; } void dagNum(int num){ cout << "the count of dog is" << num << endl; } func = catNum; func(5); //输出:the count of cat is 5 func = dogNum; func(4); //输出:the count of dog is 4
这里用了fun(int)替代了func,这个声明参数类型为int的fun函数返回一个指向参数类型为int,返回值类型为void的函数指针void (*fun(int))(int)
1.2. signal函数解析
我们可以分解来看:函数原型:void (*signal(int signo, void (*handle)(int))) (int)
- void (*handle) (int) —>指向返回值类型为void,参数类型为int的函数
- signal(int signo, void (*handle)(int))—>第一个参数为int,第二个参数为函数指针,返回值类型为指向返回值类型为void,参数类型为int的函数指针
- 综合来看,我们可以简化为以下形式:
整个函数的功能为:根据signo信号量,执行相对应的信号处理函数,即handle函数,具体运行实例:typedef void(*handle)(int) handle signal(int signo, handle)
#include <stdio.h> #include <unistd.h> #include <signal.h> void timeout(int sig){ //handle函数 if (sig == SIGALRM) puts("Time out !"); alarm(2); } void keycontrol(int sig){ //handle函数 if (sig == SIGINT){ puts("DTRL + C pressed"); } } int main(int argc, char* argv[]){ int i; signal(SIGALRM, timeout); //SIGALRM信号量-----alarm函数触发 signal(SIGINT, keycontrol); //SIGINT信号量----Ctrl+C触发 alarm(2); for (int i = 0; i < 3; ++i){ puts("wait..."); sleep(100); } return 0; }
- sigaction函数
sigaction函数是signal函数的改进版,signal函数定义复杂,不太好理解,功能也比较局限,只能传递信号量,而不能对信号量进行相关的设置,同时只能对当前的状态进行处理,无法记录之前的状态
2.1sigaction函数参数解析
sigaction结构体定义如下:int sigaction(int signo, const struct sigaction* act, struct sigaction* oldact)
整体上看,sigaction函数比signal函数功能更为强大,同时也比较好理解,更为关键的是可以对之前响应过的处理进行操作,实际上,sigaction比signal函数更为常用struct sigaction { void (*sa_handler)(int); //即信号量响应处理函数 sigset_t sa_mask; //指定信号相关选项和特性 int sa_flags; //指定信号相关选项和特性 } typedef struct { unsigned long sig[_NSIG_WORDS]; //无符号整数数组,linux中long为4个字节 } sigset_t;
具体运行实例:#include <stdio.h> #include <unistd.h> #include <signal.h> void timeout(int sig){ //信号响应处理函数 if (sig == SIGALRM) puts("Time out !"); alarm(2); } int main(int argc, char* argv[]){ int i; struct sigaction act; act.sa_handler = timeout; sigemptyset(&act.sa_mask); act.sa_flags = 0; sigaction(SIGALRM, &act, 0); alarm(2); for (int i = 0; i < 3; ++i){ puts("wait..."); sleep(100); } return 0; }
[1]https://blog.youkuaiyun.com/imxiangzi/article/details/7584917
[2]https://blog.youkuaiyun.com/ta893115871/article/details/7475095
[3]《TCP/IP网络编程》—尹圣雨