转载请注明t1234xy4原创:http://blog.csdn.net/t1234xy4/article/details/51317123
命名管道
命名管道相对于管道(pipe)有许多优点:
1、命令管道可以用于非父子关系的进程的通信;而pipe只能用于父进程创建子进程,然后进行通信,多用于shell命令。
2、命令管道是以文件的形式保存在文件中,因此可以提供给多个知道进程名字的进程通信。
3、命令管道又叫FIFO 使用mkfifo()创建。
简单的例子
client创建一个有名管道,server创建一个有名管道。client通过server的管道将自身的pid传送给server,server将通过client的管道返回值
server
//============================================================================
// Name : server.cpp
// Author : Tian
// Version :
// Copyright : Your copyright notice
// Description : Hello World in C++, Ansi-style
//============================================================================
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/ipc.h>
#include <sys/errno.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define MAXLINE 1024
#define FIFO_MODE (S_IRUSR | S_IWUSR | S_IRGRP |S_IROTH)
#define SERV_FIFO "/tmp/serv.fifo"
int main(int argc,char **argv) {
int readfifo,writefifo,dummyfd;
int fd;
char *ptr,buff[MAXLINE+1],fifoname[MAXLINE];
pid_t pid;
ssize_t n;
if( (mkfifo(SERV_FIFO,FIFO_MODE) < 0 ) && (errno != EEXIST) ) //创建
printf("can't create %s",SERV_FIFO);
readfifo = open(SERV_FIFO,O_RDONLY|O_NONBLOCK,0); // O_NONBLOCK不阻塞,否则可能会阻塞在此
dummyfd = open(SERV_FIFO,O_RDONLY|O_NONBLOCK,0);
while( (n = read(readfifo,buff,MAXLINE)) >=0 ){
if(n == 0)
continue;
if(buff[n-1] == '\n')
n--;
buff[n] = '\0';
if( (ptr = strchr(buff,'\0')) == NULL ){
printf("bogus request :%s",buff);
continue;
}
*ptr++ = 0;
pid = atol(buff);
snprintf(fifoname,sizeof(fifoname),"/tmp/fifo.%ld",(long)pid);
if( (writefifo = open(fifoname,O_WRONLY,0)) < 0){
printf("cannot open:%s",fifoname);
continue;
}
if( (fd=open(ptr,O_WRONLY,0)) < 0 ){
snprintf(buff+n,sizeof(buff)-n,":can't open,%s\n",strerror(errno));
n = strlen(ptr);
write(writefifo,ptr,n);
close(writefifo);
}else {
while( (n = read(fd,buff,MAXLINE)) > 0 )
write(writefifo,buff,n);
close(fd);
close(writefifo);
}
}
exit(0); //#include<fcntl.h>
}
client:
//============================================================================
// Name : server.cpp
// Author : Tian
// Version :
// Copyright : Your copyright notice
// Description : Hello World in C++, Ansi-style
//============================================================================
#include <iostream>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/ipc.h>
#include <sys/errno.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
using namespace std;
#define MAXLINE 1024
#define FIFO_MODE (S_IRUSR | S_IWUSR | S_IRGRP |S_IROTH)
#define SERV_FIFO "/tmp/serv.fifo"
int main(int argc,char **argv) {
int readfifo,writefifo;
char *ptr,buff[MAXLINE+1],fifoname[MAXLINE];
pid_t pid;
size_t len;
ssize_t n;
pid = getpid();
snprintf(fifoname,sizeof(fifoname),"/tmp/fifo.%ld",(long)pid);
if( (mkfifo(fifoname,FIFO_MODE) <0) && (errno!=EEXIST))
printf("can't create %s",fifoname);
snprintf(buff,sizeof(buff),"%ld",(long)pid);
len = strlen(buff);
ptr = buff+len;
//fgets(ptr,MAXLINE-len,stdin);
//len = strlen(buff);
writefifo = open(SERV_FIFO,O_WRONLY,0);
write(writefifo,buff,len);
readfifo = open(fifoname,O_RDONLY|O_NONBLOCK,0);
while((n = read(readfifo,buff,MAXLINE)) >= 0)
{
if(n == 0)
continue;
write(STDOUT_FILENO,buff,n);
}
close(readfifo);
unlink(fifoname);
exit(0);
}