管道-fifo
来源:互联网 发布:红色复仇软件破解版 编辑:程序博客网 时间:2024/05/01 19:16
一. 简介
FIFO 又称为 named pipe、命名管道,用于在不相关的进程之间传递数据,可以通过命令行创建:
mkfifo filename
也可以通过程序创建:
int mkfifo(const char *filename, mode_t mode);
此外,还可以利用 mknod,但该命令非规范。
二. 实质
FIFO 是磁盘上一个真实的文件,可以像删除普通文件那样,在命令行用 rm 删除,在程序中用 unlink 删除。
使用 ls 查看结果如下:
prwxrwxrwx 1 rick users 0 XXXX-XX-XX XX:XX /named-pipe|
输出结果中第一个字符为 p,最后一个字符为 |。
三. 深入
FIFO 使用 open 和 close 打开和关闭(底层 IO 库的使用场景,虽然它们并不是 ANSI C 的一部分)。其最重要的内容,就是 open 操作。
1. 使用 open 打开 FIFO 时,不能使用 O_RDWR 模式,因为管道是单向的,如果被以读/写的方式打开,进程就会从这个管道读回它自己的输出。
2. 打开 FIFO 和打开普通文件的区别,在于对 open_flag 的O_NONBLOCK 选项的用法。有以下 4 种组合:
open(const char *path, O_RDONLY);
该模式下,open 调用将阻塞。当另一个进程以写方式打开同一个 FIFO 后,两个程序继续运行。读进程和写进程在 open 调用处取得同步。
open(const char *path, O_WRONLY);
此时 open 调用同样将阻塞,直到另一个进程以读方式打开同一个 FIFO。
open(const char *path, O_RDONLY | O_NONBLOCK);
即使没有其它进程以写方式打开该 FIFO,该 open 调用也将成功并立即返回。总是成功
open(const char *path, O_WRONLY | O_NONBLOCK);
该调用总是立即返回。如果已经有一个进程以读方式打开 FIFO,那么可以通过其返回的文件描述符操作该 FIFO。但如果没有进程以读方式打开 FIFO,该调用将返回 -1 错误。如果没有以读方式打开,则失败,如果已经以读方式打开,则成功
3. O_NONBLOCK 对读写的影响
对一个空的、阻塞的 FIFO(即没有用 O_NONBLOCK 方式打开) 的 read 调用将等待,直到有数据可以读时才继续进行。与此相反,对一个空的、非阻塞的 FIFO 的 read 调用将立刻返回 0。
对一个完全阻塞的 FIFO 的 write 调用将等待,直到数据可以写入。
即阻塞/非阻塞的原始含义
4. FIFO 的长度
系统对任一时刻在一个 FIFO 中可以存在的数据长度是有限制的,由 #define PIPE_BUF 定义,通常在 limits.h 文件中,一般为 4096。系统规定:在一个以 O_WRONLY 方式打开的 FIFO 中,如果写入的数据长度小于等于 PIPE_BUF,那么或者写入全部字节,或者一个字节都不写入。如果写入的数据长度大于 PIPE_BUF,将可能写入部分数据并返回写入的字节数,也可能无法写入任何数据,返回 0。
5. 竞争
如果同时有多个进程往一个 FIFO 中写,此时必须保证数据不相互交错或者覆盖。 FIFO 的机制可以保证不覆盖,在一个 PIPE_BUF 范围内也不会交错,唯一的问题是,多个 PIPE_BUF 之间有可能交错。系统确保,如果所有的写请求是发往一个阻塞的 FIFO,并且每个写请求的数据长度小于等于 PIPE_BUF 字节,那么数据就不会交错在一起。
四. 思考
1. 做过测试:读写进程分别打开 FIFO 后,在写进程 write() 成功、读进程尚未 read() 之前,发现磁盘上的 FIFO 大小仍然为 0。考虑到底层的文件操作并没有 flush() 命令,即使 close(),也不会做类似 flush() 的操作,因此,磁盘上的 FIFO 大小,是否一直为 0?也即,虽然可以把 FIFO 视为磁盘文件,但其实质并不是?
2. 关于 三 中的 4、5 两点,前提都是阻塞的 FIFO。对于非阻塞的情况都没有提到,那么,非阻塞的 FIFO 是什么情况?同时,是不是意味着,建议使用阻塞方式而不是非阻塞方式?
- FIFO管道
- 管道-fifo
- 管道,fifo
- FIFO 有名管道
- 管道和FIFO
- 有名管道FIFO实例
- FIFO 有名管道
- 管道,FIFO的实现
- IPC ------有名管道fifo
- linux 有名管道FIFO
- linux fifo 有名管道
- 有名管道FIFO
- Linux命名管道FIFO
- FIFO管道练习
- 2fifo有名管道
- UNIX命名管道FIFO
- FIFO管道问题
- 命名管道(FIFO)
- 七夕感怀
- iis6.0 显示service unavailable
- POJ 3692(匈牙利算法)
- rhel5 kdump
- 轻量级的jQuery表单验证插件 - HAPPY.js
- 管道-fifo
- 多租户技术在服务器端 multi-tenant
- nfs文件系统使用
- 使用diff和patch工具
- deep copy vs shallow copy
- Objective-C 2.0的运行时编程(转)
- 风的世界里有海的七滴泪水
- minimalcomps pushbutton
- __debugbreak()