进程间通信--管道

来源:互联网 发布:python turtle教程视频 编辑:程序博客网 时间:2024/06/06 00:25

概述

管道是最初的Unix 进程间通信(IPC)的方式,它的局限在于没有名字(有名管道FIFO下节讲),从而只能由有亲缘关系的进程间使用,例如父子进程。管道和FIFO都是使用read和write函数访问的。
管道由pipe函数创建,提供一个单向的数据流

#include <unistd.h>int pipe(int pipefd[2]);

函数返回两个文件描述符,fd[0]和fd[1],0用于读,1用于写。
调用pipe函数会在内核中开辟一块缓存区用于通信,一个读端,一个写端,fd[0]指向读端,fd[1]指向写端。
父子进程如何通过管道实现通信?
1、父进程调用pipe开辟管道,得到两个文件描述符指向管道的两端;
2、父进程调用fork创建子进程,子进程有两个文件描述符指向同一管道;
3、父进程关闭读端,子进程关闭写端。父进程可以往管道里写,子进程可以从管道里读,数据从写端流入,从读端流出,这样就实现了进程间通信。
fork完成之后:
fork完成之后
关闭父进程读端、子进程写端,形成半双工(单向)数据流
关闭父进程读端、子进程写端,形成半双工(单向)数据流

//#include "stdio.h"#include "stdlib.h"#include "unistd.h"#include "errno.h"#include "string.h"int main(){    int _pipe[2];    int ret=pipe(_pipe);    if(ret==-1)//    {        printf("creat pipe error!errno code is:%d\n",errno);        return 1;    }    pid_t id = fork();    if(id<0)    {        printf("fork error!");        return 2;    }    else if(id==0)//child    {        close(_pipe[1]);        char _mesg[100];        int j=0;        while(j<6)        {            memset(_mesg,'\0',sizeof(_mesg));            int res = read(_pipe[0],_mesg,sizeof(_mesg));            printf("%d_%s strlenth is:%d\n",j,_mesg,res);            j++;        }    }    else{//father        close(_pipe[0]);        int i=0;        char* _mesg_c=NULL;        while(i<6)        {            _mesg_c="i im coder";            write(_pipe[1],_mesg_c,strlen(_mesg_c)+1);            sleep(1);            i++;        }    }    return 0;}

运行结果:
这里写图片描述

管道通信的四中特殊情况:
1、所有指向管道写端的文件描述符都关闭了,仍有进程从管道的读端读取数据,当管道中剩余的数据都被读取之后,再次读取时会返回0,就像读到文件末尾一样;
2、指向管道写端的文件描述符没关闭,持有管道写端的进程也没有向管道中写数据,这是有进程从管道的读端读取数据,当管道剩余的数据都被读取后,再次读取进程会阻塞,直到管道中有数据可读了才读取数据并返回;
3、如果指向管道读端的文件描述符都关闭了,这是有进程向管道的写端写入数据,该进程会收到SIGPIPE,会导致进程异常终止;
4、如果指向管道读端的文件描述符没关闭,而持有管道读端的进程也没有从管道中读数据,这时有进程向管道写端写数据,在管道被写满时再次写入会阻塞,直到管道中有空位置了才写入数据并返回。

管道通信的特点:
1、管道是半双工的,只能支持数据的单向流动;两进程间需要通信时需要建立起两个管道;
2、无名管道使用pipe()函数创建,只能用于父子进程或者兄弟进程之间;
3、管道对于通信的两端进程而言,实质上是一种独立的文件,只存在于内存中;
4、数据的读写操作:一个进程向管道中写数据,所写的数据添加在管道缓冲区的尾部;另一个进程在管道中缓冲区的头部读数据。

参考:
1、http://www.cnblogs.com/MrListening/p/5858358.html
2、http://760470897.blog.51cto.com/10696844/1763616

原创粉丝点击