管中窥道——我看Linux内核管道
来源:互联网 发布:网上企业信用数据库 编辑:程序博客网 时间:2024/05/16 14:59
管中窥道——记录Linux内核管道(2)
刺猬@http://blog.csdn.net/littlehedgehog
上节说了我对Linux管道的一点儿小见解,这节来看看内核中关于管道的实现代码。
以下代码摘自 Linux/include/fs.h
#define PIPE_HEAD(inode) ((inode).i_zone[0]) //这里定义了管道头
#define PIPE_TAIL(inode) ((inode).i_zone[1]) //呃,这里定义的管道尾
管道的头尾我们都定义了,大家回头来看看管道的size 的定义:
#define PIPE_SIZE(inode) ((PIPE_HEAD(inode)-PIPE_TAIL(inode))&(PAGE_SIZE-1))
这里用 (管道头-管道尾)%pagesize 取余数 从而取得了管道大小,关于这个取余数的问题,我在《求余不用模》 中已经详细阐释了这种方法的数学原理。但是这段代码最值得探讨的倒还不是这块内容。我们来看看管道的抽象图:
假设管道大小是4,(请注意管道大小必须要选择2n这种形式),我们看看上图如果管头指针指向3,而管尾指针指向的是1,那么管道的大小按照上面的算法,我们得出管道大小为2 (即是(3-1)&3),那么我们有理由说上图管道头的指针指向的3号元素其实是空的!而我们不妨再假设如果是管头指向的是1,而管尾指向的是3,那么按照上面的做法(1-3)&3,最后得出的是2,注意这里虽然是负数但是用这种办法仍然奏效。
说了这么多,其实可能有人早就注意到了管道是个队列的数组结构,而且还是队列的一种特殊形式——循环队列。
对于这种队列,我们通常空出了一个元素位置来表达队列是否已满。比如如果rear==front 则表示管道为空,如果为满的话就不能还用这个表示了,(不然我们如何区分究竟谁是满的谁是空的), 通常是在队头空出一个位置,比如这里我们就是用rear==front+1 表示已满!
回到内核代码中,看看Linus怎么定义的:
#define PIPE_EMPTY(inode) (PIPE_HEAD(inode)==PIPE_TAIL(inode))
#define PIPE_FULL(inode) (PIPE_SIZE(inode)==(PAGE_SIZE-1))
#define PIPE_FULL(inode) (PIPE_SIZE(inode)==(PAGE_SIZE-1))
- 管中窥道——我看Linux内核管道
- 管中窥道——我看Linux内核管道
- linux 内核管道通信
- Linux内核中的管道
- Linux——管道
- linux ipc—管道
- linux内核——从fork()看进程管理
- linux内核之进程间通信(1)——管道
- Linux内核学习8:进程间通信(1)——基本概念与管道通信
- 看Linux内核源码
- Linux 手册 —— 管道
- Linux程序设计——管道
- Linux内核源代码解析之——小弟我与神童聊Linux内核
- Linux进程间通信—无名管道和命名管道
- Linux — 管道与管道间通信详解
- linux内核管道pipe实现详解
- 我看我自己系列——看自己不嘚瑟
- 在看Linux内核书
- 在ASP.NET 中实现单点登录
- oracle sql plus命令大全
- 企业网站所起的作用
- 3种方式遍历Repeater中的CheckBox全选
- 北京奥运圣火传递路线(途经城市/时间)
- 管中窥道——我看Linux内核管道
- 网站设计技术规范
- Asp.net中实现同一用户名不能同时登陆(单点登陆)
- 第二人生的源码分析(五十九)字体类LLFont的实现
- 对php编译安装的修正
- Treeview的递归绑定
- 蛋白质翻译后修饰磷酸化位点预测工具 —— GPS 2.0
- 在Repeater控件中使用模版形成交叉颜色的表格。
- ASP.NET里的事务处理