1.信号使用的示例程序:
#include<stdlib.h>
#include<stdio.h>
#include<signal.h>
int catch(int sig);
int main(void)
{
signal(SIGINT,catch);
printf("runing\n");
sleep(10);
printf("end\n");
return;
}
int catch(int sig)
{
printf("Catch succeed\n");
return 1;
}
当程序运行时按下中断键(Ctrl + C),进程被中断,函数catch被执行,执行完毕后,进程回到中断点继续执行。
当程序把一个信号处理函数与SGINT和SIGQUIT联系起来后,如果该程序在后台执行,那么由于shell的作用,会使得SIGINT和SIGQUIT被忽略,这样后台程序就不会被SIGINT和SIGQUIT所中止。
2. 在进程间发送信号
一个进程通过对signal()的调用来处理其它进程发给它的信号,同时,一个进程也可以向其它进程发送信号,这一操作是由系统调用kill()来完成的。
int kill(pid_t pid, int sig)
3. 系统调用alarm()
下面这个程序使用上述方法来强制用户作出回答。在其中包括一个quickreply()函数,它有一个参数prompt,它是一个指向提示字符串的指针。quickreply 的返回值也是一个指针。它指向含有输入行信息的字符串。这个例行程序在试作五次之后,如果仍未得到输入信息,就返回一个null 指针。每当quickreply 要提醒用户时,它就向终端发送ASCII 码007,
这会使终端响铃。
quickreply 调用了标准I/O 库中的例行程序gets()。gets()把标准输入上的下一行信息存入一个字符型数组,它返回一个指向该数组的指针。当到达文件末或出错时,gets 则返回一个null 指针。函数catch 是信号SIGALRM 的关联函数,它完成对此信号的处理。catch设置了一个timed_out 标志,在quickreply 中对这个标志进行检查,看它是否超过了规定的时限。
#include <stdio.h>
#include <signal.h>
#define TIMEOUT 5
#define MAXTRIES 5
#define LINESIZE 100
#define BELL '\007'
#define TRUE 1
#define FALSE 0
/* 判断超时是否已经发生的标志 */
static int time_out;
static char inputline[LINESIZE];
char* quickreply (char* prompt);
main()
{
printf("%s\n",quickreply("Input"));
}
char* quickreply (char* prompt)
{
int (*was)(),catch(),ntries;
char* answer;
/* 设定捕捉SIGALRM 的的关联并保存原有关联 */
was=signal(SIGALRM,catch);
for (ntries=0;ntries<MAXTRIES;ntries++)
{
time_out=FALSE;
printf("\n%s>",prompt);
/* 设定定时器 */
alarm(TIMEOUT);
/* 获取输入 */
answer=gets(inputline);
/* 关闭定时器 */
alarm(0);
if (!time_out)
break;
}
/* 恢复原有的SIGALRM 关联 */
signal(SIGALRM,was);
return (time_out?((char*) 0):answer);
}
/* SIGALRM 信号处理函数 */
catch()
{
/* 设定超时标志 */
time_out=TRUE;
/* 响铃警告 */
putchar(BELL);
}
本文介绍了如何使用信号处理函数在程序中捕获和响应中断信号,并展示了如何利用alarm系统调用实现用户输入的超时机制。此外,还讨论了如何在不同进程中发送信号。
770

被折叠的 条评论
为什么被折叠?



