言之者无罪,闻之者足以戒。 ——《诗序》
二、信号的接收
接收信号的进程,需要的条件:要想使接收的进程能收到信号,这个进程就不能结束
接收信号的函数:sleep()、while(1)、pause()
sleep()函数使进程进入睡眠状态(S)
pause()函数使进程进入睡眠状态(S)
while(1)函数使进程一直在运行(R状态)
sleep()和while(1)都非常简单,上面的程序我们都已经使用过了,现在来说一下pause()函数,其实pause()函数也很简单。它没有入口参数,返回值也很简单,下面我们来看一下:
所需头文件 |
#include <unistd.h> |
函数原型 |
int pause(void); |
函数返回值 |
成功:0,出错:-1 |
下面给出关于pause函数的程序:
#include <stdio.h>
#include <sys/types.h>
#include <signal.h>
#include <stdlib.h>
int main()
{
int i=0;
printf("pause befor\n");
pause();
printf("pause after\n");
return 0;
}
三、信号的处理
收到信号的进程,应该怎样处理?处理的方式有哪些?
(1)进程的默认处理方式(内核为用户进程设置的默认处理方式)
A:忽略
B:终止进程
C:暂停
(2)自己的处理方式:
自己处理信号的方法告诉内核,这样你的进程收到了这个信号就会采用你自己的处理方式
1、signal函数:
void (*signal(int signum, void (*handler)(int)))(int);
signal函数有两个参数:
第一个参数:是一个整形变量(信号值)
第二个参数:是一个函数指针,是我们自己写的处理函数
返回值:是一个函数指针
所需头文件 |
#include <signal.h> |
|
函数原型 |
void (*signal(int signum, void (*handler)(int)))(int); |
|
函数传入值 |
signum:指定信号 |
|
|
handler: |
SIG_IGN:忽略该信号。 |
|
|
SIG_DFL:采用系统默认方式处理信号。 |
|
|
自定义的信号处理函数指针 |
函数返回值 |
成功:设置之前的信号处理方式 |
|
|
出错:-1 |
下面给出一段程序:
include <stdio.h>
#include <sys/types.h>
#include <signal.h>
#include <stdlib.h>
void myfun(int signum)
{
int i=0;
while(i < 6)
{
printf("process signal signum=%d\n",signum);
sleep(1);
i++;
}
return;//return main
}
int main()
{
int i=0;
signal(14,myfun);
printf("pause befor\n");
alarm(8);
printf("pause after\n");
while(i < 20)
{
printf("process working time is %d\n",i);
i++;
sleep(1);
}
return 0;
}
上面我们说了handler参数形式有三种,第三种我们已经演示过了下面演示一下第一种和第二种:
第一种程序代码:
#include <stdio.h>
#include <sys/types.h>
#include <signal.h>
#include <stdlib.h>
void myfun(int signum)
{
int i=0;
while(i < 6)
{
printf("process signal signum=%d\n",signum);
sleep(1);
i++;
}
return;//return main
}
int main()
{
int i=0;
signal(14,myfun);
printf("pause befor\n");
alarm(8);
printf("pause after\n");
signal(14,SIG_IGN);
while(i < 20)
{
printf("process working time is %d\n",i);
i++;
sleep(1);
}
return 0;
}
第二种程序代码:
#include <stdio.h>
#include <sys/types.h>
#include <signal.h>
#include <stdlib.h>
void myfun(int signum)
{
int i=0;
while(i < 6)
{
printf("process signal signum=%d\n",signum);
sleep(1);
i++;
}
return;//return main
}
int main()
{
int i=0;
signal(14,myfun);
printf("pause befor\n");
alarm(8);
printf("pause after\n");
signal(14,SIG_IGN);
signal(14,SIG_DFL);
while(i < 20)
{
printf("process working time is %d\n",i);
i++;
sleep(1);
}
return 0;
}
下面我们写一段程序来实现一下的功能:
(1)子进程sleep(10)之后向父进程发送一个信号
(2)父进程接收信号之后,按照自己定义的方式处理信号
(3)再sleep(10)之后再一次向父进程发送一个信号
(4)父进程接收信号之后,按照自己定义的第二种方式处理信号
#include "stdio.h"
#include "sys/types.h"
#include "signal.h"
#include "stdio.h"
#include "stdlib.h"
void myfun(int signum)
{
int i=0;
while(i < 5)
{
printf("receive signum=%d,i=%d\n",signum,i);
sleep(1);
i++;
}
return ;
}
void myfun1(int signum)
{
printf("receive signum=%d\n",signum);
wait(NULL);
return;
}
int main()
{
pid_t pid;
pid=fork();
if(pid >0)
{
int i=0;
signal(10,myfun);
signal(17,myfun1);
while(1)
{
printf("parent process things ,i=%d\n",i);
sleep(1);
i++;
}
}
if(pid == 0)
{
sleep(10);
kill(getppid(),10);
sleep(10);
exit(0);
}
return 0;
}
到这为止,关于信号通信方面的知识就已经说完了。