当前位置:首页 > C > 正文

C语言命名管道详解(Linux下FIFO实现进程间通信的完整教程)

在Linux系统中,C语言命名管道(Named Pipe,也称为FIFO)是一种重要的进程间通信(IPC)机制。与匿名管道不同,命名管道拥有文件系统中的路径名,因此即使两个不相关的进程也可以通过它进行数据交换。本教程将手把手教你如何在C语言中创建、使用和管理命名管道,适合零基础的小白读者。

什么是命名管道?

命名管道(FIFO)是一种特殊类型的文件,它遵循“先进先出”原则。虽然它在文件系统中表现为一个普通文件(可通过 ls 查看),但其内容并不存储在磁盘上,而是缓存在内核缓冲区中。任何进程只要知道该FIFO的路径,就可以打开它进行读写操作,从而实现Linux IPC

C语言命名管道详解(Linux下FIFO实现进程间通信的完整教程) C语言命名管道  Linux IPC FIFO通信 进程间通信 第1张

创建命名管道

在C语言中,可以使用 mkfifo() 函数创建一个命名管道。该函数定义在 <sys/stat.h><fcntl.h> 头文件中。

#include <stdio.h>#include <sys/stat.h>#include <fcntl.h>#include <unistd.h>int main() {    // 创建名为 "myfifo" 的命名管道    if (mkfifo("myfifo", 0666) == -1) {        perror("mkfifo failed");        return 1;    }    printf("命名管道 myfifo 已创建!\n");    return 0;}  

编译并运行上述代码后,会在当前目录下生成一个名为 myfifo 的特殊文件。你可以用 ls -l 命令查看,其类型会显示为 p(表示pipe)。

使用命名管道进行通信

下面我们将编写两个程序:一个作为写端(writer),另一个作为读端(reader),演示如何通过命名管道实现FIFO通信

写端程序(writer.c)

#include <stdio.h>#include <fcntl.h>#include <unistd.h>#include <string.h>int main() {    int fd;    char *msg = "Hello from writer!";    // 打开命名管道用于写入    fd = open("myfifo", O_WRONLY);    if (fd == -1) {        perror("open failed");        return 1;    }    // 写入消息    write(fd, msg, strlen(msg) + 1);    printf("已发送消息: %s\n", msg);    close(fd);    return 0;}  

读端程序(reader.c)

#include <stdio.h>#include <fcntl.h>#include <unistd.h>int main() {    int fd;    char buffer[256];    // 打开命名管道用于读取    fd = open("myfifo", O_RDONLY);    if (fd == -1) {        perror("open failed");        return 1;    }    // 读取消息    read(fd, buffer, sizeof(buffer));    printf("收到消息: %s\n", buffer);    close(fd);    return 0;}  

测试通信流程

  1. 先在一个终端运行 ./reader(它会阻塞等待数据)
  2. 再打开另一个终端运行 ./writer
  3. 你会看到 reader 端立即打印出接收到的消息

注意:如果先运行 writer,它会阻塞直到有 reader 打开管道。这是 FIFO 的同步特性。

清理与注意事项

  • 使用完命名管道后,可以用 unlink("myfifo") 或直接 rm myfifo 删除它。
  • 命名管道是单向通信的。如需双向通信,需创建两个 FIFO。
  • 多个写者同时写入时,若每次写入小于 PIPE_BUF(通常4KB),则写入是原子的。

总结

通过本教程,你已经掌握了如何在 C 语言中使用命名管道(FIFO)实现进程间通信。无论是简单的命令行工具还是复杂的系统服务,FIFO 都是一种轻量且高效的通信方式。希望你能将所学应用到实际项目中,深入理解 Linux IPC 机制。

关键词回顾:C语言命名管道、Linux IPC、FIFO通信、进程间通信