1. Linux进程间通信概述
在Linux系统中,每个进程都运行在独立的地址空间中,彼此隔离,互不干扰。这种隔离机制确保了系统的稳定性和安全性,但也带来了一个问题:当多个进程需要协作完成某项任务时,它们如何交换数据和信息?这就是进程间通信(IPC)要解决的问题。
1.1 进程隔离与通信需求
Linux进程的隔离性体现在以下几个方面:
- 每个进程拥有独立的虚拟地址空间
- 进程不能直接访问其他进程的内存
- 进程间的资源(如文件描述符)默认不共享
然而,在实际应用中,进程协作的需求无处不在:
- 客户端/服务器架构中的进程通信
- 管道命令的数据传递(如
ls | grep) - 多进程应用程序中的数据共享
- 系统监控和管理工具的信息收集
1.2 IPC机制分类
Linux提供了多种IPC机制,可以根据通信方式和适用场景进行分类:
| 通信方式 | 特点 | 适用场景 |
|---|---|---|
| 管道 | 单向字节流,有亲缘关系进程 | 命令行管道、简单数据传递 |
| 命名管道 | 有名称的管道,无亲缘关系进程 | 持久化进程通信 |
| 信号量 | 计数器,用于同步 | 资源访问控制 |
| 共享内存 | 高效的内存共享 | 大数据量交换 |
| 消息队列 | 结构化的消息传递 | 异步通信 |
| 套接字 | 网络和本地通信 | 灵活跨主机通信 |
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 管道通信
2.1 匿名管道
匿名管道是Linux中最简单的IPC机制,具有以下特点:
- 单向通信,数据先进先出
- 只能用于有亲缘关系的进程(如父子进程)
- 随进程结束自动销毁
实现原理:
管道在内核中实现为一个环形缓冲区,通常大小为4KB。写端进程向缓冲区写入数据,读端进程从缓冲区读取数据。
关键API:
c复制int pipe(int pipefd[2]);
示例代码分析:
c复制#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
int main() {
int pipefd[2];
char buf[20];
if (pipe(pipefd) == -1) {
perror("pipe");
exit(EXIT_FAILURE);
}
pid_t pid = fork();
if (pid == 0) { // 子进程
close(pipefd[1]); // 关闭写端
read(pipefd[0], buf, sizeof(buf));
printf("Child received: %s\n", buf);
close(pipefd[0]);
} else { // 父进程
close(pipefd[0]); // 关闭读端
write(pipefd[1], "Hello Pipe!", 12);
close(pipefd[1]);
}
return 0;
}
注意事项:
- 管道默认是阻塞的,读空管道会阻塞,
