版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/chengqiuming/article/details/89039787
一 点睛
pipe:建立管道。
表头文件
#include<unistd.h>
定义函数
int pipe(int filedes[2]);
函数说明
pipe()会建立管道,并将文件描述词由参数filedes数组返回。
filedes[0]为管道里的读取端,filedes[1]则为管道的写入端。
返回值 若成功则返回零,否则返回-1,错误原因存于errno中。
错误代码
- EMFILE:进程已用完文件描述词最大量。
- ENFILE:系统已无文件描述词可用。
- EFAULT:参数filedes数组地址不合法
二 父子进程使用管道通信
1 代码
#include <unistd.h>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <sys/wait.h>
void sys_err(const char *str)
{
perror(str);
exit(1);
}
int main(void)
{
pid_t pid;
char buf[1024];
int fd[2];
char p[] = "test for pipe\n";
if (pipe(fd) == -1) //创建管道
sys_err("pipe");
pid = fork(); // 创建子进程
if (pid < 0) {
sys_err("fork err");
}
else if (pid == 0) {
close(fd[1]); //关闭写描述符
printf("child process wait to read:\n");
int len = read(fd[0], buf, sizeof(buf)); //等待管道上的数据
write(STDOUT_FILENO, buf, len);
close(fd[0]);
}
else {
close(fd[0]); //关闭读描述符
write(fd[1], p, strlen(p)); //向管道写入字符串数据
wait(NULL);
close(fd[1]);
}
return 0;
}
2 运行
[root@localhost test]# g++ test.cpp -o test
[root@localhost test]# ./test
child process wait to read:
test for pipe
3 说明
首先创建一个管道,得到fd[0]和fd[1]两个读写描述符,然后用fork函数创建一个子进程,在子进程中,先关闭写描述符,然后开始读管道上的数据,而父进程中创建子进程后,就关闭读描述符,并向管道中写入字符串p。
三 read阻塞10秒后读数据
1 代码
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <fcntl.h>
int main(void)
{
int fds[2];
if (pipe(fds) == -1) {
perror("pipe error");
exit(EXIT_FAILURE);
}
pid_t pid;
pid = fork();
if (pid == -1) {
perror("fork error");
exit(EXIT_FAILURE);
}
if (pid == 0) {
close(fds[0]);//子进程关闭读端
sleep(10); //睡眠10秒
write(fds[1], "hello", 5); //子进程写数据给管道
exit(EXIT_SUCCESS);
}
close(fds[1]);//父进程关闭写端
char buf[10] = { 0 };
read(fds[0], buf, 10);//等待读数据
printf("receive datas = %s\n", buf);
return 0;
}
2 运行
[root@localhost test]# g++ test.cpp -o test
[root@localhost test]# ./test
receive datas = hello
3 说明
运行test后,等10秒,父进程就会读到数据了,可见read在管道中没有数据可读的时候,的确阻塞了调用进程(这里是父进程)。