在前面介绍了无名管道的通信方式,无名管道主要用于具有亲缘关系的进程通信(包括父进程与子进程通信以及兄弟进程通信),本文介绍有名管道通信,那么可想而知,有名管道是用于任意两个进程之间的通信。
特点
- 可以实现任意两个互不相关的进程之间的通信;
- 有名管道创建后,对其操作类似于文件操作,可以使用read,open,write等操作,并且有名管道可以在文件路径下显示。有名管道的数据严格执行先进先出的规则。
下面是有名管道的应用实例
//有名管道的读取操作
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <stdlib.h>
#include <fcntl.h>
#include <limits.h>
#include <string.h>
/************************************
读取管道内容写到文件中去,进行保存
int mkfifo(const char *pathname, mode_t mode);创建管道函数
mode 指的是权限
int access(const char *pathname, int mode); 判断文件名是否存在
int open(const char *pathname, int flags); //两个参数的open
int open(const char *pathname, int flags, mode_t mode);//三个参数的open
flag的取值为 O_RDONLY, O_WRONLY, or O_RDWR.
read-only, write-only, or read/write, respectively.
**************************************/
int main()
{
char *file="datareadfrompipes.txt";//存管道读取的内容文件
char *fifo_name="name_fifo";//管道名称
int fd_fifo,fd_pipe,fd_data;
int byte_read,byte_acc;
char buffer[PIPE_BUF+1];
printf("Program writeread start run!!\n");
memset(buffer,'\0',sizeof(buffer));
fd_pipe=open(fifo_name,O_RDONLY);//打开管道
fd_data=open(file,O_WRONLY|O_CREAT,0777); //打开文件
printf("Current process pid is %d,pipe is %d\n",getpid(),fd_pipe);
if(fd_pipe!=-1)
{
do{
byte_read=read(fd_pipe,buffer,PIPE_BUF);
write(fd_data,buffer,byte_read);
byte_acc+=byte_read;
}
while(byte_read>0);
close(fd_pipe);
close(fd_data);
}
return 0;
}
- 上述程序主要实现的是从管道中实现从管道中读取数据,并将其存到datareadfrompipes.txt文件中,操作完全类似于文件的读写操作。
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <stdlib.h>
#include <fcntl.h>
#include <limits.h>
/************************************
将文件的内容读取,写到管道中去
int mkfifo(const char *pathname, mode_t mode);创建管道函数
mode 指的是权限
int access(const char *pathname, int mode); 判断文件名是否存在
int open(const char *pathname, int flags); //两个参数的open
int open(const char *pathname, int flags, mode_t mode);//三个参数的open
flag的取值为 O_RDONLY, O_WRONLY, or O_RDWR.
read-only, write-only, or read/write, respectively.
**************************************/
int main()
{
char *file="data.txt";
char *fifo_name="name_fifo";
int fd_fifo,fd_pipe,fd_data;
char buffer[PIPE_BUF+1];
int byte_acc;
printf("Program writepipes start run!!\n");
if(access(fifo_name,F_OK)==-1)//文件不存在 再创建管道
{
fd_fifo=mkfifo(fifo_name,0777);
if(fd_fifo==-1)
{
printf("Creat namefifo failed!!\n");
exit(EXIT_FAILURE);
}
else
printf("Creat namefifo sucess!!\n");
}
else
{
printf("Creat namefifo failed!!\n");
exit(EXIT_FAILURE);
}
fd_pipe=open(fifo_name,O_WRONLY);//打开管道
fd_data=open(file,O_RDONLY); //打开文件
printf("Current process pid is %d,pipe is %d\n",getpid(),fd_pipe);
if(fd_pipe!=-1) //管道读取成功一直循环
{
int read_byte=0,write_byte;
read_byte=read(fd_data,buffer,PIPE_BUF);
buffer[read_byte]='\0';
while(read_byte>0)
{
write_byte=write(fd_pipe,buffer,read_byte);
if(write_byte<0)
{
printf("write pipe failed!!\n");
exit(EXIT_FAILURE);
}
byte_acc+=write_byte;
read_byte=read(fd_data,buffer,PIPE_BUF);
buffer[read_byte]='\0';
}
close(fd_pipe);
close(fd_data);
}
return 0;
}
- 此程序实现有名管道的创建于数据的写入,采用acess函数实现函数的文件名的判断,若不存在创建管道,否则创建失败。创建完管道后的操作,就完全类似于文件的操作了。打开管道后,就可以向管道中写入数据了。