管道(pipe)是一种单向且先进先出形式的通信方式,一个进程向管道的尾部写入数据,而另一个进程从管道的头部读出数据,所以把这种通信方式比喻成管子再合适不过了。
管道分为无名管道和有名管道两种
无名管道
名字上可以知道无名管道是没有标识的管道,其仅仅只能用于父子进程等具有血缘关系的进程通信,管道可以看成特定的文件,对于无名管道而言在文件系统中不可见,只存于内存中。
有名管道
有名管道算是无名管道的改进,由于无名管道通信限制较大,因此有名管道可以在任意两个进程中进行通信,该管道可以通过路径名来指出,且在文件系统中是可见的即管道文件,所以可以通过文件名或者路径来访问。
注意点:
1 ) 管道是固定大小的缓存区,在Linux中一般为1页,即4K内存空间,所以当管道满了使用write就会堵塞,等待读进程读取,以腾出空间写入。同理,read也是类似的,当管道为空的时候,使用read的进程也会堵塞,等待有进程写入。
2)Linux内核不保证管道读写的原子性,所以需要一些同步互斥机制进行灵活处理。
无名管道的简单使用
#include <stdio.h>
#include <unistd.h>
int main()
{
int pipe_fd[2];
if (pipe(pipe_fd) < 0)
{
printf("create pipe failed\n");
return -1;
}
else{
printf("create pipe success\n");
}
close(pipe_fd[0]);
close(pipe_fd[1]);
return 0;
}
结果:
VirtualBox:/media/sf_1/demo/pipe$ ./pipe
create pipe success
读无名管道:
#include <stdio.h>
#include <unistd.h>
int main()
{
int pipe_fd[2];
char recvbuff[50] = {0};
if(pipe(pipe_fd) < 0)
{
printf("create piep failed\n");
return -1;
}else{
printf("create pipe success\n");
}
write(pipe_fd[1],"hello pipe\r\n",13);
read(pipe_fd[0],recvbuff,50);
printf("read:%s\n",recvbuff);
close(pipe_fd[0]);
close(pipe_fd[1]);
return 1;
}
结果:
VirtualBox:/media/sf_1/demo/pipe$ ./pipe_wuming_read
create pipe success
read:hello pipe
有名管道通信: