Linux文件系统详解

1. Linux文件系统层次

Linux文件系统中有一个重要的感念:一切都是文件。这其实是Unix哲学的一个体现,Linux中这个概念也传承了下来。在Unix系统中,把一切资源都看作是文件,包括硬件设备(通常被看作设备文件,这样用户就可以使用读写文件的方式实现对设备的访问)。

Linux文件系统详解_第1张图片

1).硬盘驱动
常见的硬盘类型有PATA, SATA、SCIS、和AHCI等,在Linux系统中,对不同硬盘所提供的驱动模块一般都存放在内核目录树drivers/ata 中,而对于一般通用的硬盘驱动,也许会直接被编译到内核中,而不会以模块的方式出现,可以通过查看/boot/config-xxx.xxx文件来确认:
CONFIG_SATA_AHCI=y

2).General Block Device Layer
这一层的作用,正是解答了上面提出的第一个问题,不同的硬盘驱动,会提供不同的IO接口,内核认为这种杂乱的接口,不利于管理,需要把这些接口抽象一下,形成一个统一的对外接口,这样,不管你是什么硬盘,什么驱动,对外而言,它们所提供的IO接口没什么区别,都一视同仁的被看作块设备来处理。所以,如果在一层做的任何修改,将会直接影响到所有文件系统,不管是ext3,ext4还是其它文件系统,只要在这一层次做了某种修改,对它们都会产生影响。

3).文件系统
文件系统这一层相信大家再熟悉不过了,目前大多数Linux发行版默认使用的文件系统是ext4,CentOS 7上是xfs;不管什么样的文件系统,都可以用mkfs.xxx 命令创建:

mkfs.ext4 /dev/sdb
mkfs.xfs /dev/sdb
内核所支持的文件系统类型,可以通过内核目录树fs中的内容来查看
Linux文件系统详解_第2张图片
4).虚拟文件系统(VFS)
Virtual File System这一层,正是用来解决上面提出的第二个问题,试想,当我们通过mkfs.xxx系列命令创建了很多不同的文件系统,但这些文件系统都有各自的API接口,而用户想要的是,不管你是什么API,他们只关心mount/umount,或open/close等操作。所以,VFS就把这些不同的文件系统做一个抽象,提供统一的API访问接口,这样,用户空间就不用关心不同文件系统中不一样的API了。VFS所提供的这些统一的API,再经过System Call包装一下,用户空间就可以经过SCI的系统调用来操作不同的文件系统。
VFS所提供的常用API有:

mount(), umount() …
open(),close() …
mkdir() …

和文件系统关系最密切的就是存储介质,存储介质大致有RAM,ROM,磁盘磁带,闪存等。

闪存(Flash Memory)是一种长寿命的非易失性(在断电情况下仍能保持所存储的数据信息)的存储器,数据删除不是以单个的字节为单位而是以固定的区块为单位(注意:NORFlash为字节存储。),区块大小一般为256KB到20MB。闪存是电子可擦除只读存储器EEPROM)的变种,EEPROM与闪存不同的是,它能在字节水平上进行删除和重写而不是整个芯片擦写,这样闪存就比EEPROM的更新速度快。由于其断电时仍能保存数据,闪存通常被用来保存设置信息,如在电脑的BIOS(基本输入输出程序)、PDA(个人数字助理)、数码相机中保存资料等。

外存通常是磁性介质或光盘,像硬盘,软盘,磁带,CD等,能长期保存信息,并且不依赖于电来保存信息,但是由机械部件带动,速度与CPU相比就显得慢的多。内存指的就是主板上的存储部件,是CPU直接与之沟通,并用其存储数据的部件,存放当前正在使用的(即执行中)的数据和程序,它的物理实质就是一组或多组具备数据输入输出和数据存储功能的集成电路,内存只用于暂时存放程序和数据,一旦关闭电源或发生断电,其中的程序和数据就会丢失。

RAM又分为动态的和静态。。静态被用作cache,动态的常用作内存。。网上说闪存不能代替DRAM是因为闪存不像RAM(随机存取存储器)一样以字节为单位改写数据,因此不能取代RAM。这个以后可以了解下硬件的知识再来辨别.

2. CentOS磁盘与文件系统管理

2.1 ext2文件系统

Linux最传统的磁盘文件系统就是ext2,所以要了解linux的文件系统我们就得由认识从ext2开始。文件系统是创建在硬盘上面的,因此我们得了解硬盘的物理组成才行。

2.1.1 磁盘管理

2.1.1.1 设备文件

设备文件关联至设备驱动程序,用户通过操作这些设备文件间接管理对应的物理硬件;一个设备的名称表示整个磁盘,而分区则用设备名加上一个分区号来表示
设备文件类型:

  • 块设备 存取单位是块,如磁盘
  • 字符设备 存取单位是字符,如键盘

为了方便管理这些设备,系统设置了主设备号和次设备号来区分,如下所示
ll /dev/sda*
Linux文件系统详解_第3张图片
8代表主设备号,后面的数字代表次设备号(该数字与分区槽所在的位置有关).
创建设备文件

mknod 文件名 b 主设备号 次设备号		//创建块设备文件
mknod 文件名 c 主设备号 次设备号		//创建字符设备文件

2.1.1.2 磁盘介绍

针对机械硬盘,磁盘的结构图如下:
Linux文件系统详解_第4张图片
Linux文件系统详解_第5张图片

1)硬盘的chs模式

是指chs(Cylinder/Head/Sector)模式,很久以前,硬盘的容量还非常小的时候,人们采用与软盘类似的结构生产硬盘.也就是硬盘盘片的每一条磁道都具有相同扇区数. 由此产生了所谓的3D参数 (Disk Geometry). 既磁头数(Heads),柱面数(Cylinders), 扇区数(Sectors pertrack),以及相应的寻址方式

  • sector 扇区:每个磁道最多标识64个扇区,每个扇区512byte,一个扇区包含三个字段

         标识字段    校验字段    数据字段
    
  • track 磁道:磁道数最大理论上256个

  • head 磁头 :一个磁头号即一个盘面号,磁头数量=盘面数量;在硬盘上磁头用8bit标识,最多标识256个磁头

  • cylinder 柱面:一个柱面号即磁道号,通常由外向内依次编号,通常作为文件系统的最小单位。在硬盘柱面用10bit标识,最多标识1024个柱面

磁盘容量计算方式:磁盘容量=磁头数(盘面数)* 磁道数 * 扇区数 * 512bytes, 所以传统的磁盘容量最大值为:

扇区大小*64*256*1024=8589934592=8G

因此早期的硬盘无法突破8G容量

2)LBA(logical block addressing)模式

以上这种方式会浪费很多磁盘空间 (与软盘一样). 为了解决这一问题, 进一步提高硬盘容量, 人们改用等密度结构生产硬盘.也就是说,外圈磁道的扇区比内圈磁道多. 采用这种结构后, 硬盘不再具有实际的3D参数, 寻址方式也改为线性寻址,即以扇区为单位进行寻址。

为了与使用3D寻址的老软件兼容 (如使用BIOS Int13H接口的软件), 在硬盘控制器内部安装了一个地址翻译器, 由它负责将老式3D参数翻译成新的线性参数.这也是为什么现在硬盘的3D参数可以有多种选择的原因 (不同的工作模式, 对应不同的3D参数,如 LBA, LARGE, NORMAL). CHS模式只能识别大硬盘的前面8G.lba使用的线性寻址,突破了1024柱面的限制,能访问8G以外的空间了。

LBA采用48个bit位寻址,最大寻址空间128PB。

ZBR(Zoned Bit Recording)
Linux文件系统详解_第6张图片

2.1.1.3 磁盘分区

磁盘分区是使用分区编辑器(partition editor)在磁盘上划分几个逻辑部分,盘片一旦划分成数个分区,不同类的目录与文件可以存储进不同的分区。越多分区,也就有更多不同的地方,可以将文件的性质区分得更细,按照更为细分的性质,存储在不同的地方以管理文件;但太多分区就成了麻烦。空间管理、访问许可与目录搜索的方式,依属于安装在分区上的文件系统。当改变大小的能力依属于安装在分区上的文件系统时,需要谨慎地考虑分区的大小。

1)硬盘为什要分区

  • 优化I/O性能
  • 实现磁盘空间配额限
  • 提高修复速度
  • 隔离系统和程序
  • 安装多个OS
  • 采用不同文件系统

2)分区表类型(MBR和GPT)

MBR: Master Boot Record 主引导记录

又叫做主引导扇区,是计算机开机后访问硬盘时所必须要读取的首个扇区,它在硬盘上的三维地址为(柱面,磁头,扇区)=(0,0,1)。在深入讨论主引导扇区内部结构的时候,有时也将其开头的446字节内容特指为“主引导记录”(MBR),其后是4个16字节的“磁盘分区表”(DPT),以及2字节的结束标志(55AA)。因此,在使用“主引导记录”(MBR)这个术语的时候,需要根据具体情况判断其到底是指整个主引导扇区,还是主引导扇区的前446字节。

mbr分区用4个字节存储分区的总扇区数,最大能表示2的32次方的扇区个数,按每扇区512字节计算(2^32*512byte=2199023255552byte=2T),所以mbr无法识别大于2T以后的空间

0磁道0扇区 (512bytes),主要有以下部分组成:

  • 446bytes:boot loader
  • 64bytes:分区表,16bytes标识一个分区,支持4个分区,或者3个主分区和一个扩展分区
  • 2bytes:分区标示位 55AA

在分区表中记录分区的起始地址和结束地址(既可以使用CHS寻址也可以使用LBA进行寻址),这两个地址相减就是我们这个分区的实际容量

MBR分区结构图:
Linux文件系统详解_第7张图片

以Linux系统为例,我们详细讲解探索一下MBR;

[root@hdp1 ~]# hexdump -C -n 512 /dev/sda -v     //查看分区信息有数据,-C表示16进制显示

Linux文件系统详解_第8张图片

我们用Vmware给虚拟机新增一块硬盘,点击虚拟机设置–>添加–>硬盘 选择10G,disk -l 命令查看磁盘信息,如下所示:

Linux文件系统详解_第9张图片

此时查看sdc的MRB信息

[root@hdp1 ~]# hexdump -C -n 512 /dev/sdc -v						//分区信息为空,字节全为0

Linux文件系统详解_第10张图片

接下来我们对分区表做一个实验,

[root@hdp1 ~]# dd if=/dev/sda of=/dev/sdc bs=1 count=512      		//将/dev/sda磁盘前512字节信息copy到 /dev/sdc中去

再次执行hexdump -C -n 512 /dev/sdc -v,分区表信息和结束位信息如下所示

Linux文件系统详解_第11张图片
我们发现两张的磁盘分区信息一模一样,运行fdisk -l命令查看磁盘信息如结果如下图所示

Linux文件系统详解_第12张图片

dd if=/dev/zero of=/dev/sdc bs=1 count=512 破坏/dev/sdc的分区信息, disk -l 发现/dev/sdc的分区消失

继续实验(对结束位)

 dd if=/dev/sda of=/dev/sdc bs=1 count=512

 dd if=/dev/zero of=/dev/sdc bs=1 count=2 seek=510      //破坏分区信息的结束位

 hexdump -C -n 512 /dev/sdc -v,                         //结果结束位的55 aa变为了00 00

fdisk -l 显示/dev/sdb没有分区

dd if=/dev/sda of=/dev/sdc bs=1 count=2 skip=510 seek=510

hexdump -C -n 512 /dev/sdc -v

fdisk -l 显示/dev/sdc又有分区

结论: 结束位用来区分MBR分区的结束,如果没有结束位,则系统无法识别出分区表的结束,即没有分区表的信息。

MBR与开机流程

计算机主板上有两个非常重要的东西,一个是BIOS一个是CMOS,CMOS是记录各项硬件参数并且嵌入在主板上的寄存器中,BIOS则是一个写入到主板上的软件程序。这个BIOS就是在开机的时候计算机系统会主动执行的第一个程序了。

接下来BIOS会去分析计算机里有哪些存储设备,我们以硬盘为例,BIOS会根据用户的设置去取得能够开机的硬盘,并且到该硬盘里去读取第一个扇区的MBR位置。MBR中446byte的boot loader里面会放置最基本的引导加载程序,此时BIOS就功成圆满,而接下来就是MBR内的引导加载程序的工作了。

这个引导加载程序的主要目的是加载内核文件,由于引导加载程序是操作系统在安装的时候所提供的,所以它会识别硬盘内的文件系统格式,因此就能够读取内核文件,然后接下来就是内核文件的工作,引导加载程序也功成圆满,之后就是大家所熟知的操作系统的任务了。
简单来说整个开机流程到操作系统之前的动作应该是这样的:

  • BIOS: 开机主动执行的程序,会认识寻找第一个可开机的设备
  • MBR:第一个可开机设备的第一个扇区的主引导分区块,内包含引导加载程序
  • 引导加载程序(Boot loader):一个可读取内核文件来执行的软件程序
  • 内核文件: 开始操作系统的功能

扩展分区
由于MBR仅仅为分区表保留了64字节的存储空间,而每个分区则占用16字节的空间,也就是只能分4个分区,而4个分区在实际情况下往往是不够用的。因此就有了扩展分区,扩展分区中的每个逻辑分区的分区信息都存在一个类似MBR的扩展引导记录(简称EBR)中,扩展引导记录包括分区表和结束标志“55 AA”,没有引导代码部分。也就是EBR中的前446个字节是空的
扩展分区的结构如下图所示
Linux文件系统详解_第13张图片

如上图:EBR中分区表的第一项描述第一个逻辑分区,第二项指向下一个逻辑分区的EBR。如果下一个逻辑分区不存在,第二项就不需要了。
MBR分区的结构大致就介绍到这了。如果硬盘的MBR被破坏,可以复制其他硬盘的MBR到故障盘,然后修复分区表,也可以初始化故障盘然后修复分区表。

你可能感兴趣的:(linux)