文件系统与VFS简介
一、概念理解
文件系统(亦称文件管理系统),是文件存储在磁盘等存储设备上的组织方法和数据结构。具体地说,它对存储设备的空间进行组织和分配,负责为用户建立文件,存入、读出、修改、转储文件,控制文件的存取,当用户不再使用时撤销文件等。
每个计算机公司的操作系统在实现这些功能时的均有各自的方法,故大家常说,DOS、Windows、OS/2、Macintosh和UNIX-based操作系统都自有支持的文件系统。举例来说,windows 98 以前的微软操作系统主要的文件系统是 FAT (或 FAT16),windows 2000 以后的版本有NTFS 文件系统,Linux 的文件系统则有 Ext等。
当系统加载一个文件到内存后,如果该文件没有被更动过,则在内存区段的文件数据会被配置为干净(clean)的。但如果内存中的文件数据被更改过了(例如你用 nano 去编辑过这个文件),此时该内存中的数据会被配置为脏的 (Dirty)。此时所有的动作都还在内存中运行,并没有写入到磁盘中!系统会不定时的将内存中配置为『Dirty』的数据写回磁盘,以保持磁盘与内存数据的一致性。
二、Linux文件系统规划
文件系统通常会将这两部份的数据分别存放在不同的区块,权限与属性放置到 inode 中,至于实际数据则放置到 data block 区块中。另外,还有一个超级区块 (superblock) 会记录整个文件系统的整体信息。
①superblock
Superblock 是记录整个 filesystem 相关信息的地方,他记录的信息主要有:
block 与 inode 的总量;
未使用与已使用的inode / block 数量;
block 与 inode 的大小 (block 为 1, 2, 4K,inode 为 128 bytes);
filesystem 的挂载时间、最近一次写入数据的时间、最近一次检验磁盘 (fsck) 的时间等文件系统的相关信息;
一个 valid bit 数值,若此文件系统已被挂载,则 valid bit 为 0 ,若未被挂载,则 valid bit 为 1 。
②inode
记录文件的属性,一个文件占用一个inode,同时记录此文件的数据所在的 block 号码;
③block:
实际记录文件的内容,若文件太大时,会占用多个 block 。文件系统一开始就将 inode 与 block 规划好了,除非重新格式化(或者利用 resize2fs 等命令变更文件系统大小),否则 inode 与 block 固定后就不再变动。
④data block (数据区块)
data block 是用来放置文件内容数据地方,在 Ext2 文件系统中所支持的 block 大小有 1K, 2K 及 4K 三种而已。在格式化时 block 的大小就固定了,且每个 block 都有编号,以方便 inode 的记录。
block 大小而产生的 Ext2 文件系统限制如下:
Block 大小 | 1KB | 2KB | 4KB |
最大单一文件限制 | 16GB | 256GB | 2TB |
最大文件系统总容量 | 2TB | 8TB | 16TB |
Block基本限制:
block 的大小与数量在格式化完就不能够再改变了(除非重新格式化)
每个 block 内最多只能够放置一个文件的数据;
如果文件大于 block 的大小,则一个文件会占用多个 block 数量;
如果文件小于 block ,则该 block 的剩余容量就不能够再被使用了。
每个 block 仅能容纳一个文件的数据,如果你的文件都非常小,block 在格式化时却选用最大的 4K 时,可能会产生一些容量的浪费。例如 BBS 网站的数据!
在进行文件系统的格式化之前,请先想好该文件系统预计使用的情况。即分区大概使用哪些文件类型与文件大小!
⑤inode table (inode 表格)
inode 的内容在记录文件的属性以及该文件实际数据是放置在哪几号block内。
inode 记录的文件数据:
文件的存取模式(read/write/excute);
文件的拥有者与群组(owner/group);
文件的容量;
文件创建或状态改变的时间(ctime);
最近一次的读取时间(atime);
最近修改的时间(mtime);
定义文件特性的旗标(flag),如 SetUID...;
该文件真正内容的指向(pointer);
inode 的数量与大小也是在格式化时就已经固定:
每个 inode 大小均固定为 128bytes;
每个文件都仅会占用一个inode 而已;
承上,因此文件系统能够创建的文件数量与 inode 的数量有关;
系统读取文件时需要先找到inode,并分析 inode 所记录的权限与用户是否符合,若符合才能够开始实际读取 block 的内容。
⑥Filesystem Description (文件系统描述说明)
这个区段可以描述每个block group 的开始与结束的 block 号码,以及说明每个区段 (superblock, bitmap, inodemap, data block) 分别介于哪一个 block号码之间。这部份也能够用 dumpe2fs 来观察的。
⑦block bitmap (区块对照表)
从 blockbitmap 当中可以知道哪些 block 是空的,因此我们的系统就能够很快速的找到可使用的空间来处置文件。
如果你删除某些文件时,那么那些文件原本占用的 block 号码就得要释放出来,此时在 block bitmap 当中相对应到该 block 号码的标志就得要修改成为“未使用中”。
⑧inode bitmap (inode 对照表)
这个其实与 blockbitmap 是类似的功能,只是 block bitmap 记录的是使用与未使用的 block 号码,至于 inode bitmap 则是记录使用与未使用的 inode 号码。
三、观察Linux文件系统
读取磁盘的效能,特别是高并发的网站服务器,如果文件真的太过离散,确实还是会发生读取效率低落的问题。那么可以将整个 filesystme 内的数据全部复制出来,将该 filesystem 重新格式化,再将数据给他复制回去即可解决这个问题。
其次,partition 的规划并不是越大越好, 而是真的要针对您的主机用途来进行规划才行。因为一般来说,我们将 inode table 与 data block 称为数据存放区域,至于其他例如 superblock、 block bitmap 与 inode bitmap 等区段就被称为 metadata (中介数据)。因为 superblock, inode bitmap 及 block bitmap 的数据是经常变动的,每次新增、移除、编辑时都可能会影响到这三个部分的数据,因此才被称为中介数据。
做为服务器用途的文件系统,可以从上述角度去优先磁盘性能。
[root@www ~]# dumpe2fs[-bh] 设备文件名
选项与参数:
-b :列出保留为坏轨的部分(一般用不到吧!?)
-h :仅列出 superblock 的数据,不会列出其他的区段内容!
[root@localhost~]# dumpe2fs /dev/sda2
dumpe2fs 1.39 (29-May-2006)
Filesystem volume name: / <==这个是文件系统的名称(Label
Last mounted on: <not available>
Filesystem UUID: dac4804e-d7d9-4265-ae6d-4216d5eaa70a
Filesystem magic number: 0xEF53
Filesystem revision #: 1 (dynamic)
Filesystem features: has_journal ext_attr resize_inodedir_index filetype needs_recovery spars e_super large_file
Default mount options: user_xattr acl <==默认挂载的参数
Filesystem state: clean <==这个文件系统是没问题的(clean
Errors behavior: Continue
Filesystem OS type: Linux
Inode count: 1280000 <==inode的总数
Block count: 1279175 <==block的总数
Reserved block count: 63958
Free blocks: 1142588 <==还有多少个 block 可用
Free inodes: 1274746 <==还有多少个 inode 可用
First block: 0
Block size: 4096 <==每个 block 的大小
Fragment size: 4096
Reserved GDT blocks: 312
Blocks per group: 32768
Fragments per group: 32768
Inodes per group: 32000
Inode blocks per group: 1000
Filesystem created: Fri Nov 13 07:31:36 2015
Last mount time: Mon Nov 16 09:32:59 2015
Last write time: Mon Nov 16 09:32:59 2015
Mount count: 9
Maximum mount count: -1
Last checked: Fri Nov 13 07:31:36 2015
Check interval: 0 (<none>)
Reserved blocks uid: 0 (user root)
Reserved blocks gid: 0 (group root)
First inode: 11
Inode size: 128 <==每个 inode 的大小
Journal inode: 8
Default directory hash: tea
Directory Hash Seed: db1e05f7-5293-49e4-a654-6f4ea6a401cb
Journal backup: inode blocks
Journal size: 128M
Group 0: (Blocks 0-32767) // block 的启始/结束号码
Primary superblock at 0, Group descriptors at 1-1 <==超级区块在 0 号 block
Reserved GDT blocks at 2-313
Block bitmap at 314 (+314), Inode bitmap at 315 (+315) <== Block bitmap 所在的 block
Inode table at 316-1315 (+316) <==inodetable 所在的 block
0free blocks, 31989 free inodes, 2 directories <==所有 block 都用完
Free blocks:
Free inodes: 12-32000 <==剩余未使用的 inode 号码
实际观察 root 家目录内的文件所占用的 inode 号码时,可以使用 ls -i 这个选项来处理.
[root@localhost ~]# ls -li
800009 -rw------- 1 root root 1646 Nov 12 23:42 anaconda-ks.cfg
800037 drwxr-xr-x 2 root root 4096 Nov 12 23:51 Desktop
800224 -rw-r--r-- 1 root root 0 Nov 15 15:51 enginer001.txt
800223 lrwxrwxrwx 1 root root 14 Nov 14 11:10 enginer002.txt ->enginer001.txt
800002 -rw-r--r-- 1 root root 33244 Nov 1223:42 install.log
800003 -rw-r--r-- 1 root root 4068 Nov 12 23:42 install.log.syslog
800228 -rwxr-xr-x 1 root root 21 Nov 14 11:56 mylsfile.shell
800220 d--------- 2 root root 4096 Nov 15 17:45 mysoft_dir
800225 -rw-r--r-- 1 root root 33 Nov 14 11:01 sinfo001.txt
举例:
[root@localhost ~]# ll -d / /bin /boot /proc /sbin
drwxr-xr-x 25 root root 4096 Nov 17 09:13 / <==一个 4K block
drwxr-xr-x 2 root root 4096 Nov 13 08:38/bin
drwxr-xr-x 4 root root 1024 Nov 12 23:50/boot <==一个 1K block
dr-xr-xr-x 125 root root 0 Nov 16 17:32 /proc
drwxr-xr-x 2 root root 12288 Nov 13 08:38 /sbin <==三个 4K block
文件名是记录在目录的block 当中,因此当我们要读取某个文件时,就务必会经过目录的inode 与 block ,然后才能够找到那个待读取文件的 inode 号码,最终才会读到正确的文件的 block 内的数据。
目录树是由根目录开始读起,因此系统透过挂载的信息可以找到挂载点的 inode 号码(通常一个 filesystem 的最顶层 inode 号码会由 2 号开始喔!),此时就能够得到根目录的 inode 内容,并依据该 inode 读取根目录的 block 内的文件名数据,再一层一层的往下读到正确的档名。如下:
[root@localhost ~]# ll -di / /etc /etc/passwd
2 drwxr-xr-x 25 rootroot 4096 Nov 17 09:13 /
544001 drwxr-xr-x 98 root root 12288 Nov 17 19:15 /etc
546076 -rw-r--r-- 1 rootroot 1656 Nov 17 19:15 /etc/passwd
四、数据的不一致(Inconsistent) 与日志式文件系统(Journalingfilesystem)
例如你的文件在写入文件系统时,因为不知名原因导致系统中断(例如突然的停电啊、系统核心发生错误啊~等等的怪事发生时),所以写入的数据仅有 inode table 及 data block 而已,最后一个同步升级中介数据的步骤并没有做完,此时就会发生 metadata 的内容与实际数据存放区产生不一致 (Inconsistent) 的情况。
不过,这样的检查真的是很费时~因为要针对 metadata 区域与实际数据存放区来进行比对,呵呵~得要搜寻整个 filesystem 呢~如果你的文件系统有 100GB 以上,而且里面的文件数量又多时。在对 Internet 提供服务的服务器主机上面,这样的检查真的会造成主机复原时间的拉长。
这也就造成后来所谓日志式文件系统的兴起了!避免文件系统不一致的情况发生,在我们的 filesystem 当中规划出一个区块,该区块专门在记录写入或修订文件时的步骤,简化一致性检查的步骤。日志方法如下:
①预备:当系统要写入一个文件时,会先在日志记录区块中纪录某个文件准备要写入的信息;
②实际写入:开始写入文件的权限与数据;开始升级 metadata 的数据;
③结束:完成数据与metadata 的升级后,在日志记录区块当中完成该文件的纪录。
在这样的程序当中,万一数据的纪录过程当中发生了问题,那么我们的系统只要去检查日志记录区块,就可以知道哪个文件发生了问题,针对该问题来做一致性的检查即可,而不必针对整块 filesystem 去检查,这样就可以达到快速修复 filesystem 的能力!这就是日志式文件最基础的功能。
五、文件系统与 VFS
U盘插入电脑的usb接口,其文件系统格式fat32,挂载后,我们可以使用 cp 命令从fat32文件系统格式的u盘拷贝数据到 ext3 文件系统格式的硬盘;而这样的操作涉及到两个不同的文件系统。
其次,虽然 Linux 的标准文件系统是 ext2,ext3(日志功能的),但是,Linux还有支持很多文件系统格式的,包括 SGI 的 XFS 文件系统,可以适用更小型文件的 Reiserfs 文件系统,以及 Windows 的 FAT 文件系统等等。
常见的支持文件系统有:
传统文件系统:ext2 / minix / MS-DOS / FAT (用 vfat 模块) / iso9660(光盘)等等;
日志式文件系统:ext3 / ReiserFS / Windows' NTFS / IBM's JFS / SGI's XFS
网络文件系统: NFS / SMBFS
通过上述描述,Linux 的核心又是如何认识与管理这些文件系统呢?
原因是:整个 Linux 的系统都是透过一个名为Virtual Filesystem Switch 的核心功能去读取 filesystem 的。
假设你的 / 使用的是/dev/hda1 ,用 ext3 ,而 /home 使用 /dev/hda2 ,用 reiserfs ,那么你取用 /home/dmtsai/.bashrc 时,有特别指定要用的什么文件系统的模块来读取吗?应该是没有吧!这个就是 VFS 的功能啦!透过这个 VFS 的功能来管理所有的 filesystem。
实现VFS原理如下:
Linux系统以一组通用对象的角度看待所有文件系统。这些对象是超级块(superblock)、inode、dentry 和文件。
超级块:在每个文件系统的根上,超级块描述和维护文件系统的状态。
Inode:文件系统中管理的每个对象(文件或目录)在 Linux 中表示为一个 inode
Dentry:用来实现名称和 inode 之间的映射,有一个目录缓存用来保存最近使用的 dentry。dentry 还维护目录和文件之间的关系,从而支持在文件系统中移动。
想要知道你的 Linux 支持的文件系统有哪些,可以察看底下这个目录
[root@localhost ~]# ls -l/lib/modules/$(uname -r)/kernel/fs
total 232
drwxr-xr-x 2 root root 4096 Nov 12 23:39 autofs4
drwxr-xr-x 2 root root 4096 Nov 12 23:39 cachefiles
drwxr-xr-x 2 root root 4096 Nov 12 23:39 cifs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 configfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 cramfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 dlm
drwxr-xr-x 2 root root 4096 Nov 12 23:39 ecryptfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 exportfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 ext3
drwxr-xr-x 2 root root 4096 Nov 12 23:39 ext4
drwxr-xr-x 2 root root 4096 Nov 12 23:39 fat
drwxr-xr-x 2 root root 4096 Nov 12 23:39 freevxfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 fscache
drwxr-xr-x 2 root root 4096 Nov 12 23:39 fuse
drwxr-xr-x 3 root root 4096 Nov 12 23:39 gfs2
drwxr-xr-x 2 root root 4096 Nov 12 23:39 hfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 hfsplus
drwxr-xr-x 2 root root 4096 Nov 12 23:39 jbd
drwxr-xr-x 2 root root 4096 Nov 12 23:39 jbd2
drwxr-xr-x 2 root root 4096 Nov 12 23:39 jffs2
drwxr-xr-x 2 root root 4096 Nov 12 23:39 lockd
drwxr-xr-x 2 root root 4096 Nov 12 23:39 msdos
drwxr-xr-x 2 root root 4096 Nov 12 23:39 nfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 nfs_common
drwxr-xr-x 2 root root 4096 Nov 12 23:39 nfsd
drwxr-xr-x 2 root root 4096 Nov 12 23:39 nls
drwxr-xr-x 2 root root 4096 Nov 12 23:39 squashfs
drwxr-xr-x 2 root root 4096 Nov 12 23:39 udf
drwxr-xr-x 2 root root 4096 Nov 12 23:39 vfat
[root@localhost ~]# ls -l/lib/modules/$(uname -r)/kernel/fs | wc –l
30
合计支持30种文件系统。

本文介绍了Linux文件系统的组成和工作原理,包括superblock、inode、block等关键组件的作用,以及日志式文件系统如何提高数据一致性。同时,文章探讨了虚拟文件系统(VFS)的概念及其如何统一管理不同类型的文件系统。
1806

被折叠的 条评论
为什么被折叠?



