Linux系统编程43 信号- signal(),信号会打断阻塞的系统调用

查看信号

mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ kill -l

在这里插入图片描述 0 - 31 : 标准信号
32 - 64:实时信号

NAME
       signal - ANSI C signal handling

SYNOPSIS
       #include <signal.h>

       typedef void (*sighandler_t)(int);

       sighandler_t signal(int signum, sighandler_t handler);

==> 
void (*signal(int signum, void (*func)(int)))(int)

signal()将信号符号的配置设置为handler, handler可以是SIG_IGN、SIG_DFL,也可以是程序员定义的函数(“信号处理器”)的地址。

SIG_IGN:向内核表示忽略此信号
SIG_DFL:向内核表示接到此信息的动作是系统默认动作
当指定函数地址的时候,则在信号发生时,调用该函数,即调用信号处理函数。

信号 SIGINT 指的是 程序终止(interrupt)信号, 在用户键入INTR字符(通常是Ctrl-C)时发出,用于通知前台进程组终止进程。

实验1:忽略 SIG_IGN信号

#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>

int main()
{
	int i;

	signal(SIGINT,SIG_IGN);

	for(i=0 ; i<12 ; i++)
	{
		write(1,"*",1);
		sleep(1);
	}

	exit(0);
}



mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ gcc test.c 
mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ ./a.out 
***^C*^C^C^C*^C^C***^C^C^C**^C^C*^C^C^C*mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ 
mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ 
mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ 

可以看到 程序运行中 不会收到 Ctrl-C 影响

实验2:响应SIG_IGN信号

#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>

void sig_handler(int s)
{
	write(1,"!",1);
}

int main()
{
	int i;

	signal(SIGINT,sig_handler);

	for(i=0 ; i<12 ; i++)
	{
		write(1,"*",1);
		sleep(1);
	}

	exit(0);
}

mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ gcc test.c 
mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ ./a.out 
*^C!*^C!*^C!*^C!*^C!*^C!*^C!*^C!*^C!**^C!*^C!mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ ^C
mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ 

信号会打断阻塞的系统调用

实验3:信号会打断阻塞的系统调用

#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>

void sig_handler(int s)
{
	write(1,"!",1);
}

int main()
{
	int i;

	signal(SIGINT,sig_handler);

	for(i=0 ; i<12 ; i++)
	{
		write(1,"*",1);
		sleep(1);
	}

	exit(0);
}

mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ ./a.out 
*^C!*^C!*^C!*^C!*^C!*^C!*^C!*^C!*^C!*^C!*^C!*^C!mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ ^C
mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ ^C
mhr@ubuntu:~/Desktop/xitongbiancheng/parallel/signal$ ^C

如果执行过程中 一直按住 Ctrl-C ,那么程序会很快结束,用不到15秒。

这是因为 信号会打断阻塞的系统调用。

如:open() 中也有说明

EINTR While blocked waiting to complete an open of a slow device (e.g., a FIFO; see fifo(7)), the call was interrupted by a signal handler; see signal(7).

当阻塞的等待 打开一个比较慢地方设备的时候,这个调用有可能被信号打断。
如 正在打开一个设备,这个设备可能比较慢,或者这个设备正忙,open()在打开它的时候需要消耗一点时间,即 open()会阻塞,这时候如果有信号 则会打断正在阻塞的系统调用。

如 read() 中也有说明

EINTR The call was interrupted by a signal before any data was read; see signal(7)
在我读到任何内容之前,如果有信号,将会被打断。即信号会打断阻塞的系统调用。

所以之前的程序 ,如 open() , read() 需要加阻塞出错的判断:
在这里插入图片描述
在这里插入图片描述

系统调用执行中不会被打断,而是等待,阻塞中会被打断。如等待打开,等待读取。

猜你喜欢

转载自blog.csdn.net/LinuxArmbiggod/article/details/113999715