管道文件

一、管道
1.定义:
管道是一种两个进程间进行单向通信的机制。因为管道传递数据的单向性,管道又称为半双工管道。 本质上,管道也是一种文件,但却和一般的文件有不同。
(单向:数据只能从一个进程到另一个进程,一个写管道,一个读管道)
2.不足:
1)管道的缓冲区大小是受限制的(缓冲区固定)。在Linux中,该缓冲区大小为1页(4K字节)
2)管道所传输的是无格式的字节流。这就需要管道输入方和输出方事先约定好数据格式。
3.通信方式:
通过管道通信的两个进程,一个进程向管道写数据,另外一个从中读数据。写入的数据每次都添加到管道缓冲区的末尾,读数据的时候都是从缓冲区的头部读出数据的。
一次性操作:对于管道文件指向的内存中存储数据一旦被读,它就从管道中被抛弃,释放空间以便写入更多数据。
4.分类:
管道分为有名管道和无名管道。
5.管道结构:
在Linux中,管道的实现没有专门的数据结构,而是借助于文件系统的file结构和VFS的索引节点iNode,将两个file结构指向同一个临时的VFS索引节点,而VFS 索引节点又指向一个物理页面而实现。
二、有名管道(name pipe或者FIFO)
1.定义: 利用管道文件实现进程间通讯,管道文件仅仅是磁盘上的一个文件标识,其真实数据存储在内存上。
2.创建:1)命令:mkfifo filename 2)函数:int mkfifo();
4. 有名管道(name pipe或FIFO):FIFO不同与管道之处在与她提供一个路径名与之关联,以FIFO的文件形式存储在文件系统中。有名管道是一个设备文件,因此,即使进程与创建FIFO的进程不存在亲缘关系,只要可以访问该路径,就能够通过FIFO相互通信了。值得注意的是FIFO(First In First Out)总是按照先进先出的原则工作,第一个被写入的数据首先从管道中读出。
对于管道文件的打开操作,必须有读有写,否则open函数阻塞;
三、无名管道
1.定义:相对于有名管道,其并不存在管道文件。
2.限制:无名管道能完成进程间通讯,必须借助于父子进程共享fork之前打开的文件描述符,因此,无名管道只能应用于父子进程之间的通讯。
3.int pipe(int pipefd[2]):无名管道两端分别用描述符pipefd[0]及pipefd[1]来描述。需要注意的是,管道两端的任务是固定的,一端只能用于读,有描述符pipefd[0]表示,称其为管道读端;另一端只能用于写,由描述符pipe[1]来表示,称其为管道写端。
#include<stdio.h>
#include<unistd.h>

int main()
{
int n,fd[2];//fd[]文件描述符的数组,用于创建管道
pid_t pid;
char line[100];
if(pipie(fd)<0)//创建管道
{printf(“pipe create error\n”);}
if( pid=fork() )< 0 )//fork创建新进程
{printf(“fork error\n”);}
else if(pid>0)//父进程:关闭管道的读端,在写端写入
{
close(fd[0]);
write(fd[1],“hello\n”,5);
}
else
{
close (fd[1]);//子进程:关闭写端,读出数据
n=read(fd[0],line,100);
write(STDOUT_FILENO,line,n);
}
return 0;
}

四、read函数
read函数对于普通文件是非阻塞运行的,但是对于管道文件其是一种阻塞运行的。
read函数返回的条件:1)管道中有数据;2)所有的写端关闭。

### Linux 管道文件的概念及用法 #### 什么是管道文件? 在 Linux 中,管道是一种用于进程间通信(Inter-Process Communication, IPC)的机制。它允许一个程序的标准输出被另一个程序作为标准输入读取。通常分为两种形式:匿名管道和命名管道。 - **匿名管道**:仅限于父子进程或兄弟进程之间使用,无法跨不相关的进程传递数据。 - **命名管道 (FIFO)**:通过文件系统提供接口,任何有权访问该文件的进程都可以进行通信[^2]。 #### 创建命名管道 可以通过 `mkfifo` 命令创建命名管道文件。语法如下: ```bash mkfifo pipe_name ``` 这将在当前目录下创建一个名为 `pipe_name` 的特殊文件,表示 FIFO 文件。 #### 使用示例 下面是一个简单的例子展示如何利用命名管道实现两个独立进程之间的通信。 ##### 步骤说明 假设我们有两个脚本分别负责写入和读取操作。 ###### 写入端 (`writer.sh`) ```bash #!/bin/bash echo "Hello from writer!" > my_pipe ``` 此脚本会向已存在的 FIFO 文件 `my_pipe` 发送消息。 ###### 读取端 (`reader.sh`) ```bash #!/bin/bash cat < my_pipe ``` 这个脚本则从同一个 FIFO 文件中接收并显示发送过来的消息。 为了运行上述代码,请先执行以下命令来建立必要的环境: ```bash mkfifo my_pipe chmod 666 my_pipe ``` 接着可以在不同的终端窗口启动这两个脚本观察效果。 #### 注意事项 尽管书中有提到“进程间最好使用 TCP”,但在某些场景下,比如本地轻量级应用或者受限环境下,命名管道可能更为合适。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值