UNIX环境高级编程读书笔记(十)—信号 (3)

来源:互联网 发布:淘宝的电器为什么便宜 编辑:程序博客网 时间:2024/06/07 22:31

 

4.

名称:

alarm

功能:

set an alarm clock for delivery of a signal

头文件:

#include <unistd.h>

函数原形:

unsigned int alarm(unsigned int seconds);

参数:

seconds 时间

返回值:

0或以前设置时间的剩余数

 

 

 

 

 

 

 

 

 

使用alarm函数可以设置一个时间值(闹钟时间),在将来的某个时刻时间值会被超过。当所设时间值被超过后,产生SIGALRM信号。如果不忽略或不捕捉此信号,则其默认动作是终止该进程。

 

/*10_5.c*/

#include <signal.h>

#include <unistd.h>

main()

{

unsigned int i

alarm(1)

for(i=0;1;i++)

printf("I=%d",i)

}

下面这个函数会有什么结果呢?

SIGALRM的缺省操作是结束进程,所以程序在1秒之后结束,你可以看看你的最后I值为多少,来比较一下大家的系统性能差异(我的是40300)

 

5.

名称:

abort

功能:

信号发送函数

头文件:

#include <stdlib.h>

函数原形:

void abort(void);

参数:

 

返回值:

 

 

 

 

 

 

 

 

 

此函数将SIGABRT信号发送给调用进程。进程不应该忽略此信号。

 

三、可靠信号安装和发送函数。

可靠信号的处理函数和不可靠信号的处理函数基本原理是一样的,只不过是可靠信号的处理函数支持排队,信号不会丢失。

 

6

名称:

sigaction

功能:

可靠信号的安装函数

头文件:

#include <signal.h>

函数原形:

int sigaction(int signo,const struct sigaction *act,struct sigaction *oact);

参数:

 

返回值:

若成功返回0,若出错返回-1

 

 

 

 

 

 

 

 

 

 

 

sigaction结构的原形为:

struct sigaction {

void (*sa_handler)(int signo)

void (*sa_sigaction)(int siginfo_t *infovoid *act)

sigset_t sa_mask

int sa_flags

void (*sa_restore)(void)

}

这个函数和结构看起来是不是有点恐怖呢。不要被这个吓着了,其实这个函数的使用相当简单的。我们先解释一下各个参数的含义。 signo很简单就是我们要处理的信号了,可以是任何的合法的信号。有两个信号不能够使用(SIGKILLSIGSTOP) act包含我们要对这个信号进行如何处理的信息。oact更简单了就是以前对这个函数的处理信息了,主要用来保存信息的,一般用NULLOK了。

信号结构有点复杂。不要紧我们慢慢的学习。

sa_handler是一个函数型指针,这个指针指向一个函数,这个函数有一个参数。这个函数就是我们要进行的信号操作的函数。 sa_sigactionsa_restoresa_handler差不多的,只是参数不同罢了。这两个元素我们很少使用,就不管了。

sa_flags用来设置信号操作的各个情况。一般设置为0好了。sa_mask用来设置信号屏蔽字,将在后面介绍。

在使用的时候我们用sa_handler指向我们的一个信号操作函数,就可以了。sa_handler有两个特殊的值:SIG_DELSIG_IGNSIG_DEL是使用缺省的信号操作函数,而SIG_IGN是使用忽略该信号的操作函数。

这个函数复杂,我们使用一个实例来说明。下面这个函数可以捕捉用户的CTRL+C信号。并输出一个提示语句。

 

/*10_6.c*/

#include <stdio.h>

#include <signal.h>

 

#define PROMPT "catch the signal of ‘ctrl+c’/nplease enter ‘ctrl+z’ to exit/n"

 

char *prompt=PROMPT

 

void ctrl_c_op(int signo) /*信号处理程序*/

{

write(STDERR_FILENOpromptstrlen(prompt))

}

 

int main()

{

struct sigaction act

act.sa_handler=ctrl_c_op

act.sa_flags=0

if(sigaction(SIGINT&actNULL)<0)

{

preeor(“error”);

exit(1)

}

while(1)

}

 

运行程序后,当用户按ctrl+c(会产生SIGINT信号)后屏幕上会打印。

catch the signal of ‘ctrl+c’

please enter ‘ctrl+z’ to exit

也就是说当用户按ctrl+c时我们调用我们自己写的函数来处理中断。

 

7

名称:

sigqueue

功能:

可靠信号的发送函数

头文件:

#include <signal.h>

函数原形:

int sigqueue(pid_t pid,int sig,const union sigval value);

参数

 

返回值

若成功返回0,若出错返回-1

 

 

 

 

 

 

 

 

 

typedef union sigval

{

int sival_int;

void *sival_ptr;

}sigval_t;

 

sigqueue()是比较新的发送信号系统调用,主要是针对实时信号提出的(当然也支持前32种),支持信号带有参数,与函数sigaction()配合使用。sigqueue的第一个参数是指定接收信号的进程ID,第二个参数确定即将发送的信号,第三个参数是一个联合数据结构union sigval,指定了信号传递的参数,即通常所说的4字节值。

 

sigqueue()kill()传递了更多的附加信息,但sigqueue()只能向一个进程发送信号,而不能发送信号给一个进程组。如果sig0,将会执行错误检查,但实际上不发送任何信号,0值信号可用于检查pid的有效性以及当前进程是否有权限向目标进程发送信号。

在调用sigqueue时,sigval_t指定的信息会拷贝到3参数信号处理函数的siginfo_t结构中,这样信号处理函数就可以处理这些信息了。由于sigqueue系统调用支持发送带参数信号,所以比kill()系统调用的功能要灵活和强大得多。

注:sigqueue()发送非实时信号时,第三个参数包含的信息仍然能够传递给信号处理函数; sigqueue()发送非实时信号时,仍然不支持排队,即在信号处理函数执行过程中到来的所有相同信号,都被合并为一个信号。

 

文章转自:http://blog.chinaunix.net/u1/59291/showart.php?id=538594

原创粉丝点击