文件是以硬盘为载体的存储在计算机上的信息集合,可以是文本文档,图片,程序等。
系统运行时计算机以进程为基本单位进行资源的调度和分配;用户进行的输入输出中,则以文件为基本单位
当用户将文件进行程序输入输出时,还希望可以访问,修改和保存文件等,实现对文件的维护管理,这就需要系统提供一个文件管理系统,操作系统中的文件系统就是用于实现用户的这些管理要求的
文件中肯定包括一块存储空间,包含分类和索引的信息,以及一些关于访问权限的信息
文件的结构:
(1)数据项:文件系统中最低级的数据组织形式
(2)记录:一组相关的数据项的集合,描述一个对象在某方面的属性
(3)文件:有创建者所定义的具有文件名的一组相关元素的集合,可以分为有结构文件和无结构文件两种
便于文件管理,操作系统引入了==文件控制块(FCB)==的数据结构
文件的属性
名称:唯一,以容易读取的形式保存
类型:被支持不同类型的文件系统所使用
创建者:ID
所有者:ID
位置:指向设备和设备上文件的指针
大小:文件当前大小,也可 包含文件允许的最大值
保护:对文件进行保护的访问控制信息
创建时间,最后一次修改时间和最后一次存取时间
文件控制块FCB
存放控制文件所需要的各种信息的数据结构,以实现按名存取
FCB的有序集合称为文件目录,一个FCB就是一个文件目录项;一个新文件的FCB会存放在文件目录中,称为目录项
FCB主要包含以下信息:
基本信息:文件名,位置,逻辑结构,物理结构等
存取控制信息:文件主的存取权限,核准用户的存取权限及一般用户的存取权限
使用信息:文件建立时间,上次修改时间等
一个文件目录也被视为一个文件,称为目录文件
索引结点
检索目录的过程中,只用到了文件名,仅当找到一个目录项(匹配时)时才需要从目录项中读出该文件的物理地址,所以文件的其他描述信息不会用到,也就不需要调入内存,有点系统就采用了文件名和文件描述信息分开的方法,使文件描述信息单独形成一个称为索引结点的数据结构,简称i结点。在文件目录中的每个目录项仅由文件名和指向该文件所对应的i结点的指针构成。
(1)磁盘索引结点:存放在磁盘的索引结点,每个文件唯一
(2)内存索引结点:存放在内存中的索引结点,文件被打开时,要将磁盘索引结点复制到内存的索引结点中,便于以后使用
文件的基本操作
(1)创建文件:分配空间,创建目录项
(2)写文件
(3)读文件
(4)重新定位文件
(5)删除文件
(6)截断文件
文件的打开与关闭
为避免多次重复的检索目录,大多数操作系统要求,在文件使用之前通过系统调用open被显式的打开
操作系统维护一个包含所有打开文件信息的表(打开文件表)
打开:是指调用open根据文件名检索目录,将指明文件的属性(包含物理位置),从外存复制到内存打开文件表的一个表目中,并将该表目的编号(也称索引)返回给用户
当用户再次向系统发出文件操作请求时,可通过索引在打开文件表中查到文件信息,从而节省再次搜索目录的开销;当文件不再使用时,可利用系统调用close关闭它,操作系统将会从打开文件表中删除这一条目
多个不同进程可以同时打开文件的操作系统中,通常采用两级表,整个系统表和每个进程表
系统的打开文件表包含FCB的副本及其他信息,进程的打开文件表根据打开的所有文件,包含指向系统表中适当条目的指针
系统打开文件表为每个文件关联一个打开计数器open count,以记录多少进程打开了该文件,count=0表示文件不再被使用,可从系统打开文件表中删除相应条目
文件名不必是打开文件表的一部分,因为一旦完成对FCB在磁盘上的定位,系统就不再使用文件名
对于访问打开文件表的索引,UNIX称之为文件描述符,Windows称之为文件句柄
每个打开文件都具有如下关联信息:
可以通过口令保护,加密保护和访问控制等方式实现
访问控制
解决访问控制最常用的方法是根据用户身份进行控制,实现基于身份访问的最为普通的方法是,为每个文件和目录增加一个访问控制列表,规定每个用户名及其所允许的访问类型
优点是可以使用复杂的访问方法,缺点是铲毒无法预计并且可能导致复杂的空间管理,使用精简的访问列表可以解决这个问题:
(1)拥有者:创建文件的用户
(2)组:一组需要共享文件且具有类似访问的用户
(3)其他:系统内的所有其他用户
口令是指用户建立文件时提供一个口令,系统为其建立FCB时附上相应口令,请求访问时必须提供相应的口令
密码是对文件进行加密,访问时需要使用密匙
从用户观点出发看到的文件的组织形式,与存储介质特性无关,实际是指在文件的内部,数据逻辑上是如何组织起来的
按逻辑结构分为无结构文件和有结构文件两大类
无结构文件
最简单的文件组织性质,将数据按顺序组织成记录并积累,保存,是有序相关信息项的集合,以字节为单位,只能通过穷举搜索的方式;对基本信息单位操作不多的文件较适于采用字符流的无结构方式,如源程序文件,目标代码文件等
有结构文件
(1)顺序文件
文件的记录一个接一个的顺序排列,记录通常是定长的,可以顺序存储或以链表形式存储
有两种结构:
串结构:通常按存入时间的先后进行排列,必须从头开始顺序依次查找,费时
顺序结构:所有记录按关键字顺序排列,可采用折半查找,提高了效率
批量操作时顺序文件效率高,但是单个记录的操作,顺序文件性能较差
(2)索引文件
变长记录文件只能顺序查找,效率低,为此可以建立一张索引表,为每个记录设置一个表项,包含指向变长记录的指针和记录长度
索引表按关键字排序,因此其本身也是一个定长记录的顺序文件
(3)索引顺序文件
是顺序文件和索引文件的结合,最简单的索引顺序文件只使用了一级索引
将顺序文件中的所有记录分为若干组,为顺序文件建立一张索引表,在索引表中为每组中的第一条记录建立一个索引项,其中含有该记录的关键字值和指向该记录的指针
索引表只包含关键字和指针两个数据项,所有姓名关键字递增排列;主文件中记录分组排列,同一个组中的关机子可以无序,但组与组之间的关键字必须有序;查找一条记录时,首先通过索引表找到其所在的组,然后在该组中使用顺序查找,就能很快的找到记录
顺序文件平均查找N/2次,索引顺序文件平均查找== N \sqrt{N} N次==
速度提高了但配置索引表增加了存储空间
(4)直接文件或散列文件
给定记录的键值或通过散列函数转换的键值直接决定记录的物理位置。没有顺序的特性
存取速度开,但会引起冲突
文件的分配方式:对磁盘非空闲块的管理
文件的存储空间管理:对磁盘空闲块的管理
常见的磁盘空间分配方法有三种:连续分配,链接分配和索引分配
连续分配
每个文件在磁盘上占用一组连续的块,使得作业访问磁盘时需要的寻道数和寻道时间最小
支持顺序访问和直接访问,实现简单,存取速度快;
缺点:文件长度不宜动态增加,否则开销大;删除插入时都需要相邻记录物理上移动,还会动态改变文件的长度;反复增删文件产生外部碎片;很难确定文件需要的空间大小,因此只适合长度固定的文件
链接分配
是一种离散分配,消除了磁盘的外部碎片,提高了磁盘的利用率
(1)隐式链接
目录项中含有文件的第一块指针和最后一块指针
缺点:只适合顺序访问;稳定性也是一个问题,系统在运行过程中指针丢失或损坏导致文件数据的丢失
解决方案是将几个盘块组成簇,按簇而不按块来分配,可以成倍的减少查找时间,但是增加了内部碎片
(2)显式链接
把用于链接文件各物理块的指针,从每个物理块的末尾中提取出来,显式的存放在内存的一张链接表,该表在整个磁盘中仅设置一张,称为文件分配表(FAT),每个表项存放链接指针,即下一个盘块号,文件第一个盘块号记录在目录项物理地址字段中,后续的盘块可通过查FAT找到
FAT不仅记录了文件各块直接的先后链接关系,还标记了空闲的磁盘块,操作系统也通过FAT对文件存储空间进行管理
FAT表在系统启动时被读入内存,不仅提高了检索速度,还减少了访问磁盘的次数
链接分配的问题:不能有效支持直接访问(FAT除外);FAT需要占用较大的内存空间
索引分配
打开文件时,实际上只需将该文件对应盘块的编号调入内存即可,完全没有要将整个FAT调入内存,为此,索引分配将每个文件所有的盘块号都集中放在一起构成索引块(表)
优点:支持直接访问,没有外部碎片
缺点:增加了系统存储空间的开销
每一个文件一个索引块,所以索引块应尽可能小,但太小无法支持大文件,解决办法:
但是访问文件需要两次访问外存,先读取索引块的内容,然后访问具体的磁盘块,降低了文件的存取速度,可以将文件的索引块读入内存,提高访问速度
混合索引分配
与文件管理系统和文件集合相关联的是文件目录
基本要求:实现按名存取;提高检索速度;提供用于控制访问文件的信息
允许不同用户对不同文件采用相同的名字,以便于用户按自己的习惯给文件命名,目录管理通过树形结构来解决和实现
单级目录结构
整个文件系统一张目录表,每个文件占一个目录项
查找速度慢,不允许重名,不便于共享等缺点,对多用户系统不适用
两级目录结构
分成主文件目录MFD和用户文件目录UFD
访问文件只需搜索用户对应的UFD,解决了重名问题,又保证了一定的安全
提高了检索速度,解决了多用户重名问题,但是缺乏灵活性,不能对文件分类
树形目录结构
从根目录出发的路径成为绝对路径
层次较多时,从根目录查询会浪费时间,于是加入了当前目录(工作目录),进程对各文件的访问都是相对于当前目录进行的,用户访问文件使用相对路径标识文件
树形目录很方便对文件分类,层次结构清晰,有效的进行管理和保护;但是查找一个文件需要按路径名逐级访问中间结点,增加了磁盘访问次数,影响了查询速度,且不便于文件共享
无环图目录结构
在树形的基础上增加了一些指向同一结点的有向边,使得整个目录称为一个有向无环图
给每个共享结点设置一个共享计数器,每当图中增加对该结点的共享链时,计数器加1,删除该结点时,计数器减1,为0才是真的删除该结点
无环图实现了文件的共享但系统的管理变得更加复杂
搜索;创建文件;删除文件;创建目录;删除目录;移动目录;显示目录;修改目录
线性列表;哈希表
文件的物理地址及其他的文件属性等信息,不再放在目录项中,而放在索引结点中,在文件目录中只设置文件名及指向相应索引结点的指针,同时还有一个链接计数count,只有count=0才能删除文件
用户B共享用户A的一个文件F,系统创建一个LINK类型的新文件,也取名F,并将该文件写入用户B的目录中,以实现用户B的目录与文件F的链接;新文件中只包含被链接文件的路径名;用户B访问F,系统就通过路径名找到F,实现共享,这就是符号链接(比如桌面快捷方式)
只有文件主才拥有指向其索引结点的指针
所以删除文件后,其他用户就无法访问了
同时访问文件可能需要多次读盘,开销大
软硬链接都是文件系统的静态共享方法,还存着另外的共享需求,即两个进程同时对同一个文件进行操作,称为动态共享
文件系统提供高效和便捷的磁盘访问,以便允许存储,定位,提取数据
两个不同的设计问题:定义文件系统的用户接口;创建算法和数据结构,以便映射逻辑文件系统到物理外存设备
(1)I/O控制
包括设备驱动程序和中断处理程序
(2)基本文件系统
向对应的设备驱动程序发送通用命令,以读取和写入磁盘的物理块,同时对缓冲区进行管理
(3)文件组织模块
组织文件及其逻辑块和物理块,可以将逻辑块地址转换成物理块地址
(4)逻辑文件系统
管理元数据信息
文件系统在磁盘中的结构
存放在磁盘上,多数磁盘划分为一个或多个分区,每个分区中有一个独立的文件系统
主引导记录MBR:计算机启动时,BIOS读入并执行MBR,MBR做的第一件事是确定活动分区,读入它的第一块,即引导块
引导块:负责启动该分区中的操作系统
超级块:文件系统的所有关键信息
文件系统的空闲块信息,可以使用位示图或指针链接的形式给出
文件系统在内存中的结构
内存中的信息用于管理文件系统并通过缓存提高性能。
这些数据结构的类型可能包括:
(1)内存中的安装表:包含每个已安装文件系统分区的有关信息
(2)内存中的目录结构的缓存:包含最近访问目录的信息
(3)整个系统的打开文件表:包含每个打开文件的FCB副本以及其他信息
(4)每个进程的打开文件表:包含一个指向整个系统的打开文件表中的适当条目的指针以及其他信息
包含文件系统的分区通常称为卷,卷可以是磁盘的一部分,也可以是整个磁盘,还可以是多个磁盘组成的RAID集
在一个卷中,存放文件数据的空间(文件区)和FCB的空间(目录区)是分离的,卷在提供文件服务前,必须对相应的文件程序进行初始化,划分好目录区和文件区,建立空闲空间管理表格及存放卷信息的超级块
文件存储设备分成许多大小相同的物理块,并以块为单位交换信息
空闲表法
属于连续分配方式,为每个文件分配一块连续的存储空间,为所有空闲区建立一块空闲表,每个空闲区对应一个空闲表项,其中包括表项序号,该空闲区的第一个盘块号,该区的空闲盘块数等信息;所有空闲区按其起始盘块号递增的次序排列
也可以采用首次适应算法和最佳适应算法
空闲链表法
将所有空闲盘区拉成一条空闲链,可分为两种形式
(1)空闲盘块链:所有空闲空间以盘块为单位拉成一条链,实现简单,但可能重复操作,效率低,链会很长
(2)空闲盘区链:所有空闲盘区拉成一条链,除了含有指示下一个空闲盘区的指针外,还应有能指明本盘区大小(盘块数)的信息,回收分配过程复杂但是效率高,链短
空闲表和空闲链表都不适用于大型文件系统,因为会使得空闲表过大
位示图法
利用二级制的一位来表示磁盘中一个盘块的使用情况,0表示空闲,1表示已分配
下标也可以从0开始,下列计算公式需要改变
盘块的分配:
(1)顺序扫描位示图,找到一个或一组0的二进制位
(2)将找到的二进制位转换成对应的盘块号,b=n(i-1)+j
(3)修改位示图,map[i,j]=1
盘块的回收:
(1)将回收的盘块号转换成位示图的行号和列号
i=(b-1)DIV n+1
j=(b-1)MOD n+1
(2)map[i,j]=0
成组链接法
结合了空闲表和空闲链表法,用来存放一组空闲盘块号(空闲盘块的块号)的盘块称为成组链块
把顺序的n个空闲盘块号保存在第一个成组链块中,其==最后一个空闲盘块(作为成组链块)==则用于保存另一组空闲盘块号,如此继续,直到所有的空闲盘块都链接了
分配:根据第一个指针把对应的盘块分配给用户,指针下移,如果指针指向最后一个盘块,把盘块读入内存,并将指针指向新的成组链块的第一条记录,然后继续操作
回收:成组链块的指针上移一格,再计入回收盘块号,连接数为n表示已满,将现有已记录n个空闲盘块号的成组链块号计入新回收的盘块
超级块:位向量表或成组链块,以及卷中的目录区,文件区划分信息都要存放在磁盘中,一般放在卷头位置
对卷中文件进行操作前,超级块需要预先读入系统空闲的主存,并且经常保持主存超级块与磁盘卷中超级块的一致性
虚拟文件系统VFS为用户程序提供了文件系统操作的统一接口(统一调用函数如open),屏蔽了不同文件系统的差异和操作细节
为了实现VFS,Linux主要抽象了四种对象类型,每个VFS对象都存放在一个适当的数据结构中,其中包括对象的属性和指向对象方法(函数)表的指针
下图是一个进程与文件进行交互的简单实例,两个进程使用同一个硬链接,只需两个目录对象,每个硬链接对应一个目录项对象
VFS还能提高系统性能,最近最常使用的目录项对象放在目录项高速缓存的磁盘缓存中,以加速从文件路径名到最后一个路径分量的索引结点的转换过程
VFS实际不是一种文件系统,只存在内存中,不存在任何外存空间,在系统启动时建立,关闭时消亡