Linux 进程通信之:管道 (Pipe)

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/afei__/article/details/84106493

一、简介

管道(pipe) 是一种最基本的 IPC(Inter Process Communication) 机制,优点是简单。

二、特点:

  1. 管道只适用于 存在血缘关系 的两个进程之间通信,因为只有存在血缘关系的两个进程之间才能共享文件描述符
  2. 管道分为两端,一端读,一端写,有两个文件描述符分别表示读端和写端
  3. 管道是单向的,数据从写端输入,从读端取出
  4. 管道的本质是一个伪文件(实为内核缓冲区)
  5. 管道有容量限制,2.6.11 版本之前的 Linux 内核管道容量为 page size(4 Kb),之后版本改为 65535 字节
  6. 当管道满时,写端将堵塞。当管道空时,读端将堵塞

三、API 说明

1. 头文件

#include <unistd.h>

2. 创建并打开管道

int pipe(int pipefd[2]);

3. 参数说明

pipefd[0] :读端的文件描述符
pipefd[1] :写端的文件描述符

4. 返回值说明

成功返回 0,失败返回 -1,并设置相应的 errno

四、示例

下面演示一个,父进程往管道写入数据,子进程从管道读出数据并输出到标准输出流。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/wait.h>
 
int main() {
    int pipe_fd[2]; // pipe_fd[0] 表示读端,pipe_fd[1] 表示写端
    pid_t child_pid;
    char buf[] = "Hello World";
 
    if (pipe(pipe_fd) == -1) { // 创建管道
        perror("pipe failed");
        exit(EXIT_FAILURE);
    }
 
    child_pid = fork(); // 创建一个子进程
    if (child_pid == -1) {
        perror("fork failed");
        exit(EXIT_FAILURE);
    }
 
    if (child_pid == 0) { // 根据 fork 的特点,child_pid 等于 0 表示子进程
        close(pipe_fd[1]); // 子进程从管道读数据,所以关闭写端
        while (read(pipe_fd[0], &buf, 1) > 0) { // 从读端读出数据
            write(STDOUT_FILENO, &buf, 1); // 写入到标准输出流显示
        }
        close(pipe_fd[0]);
        _exit(EXIT_SUCCESS);
    } else { // 根据 fork 的特点,child_pid 大于 0 表示父进程
        close(pipe_fd[0]); // 父进程从管道写数据,所以关闭读端
        write(pipe_fd[1], &buf, strlen(buf)); // 往写端写入数据
        close(pipe_fd[1]);
        wait(NULL); // 等待并回收子进程
        _exit(EXIT_SUCCESS);
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/afei__/article/details/84106493