管道通信机制和消息缓冲机制.docx

上传人:李医生 文档编号:6124145 上传时间:2020-09-11 格式:DOCX 页数:14 大小:239.10KB
返回 下载 相关 举报
管道通信机制和消息缓冲机制.docx_第1页
第1页 / 共14页
管道通信机制和消息缓冲机制.docx_第2页
第2页 / 共14页
管道通信机制和消息缓冲机制.docx_第3页
第3页 / 共14页
管道通信机制和消息缓冲机制.docx_第4页
第4页 / 共14页
管道通信机制和消息缓冲机制.docx_第5页
第5页 / 共14页
点击查看更多>>
资源描述

《管道通信机制和消息缓冲机制.docx》由会员分享,可在线阅读,更多相关《管道通信机制和消息缓冲机制.docx(14页珍藏版)》请在三一文库上搜索。

1、实验题目管道通信机制和消息缓冲机小组合作否制姓名班级学号一、实验目的1、理解和掌握管道通信机制中使用的系统调用命令的格式和如何利用系统调用命令进行进程通信编程。2、理解和掌握消息缓冲机制中使用的系统调用命令的格式和如何利用系统调用命令进行进程通信编程。二实验环境1、 VMware Workstation工作平台2、 Linux 系统三、实验内容与步骤一、管道通信机制1、无名管道的通信(1)创建无名管道的格式#include#include#includeint pipe(int filedes2);正确返回: 0;错误返回: -1。(2)无名管道 pipe()的使用16.1、使用无名管道pip

2、e()进行父子进程之间的通信源程序代码如下:#include#include#includeint pipe(int filedes2);char parent=A message to pipecommunication.n; main()int pid,chan12;char buf100;pipe(chan1);pid=fork();if(pid0)close(chan10);printf(parent process sends a message to child.n); write(chan11,parent,sizeof(parent); close(chan11);printf

3、(parent process waits the child to terminate.n); wait(0);printf(parent process terminate.n);elseclose(chan11);read(chan10,buf,100);printf(The message read by child process from parent is:%s.n,buf);close(0);printf(child process terminaten);实验运行结果如图所示:2、以命令行为参数的管道通信(1)命令格式#include#include#includeFiLe

4、popen(const char cmdstring,const char type);(2)打开一个以命令行为参数的管道文件,完成进程之间的通信16.2、以命令行为参数的管道文件的示例假设有一个可执行程序chcase,从标准输入设备读字符,将小写字母转换成大写字母并进行输出。主程序使用 popen 创建管道,实现将某文本文件中的字母转换成大写字母,期中的文本文件名作为参数传进来。源程序代码如下:#include#include#define MAXLINE 100int main(int argc,char*argv)char lineMAXLINE;FILE*fpin,*fpout;if(

5、argc!=2)fprintf(stderr,usage:a.outn);exit(1);if(fpin=fopen(argv1,r)=NULL)fprintf(stderr,cant open%sn,argv1);exit(1);if(fpout=popen(/root/LiFang/chcase.exe,w)=NULL)fprintf(stderr,popen errorn);exit(1);while(fgets(line,MAXLINE,fpin)!=NULL)if(fputs(line,fpout)=EOF)fprintf(stderr,fputs error to pipe.n);

6、exit(1);if(ferror(fpin)fprintf(stderr,fgets error.n);exit(1);if(pclose(fpout)=-1)fprintf(stderr,pclose error.n);exit(1);exit(0);实验运行结果如下图所示:3、有名管道的通信(1) 创建一个有名管道的系统调用mknod()#include#include#include#includeint mknod (const char * pathname,mode_t mode ,dev_t dev);(2) 打开一个有名管道open(pathname,oflg);(3)有名管

7、道的使用16.3、创建有名管道的例子源程序代码如下:#includechar string=this is a example to show fifo communication; main(argc,argv)int argc;char * argv;int fd;char buf256;int i;mknod(fifo,010777,0);if(argc=2)fd=open(fifo,O_WRONLY);elsefd=open(fifo,O_RDONLY);for(i=0;i26;i+)if(argc=2)printf(n I have wrote:%s,string);write(fd

8、,string,45);string0+=1;elseread(fd,buf,256);printf(nThe context by I have read is:! %s,buf);buf0=0;close(fd);试验运行结果如下图所示:二、消息缓冲机制1、消息缓冲机制使用的数据结构(1)消息缓冲区struct msgbuflong mtype;char mtextN;(3) 消息头结构struct msgstruct msg * msgnext;long msgtype;short msgts;short msgspot;2、消息缓冲的系统调用(1)建立一个消息队列#include #i

9、nclude #include int msqid=msgget(key_t key,int msgflg);(2)向消息队列发送消息#includeint msgsnd(int msqid,void * msgp,size_t msgsz,int msgflg);(3)接收消息#includeint msgrcv(int msqid,void msgp,size_t msgsz,long msgtyp,int msgflg);(4) 取或送消息队列的控制信息#includeint msgctl(int msqid,int cmd,struct msqid_ds * buf);3、利用消息缓冲

10、机制的通信过程16.4创建一个私有消息队列,一个进程自己发送消息和接收消息。源程序代码如下图所示:实验运行结果如下图所示:16.5创建一个公共消息队列, 实现客户进程和服务者进程之间进行通信源程序代码如下:客户进程:#include #include #include #define REQ 1#define SVKEY 75struct msgformlong mtype;char mtext256;main()struct msgform msg;int msqid,pid,* pint;msqid=msgget(SVKEY,0777);pid=getpid();pint=(int *)m

11、sg.mtext;*pint=pid;msg.mtype=REQ;msgsnd(msqid,&msg,sizeof(int),0);msgrcv(msqid,&msg,256,pid,0);printf(client received servers service result is servers pid: %d .n,*pint);服务者进程:#include #include #include #define REQ 1#define SVKEY 75int msqid;struct msgformlong mtype;char mtext256;main()struct msgfor

12、m msg;int i,pid,* pint;msqid=msgget(SVKEY,0777|IPC_CREAT);for(; ;)msgrcv(msqid,&msg,256,REQ,0);printf(server is doing the service for a client. n);pint=(int *)msg.mtext;pid=* pint;printf(server receive clients service request is clientspid: %d .n,pid);msg.mtype=pid;* pint=getpid();msgsnd(msqid,&msg,

13、sizeof(int),0);试验运行结果如下图所示:四、实验过程与分析分析:1、无名管道的通信父进程先使用 pipe(chan1)系统调用打开一个无名管道, 之后创建一个子进程。子进程复制父进程的打开文件表。为了正确通信,父进程关闭读通道 close(chan10),子进程分别关闭写通道close(chan11)。父进程向管道写,子进程从管道读。完成一次通信后,父进程分别关闭自己的写或者读通道,管道文件消失。次进程先运行父进程,父进程向无名管道写一条消息,此时父进程等待子进程从管道读取消息,直到子进程结束,最后父进程结束。2、以命令行为参数的管道通信本程序先运行 chcase.c程序,生成

14、chcase.exe可执行文件,次程序的目的是将小写字母转换成大写字母,主程序先打开文本文件,通过popen创建一个可写管道, 将命令行的 chcase的输入与管道的输出连接起来,然后向管道输入数据,那么,命令行就可以通过管道连接收文本文件的数据了,可实现将文本文件中的小写字母转换成大写字母。3、有名管道的通信进程间使用有名管道实现通信时,必须有三次同步。 第一次是打开同步。当一个进程以读方式打开有名管道时,若已有写者打开过,则唤醒写着后继续前进,否则,睡眠等待写者。当一个进程以写方式打开有名管道时,若以有读者打开过,则唤醒读者继续前进,否则等到读者。第二次是读写同步。其同步方式与pipe 相

15、同。允许写者超前读者 1024 个字符。当一次写超过1024 时,超前的字符要写入时,超前的字符要写入时,则写者必须等待,读者从有名管道时,若没有可读则等待。若有数据可读,读完后要检测有无写者等待。若有唤醒写者。而且要求读写两方面随时检查通信的另一方是否还存在,一旦有一方不存在,应立即终止通信过程。第三次是关闭同步。当一个写进程关闭有名管道时,若发现有进程睡眠等待从管道读,则唤醒它,被唤醒进程立即从读调用返回。当一个读进程有名管道时, 若发现有进程睡眠等待向管道写, 则唤醒它,并向他发一个指示错误条件的信号后返回,最后一个关闭有名管道的进程,释放该管道占用的全部盘块及相应主存 i 节点。有名管

16、道打开后, 就可以使用读写命令进行读写, 读写完成后就立即关闭。有名管道文件关闭后,文件本身并没有消失。有名管道的读写和关闭动作与普通文件完全相同。4、利用消息缓冲机制的通信过程该进程创建了一个公共消息队列, 实现客户进程和服务进程之间进行通信。客户进程向服务进程发送消息,请求服务,服务进程接收消息,完成客户的服务请求后,再将服务结果消息发送给客户。具体实现描述为:服务进程用关键字 SVKEY 和标志 IPC_CRAT 调用 msgget()建立一个消息队列,得到其队列标识符 msqid 之后,用 msqid 调用 msgrcv() 接收类型为 REQ 的消息。客户进程用关键字 SVKEY 调

17、用 msgget()得到消息队列标识符 msqid,之后用 msqid 调用 msgsnd()将自己的 pid 发送到消息队列( SVKEY )中,表示其所请求的服务。然后调用 msgrcv()等待服务结果消息的到来。服务者进程接收到请求服务的消息后进行服务工作, 完成服务后向客户进程发回一条消息,消息类型为客户的标识 pid,消息正文是服务进程自己的标识 pid。五、实验总结通过本次实验,我掌握了 UNIX和 LINUX进程通信系统的调用的功能。理解了 UNIX和 Linux 操作系统进程通信的系统调用。最终学会如何利用系统调用命令进行进程通信编程, 通过学习,提高对进程之间可通过系统的编程能力,最后在老师的指导下顺利地完成了本次的实验。

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 科普知识


经营许可证编号:宁ICP备18001539号-1