【操作系统原理-陈渝老师】第十二章 文件系统

本文详细介绍了文件系统的概念、功能,包括文件与块、文件描述符、文件内部结构、权限管理、目录结构、文件系统的挂载、文件别名(硬链接和软链接)以及文件系统的类别。同时,讨论了虚拟文件系统、数据缓存策略、打开文件的数据结构、文件分配方法、空闲空间管理、RAID技术及其不同级别,以及磁盘调度策略。通过对这些核心概念的深入理解,有助于把握文件系统的工作原理。

 

目录

 

0.总览

1.文件系统介绍

1.1 文件系统和文件的概念

1.2  文件系统的功能

1.3 文件与块

1.4 文件描述符

1.5 文件内部结构

1.6 文件的权限

1.7 文件的目录

1.7.1 目录存在的意义

1.7.2 目录的典型操作

1.7.3 目录中文件的组织方式

1.7.4 目录中的路径遍历

1.8 文件系统的挂载

1.9 文件别名

1.9.1 硬链接和软连接

1.9.2 删除一个有别名的文件会怎样?

1.9.3 别名与循环问题

1.10 文件系统的类别

1.10.1 总览

1.10.2 分布式文件系统的进一步说明

1.10.3 扫盲AFS

2.虚拟文件系统

3.数据缓存

3.1 解决的问题

3.2 数据缓冲的方式 

4.打开文件的数据结构

4.1 打开文件描述符和打开文件表

4.2 进程打开文件表的过程

4.3 进程对打开文件的权限设置

5.分配文件

5.1 分配需要考虑的问题

5.2 分配数据块的方法及指标

5.2.1 连续分配

5.2.2 链式分配

5.2.3 索引分配

6.空闲空间列表

6.1 位图 

6.2 链式与分组

6.3 最佳选择

7.多磁盘管理-RAID

7.1 基本概念-磁盘

7.2 基本概念-分区与卷

7.3 RAID

7.3.1 RAID的提出

7.3.2 RAID的发展与实现

 7.3.3 RAID-0 能提升吞吐量

7.3.4 RAID-1 提高可靠性

7.3.5 RAID-4 高性能高可靠

7.3.6 RAID-5 开销均衡的高性能高可靠

7.3.7 奇偶校验的粒度

7.3.8 进一步发展

8.磁盘调度

8.1 访问时间的计算

8.2 调度策略

8.2.1 先进先出

8.2.2 最短服务优先

8.2.3 SCAN

8.2.4 C-SCAN&C-LOOK

8.2.5 N-Step-SCAN

8.2.6 FSCAN

8.2.7 对算法的总结


0.总览

1.文件系统介绍

1.1 文件系统和文件的概念

1.2  文件系统的功能

1.3 文件与块

1.4 文件描述符

文件描述符不仅仅是一个简单的数字,操作系统内核对每个进程打开的文件维护了一个打开文件表,
文件描述符仅仅是这个表中的一个索引,这个文件描述符指出了打开文件表中的第几项代表这个文件,
我们只需要知道这个索引就可以找到这个文件.

问题:老师这里说的这个打开文件表长的什么样子的?
      是每个进程都有这样一个表还是整个系统中所有的进程共用这样一张表?
答案:在本文的“打开文件的数据结构”这一节(第四节)中有介绍,每个进程都有这样一张表,系统中也会有
      一个全局的.



一般操作系统上不会基于内容访问,一般都会交给数据库系统来提供基于内容访问的功能.    

1.5 文件内部结构

当我们平时用各种各样的文件,比如说word,ppt,里面有个中复杂的结构,这个结构
的具体含义是用应用程序来识别的.但对于操作系统来说,无论是什么结构,它都需要
用一种统一的简介的方式来理解文件的内容,也就是字节流.
操作系统把它理解成没有意义的串行的一维的字节流,这使得操作系统与应用层的功能
分开了,文件可以用很多复杂的结构,但是这个文件和特定的应用相关,但是与操作系统
无关,这大大地简化了操作系统的实现,而且使得操作系统有更好的通用性,应用程序
可以根据自己的特点来选择最适合的面向应用的表现方式,操作系统做的事与应用做的事
分开了.

1.6 文件的权限

UFS语义:
对同一文件多处在写的话,如果没有相应的同步同步机制,有可能出现竞态.
所以我们还要确保如果是写操作还要用写在不同的地方或者用互斥的方式来进行写操作,可以
确保写的内容不会出现意想不到的情况.


会话语义:
文件虽然是一堆数据,但是它的读写还是不太一样的,从打开到关闭这实际上是一个会话,这个
会话过程只有当一个文件做了关闭操作之后,我们才会把它的数据写到硬盘中去,使得接下来打开
同一个文件的进程能够将数据读出.确保会话结束之后,会话结束之前的那些内容都可以被会话结束
后的进程访问到.

锁:
为了支持共享,对于一个文件而言,我们建立在哪个粒度上的锁来对完成文件的保护.
是以一个文件为粒度实现的锁,打开文件之后就把文件锁住,别的用户进程就不能打开文件了;
以文件中不同的位置,不同的块形成锁,这个锁的粒度就更小一点了,只要块之间不存在重叠,
即使我们用并发的写操作也没有关系,这个锁的粒度就可以减小.
操作系统可以提供不同的锁方便应用程序写出更高效的程序.

1.7 文件的目录

1.7.1 目录存在的意义

为什么要有目录呢?
文件越来越多,如果把所有的文件都堆在一起,形成一个一维的展示的环境对人的访问来说很不方便,
通过分层的方式,这样整个空间更加有层次整洁,便于查找和组织不同类型的文件,称为层次的命名
空间.

 1.7.2 目录的典型操作

1.7.3 目录中文件的组织方式

1.7.4 目录中的路径遍历

文件系统中有一块很大的开销就来源于路径的遍历,因为这个路径可以很长,一个一个找的
话就不得不访问硬盘,把相应的数据取出来,当然我们操作系统提供了缓存机制来加速寻找.
一般来说路径的遍历要把路径名逐一解析成路径的名字,然后找到子目录,最后再找到文件,
完成对文件的访问.我们要清楚目录大致是怎样的命名规则,如果是绝对目录,就是要根目录
开始.

我们对当前目录的信息做了缓存,所以我们查找当前目录实际上会快一些.

1.8 文件系统的挂载

用起来还是比较简单的,但是原理其实还有有一些内容的.

1.9 文件别名

1.9.1 硬链接和软连接

有可能多个文件名关联同一个文件,就是文件有多个名字,为什么要有多个名字?
因为一个文件在不同的用户眼中的名字是不一样的,便于不同的用户对文件进行分类和查找.
这种方式在Unix中有两种实现方式,一个是硬链接,一个是软连接.

硬链接是指多个文件项指向用一个文件,在不同目录中存的是目录项,这个文件项虽然不一样,
但是它们指向的时候同一个文件的内容,这个内容就是放在磁盘上的.这几个不同文件名的文件
内容就只有一个,就是它们真实的文件.

软连接是类似于Windows中的快捷方式,就是文件里面的内容存的是另一个文件的路径名,如果
是软连接的话,要查找所指向文件的内容,就是根据软连接中指向的文件路径名去访问实际要访
的那个文件,这就是所谓的软连接.

1.9.2 删除一个有别名的文件会怎样?

如果删除了一个有别名的文件会怎样呢?
这取决于怎么实现.看看是用的软连接方式还是硬链接方式.
如果使用的软连接方式,把真实的文件删了,那么软连接文件就指向了一个空的地方,形成了一个
“悬空指针”.

如果采用的是硬链接方式,可能说,这个文件包含了一个特殊的数据结构,记录了引用计数,指出
到底有多少个不同的文件名指向同一个文件,删除了一个有别名的文件之后,只是文件的引用计数
减少了1,只有当这个文件的引用计数减少到0的时候,这个文件才会彻底地被删除.具体的实现可以
采取不同的链表方式来实现,或者采用计数,数组来管理所谓的别名到文件的一个映射关系.有一种
方式叫做Backpointers,这个就是菊花链的方式来进行管理的.

还有一种管理方式可以添加一个间接层,在目录下可以添加一个间接层,可以取不同的文件,先指向
一个间接层,然后由这个间接层再指向不同的文件,这也是一种方式.


相对来说,硬链接和软连接的方式更常用一些.

1.9.3 别名与循环问题

有别名机制就可能存在一种潜在的情况--循环,一般来说目录是一个树状结构,但是如果有了别名机制可能
会导致这个树会变成图,里面有环的存在,这可能导致查找文件检索路径的时候导致死循环,这个不是我们期
望看到的现象,我们需要避免这样的情况,如何避免呢?

在创建连接的时候,我们需要一种循环检测算法,来确定它是否合法,这是一个有效的检测机制,来确保一旦
出现循环的时候就报错提醒,当然还有其他的方法,此处就不逐一讲解了.


我们需要注意的就是当我们应用链接机制的时候,无论是硬链接还是软连接,都有可能不注意就出现循环的
路径,一旦出现这种路径就可能导致系统找文件出现异常.除了循环检测算法来判断创建的目录或者文件是
否形成环以外,还有一个简单的方法就是限制路径的可配置目录的数量,在某种程度上也可以减少出现循环
的情况.

当然,这种情况在我们创建文件的时候只要注意一点就不会出现,但确实也很难保证,所以我们还是需要一
些方法来进行保证.

问题与思考:自己动手测试一下什么时候会生成环和如何避免环.

1.10 文件系统的类别

1.10.1 总览

磁盘文件系统:
文件系统其实有很多中,不同的需求和不同的存储介质催生了繁多的文件系统.
比如说windows支持FAT,NTFS,ext2/3,IS09660等;
对于linux而言ext2,ext3等可能是它目前主要的文件系统,当然linux只要想,可以方便编译出各式各样的文
件系统.
ext2/3和NTFS很不一样,是实现起来完全不同的文件系统.
这些文件系统的存储介质是磁盘或者光盘.


数据库文件系统:
微软做Windows操作系统的时候曾经想要提供出WinFS,把文件系统以数据库的形式来展示出来便于用户
访问,想法很美好,专门取了一个WinFS这个名字,2014年说这个课的时候据老师所知,当时还没有成功,目
前
window的文件系统还是用的NTFS.

交互式文件系统:虚的文件系统.--好像漏了一些内容.


日志文件系统:
相对于传统的FAT系统而言的,计算机经常会掉电,一掉电由于一些内存里面的数据还没有写到文件系统中,
导致文件系统里面的内容出现了混乱,下一次开机的时候,文件系统会做一些check,确保文件系统内容的
一致性,确保源数据和内容是一致的,这个开销是很大的.这个是早期文件系统中会存在的一个问题.为此,
NTFS,ext3,ext4等文件系统增加了日志功能,有了日志功能之后就可以确保掉电之后可以快速回复.这种
TRANSACTION和JOURANLING的机制的思路来源于数据库的日志功能,一个读操作或者写操作要么完成要么
不完成,避免在中间状态被打断.可以查询更多日志文件系统的相关文章,这个代表了当前主要的文件系统
的特点.


网络/分布式文件系统:
网络文件系统,如window中的网络邻居,这类文件系统可以在局域网范围内很方便地访问另一台机器的
文件,只要有网络就好了,NFS和SMB都是这样的系统.
分布式文件系统,如GFS,谷歌管理的巨大的集群,做数据的存储,检索,访问等,这个是很厉害的分布式
文件系统,它可以管理大量的数据,用的是server端,网络中心,计算中心,数据中心这个领域,特点是
高速高吞吐高可靠的访问.
这个是当前网络背景下面向服务的,或者桌面的,或者嵌入式移动终端,都有大量的分布式网络的文件
系统存在,适应不同的需求.

特殊/虚拟文件系统:
这种文件系统的目的并不是为了存数据,而是以文件的方式展现文件的读写接口,来交互或者访问内核
中的数据,比如说linux系统下的/proc目录下的可以看到很丰富的内核信息,如内存几何,CPU几个,
多少次中断,当前打开了多少个进程等,这些内容看起来和文件系统一点关系也没有,但是它通过文件的
方式来展现,使得我们能够很好地读或者控制,配置一些参数来与操作系统的内核进行交互.


更多信息访问维基百科.

1.10.2 分布式文件系统的进一步说明

跨网络使得分布式文件系统与我们的单机上的文件系统很不一样,网络意味着延迟大,
不可靠,访问时间不可控,这些都是网络文件系统具有的特点,但是单机文件系统中基于
PCI总线或者计算机内部高速可靠的总线可以快速完成内存与磁盘中之间的访问,中间
没有一个不确定的延迟大的容易出错的网络存在,这使得分布式文件系统需要考虑读写的
一致性,可靠性和安全性问题,使得在设计或者实现分布式文件系统的时候更加复杂.
分布式文件系统需要考虑更多的因素,是当前研究热点.

1.10.3 扫盲AFS

ASF是Advanced Streaming Format的简称,由微软公司开发。ASF格式用于播放网上全动态影像bai,让
用户可以在下载的同时同步播放影像,无需等候下载完毕。 用Windows MediaPlayer 可以打开.
Microsoft公司的Windows Media的核心是ASF(Advanced Stream Format)。微软将ASF 定义为同步媒
体的统一容器文件格式。ASF是一种数据格式,音频、视频、图像以及控制命令脚本等多媒体信息通过这
种格式,以网络数据包的形式传输,实现流式多媒体内容发布。
ASF最大优点就是体积小,因此适合网络传输,使用微软公司的最新媒体播放器(Microsoft Windows 
Media Player)可以直接播放该格式的文件。用户可以将图形、声音和动画数据组合成一个ASF格式的
文件,当然也可以将其他格式的视频和音频转换为ASF格式,而且用户还可以通过声卡和视频捕获卡将诸
如麦克风、录像机等等外设的数据保存为ASF格式。另外,ASF格式的视频中可以带有命令代码,用户指
定在到达视频或音频的某个时间后触发某个事件或操作。
ASF的特征 可扩展的媒体类型- ASF文件允许制作者很容易地定义新的媒体类型。ASF格式提供了非常有
效的灵活地定义符合ASF文件格式定义的新的媒体流类型。任一存储的媒体流逻辑上都是独立于其他媒体
流的,除非在文件头部分明显地定义了其与另一媒体流的关系。 部件下载-特定的有关播放部件的信息
(如,解压缩算法和播放器)能够存储在ASF 文件头部分,这些信息能够为客户机用来找到合适的所需
的播放部件的版本---如果它们没有在客户机上安装。
可伸缩的媒体类型- ASF是设计用来表示可伸缩的媒体类型的"带宽"之间的依赖关系。ASF存储各个带宽
就像一个单独的媒体流。媒体流之间的依赖关系存储在文件头部分,为客户机以一个独立于压缩的方式
解释可伸缩的选项提供了丰富的信息流的优先级化- 现代的多媒体传输系统能够动态地调整以适应网络
资源紧张的情况(如,带宽不足)。多媒体内容的制作者要能够根据流的优先级表达他们的参考信息,
如最低保证音频流的传输。随着可伸缩媒体类型的出现,流的优先级的安排变得复杂起来,因为在制作
的时候很难决定各媒体流的顺序。ASF允许内容制作者有效地表达他们的意见(有关媒体的优先级),甚
至在可伸缩的媒体类型出现的情况下也可以。
多语言- ASF设计为支持多语言。媒体流能够可选地指示所含媒体的语言。这个功能常用于音频和文本
流。一个多语言ASF文件指的是包含不同语言版本的同一内容的一系列媒体流,其允许客户机在播放的过
程中选择最合适的版本。
目录信息- ASF提供可继续扩展的目录信息的功能,该功能的扩展性和灵活性都非常好。所有的目录信
息都以无格式编码的形式存储在文件头部分,并且支持多语言,如果需要,目录信息既可预先定义(如,
作者和标题),也可以是制作者自定义。目录信息功能既可以用于整个文件也可以用于单个媒体流。
ASF文件格式 ASF 对象定义 ASF文件基本的组织单元叫做ASF 对象,它是由一个128位的全球唯一的对
象标识符(Object ID),一个64位整数的对象大小(Object Size)和一个可变长的对象数据(Object 
Data)组成。对象大小域的值是由对象数据的大小加上24比特之和。
这个文件组织单元有点类似于RIFF(Resource Interchange File Format)字节片。RIFF字节片时AVI
和WAV文件的基本单位。ASF对象在两个方面改进了RIFF的设计。首先,无需一个权威机构来管理对象标
识符系统,因为计算机网卡能够产生一个有效的唯一的GUID。其次,对象大小字段已定义得足够处理高
带宽多媒体内容的大文件。
高层文件结构 ASF文件逻辑上是由三个高层对象组成:头对象(Header Object)、数据对象(Data 
Object)和索引对象(Index Object).。头对象是必需的并且必须放在每一个ASF文件的开头部分,数据
对象也是必需的,且一般情况下紧跟在头对象之后。索引对象是可选的,但是一般推荐使用。

高层ASF文件结构 在具体实现过程中可能会出现一些文件包含无序的(Out-Of-Order)的对象,ASF也
支持,但在特定情况下,将导致ASF 文件不能使用,如从特定的文件源如HTTP服务器读取该类ASF文
件。同样地,额外的高层对象也可能被运用并加入到ASF文件中。一般推荐这些另加的对象跟在索引对象
之后。

ASF数据对象能够被解释的一个前提条件是头对象已被客户机接收到。ASF没有声明头对象信息是如何到
达客户端的,"到达机制"是一个"本地实现问题",显然已超过了ASF 的定义范围。头对象先于数据对象
到达有三种方式:
包含头对象的信息作为"会话声明"的一部分。
利用一个与数据对象不同的"通道"发送头对象。 在发送ASF 数据对象之前发送头对象。
ASF 头对象 在ASF的三个高层对象中,头对象是唯一包含其他ASF 对象的对象。头对象可能包含一下对
象:
文件属性对象(File Properties Object)----全局文件属性。
流属性对象(Stream Properties Object)----定义一个媒体流和其属性。
内容描述对象(Content Description Object)----包含所有目录信息。
部件下载对象(Component Download Object)----提供播放部件信息。
流组织对象(Stream Groups Object)----逻辑上把多个媒体流组织在一起。
可伸缩对象(Scalable Object)----定义媒体流之间的可伸缩的关系。
优先级对象(Prioritization Object)----定义相关流的优先级。
相互排斥对象(Mutual Exclusion Object)----定义排斥关系如语言选择。
媒体相互依赖对象(Inter-Media Dependency Object)----定义混合媒体流之间的相互依赖关系。
级别对象(Rating Object)----根据W3C PICS定义文件的级别。
索引参数对象(Index Parameters Object)----提供必要的信息以重建ASF文件的索引。
ASF 头对象
头对象的作用是在ASF文件的开始部分提供一个众所周知的比特序列,并且包含所有其它头对象信息。头
对象提供了存储在数据对象中的多媒体数据的全局的信息。
ASF数据对象
数据对象包含一个ASF 文件的所有多媒体数据。多媒体数据以ASF数据单元的形式存储,每一个ASF数据
单元都是可变长的,且包含的数据必须是同一种媒体流。数据单元在当它们开始传输的时候在数据对象
中自动地排序,这种排序来自于交叉存储的文件格式。
ASF索引对象
ASF索引对象包含一个嵌入ASF文件的多媒体数据的基于时间的索引。每以索引进入表现的时间间隔是在
制作时设置的,并且存储在索引对象中。由于没有必要为一个文件的每一个媒体流建立一个索引,因
此,通常利用一个时间间隔列表来索引一系列的媒体流。

2.虚拟文件系统

用户直接调用open,read,write就行,device I/O和Network I/O等信息交给驱动自己实现就好了,
用户不用去管.

底下的Disk中依次装入信息的是
(1)super block
(2)dentries
(3)inodes
(4)datablocks

3.数据缓存

3.1 解决的问题

硬盘的速度相对于内存速度的差远了,所以我们会在内存中开辟一些空间来将一些经常用到的
或者当前正在访问的一些数据从硬盘读到内存中来,接下来的访问都会在内存中进行,以此来提
高效率,这个就是数据缓冲技术(data buffer).

3.2 数据缓冲的方式 

(1)预读入;
(2)延迟写;
(3)缓存方式,磁盘块和页的size不一定是一样的,我们需要知道怎么来组织它们,数据缓存中需要考虑
   这些内容.

我们希望缓存和页式管理可以结合在一些,形成一个分页的缓存机制,使得数据可以更好地被上层应用
来访问,这是一种访问模式.甚至我们可以将一个文件以数据块的结构展现给我们的应用程序,访问的时
候就按照内存的读写来操作就好了,通过内存文件管理子系统的结合,就可以完成高效的缓存和访问方式.
读写的是一个个内存单元,避免了传统的read,write这种传统的系统调用带来的开销,这是一种高效的
基于分页的文件访问手段.这也是值得考虑的.

在这里如何去缓存,缓存哪些页的算法类似于我们说到的页替换算法,I/O缓存的替换算法,需要把经常需要
访问的放到内存中,不需要经常访问的放在磁盘中,缓存空间是有限的.

 

4.打开文件的数据结构

4.1 打开文件描述符和打开文件表

打开一个文件就可以对文件进行读写了,为什么能做到这一步?
首先要对打开文件之后,操作系统做了什么事情有所了解,就知道为什么打开一个文件就可以对文件进行
读写了.

打开一个文件首先要知道文件在这个硬盘中的什么地方,所谓打开,就是把那些硬盘里面存着的关于文件的
文件控制块的内容读到内存中来,首先要查找要找这个文件,找到之后要把文件控制块的内容读到内存中去,
把相关的关键信息放到“打开文件表”里,文件表里专门设置了一个项,然后把这个项的索引返回给我们的应
用程序,所以会有一个fd=open(...),fd就是返回的这个index,接下来的程序只要基于这个index进行读写
就好了,因为正常打开一个文件之后,就以为这“打开文件表”中有一个文件项来表示了这个进程打开的一些
基本的属性在里面了,有了这个属性之后就可以找到和文件相关的数据在硬盘的什么地方.

 4.2 进程打开文件表的过程


当一个进程做了打开操作之后,其实会返回一个index,会指出在进程的打开文件表的哪个位置,把这个项
取出来之后再基于这个项找到系统这个层面打开的文件表,因为是不同进程打开同一个文件,那么在系统
这个层面只要记录一项就可以了,基于这么一项,对于它是目录还是文件,会有不同的处理,这里仅仅对是
文件的时候来做一个讲解:
是一个文件的时候,会通过inode知道这个文件到底在什么地方,会有offset来知道从哪个位置开始读,
这个offset会经过文件控制块的一些转换,会把offset转换成磁盘的一个扇区的编号,要访问这块数据,
就是要访问相应的一系列的扇区,然后文件系统就会把扇区的内容,或者读或者写,以读为例的话,就会
把相应的数据读到内存中去,然后在从这个内存(我们称之为buffer)传回给应用程序.这个就是读操作的
过程.

  4.3 进程对打开文件的权限设置

还有一点就是说,文件是一个共享的资源,会存在锁的保护机制,如果一个进程打开之后就不想
别人来操作了,可以加一些参数来进行权限的保护机制,打开的时候用一些参数来告诉操作系统,
如果不想别的进程访问某个文件并且正常以这种权限打开文件之后,其他进程就不能访问这个文件
了.这是一种强制的方式.

还有一种建议的方式,至于做不做得到,操作系统根据一个缺省的情况来给出一个缺省的配置.

5.分配文件

5.1 分配需要考虑的问题

打开一个文件之后,如果要执行写操作的话,需要给这个文件添加更多的数据,这个就涉及到对这个文件
的数据空间进行管理,需要增加或者减少数据空间,如何进行管理,属于文件分配的内容.

对于用户而言,文件到底有多大,决定了接下来分配的方法,有些文件很小,有些文件很大,比如一个文本
文件只有几k,有的视频文件甚至几个G,文件的类型确实有很多,很难说是一种,只有大或者只有小的,
所以我们要应对不同的文件,针对这个不同的文件,我们希望有一种比较通用的办法,既能对小文件进行
有效访问,也能对大文件的有效访问,需要设计一个如何去分配和管理一个文件块的方法.

 5.2 分配数据块的方法及指标

图中所说的高效在于存储的空间的高效和访问速度的高效.空间利用率高不高,
为了存这么多数据是不是还要用更多的其他数据辅助存储这些数据,这属于存储
的效率问题.性能和存储的效率都是我们需要考虑的.

5.2.1 连续分配

只要给出起始块的位置和长度就可以了,问题是什么呢?
比如说有两个文件:文件A和文件B,文件A在文件B前面,两者相连,现在要对文件A做扩展,
可能不得不把文件B挪一个位子才能对A做扩展,或者把A自身挪到一个拥有更大空间的一个
地方去.这个就是连续分配的问题.这个其实很类似我们对数组的一个操作.
如果说有的文件不扩展,那么是可以的,比如CD-ROM,它是只读的文件光盘,一次性写了一个
之后就不会改变了,那对于这种需求来说,连续分配就很适合.

如果真的要灵活的添加删除或者扩展相应的文件,连续分配的方式就会开销很大,那么它的
性能就会很糟糕,对于它的数据块的分配我们可以采取内存的,连续内存的分配算法,比如
说先适配,最佳适配和首次适配等方法.这个是我们对连续分配策略的一个选择.


优势:
读取效率高.

缺点:
碎片
文件增长问题


使用场景:
只读操作

5.2.2 链式分配

数据块是以链表的形式链起来的,连续分配是数组方式组织起来的,链表的话,增加
和删除就很方便了.

优点:
(1)创建,增大,缩小很容易
(2)没有外碎片(可能在最后的文件块存在扇区没有用满的内碎片)

缺点:
(1)不能实现真正的随机访问(访问必须是串行的,要访问第二块就必须要先找到第一块,不能实现高效的随
   机访问,它是串行访问的特征)
(2)可靠性(文件系统是存在硬盘上的,如果突然断电,数据来不及导进,链接信息可能会丢失,一旦丢失之后,
   能不能够把文件数据都能够找到就可能是一个问题,所以可靠性是一个问题,一旦断了一个链,整个文件 
   就崩了,就不是一个完整的链,不能做后序的访问了,这个是链式存储的问题.

5.2.3 索引分配

基于索引:
它会把特定的磁盘块,数据块作为索引的功能来体现,每个索引项指向了一个数据块.
索引数据块很重要,索引块指出了这个文件所需要的的数据所在的磁盘块的位置.
一般会把索引的数据块专门放在文件头中,作为元数据的一部分保存起来,使得一旦
得到这个索引块之后就可以把索引块调到内存中去,然后再去查找对应要访问的
文件中的位置和对应磁盘块的位置就可以完成后续的工作了.
链式存储需要把一个个磁盘块都顺着找一遍,这里只需要把一个索引块调入内存,
基于索引块可以找到数据块在什么位置,从而可以实现高效查询,对于基于索引的
存储,无论是顺序的还是随机的查询都可以高效地实现.

优点如图

缺点:
当文件很小时,甚至小于数据块,存储索引本身也要占数据块,此时元数据相对来说
占的比例就较大,小文件有问题.
大文件的问题,索引块也是有容量限制的,一个索引块能够描述的数据块的个数是有限的,
当文件很大的时候,一个索引块就不够了,其他索引块如何管理呢?是不是要对索引块进行
扩展,如果索引要扩展的话,那索引块要以什么方式来进行组织呢?这又回到了以前的数组
的方式或者链表的方式呢?这个是要考虑的问题.这里要采取的就是分层的分配方式.
这个方式在之前内存管理的时候提到过,内存管理大的内存空间的页表也是分级的,这里也
一样,会把索引也分级,会有一级索引,二级索引和三级索引,从而实现对大文件的支持.
这样确实会支持多级索引块的方式,但是这个会引入很多开销,需要读多个数据块才能
查到具体的数据块,和页表是一样的.
链式索引块的是线性扩展的方式,对于大文件来说扩展的能力有限,而且链式存储一旦有
链断了就会有问题,所以链式索引块的方式不合适,多级索引块更加合适些.


多级索引块和多级页表有异曲同工之妙.分层的方式来支持大文件和小文件.

6.空闲空间列表

空闲空间主要是站在磁盘的角度来看,要针对一个文件要分配数据块,这个空闲的数据块不属于
具体的文件,但是要被文件系统管理起来,文件系统需要把空闲的空间组织起来,能够快速地在需要
空间的时候快速查找到合适的空间.

6.1 位图 

6.2 链式与分组

6.3 最佳选择

合适的就是最好的,看各个系统的具体实现.

7.多磁盘管理-RAID

7.1 基本概念-磁盘

磁盘是一个机械设备,通过分区来最大限度减少寻道时间,结构如图,是一个个盘片,
它有一个磁头在前后移动,盘面旋转,磁头前后移动来寻道,寻道成功以后在一个圈
里面会有不同的扇区,探针就会读取扇区中的数据,就会把扇区中的数据读到内存中
去,这时它大致的一个工作过程.这里需要注意的是,最慢的一部分就是磁头的前后
挪动.后面还会讲到一些方法来减少磁头开销的访问开销.这个是我们进一步会说明的.

7.2 基本概念-分区与卷

一个典型的文件系统是由分区组成的,磁盘可以分不同的分区,不同的分区由不同的文件系统来
组成.
如图disk1分类两个区,partitionA和partitionB,分别来放置不同的文件系统.
其次还可以有卷,卷可以将多个disk变成一个disk来管理,可以把一个文件系统扩展到多个磁盘上去.

有意思的事情来了.
可以看到,图中的文件系统它是位于不同的磁盘上的,既然是不同的磁盘上,一个磁盘是一个设备,
(1)如果这两个磁盘并行的工作,是不是可以提升文件系统的访问效率呢?
(2)如果这两个磁盘存文件系统中的同样的内容,是不是可以提高系统的可靠性呢?
这就是RAID里面的基本想法.

7.3 RAID

7.3.1 RAID的提出

RAID提出之前,早期的磁盘经常坏掉,访问速度和性能也不高,我们为此想出一个办法,让多个
比较便宜性能不太高的磁盘通过并行的方式并行工作,通过冗余的方式提高数据的可靠性,
实现一种既可靠又高速的存储介质,这就是RAID产生的基本原理,RAID即冗余磁盘阵列.


RAID最早来源于学术界的伯克利大学的一个教授,受制于经费,教授提出让多个比较便宜性能
不太高的磁盘通过并行的方式并行工作的想法.

7.3.2 RAID的发展与实现

RAID随着进一步的发展,从RAID-0开始,一直发展到了RAID-5,RAID-6,不同的代号代表了不同
的组织方式和不同的特征,我们会对不同的特征做一个介绍.在实验上面,可以可以把RAID的功
能实现在硬件里面,也可以实现在软件里面,即所谓的硬RAID和软RAID.(想起了硬负载和软负载)

软RAID是在操作系统里面在文件系统之下,磁盘驱动之上有个RAID层,来完成磁盘阵列的管理.
硬RAID实现在一个芯片里面,放在硬件的控制单元里面,放在主板上,这样对于操作系统而言它
看不到底下具体的RAID,看到的是一个RAID控制器映射出来的虚拟的一个大硬盘,这样操作系统
操作起来很简单,还是正常的文件系统的管理和磁盘的管理,但是它不用意识到底下的具体的硬盘
是如何管理的,底下的硬盘是由我们的RAID硬件控制器来完成的.

老师希望我们对RAID的基本理论有所理解,无论是在软件层面还是在硬件层面.

 7.3.3 RAID-0 能提升吞吐量

这与计算机原理中说的"内存交叉组织"是类似的,我们把数据放在独立的硬盘里面,每个硬盘
可以相对独立的并行的工作,这与就可以实现数据的并行访问,这是一个基本的原则,这个是
RAID-0里面要做的事情.
如图,对于操作系统而言,我们要访问0,1,2,3,12,13,14,15,8,9,10,11这么多数据,发出访问
请求,如果在系统中有三个硬盘,0,1,2,3位于一个硬盘,12,13,14,15位于一个硬盘,8,9,10,11
位于一个硬盘,在这种情况下,这三个硬盘不需要串行可以并行地将这三个硬盘中的数据读出来,
读到我们的内存中来.本来的硬盘访问速度就慢,并行操作之后可以减少硬盘的访问开销,一下
提升了三倍,相当不错,这个就是RAID-0的功劳.
这个是RAID-0提高吞吐率的方法.

7.3.4 RAID-1 提高可靠性

我们写数据的时候是向两个硬盘里面写同样的数据,这个是RAID-1的组织方式,从操作系统里面
做一次写操作实际上最后映射为向两个一样的硬盘写同样的一份数据,这使得两块硬盘里的数据
完全一样,这有什么好处呢?如果第一个硬盘崩了,那么第二个硬盘可以代替第一个硬盘继续工作,
这个就是容错的概念.
当然这个也是有代价的,代价就是本来的一次写操作变成了两次写操作来实现,硬盘起到了镜像的
作用,而不是像在RAID-0中那样要存不同的数据,RAID-1中要存相同的数据.

7.3.5 RAID-4 高性能高可靠

有没有一种方式既可靠性能又高呢?
这其实就是RAID-4,希望既能提高性能又能增加容错的能力.
我们希望有额外的盘来做奇偶校验,用来纠错的.
比如说现在我们有1,2,3,4,Parity这五个盘,把数据均匀分布在1-4这四个盘上,这样可以实现
1-4这四个盘的并行访问.
如果说1-4中的有任何一个盘的数据坏了,我们希望可以通过Parity这个盘把数据恢复回来,
我们可以做到这一步吗?
当然可以,我们可以通过一些纠错码的方式,假设这里面某一个disk坏了,Parity这里存的数据
其实是1-4这些盘里面的奇偶校验,这样某个坏了之后就可以推算出坏的盘里面的内容是什么.
这实际上用了额外的盘来实现容错.

这里需要注意的是,出现一个故障的时候可以恢复,如果四个都坏了,就没戏了.

在这种情况下,往1-4任何一个盘中写一个数据,都要想Parity这个盘里也写一份,这里就有一个
瓶颈,Parity盘的读写非常频繁,它会成为一个瓶颈.自然会带来一个想法,能不能把Patity盘中的
开销均匀地分配在不同的盘里,而不是集中在一个盘里来完成奇偶校验呢?这就推出了RAID-5.

7.3.6 RAID-5 开销均衡的高性能高可靠

将奇偶校验的块均匀分布到不同的disk中,使得大家每个块的开销是类似的,这种
组织方式的校验开销是均匀的且访问是并行,综合了RAID-0和RAID-1的好处,既保证
了高可靠性也提高了效率,这个是目前高端的磁盘阵列里面一个常用的组织方式.

但这个方式只能纠一个错,如果我们想要能够纠两个错,比如说两个盘坏了,那么我们
就需要增加新的奇偶校验的盘的个数.也许就是我们说的其他的方法,如RAID-6等.

7.3.7 奇偶校验的粒度

奇偶校验的单位是以bit还是byte还是block来做呢?
0,4,5是基于block的,3是bit来做的,bit粒度太细,RAID-3理论上是可行的,但是
实际上用的比较少,老师说他没看到过具体产品,一般更多地看到的是RAID-5.

7.3.8 进一步发展

RAID-6可以允许两个磁盘坏掉.
可以通过分层来将RAID-0和RAID-1分层次来形成RAID 0+1或者RAID 1+0这样的组织方式,
来完成特定的既高效又安全的简单组织方式,它不像RAID-5/6那么复杂,但在一定程度上
也能实现容错.这也是一种分层或者嵌套的组织方式,还有更多组织方式可自行研究.

 

8.磁盘调度

8.1 访问时间的计算

磁盘调度是在OS层面通过重新组织IO请求的顺序来有效地减小磁盘访问的开销.
磁盘有旋转来寻道,具体的磁头前后移动找到位子,读相应的扇区才完成整个数据
的读取工作,对于一个硬盘而言,里面可能有多个盘片,每个盘片都有一个或者两
个磁头,如果有正反面就有两个磁头,来完成对数据的读取,所有这些操作,包括旋转
和前后移动都是机械操作,机械操作的速度和我们的内存的电子单元的访问相比
慢了几个数量级,优化机械访问的开销能够提高性能.

磁盘的性能如何表示?
对于一个读写操作,前后移动的磁头首先要固定在一个特定的磁道上,一圈是一个磁道,
不同大小的圈形成整个磁盘,首先找到具体的磁道,磁道上有不同的扇区,然后再具体地
读不同的扇区,定位到磁道的时间叫做寻道时间,在特定磁道上找到对应的扇区的旋转延迟
和具体读扇区的时间合在一起是整个磁盘访问数据的开销.

平均旋转延迟时间=磁盘旋转一周时间的一半

磁盘I/O传输时间的分类:
(1)寻道时间Ts
(2)平均旋转延迟(1/2r)
(3)数据访问时间(b/(rN))
1/r表示旋转一周的时间

8.2 调度策略

寻道时间与其他两个时间相比开销更大,因为前后移动是很慢的,对于单个磁盘来说,
我们希望能够减少寻道的前后移动的时间开销,如何做呢?
如果发现如果请求是随机的,开始寻第一个道然后寻第二个道然后来回循环会导致性
能的急剧下降,那能不能一次寻道把所有的数据都读出来,而不用来回跳转,导致时间
都消耗在磁头的移动上,这个是我们优化的思路.

不同的调度策略可以来减少移动的开销.

8.2.1 先进先出

先来先服务,开销很大,简单但不高效.

8.2.2 最短服务优先

离当前请求最短的位置,确保移动的距离很小,可以得到一个最短的寻道时间.
问题是如果一些请求频繁出现在当前访问的位置,而一些其他请求离当前访问位置很远,
就会出现里当前访问位置很远的请求长时间得不到服务,就导致了饥饿现象.

8.2.3 SCAN

 

SCAN方法有一个约束,就是说磁头(磁臂)先顺着一个方向移到头然后再回来一个防线,有点
类似于我们的电梯,先上到头再下来.
这个请求比较公平的能够使得所有的I/O访问都得到处理.
也称电梯I/O请求调度算法.
这里到头到底是要到最高和最低处.

8.2.4 C-SCAN&C-LOOK

C-SCAN相比于SCAN在位置上显得更公平一些,可以让最初的位置不用等太久.
但它也可以做一个优化--C-LOOK.

C-LOOK并不一定要到达磁盘的某一个终点,而是到底磁盘的最后一个请求处,比如说里终点
最接近的一个请求,再往上走已经没有新的请求点了,这时候就结束了,再往上走其实也没有
意义了,此时就会从起点开始重新开始新一轮的单向扫描.

8.2.5 N-Step-SCAN

8.2.6 FSCAN

8.2.7 对算法的总结

以上算法不能说哪一个是最好的,因为不同场景有不同的需求,实际场景中可能需要更复杂
的算法也可能不需要任何算法.
SSD的硬盘不是一种传统的机械硬盘,就不需要设计算法了;
在硬盘内部有个硬盘控制器,它在内部自己会自己做调整,有时候我们在软件层面做的调整
对于一些高性能的或者更加智能的硬盘来说并不显著.
这些方法是理解的角度来看问题,实际上可能是另一番天地了.

我们需要具体问题具体分析,看看我们的硬盘是普通SSD,还是高端SSD-PCLe,还是机械硬盘等等,都需要
我们做出相应的最好的反应.

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值