- 进程间通信目的:
1.数据传输:一个进程需要将它的数据发送给另一个进程
2.资源共享:多个进程之间共享同样的资源
3.通知事件:一个进程需要向另一个或者一个组进程发送消息,通知它发生了某种事件
4.进程控制:有些进程希望完全控制另一个进程的执行,此时控制进程希望能够拦截另一个进程的所有陷入和异常,并能够及时知道它的状态改变。
管道:
1.匿名管道
2.命名管道
我们下面看看匿名管道:
匿名管道注意的点:
1.匿名管道只能应用于具有亲缘关系的两个进程之间
2.管道提供流式服务
3.进程退出,管道释放,管道的生命周期随进程
4.内核会对管道操作进行同步与互斥
5.管道是半双工的,数据只能向一个方向流动,需要双方通信时,需要建立起两个管道
命名管道:是一种特殊类型的文件,可以是任意两个进程之间通信
可以在命令行中创建:
mkfifo filename
也可以在程序中创建:
int mkfifo(const char *filename,mode_t mode);
下面是创建命名管道,进行文件的拷贝:
mkfifowrite.c
#include<stdio.h>
#include<unistd.h>
#include<stdlib.h>
#include<errno.h>
#include<string.h>
#include<fcntl.h>
int main()
{
mkfifo("tp",0644); //创建命名管道
int infd;
infd = open("abc",O_RDONLY); //打开文件
if(infd == -1)
{
perror("open\n");
exit(EXIT_FAILURE);
}
int outfd;
outfd = open("tp",O_WRONLY); //打开管道
if(outfd == -1)
{
perror("open\n");
exit(EXIT_FAILURE);
}
char buf[1024];
int n ;
while(( n = read(infd,buf,1024)) > 0) //进行写管道
{
write(outfd,buf,n);
}
close(infd);
close(outfd);
return 0;
}
mkfiforead.c
#include<stdio.h>
#include<stdlib.h>
#include<fcntl.h>
#include<string.h>
#include<unistd.h>
#include<errno.h>
int main()
{
int outfd;
outfd = open("abc.back",O_WRONLY | O_CREAT | O_TRUNC, 0644); //创建一个文件
if(outfd == -1)
{
perror("open \n");
exit(EXIT_FAILURE);
}
int infd;
infd = open("tp",O_RDONLY); //打开管道
if(infd == -1)
{
exit(EXIT_FAILURE);
}
char buf[1024];
int n;
while((n = read(infd,buf,1024))> 0) //从管道中读,写到文件中
{
write(outfd,buf,n);
}
close(infd);
close(outfd);
unlink("tp");
return 0;
}
管道是半双工的,在上面代码运行中,当我只运行写程序时,发现程序没有结束。这时在另一个窗口运行读程序时,两个程序同时结束。这充分说明了,管道中通信两方都必须是畅通的,否则管道使用失败。