我们知道SSD是一场存储革命,设计和制造一个好的SSD固然重要,但如何正确使用以充分发挥SSD性能同样重要。SSD内在的并行性和先擦再写的特性决定了它不同于机械硬盘简单的LBA和存储块一一对应,要充分挖掘SSD的并行性,提升性能,延长寿命,缩短延迟,就必须在上层应用做出改动。很多SSD的使用大户都作出了这种尝试,从国外的Google,Microsoft,Facebook,到国内的Baidu,Alibaba等,本站就曾经介绍过百度的软件定义闪存,把对象存储和SSD内部结构统一起来使用。但对大部分企业来讲,这种结构还是太独特了,我们还是要关注通用的架构,首先来了解离硬盘最近的软件:文件系统。本系列文章将以Linux系统最常见的EXT4文件系统为例,从SSD爱好者的角度来揭开文件系统的庐山真面目。
VFS架构
要说Linux文件系统,不得不说VFS:Virtual File System,如上图,Linux设计了一个文件系统的中间层,上层用户都直接和VFS打交道,文件系统开发者再把VFS转换为自己的格式。这样做的优点主要有:
- 用户层应用不用关心具体用的是什么文件系统, 使用统一的标准接口进行文件操作;
- 如果一个系统包含不同分区,不同分区使用不同的文件系统,他们之间可以通过这个VFS交互,比如从U盘、网盘拷数据到硬盘就得通过VFS转换管理信息,如下图;
- 可以动态支持很多文件系统,添加一个只需要安装驱动就可以了,不需要内核重新编译。
我们来看看这张文件系统层次图中的每一层。
- 用户层:最上面用户层就是我们日常使用的各种程序,需要的接口主要是文件的创建、删除、打开、关闭、写、读等。
- VFS层:我们知道Linux分为用户态和内核态,用户态请求硬件资源需要调用System Call通过内核态去实现。用户的这些文件相关操作都有对应的System Call函数接口,接口调用 VFS对应的函数。
- 文件系统层:不同的文件系统实现了VFS的这些函数,通过指针注册到VFS里面。所以,用户的操作通过VFS转到各种文件系统。文件系统把文件读写命令转化为对磁盘LBA的操作,起了一个翻译和磁盘管理的作用。
- 缓存层:文件系统底下有缓存,Page Cache,加速性能。对磁盘LBA的读写数据缓存到这里。
- 块设备层:块设备接口Block Device是用来访问磁盘LBA的层级,读写命令组合之后插入到命令队列,磁盘的驱动从队列读命令执行。Linux设计了电梯算法等对很多LBA的读写进行优化排序,尽量把连续地址放在一起。
- 磁盘驱动层:磁盘的驱动程序把对LBA的读写命令转化为各自的协议,比如变成ATA命令,SCSI命令,或者是自己硬件可以识别的自定义命令,发送给磁盘控制器。Host Based SSD甚至在块设备层和磁盘驱动层实现了FTL,变成对Flash芯片的操作。
- 磁盘物理层:读写物理数据到磁盘介质。
网络文件系统NFS把文件层之后的操作在远端实现。下面是NFS基本原理。
VFS组成
尽管Linux内核是C语言写的,但VFS是一种面向对象的框架,把文件相关的东西分为4个对象:
-
Superblock:一个文件系统有一个,含有文件系统的属性和接口,
- 属性:文件系统的一些参数;
- 接口:mount和umount接口等。
-
Inode:一个文件有一个,含有文件的属性和文件属性的接口(不是文件读写的接口)。文件夹也当成文件处理,有自己的inode。
- 属性:文件名,创建时间,修改时间,访问权限,文件保存的LBA等;
- 接口:创建,删除文件夹等。
-
Dentry :一个目录有一个,用来方便目录查找等。访问文件的时候,用户发下来文件路径,VFS通过Hash的方法直接通过路径查到最终Dentry,找到inode,来直接查找一个路径,而不是一级级翻下来。
- 属性:目录名等;
- 接口:查找文件路径等。
-
File :对文件进行操作的接口,这个是大家最熟悉的了,读写都通过它。
- 属性:文件锁,当前访问的偏移地址等;
- 接口:fopen,fclose,fwrite,fread,fsync,异步读写等。
这些对象平时保存在磁盘上,使用时加载到内存并给各种属性和接口赋值,同时inode和dentry都是有缓存的,这样每次查找一个路径,就不用等啊等啊读磁盘了,翻一下缓存就能快速找到。
下面是一个文件结构示例:
Unix风格文件
那么问题来了,挖掘机技术到底哪家强?有人要问,真的靠一个VFS能统一所有的文件系统操作吗?微软那么配合啊,会采用和Linux一样的接口?所以VFS要求文件系统要有Unix风格,主要是三种Style:
- 文件夹和文件都是一样的处理;
- 文件的信息和文件数据分开,文件信息放在inode里面,数据放在数据块里面;
- Superblock来表示文件系统的信息。
Windows的文件系统FAT,NTFS其实不太一致,有的文件信息不专门用inode来存,有的文件夹和文件区别开来,这些文件系统磁盘里面没有superblock,inode,需要在内存中生成inode和superblock来模拟。
引用
Robert Love, Linux Kernel Development.
https://swbae98.wordpress.com/tag/ext4/
想要每天看一条SSD文章吗?扫一扫,微信关注我们!或者微信搜索公众号ssdfans关注。