Linux 的虚拟文件系统
11/03/09 OS嵌入式 2/31
提纲
虚拟文件系统 VFS的作用VFS的数据结构文件系统类型文件系统安装路径名查找VFS系统调用的实现文件加锁
11/03/09 OS嵌入式 3/31
虚拟文件系统 VFS的作用
虚拟文件系统Virtual FilesystemVirtual Filesystem SwitchVFS是一个软件层,用来处理与 Unix标准文件系统相关的所有系统调用。是用户应用程序与文件系统实现之间的抽象层
能为各种文件系统提供一个通用的、统一的接口Linux与其他类 Unix系统一样,采用虚拟文件系统 VFS来达到支持多种文件系统格式的目标
11/03/09 OS嵌入式 4/31
VFS在一个简单文件复制操作中的作用
假设用户输入以下 shell命令$ cp /floppy/TEST /tmp/test 其中,
/floppy是MS-DOS的磁盘的一个挂载点(安装点) /tmp是 Ext2文件系统中的一个目录
对于 cp命令而言,它不需要知道 /floppy/TEST和 /tmp/test分别是什么文件系统类型在 cp命令中,它通过 VFS提供的系统调用接口进行文件操作
11/03/09 OS嵌入式 5/31
11/03/09 OS嵌入式 6/31
VFS支持的文件系统类型
VFS支持的文件系统可以划分为三种主要类型 基于磁盘的文件系统:它们管理在本地磁盘分区中可用的存储空间
Linux使用的文件系统: ext2、 ext3、 ReiserFSUnix家族的文件系统: SYSV文件系统, UFS,MINIX文件系统以及 VERITAS VxFS
微软公司的文件系统:MS-DOS、 VFAT以及 NTFSISO9660CD-ROM文件系统和通用磁盘格式的 DVD文件系统其他有专利权的文件系统,如 HPFS、 HFS、 AFFS、 ADFS起源于非 Linux系统的其他日志文件系统, JFS, XFS
11/03/09 OS嵌入式 7/31
网络文件系统:用于访问属于其他网络计算机的文件系统所包含的文件
NFS、 Coda、 AFS、 SMB、 NCP 特殊文件系统
不同于上述两大类不管理具体的磁盘空间/proc
各种不同的文件系统通过mount(挂载、安装)到根文件系统中 在 Linux中,根文件系统即根目录所代表的文件系统 通常是 ext2文件系统
11/03/09 OS嵌入式 8/31
VFS中通用文件模型概念
VFS的基本思想:引入一个通用文件模型,这个模型能够表示所有支持的文件系统对于一个具体实现的文件系统,在处理时,需要将其进行概念上的转换例如,在通用文件模型中,目录被看成是普通文件
在实现上,
read()sys_readfile数据结构 f_opMS_DOS文件操作指针(其中的 read操作)类似面向对象的概念
11/03/09 OS嵌入式 9/31
通用文件模型有下列对象类型组成超级块对象( superblock object)
存放文件系统相关信息:例如文件系统控制块索引节点对象( inode object)
存放具体文件的一般信息:文件控制块 /inode文件对象( file object)
存放已打开的文件和进程之间交互的信息目录项对象( dentry object)
存放目录项与文件的链接信息
11/03/09 OS嵌入式 10/31
三个不同的进程打开同一个文件
两个不同的硬链接
同一个硬链接
11/03/09 OS嵌入式 11/31
VFS所处理的系统调用
mount、 umount:挂载 /卸载文件系统 sysfs :获取文件系统信息 statfs、 fstatfs、 ustat :获取文件系统统计信息 chroot :更改根目录 chdir、 fchdir、 getcwd :操纵当前工作目录 mkdir、 rmdir :创建 /删除目录 getdents、 readdir 、 link 、 unlink 、 rename :对目录项进行操作
readlink 、 symlink :对符号链接进行操作 chown 、 fchown 、 lchown :更改文件所有者 chmod 、 fchmod 、 utime :更改文件属性 open、 close、 create …
11/03/09 OS嵌入式 12/31
上述大部分操作之需要与通用文件模型中的一些对象打交道,而不需要真正操作具体的文件系统和文件,因此可以把 VFS “ ”看成是一个 通用 的文件系统,在必要时依赖某种具体的文件系统
11/03/09 OS嵌入式 13/31
VFS的数据结构
每个 VFS对象都对应一定的数据结构,在这个数据结构中包含对象的属性及其方法
一个具体的文件系统:超级块对象: super_block所有超级块链表: super_blocks : s_list域文件系统特有信息: s_fs_info域脏标志: s_dirt域文件系统特有方法: super_operations数据结构及域
include/linux/fs.h
11/03/09 OS嵌入式 14/31
一个具体的文件: Inode对象: inode Inode特有的方法
目录项对象: dentry
一个打开文件:文件对象: file文件操作指针 f_pos文件对象特有的方法
专用高速缓存 “: filp” , filp_cachep
include/linux/fs.h
include/linux/dcache.h
include/linux/fs.h
11/03/09 OS嵌入式 15/31
11/03/09 OS嵌入式 16/31
11/03/09 OS嵌入式 17/31
与进程相关的文件
文件系统相关信息 fs_struct打开文件相关信息 files_struct
include/linux/fs_struct.h
include/linux/path.h
11/03/09 OS嵌入式 18/31
include/linux/fdtable.h
include/linux/fdtable.h
include/linux/types.h
include/linux/posix_types.h
11/03/09 OS嵌入式 19/31
11/03/09 OS嵌入式 20/31
文件系统类型
特殊文件系统用来为系统程序员、系统管理员等提供一种容易的方式来操作内核的数据结构并实现操作系统的特殊特征
常用的特殊文件系统
11/03/09 OS嵌入式 21/31
11/03/09 OS嵌入式 22/31
文件系统类型的注册
文件系统类型: file_system_type
在系统初始化期间, register_filesystem()用来注册编译时指定的每个文件系统相应的文件系统对象被插入到 file_systems链表中
unregister_filesystem()
11/03/09 OS嵌入式 23/31
文件系统的挂载
根文件系统在系统初始化过程中被直接 mount提供系统初始化脚本以及基本命令
每个文件系统都有自己的根目录如果一个文件系统的根目录是系统目录树的根目录,那个这个文件系统就是根文件系统
其他文件系统可以挂载到系统的目录树上这样的目录称为挂载点( mount点,安装点)
文件系统之间的挂载关系对应文件系统之间的父子关系
11/03/09 OS嵌入式 24/31
例如,放在软盘 /dev/fd0上的 ext2文件系统,可通过下列命令安装在 /flp上
mount -t ext2 /dev/fd0 /flp 一般情况下,只允许挂载一次在 umount之前,其他对 /dev/fd0的挂载命令会失败
在 2.4中,可以挂载多次不管被挂载多少次,只有一个真实的文件系统,因此只有一个超级块对象
11/03/09 OS嵌入式 25/31
已挂载文件系统描述符 vfsmount
挂载根文件系统第一阶段:安装一个特殊的文件系统,该文件系统仅提供一个作为初始安装点的空目录: init_mount_tree
第二阶段: mount_root挂载一个文件系统
sys_mount卸载一个文件系统
sys_umount
11/03/09 OS嵌入式 26/31
路径名查找
VFS是如何从文件路径名找到相应的索引节点的?分析路径名,将它拆分成一个文件名序列除了最后一个文件名之外,其他所有文件名必定都是目录名
搜索的起点:绝对路径: currentfsroot相对路径: currentfspwd
11/03/09 OS嵌入式 27/31
首先找到起点目录的索引节点在这个索引节点的目录文件中,找到第一个目录名(文件名)所对应的索引节点
在第一个目录名的索引节点的目录文件中找到第二个目录名(文件名)所对应的索引节点
…反复,直到文件名序列的最后一项
11/03/09 OS嵌入式 28/31
在上述查找过程中要处理的其他问题:对每个目录的访问权限必须进行检查若是符号链接,需要进行扩展要考虑符号链接的循环引用(进行处理)目录名可能是一个文件系统的安装点,必须扩展到一个新的文件系统中
路径名查找数据结构: struct nameidata在需要进行路径名查找的时候,依此调用如下函数: path_init, path_walk, path_release
11/03/09 OS嵌入式 29/31
查找操作的标志
11/03/09 OS嵌入式 30/31
标准查找操作
要处理的问题跳过第一个路径名分量前的任何 /考虑符号链接的查找检查权限 “考虑 .” “考虑 ..”考虑普通目录,要在目录项高速缓存中查找…
11/03/09 OS嵌入式 31/31
父路径名的查找
在很多情况下,查找操作的真正目的不是路径名的最后一个分量,而是最后分量的前一个分量例如创建一个文件时此时,路径解析的结果中存放最后一个分量所在目录对应的对象
11/03/09 OS嵌入式 32/31
符号链接的查找
关于符号链接的解析由内核来完成
如何识别这是一个符号链接?如何处理符号链接的循环情况?
11/03/09 OS嵌入式 33/31
VFS系统调用的实现
仍然考虑$ cp /floppy/TEST /tmp/test假定 cp执行下列代码片段(实际要更复杂)
inf = open("/floppy/TEST", O_RDONLY, 0); outf = open("/tmp/test", O_WRONLY | O_CREAT | O_TRUNC, 0600); do {
len = read(inf, buf, 4096); write(outf, buf, len);
} while (len); close(outf); close(inf);
11/03/09 OS嵌入式 34/31
open()系统调用 sys_open
read和 write系统调用 sys_write sys_read
close系统调用 sys_close
Ext2 文件系统简介
11/03/09 Linux OS analysis 36/31
EXT2文件系统是 EXT文件系统的升级,在Linux中得到了广泛的使用。
介绍 EXT2文件系统的磁盘组织目录项和支持的文件类型
11/03/09 Linux OS analysis 37/31
(一) EXT2 文件系统的磁盘组织
除了引导扇区之外, EXT2磁盘分区被顺序划分为若干个磁盘块组( Block Group)。
每个块组由若干个磁盘块,按照相同的方式组织,具有相同的大小。
EXT2磁盘块组中的磁盘块按顺序被组织成: 一个用作超级块的磁盘块。
在这个磁盘块里,存放了文件系统超级块的一个拷贝; N个记录组描述符的磁盘块; 1个记录数据块位图的磁盘块; 1个记录索引结点位图的磁盘块; N个用作索引结点表的磁盘块; N个用作数据块的磁盘块。
11/03/09 Linux OS analysis 38/31
EXT2的超级块
每个块组的第一个磁盘块用来保存所在 EXT2 fs的超级块
多个块组中的超级块形成冗余在某个或少数几个超级块被破坏时,可用于恢复被破坏的超级块信息。
11/03/09 Linux OS analysis 39/31
超级块
11/03/09 Linux OS analysis 40/31
11/03/09 Linux OS analysis 41/31
Linux 2.4.18中在内存中记录 ext2超级块的数据结构
11/03/09 Linux OS analysis 42/31
组描述符
组描述符用来描述一个磁盘块组的相关信息
11/03/09 Linux OS analysis 43/31
索引结点
EXT2中所有的索引结点大小相同,都是 128个 字节。
11/03/09 Linux OS analysis 44/31
11/03/09 Linux OS analysis 45/31
索引节点表
EXT2的一个磁盘块组中的索引结点存储在一组 连续的磁盘块中,形成一个索引结点表。
这组磁盘块中的第一个磁盘块的块号存储在超级块的 bg_inode_table数据项中。
根据磁盘块的大小,可以计算出每个磁盘块能容纳多少个索引结点
根据索引结点的总个数,可以计算出索引结点表 所需要占用的磁盘块的个数。
11/03/09 Linux OS analysis 46/31
关于索引节点中的 i_block[]
ext2 的索引结点中使用了组合索引方式。
前 12项用作直接索引第 13项用作间接索引第 14项用作二次间接索引第 15 项用作三次间接索引
11/03/09 Linux OS analysis 47/31
数据块位图和索引结点块位图
EXT2的空闲盘块分配算法采用了位图法位图:为便于查找数据块或索引结点的分配信息
每个位( bit)都对应了一个磁盘块:0,表示对应的磁盘块(或索引结点)空闲1,表示占用。
2个位图分别占用一个专门的磁盘块。根据磁盘块的大小,可以计算出每个块组中最多
能容纳的数据块个数和索引节点块个数。
11/03/09 Linux OS analysis 48/31
(二) EXT2 中的目录项和文件类型
在 EXT2中,目录是一种特殊的文件,这种文件 的数据块中存放了该目录下的所有目录项
11/03/09 Linux OS analysis 49/31
新版的目录项结构
11/03/09 Linux OS analysis 50/31
EXT2 支持的文件类型
EXT2在目录项中存放了文件的类型信息。文件类型可以是 0~ 7中的任意一个整数。它们分别代表如下含义:0:文件类型未知;1:普通文件类型;2:目录;3:字符设备;4:块设备;5:有名管道 FIFO;6:套接字;7:符号链接。
11/03/09 Linux OS analysis 51/31
注意:
11/03/09 Linux OS analysis 52/31
(三)创建一个 ext2文件系统
在磁盘上创建文件系统通常有两个步骤:格式化磁盘
Linux中: superformat或者 fdformat创建文件系统
Ext2: mke2fs
mke2fs的缺省参数磁盘块大小: 1024字节分片:目前不支持,因此与磁盘块一样分配 inode的个数: 1/8192B永久保留的块的个数: 5%
11/03/09 Linux OS analysis 53/31
创建流程
1. 初始化超级块和组描述符2. Optionally, 检查是否有坏块,若有创建坏块列表3. 对每个块组,保留所有用来存放超级块、组描述符、 inode表、 2个位图的磁盘块
4. 初始化每个块组中的位图5. 初始化每个块组中的 inode表6. 创建 /root 目录7. 创建 lost+found 目录(供 e2fsck 使用,与坏块相关)
8. 为上述两个目录而更新位图信息9. 若有坏块,则将其在 lost+found 目录中组织起来
11/03/09 Linux OS analysis 54/31
以 1.44MB的软盘为例,创建 ext2文件系统后
11/03/09 Linux OS analysis 55/31
(四) Ext2提供的各种对象方法
超级块对象方法
11/03/09 Linux OS analysis 56/31
索引节点对象方法
11/03/09 Linux OS analysis 57/31
文件对象方法
11/03/09 Linux OS analysis 58/31
(五)管理 ext2的磁盘空间
“ ”存储在磁盘上的文件与用户所 看到 的文件有所不同:用户感觉,文件在逻辑上是连续的而在磁盘上,存储文件数据的磁盘块可能分散在磁盘各处
用户感觉,文件可能比较大而在磁盘上,由于文件空洞的存在,分配给文件的磁盘空间可能小于用户感觉到的文件大小。
11/03/09 Linux OS analysis 59/31
涉及到如下操作:创建 /删除一个索引节点数据块的寻址文件空洞分配 /释放一个数据块
11/03/09 Linux OS analysis 60/31
创建 /删除一个索引节点
创建一个磁盘索引节点
删除一个索引节点
11/03/09 Linux OS analysis 61/31
关于数据块的寻址
任何一个常规文件都会包含一系列数据块 文件内块号 vs. 逻辑块号
根据数据在文件中的偏移可以计算逻辑块号: 首先计算出文件内块号 =(偏移 f- 1) / 块大小的商 +
1 根据索引信息,查询到逻辑块号
11/03/09 Linux OS analysis 62/31
混合索引示意图
11/03/09 Linux OS analysis 63/31
文件大小限制
11/03/09 Linux OS analysis 64/31
关于文件空洞
A file hole is a portion of a regular file that contains null characters and is not stored in any data block on disk.
这是 UNIX文件一直以来都有的一个特性
例如命令:
创建一个大小为 1024×6+ 1字节的文件,这个文件有一个 1024×6= 6144个字节大小的空洞。只有最后一个字
“节存放了字母 X”
文件空洞可以节省磁盘空间 Ext2通过数据块的动态分配来实现这一点:当且仅当一个进程要写数据到文件中的时候才真正分配磁盘块
11/03/09 Linux OS analysis 65/31
分配 /释放一个数据块
当一个文件需要新的数据块来存放数据时
当一个文件被删除或者被截断时
Thanks !The end.
Top Related