实验八信号
1 实验目的
1.学习使用信号
2 实验内容
在实验一建立的 project 中,编写一段信号处理程序,将其与SIGINT 相关连,
使用kill()发送SIGINT 信号并调用信号处理程序。观察运行结果。
3 实验设备及工具
1.硬件:
a) PC 机
2.软件:
a) PC 机操作系统Windows2000 或windowsXP
b) Tornado2.2
4 实验原理
信号可以用来通知任务处理特定的事件。当引起一个信号的事件发生时,信号产生(generated)。当处理事件的任务激活时,信号释放(delivered)。信号的
生命期是从产生到释放之间的时间。一个已经产生但还没有释放的信号是挂起的(pending)。信号的生命期可能比较长。VxWorks 允许软件信号功能。信号将异步地改变任务的控制流。任何任务都可以向一个特定任务发送信号。被信号通知的任务立即挂起它当前的执行线程,在下次任务被调度运行的时刻,指定的信号处理程序将获得处理器。甚至尽管任务处于阻塞状态,其信号处理程序仍可以被调用执行。信号处理程序是由用户提供并与特定的信号相联系,用于执行当信号发生时必要的处理工作。信号适用于错误和异常处理,很少用于任务间通信。Wind 内核提供了两种信号接口:BSD4.3 和POSIX 信号接口。POSIX 接口提供比BSD4.3 接口更强大的标准接口。应用程序仅能使用其中一个。VxWorks 提供31 种不同的信号。程序可以调用kill()产生一个信号,与中断和硬件异常类似;调用sigaction()将信号与指定的信号处理程序相对应。当信号处理程序运行时,其他信号被阻塞。通过调用sigprocmask(),任务可以阻止一些信号的出现,如果当信号产生时被阻塞,它的信号处理程序将在信号解除阻塞时调用。信号处理程序通常定义形式为:
数据结构 struct sigaction 包含处理程序的信息,sigaction()含有三个参数:需要捕获的信号编号、指向新的处理数据结构的指针(类型为struct sigaction),指向旧的处理数据结构的指针(类型为struct sigaction)。如果程序不需要旧的处理数据结构的指针(*pOact),那么可以传递一个空指针NULL。当需要把一个信号发送给一个任务时,可以调用kill()函数,第一个参数是任务的id 号,第二个参数是欲发送信号。
5 实验步骤
1.编程(假设编写的源文件为s8_signal.c)
2.将s8_signal.c 添加到project 中
3.编译(如果有错误,则改正)
4.下载到VxSim 模拟器上运行,观察输出。
6 实验报告要求
1.写出实验过程
2.记录输出结果。
3.附上源程序
附C源程序如下:
1 #include"vxWorks.h" 2 #include"sigLib.h" 3 #include"taskLib.h" 4 #include"stdio.h" 5 6 SEM_ID semMutex; 7 int sigflag=0; 8 9 static void catchSIGINT(int signal) 10 { 11 logMsg("sigCatcher:i got this sig\n",0,0,0,0,0,0); 12 sigflag=1; 13 } 14 15 static void sigCatcher(void) 16 { 17 struct sigaction newAction; 18 int i; 19 20 newAction.sa_handler=catchSIGINT; 21 sigemptyset(&newAction.sa_mask); 22 newAction.sa_flags=0; 23 if(sigaction(SIGINT,&newAction,NULL)==-1) 24 logMsg("couldn‘t install signal handler.\n"); 25 logMsg("sigCatcher:install SIGINT handler success.\n"); 26 semGive(semMutex); 27 for(i=0;i<15;i++) 28 logMsg("sigCatcher:i am doing some work.\n"); 29 logMsg("sigCatcher: i exit.\n"); 30 31 } 32 33 void s8(void) 34 { 35 int i,j,taskId; 36 STATUS taskAlive; 37 semMutex=semBCreate(SEM_Q_PRIORITY,SEM_EMPTY); 38 if((taskId=taskSpawn("signal",100,0x100,20000, 39 (FUNCPTR)sigCatcher,0,0,0,0,0,0,0,0,0,0))==ERROR) 40 semTake(semMutex,WAIT_FOREVER); 41 logMsg("sigSender:i send SIGINT.\n"); 42 kill(taskId,SIGINT); 43 logMsg("sigSender:i exit.\n"); 44 }
运行的主要步骤如下: