UC编程8-信号发送函数kill/raise/setitimer/alarm和信号集函数segprocmask

简介: //myuc.h #include//io流#include//标准库#include//uc标准头文件#include//文件控制#include//c字符串#include#include//内存映射#include//文件...

//myuc.h

#include<stdio.h>//io流
#include<stdlib.h>//标准库
#include<unistd.h>//uc标准头文件
#include<fcntl.h>//文件控制
#include<string.h>//c字符串
#include<sys/types.h>
#include<sys/mman.h>//内存映射
#include<sys/stat.h>//文件状态信息
#include<sys/wait.h>//进程等等
#include<dirent.h>//目录操作
#include<signal.h>//信号
#include<sys/time.h>//时间,计时器
#include<sys/ipc.h>//ipc进程间通信
#include<sys/shm.h>//共享内存段
#include<sys/msg.h>//消息队列


//8itimer.c

#include "myuc.h"
void fa(int signo){
printf("get signo %d\n",signo);
}
void test1(){
	signal(SIGALRM,fa);
	struct itimerval timer;
	timer.it_interval.tv_sec=3;//循环时间
	timer.it_interval.tv_usec=100000;//0.1秒
	timer.it_value.tv_sec=2;//开始时间
	timer.it_value.tv_usec=100000;
	setitimer(ITIMER_REAL,&timer,NULL);
	//设定循环向本进程发送SIGALRM信号。
	while(1);
}
void test2(){

}
int main()
{
	test1();
	test2();
	return 0;
}

//8killalarm.c

#include "myuc.h"
void fa(int signal){
	printf("pid:%d catched signal %d\n",getpid(),signal);
	if(signal==SIGALRM){
	printf("闹钟信号\n");
	alarm(2);
	}
}
//raise发信号
void test1(){
	signal(SIGINT,fa);
	raise(SIGINT);//给自己发信号
	int lefts=sleep(3);//时间到或者非忽略信号到来时,就执行后面的代码
	usleep(3000000);// 微妙,10(-6次方),不会被信号打断
	if(lefts!=0) printf("lefts=%d\n",lefts);//lefts为sleep的剩余秒数
	raise(SIGQUIT);
	while(1);
}
//kill发信号
void test2(){
pid_t pid=fork();
if(pid==0){
	signal(SIGINT,fa);
	printf("child:pid=%d\n",getpid());
	//while(1);
	sleep(10);
	printf("child end\n");
	exit(1);
}
sleep(1);
printf("send signal\n");
kill(pid,SIGINT);
sleep(2);
printf("father end\n");
}
//闹钟信号
void test3(){
	
	signal(SIGALRM,fa);
	alarm(10);
	sleep(1);
	int res=alarm(5);//返回上一个闹钟剩余秒数
	printf("res=%d\n",res);
	sleep(1);
	res=alarm(2);//alarm秒数到了,才发出信号
	printf("res=%d\n",res);
	while(1);
}
int main()
{
	//test1();
	//test2();
	test3();
	return 0;
}

//8sigaction.c

#include "myuc.h"
void fa(int signo){
	printf("catched signal %d\n",signo);
	sleep(2);
	printf("sleep end\n");
}
void fa2(int signo,siginfo_t * info,void * p){
printf("catched signal %d from %d\n",signo,info->si_pid);
}
void fa3(int signo,siginfo_t * info,void * p){
printf("catched signal %d from %d,data:%d\n",
		signo,info->si_pid,info->si_value);
}
void test1(){
	struct sigaction act={};
	act.sa_handler=fa;//函数指针
	sigemptyset(&act.sa_mask);
	sigaddset(&act.sa_mask,3);
	act.sa_flags=SA_NOMASK|SA_RESETHAND;
	//不屏蔽自身|执行一次恢复默认
	sigaction(SIGINT,&act,NULL);
	while(1);
}
void test2(){
	printf("mypid=%d\n",getpid());
	struct sigaction act={};
	act.sa_sigaction=fa2;//函数指针
	sigemptyset(&act.sa_mask);
	
	act.sa_flags=SA_NOMASK|SA_SIGINFO;
	//不屏蔽自身|执行一次恢复默认
	sigaction(SIGINT,&act,NULL);
	while(1);
}
void test3(){
	printf("mypid=%d\n",getpid());
	struct sigaction act={};
	act.sa_sigaction=fa3;//函数指针
	sigemptyset(&act.sa_mask);
	
	act.sa_flags=SA_NOMASK|SA_SIGINFO;
	//不屏蔽自身|使用sa_sigaction函数处理
	sigaction(/*SIGINT*/40,&act,NULL);
	pid_t pid=fork();
	if(pid==0){
		int i;
		for(i=0;i<20;i++)
		{
			union sigval v;
			v.sival_int=i;
			sigqueue(getppid(),/*2*/40,v);//给父进程发信号,带数据
		}
		exit(1);
	}
	while(1);
}
int main()
{
	//test1();
	//test2();
	test3();
	return 0;
}

//8sigset.c

#include "myuc.h"
void fa(int signo){
printf("catched signal %d\n",signo);
}
//信号集合操作
void test1(){
printf("size=%d\n",sizeof(sigset_t));
sigset_t set;
printf("set=%g\n",set);
sigemptyset(&set);
printf("set=%d\n",set);
sigaddset(&set,2);//倒数第2位置1
printf("set=%d\n",set);
sigaddset(&set,3);//倒数第3位置1
printf("set=%d\n",set);
if(sigismember(&set,2)){
	printf("signal 2 exist\n");
}
}
//信号屏蔽和解除
void test2(){
signal(SIGINT,fa);
signal(SIGQUIT,fa);
signal(40,fa);//自定义处理40的信号
printf("pid=%d\n",getpid());
printf("信号没屏蔽\n");
sleep(10);
printf("信号屏蔽\n");
sigset_t set,oldset;
sigemptyset(&set);
sigaddset(&set,2);sigaddset(&set,3);//不可靠信号,多种相同信号只保留一个
sigaddset(&set,40);//可靠信号
sigprocmask(SIG_SETMASK,&set,&oldset);
sleep(5);
printf("获取屏蔽期收到的信号\n");
sigset_t recset;
sigpending(&recset);//接收屏蔽期间收到过的信号集合,不能获取次数
if(sigismember(&recset,2)){
	printf("接收到信号2\n");
}
else{
	printf("没收到信号2\n");
}
printf("屏蔽解除\n");
sigprocmask(SIG_SETMASK,&oldset,NULL);//解除屏蔽之后,会处理之前接收到的信号

}
int main()
{
 	//test1();
	test2();
	return 0;
}


相关文章
|
9月前
QT自定义信号,信号emit,信号参数注册
使用signals声明返回值是void在需要发送信号的地方使用emit 信号名字(参数)进行发送在需要链接的地方使用connect进行链接ct进行链接。
89 0
QT自定义信号,信号emit,信号参数注册
|
设计模式 Unix Shell
ECF机制:信号 (Signal)
ECF机制:信号 (Signal)
210 0
|
消息中间件 Unix Linux
进程通信 软中断 signal()解读
进程通信 软中断 signal()解读
|
5月前
|
NoSQL
gdb中获取进程收到的最近一个信号的信息
gdb中获取进程收到的最近一个信号的信息
信号外带数据---sigaction()函数和sigqueue()函数的使用
信号外带数据---sigaction()函数和sigqueue()函数的使用
|
9月前
|
存储 算法 Linux
【探索Linux】P.17(进程信号 —— 信号保存 | 阻塞信号 | sigprocmask() | sigpending() )
【探索Linux】P.17(进程信号 —— 信号保存 | 阻塞信号 | sigprocmask() | sigpending() )
130 0
|
Unix Linux
Linux系统应用编程 --- 信号处理函数(sigaction实现信号捕捉设定)
Linux系统应用编程 --- 信号处理函数(sigaction实现信号捕捉设定)
145 0
|
Linux
Linux 进程信号的基本概念、信号类型、信号处理方式、信号传递机制以及如何使用进程信号进行进程间通信、异常处理
Linux 进程信号的基本概念、信号类型、信号处理方式、信号传递机制以及如何使用进程信号进行进程间通信、异常处理
719 0
|
Linux
【Linux信号专题】三、未决信号集、阻塞信号集与信号集操作函数
【Linux信号专题】三、未决信号集、阻塞信号集与信号集操作函数
388 0
【Linux信号专题】三、未决信号集、阻塞信号集与信号集操作函数
|
Shell Linux
trap - 在脚本中处理信号
一:用途说明      trap命令是shell内建的命令,它用在脚本中指定信号如何处理。   比如,按Ctrl+C会使脚本终止执行,实际上系统发送了SIGINT信号给脚本进程,SIGINT信号的默认处理方式就是退出程序。
1326 0

热门文章

最新文章