进程间的通信之无名管道

it2025-01-30  13

从一个进程连接数据流到另一个进程时,就使用管道,通常是把一个进程的输出通过管道连接到另一个进程的输入。

1.pipe函数

该函数的原型为int pipe(int file_descritor[2]),其参数是一个由两个整数类型的文件描述符组成的数组的指针,该函数在数组中填上两个新的文件描述符后返回0,如果失败返回-1.两个文件描述符以一种特殊的方式连接起来,写到file_descriptor[1]的数据都可以从file_descriptor[0]读回来。数据基于先进先出的原则进行处理。

2.读写规则

管道两端可分别用描述字fd[0]以及fd[1]来描述,需要注意的是,管道的两端是固定了任务的。即一端只能用于读,由描述字fd[0]表示,称其为管道 读端;另一端则只能用于写,由描述字fd[1]来表示,称其为管道写端。如果试图从管道写端读取数据,或者向管道读端写入数据都将导致错误发生。一般文件 的I/O函数都可以用于管道,如close、read、write等等。

2.1从管道中读取数据

如果管道的写端不存在,则认为已经读到了数据的末尾,读函数返回的读出字节数为0; 当管道的写端存在时,如果请求的字节数目大于PIPE_BUF,则返回管道中现有的数据字节数,如果请求的字节数目不大于PIPE_BUF,则返回管道中现 有数据字节数(此时,管道中数据量小于请求的数据量);或者返回请求的字节数(此时,管道中数据量不小于请求的数据量)。

2.2向管道中写入数据

向管道中写入数据时,linux将不保证写入的原子性,管道缓冲区一有空闲区域,写进程就会试图向管道写入数据。如果读进程不读走管道缓冲区中的数据,那么写操作将一直阻塞。 注:只有在管道的读端存在时,向管道中写入数据才有意义。

3.read

read(fd,buf,nbyte) 功能:从fd所指示的文件中读出nbyte个字节的数据,并将它们送至由指针buf所指示的缓冲区中。如该文件被加锁,等待,直到锁打开为止。

4.write

write(fd,buf,nbyte) 功能:把nbyte个字节的数据,从buf所指向的缓冲区写到由fd所指向的文件中。如文件加锁,暂停写入,直至开锁。

5.sprintf

sprintf(str, format ) 功能:根据参数format 字符串来转换并格式化数据,然后将结果复制到参数str所指的字符串数组,直到出现字符结束(‘\0’)为止。

6.程序源码

创建文件 vi noNamepipe.c

#include<sys/types.h> #include<stdio.h> #include<unistd.h> #include<errno.h> #include<stdlib.h> #include<string.h> int main(void) { pid_t pid1; int fields[2]; char buffer[80]; char s[100]; char ss[100]; if(pipe(fields)!=0){ fprintf(stderr,"Createpipe error:%s\n\a",strerror(errno)); exit(1); } if((pid1=fork())<0)printf("fork child error!\n"); /* 子进程写入数据 */ if(pid1==0){ printf("fork child,child is sending a message !\n"); char s[]="hello!\n"; write(fields[1],s,sizeof(s)); exit(0) } /* 父进程读取数据 */ else { printf("parent read start !\n"); read(fields[0],buffer,80); printf("parent receive the message:%s",buffer); } exit (0); }

编译运行

cc -o unamepipe unamepipe.c -g ./unamepipe

参考:Linux程序设计第四版

最新回复(0)