实验二 进程控制
实验目的:
(1)理解进程的同步、互斥、撤消等控制方法
(2)熟悉进程间通过软中断传递控制信息的方法(低级通信)
实验仪器及材料:
微型计算机、红帽子Linux系统
实验内容:
任务1:并发进程间通过软中断传递控制信号,实现进程同步
#include<stdio.h>
#include<signal.h>
#include<unistd.h>
intwait_mark;
voidwaiting( ),stop( );
main( ){
intp1,p2;
while((p1=fork())==-1);
if (p1>0) { /*主进程的处理*/
while ((p2=fork())==-1);
if (p2>0) { /*主进程的处理*/
wait_mark=1;
signal(SIGINT,stop);/*预设对SIGINT信号的处理过程*/
waiting();/*等待接收ctrl+c信号*/
kill(p1,16);/*向p1发出信号16*/
kill(p2,17);/*向p2发出信号17*/
wait(0);/*同步*/
wait(0);
print(“parents is killed\n”);
exit(0);
}
else { /*p2进程的处理*/
wait_mark=1;
signal(17,stop); /*预设对17信号的处理过程*/
signal(2,1);/*忽略ctrl+c*/
waiting();/*等待信号17*/
lockf(stdout,1,0);/*用上锁的方法实现互斥*/
printf(“P2 iskilled by parent\n”);
lockf(stdout,0,0);
/*模拟P2被kill时进程的工作*/
exit(0);/*P2正常结束*/
}
}
else { /*p1进程的处理*/
wait_mark=1;
signal(16,stop);
signal(2,1);
waiting();/*等待信号16*/
lockf(stdout,1,0); /*用上锁的方法实现互斥*/
printf(“P1 iskilled by parent\n”);
lockf(stdout,0,0);
/*模拟P1被kill时进程的工作*/
exit(0); /*P1正常结束*/
}
}
voidwaiting()
{
while(wait_mark!=0);
}
voidstop()
{
wait_mark=0;
}
运行程序,观察运行结果,并分析。
涉及到的系统调用:
1、wait( )
等待子进程运行结束。如果子进程没有完成,父进程一直等待。wait( )将调用进程挂起,直至其子进程因暂停或终止而发来软中断信号将其唤醒为止。如果在wait( )前已有子进程暂停或终止,则调用进程做适当处理后便返回。
系统调用格式:
int wait(status)
int *status;
其中,status是用户空间的地址。它的低8位反应子进程状态,为0表示子进程正常结束,非0则表示出现了各种各样的问题;高8位则带回了exit( )的返回值。exit()返回值由系统给出。
2、exit( )
终止本进程的执行。
系统调用格式:
void exit(status)
intstatus;
其中,status是返回给父进程的一个整数,以备查考。
为了及时回收进程所占用的资源并减少父进程的干预,UNIX/LINUX利用exit( )来实现进程的自我终止,通常父进程在创建子进程时,应在子进程的末尾安排一条exit(),使子进程自我终止。exit(0)表示进程正常终止,exit(1)表示进程运行有错,异常终止。
如果调用进程在执行exit( )时,其父进程正在等待它的终止,则父进程可立即得到其返回的整数。
3、lockf( )
用作锁定文件的某些段或者整个文件。
本函数的头文件为:
#include "unistd.h"
系统调用格式:
int lockf(files,function,size)
int files,function;
long size;
其中:files是文件描述符;function是锁定和解锁:1表示锁定,0表示解锁。size是锁定或解锁的字节数,若为0,表示从文件的当前位置到文件尾。
4、kill( )
向一个或一组进程发送一个软中断信号。
系统调用格式:
int kill(pid,sig)
int pid,sig;
其中,pid是一个或一组进程的标识符,参数sig是要发送的软中断信号。
(1)pid>0时,核心会将信号发送给进程pid。
(2)pid=0时,核心会将信号发送给与发送进程同组的所有进程。
(3)pid=-1时,核心会将信号发送给所有用户标识符真正等于发送进程的有效用户标识号的进程。
5、signal( )
预置对信号的处理方式,允许调用进程控制软中断信号。
本函数的头文件为:
#include <signal.h>
系统调用格式:
signal(sig,function)
int sig;
void (*func) ( )
其中sig用于指定信号的类型,sig为0则表示没有收到任何信号。function是该进程中的一个函数地址,function 的解释如下:
(1)function=1时,进程对sig类信号不予理睬,亦即屏蔽了该类信号;
(2)function=0时,缺省值,进程在收到sig信号后应终止自己;
(3)function为非0、非1整数时,function的值即作为信号处理程序的指针。
思考:
1 在本程序中,进程的同步和互斥是如何实现的?
2 在本实验程序中调用lockf(),参数stdout指的是什么?
3 将子进程P1、P2的程序段改为2个独立的函数,设计好后给父进程调用,程序应该如何改写?(实验报告上给出完整的源码,并在机器上运行。)
Stty –a ;在linux下显示键盘的“键”与其输入信号的对应关系。