Linux I/O及 I/O Cache

原创 2011年10月13日 18:16:35

总结一下平时使用的文件操作方法:

1. 通过标准c的库函数访问文件

2. 通过Linux系统调用访问文件

3. 通过内存映射(mmap)访问文件

其中,标准c的库函数里,实际也是调用了系统调用完成IO,但是库函数有自己的缓存机制。内存映射是将文件映射到虚存中的一块空间,将文件读写操作转变成了页交换操作。

默认情况下这三种方式都会使用文件系统的页缓存( page cache ),也就是说,数据会先被拷贝到操作系统内核的缓冲区中,然后才会从操作系统内核的缓冲区拷贝到应用程序的地址空间。缓存 I/O 有以下这些优点:

  • 缓存 I/O 使用了操作系统内核缓冲区,在一定程度上分离了应用程序空间和实际的物理设备。
  • 缓存 I/O 可以减少读盘的次数,从而提高性能
在缓存 I/O 机制中,DMA 方式可以将数据直接从磁盘读到页缓存中,或者将数据从页缓存直接写回到磁盘上,而不能直接在应用程序地址空间和磁盘之间进行数据传输,这样的话,数据在传输过程中需要在应用程序地址空间和页缓存之间进行多次数据拷贝操作,这些数据拷贝操作所带来的 CPU 以及内存开销是非常大的。


Linux 中的直接 I/O 技术非常适用于自缓存这类应用程序,该技术省略掉缓存 I/O 技术中操作系统内核缓冲区的使用,数据直接在应用程序地址空间和磁盘之间进行传输,从而使得自缓存应用程序可以省略掉复杂的系统级别的缓存结构,而执行程序自己定义的数据读写管理,从而降低系统级别的管理对应用程序访问数据的影响。例如,关系型数据库一般都会使用直接IO。

下面是一组实验数据:

读取1.7G的数据,各种文件读取方式的时间成本为:

1. 标准c的库函数fread():
首次读取: 14.756932 s
再次读取:1.930997 s

2. 通过Linux系统调用read()访问文件: 
首次读取:14.069852 s
再次读取:1.858485

3. 通过内存映射mmap()访问文件: 
首次读取11.798804 s
再次读取:2.101747 s

4. 通过Linux系统调用read(O_DIRECT)访问文件,访问方式为直接IO
首次读取14.1502176 s
再次读取:14.2386592 s

通过上述实验证实,read(O_DIRECT)的第二次读写没有使用缓存

篇外话:
文件的 page cache 结构
图1显示了一个文件的 page cache 结构。文件被分割为一个个以 page 大小为单元的数据块,这些数据块(页)被组织成一个多叉树(称为 radix 树)。树中所有叶子节点为一个个页帧结构(struct page),表示了用于缓存该文件的每一个页。在叶子层最左端的第一个页保存着该文件的前4096个字节(如果页的大小为4096字节),接下来的页保存着文件第二个4096个字节,依次类推。树中的所有中间节点为组织节点,指示某一地址上的数据所在的页。此树的层次可以从0层到6层,所支持的文件大小从0字节到16 T 个字节。树的根节点指针可以从和文件相关的 address_space 对象(该对象保存在和文件关联的 inode 对象中)中取得(更多关于 page cache 的结构内容请参见参考资料)。
图1 文件的 page cache 结构






对于我们用来做实验的K均值算法,是一个迭代的过程,当数据量超过集群总内存大小的时候,已经无法建立完整的缓存,新数据的缓存覆盖了旧数据的缓存,所以在当前迭代过程中,实际上并没有使用到上次迭代建立的缓存。


两条路:
1,使用直接IO,在应用程序中建立完全属于自己的缓存机制。缓存替换机制与应用相关。
2,深入内核,调整Page Cache的替换机制。

对于迭代式的应用,可以通过调整文件块的读取顺序,使下次迭代可使用到一部分本次迭代的缓存。
通过MPI-KMeans的实验,提高了近50%的速度。

Android网络框架Volley项目实战

-
  • 1970年01月01日 08:00

关于高速缓存和I/O高速缓冲的讲解

1. 磁盘高速缓存(Disk Cache) 操作系统中使用磁盘高速缓存技术来提高磁盘的I/O速度,对高速缓存复制的访问要比原始数据访问更为高效。例如,正在运行的进程的指令既存储在磁盘上,也存储在物理...
  • abel__ing
  • abel__ing
  • 2015-09-13 10:25:09
  • 1267

Linux 2.x 内核对内存的管理

Linux 2.x 内核对内存的管理 其着重点在于分页,用分页的机制把进程间的虚拟地址分隔开来。 每个进程都有一套页表,整个系统有一张GDT表(此机制由逻辑地址到线性地址变换,实际上是走了个形式...
  • yang_yulei
  • yang_yulei
  • 2014-04-24 23:44:31
  • 3060

搭建Ubuntu14.04编译环境并下载源码(二)

续上搭建Ubuntu14.04编译环境并下载源码(一) 今天临时买了个VPN的帐号,继续下载,翻墙的感觉还是不错的,推荐一下:http://a.wy002.com/385947 使用repo sy...
  • deng0zhaotai
  • deng0zhaotai
  • 2014-07-09 10:57:49
  • 9197

Linux系统安装Redis

Redis is an open source (BSD licensed), in-memory data structure store, used as database, cache and...
  • manmanxiaohui
  • manmanxiaohui
  • 2016-06-19 15:57:05
  • 495

Android视频/音频缓存框架AndroidVideoCache(Okhttp)

关于安卓边下边播功能对于视频/音频软件,音乐软件,视频软件,都有缓存这个功能,那如何实现边下边播功能: 如何实现这个边下边播功能? 文件是否支持同时读写?(Mediaplayer 播放文件,从网络上下...
  • CSDNno
  • CSDNno
  • 2016-07-27 23:17:16
  • 7486

fastdfs 安装配置所需的安装包

ngx_<em>cache</em>_purge-<em>2</em>.1.tar.gz pcre-8.34.tar.gz...Ev56<em>i</em>YXJiA9eX9SkE0gUAbeqH9yDV3X0-KRUsxGiQ<em>Fo</em>...fastdfs <em>linux</em>集群安装配置(详细流程) 立即下载 ...
  • 2018年04月03日 00:00

整理一下用得着的链接

http://www.embedworld.com/http://c-faq.com/Cross-Referencing Linux(基于lxr的linux源码阅读,emacs的etags不好使的时候...
  • dozec
  • dozec
  • 2006-07-20 17:17:00
  • 17862

Linux查看应用可用内存-free命令详解

Linux free命令详解,-buffers/cache反映的是被程序实实在在吃掉的内存,看应用可用内存看这个。...
  • loongshawn
  • loongshawn
  • 2016-06-25 13:18:27
  • 10487

Linux进程内核栈与thread_info结构详解--Linux进程的管理与调度(九)

日期 内核版本 架构 作者 GitHub CSDN 2016-06-03 Linux-4.5 X86 & arm gatieme LinuxDeviceDrive...
  • gatieme
  • gatieme
  • 2016-06-03 11:21:20
  • 6194
收藏助手
不良信息举报
您举报文章:Linux I/O及 I/O Cache
举报原因:
原因补充:

(最多只允许输入30个字)