信号是什么:用户模式下用来模拟硬件中断的一种方式
中断:异常(有变化也算)的一种
硬件中断:硬件引发的中断,物理层面的,如:上电、鼠标移动、电平的变化
软件中断:模拟硬件中断
信号的产生:可由硬件、内核、进程产生
结束当前终端进程的信号:
ctrl + c SIGINT
ctrl + \ SIGQUIT
信号处理过程:
1.进程A正常运行 硬件、内核或其他进程发送一个信号给A
2.进程A收到信号
操作1:直接做信号本身规定的对应的处理
操作2:调用注册好的信号处理函数
操作3:屏蔽信号
3.继续执行
信号分类:
Linux提供64个信号(kill -l 查看)
不可靠信号(非实时的) unix提供的 1-31
可靠信号(实时的) 后来扩充的 32-64
标准信号:操作系统提供的
自定义信号:用户自定义的 SIG_USR+
man 7 signal 查看signal信息
SIGWITCH 终端大小发生改变
SIGALRM 定时器信号
有些信号可以注册处理代替默认的处理,有些不行,例如SIGKILL(9)
信号发送:
kill 命令
kill 函数(man 2 kill)
raise 函数,向当前进程发送信号(man raise)
sigqueue 高级的信号发送(man sigqueue)
要配合高级的信号注册函数来使用sigaction(man sigaction)
信号屏蔽(man sigprocmask):
#include <signal.h>
int sigprocmask(
int how,
SIG_BLOCK 设置屏蔽
SIG_UNBLOCK 解除屏蔽
const sigset_t *set,
(man sigaddset)
int sigemptyset(sigset_t *set);//清空
int sigfillset(sigset_t *set);//填充
int sigaddset(sigset_t *set, int signum);//添加信号到信号集
int sigdelset(sigset_t *set, int signum);//从信号集删除某个信号
int sigismember(const sigset_t *set, int signum);//判断某个信号是否在信号集里
sigset_t *oldset
);
相关代码
void hand(int s)
{
printf("收到信号:%d\n", s);
}
void _signal()
{
signal(2, hand);
int n = 0;
while (1)
{
printf("%d\n", n++);
sleep(1);
}
}