7. 文件管理
7.1 磁盘结构与管理
7.1.1 磁盘结构
磁盘是一种随机存取(直接存取)的存储设备,可以直接存取设备上的数据。磁盘由盘片、盘片主轴、磁头和磁头控制器组成,其中,盘片是用于存储数据的,盘片被划分成多个同心圆,称为磁道,磁道由外向内从0开始顺序编号,所有的数据信息被记录在磁道上。磁盘一般由多个盘片组成,每一个盘片包含两个面,其中,最上面和最下面的外侧一般不存储信息。例如,一个磁盘由6个盘片组成,则有10个面可保存信息。
所有的盘面的同一磁道构成一个圆柱,称为柱面,位于同一柱面上的磁道由上往下从0开始编号。每个磁道还可以划分成若干个部分,称为扇区,每个扇区的大小是512字节。扇区所在的磁道地址称为扇区号。
例如,某磁盘有10个有效记录面,记录面上有效记录区域的内径为20cm,外径为30cm,道密度为10道/mm,每个磁道有16个扇区,每个扇区记录512字节,则该磁盘容量是: 记录面数x磁道数x磁道扇区数x扇区的字节数=10x(30-20)/2x10x10x16x512=40960000字节。
要存取某一数据信息,首先需要找到数据所在的柱面,移动磁头到所在的柱面即磁道,然后移动磁头到具体的数据存放位置,因此,要存取磁盘上的数据信息所需要的时间由3部分组成:寻道时间、等待时间和传输时间。其中,寻道时间Tseek就是读写磁头寻找数据所在磁道并定位的时间,等待时间Tw就是将磁头移动到数据所在的起始位置,传输时间Trw就是读或写数据所需要的时间。即T=Tseek+Tw+Trw。
7.1.2 磁盘调度算法
磁盘调度分为移臂调度和旋转调度两类,并且是先进行移臂调度,然后再进行旋转调度。
1. 移臂调度
在有对个进程访问磁盘时,选择什么样的算法以求得最小的访问时间,是所要研究的问题。当有不同进程的磁盘I/O请求构成一个随机分布的请求队列,磁盘I/O调度的目标就是减少请求队列对应的平均柱面定位时间。平均柱面定位时间决定了读取速度。
1)先进先出(FIFO)算法
磁盘I/O执行顺序为磁盘I/O请求的先后顺序。该算法的特点是公平,在磁盘I/O负载较轻且每次读写多个连续扇区时,性能较好。
2)短查找时间优先(Shortest Seek Time First,SSTF)算法
即考虑磁盘I/O请求队列中各请求的磁头定位位置,选择从当前磁头位置出发,移动最少的磁盘I/O请求。该算法的目标是使每次磁头移动时间最少。他不一定是最短平均柱面定位时间,但比FIFO算法有更好的性能。对中间的磁道有利,可能会有进程处于“饥饿”状态。
3)扫描(SCAN)算法
选择在磁头前进方向上从当前位置移动最少的磁盘I/O请求执行,没有前进方向上的请求时才改变方向。该算法是对SSTF算法的改进,磁盘I/O较好,且没有进程会饿死。
4)循环扫描(C-SCAN)算法
在一个方向上使用扫描算法,当到达边沿时直接移动到另一沿的第一个位置。该算法可改进扫描算法对中间磁道的偏好。实验表明,该算法在中负载或重负载时,磁盘I/O性能比扫描算法好。
5)N步扫描(N-step-SCAN)算法
把磁盘I/O请求队列分为长度为N的段,每次使用扫描算法处理这N个请求。当N=1时,该算法退化为FIFO算法。该算法的目标是改进前几种算法中可能的在多磁头系统中出现磁头静止在一个磁道上,导致其他进程无法及时运行磁盘I/O。
6)双队列扫描(FSCAN)算法
把磁盘I/O请求分成两个队列,交替使用扫描算法处理一个队列,新生成的磁盘I/O请求放入另一队列中。该法算法的目标与N步扫描算法一致。
2. 旋转调度
当移动臂定位后,有多个进程等待待访问该柱面时,应当如何决定这些进程的访问顺序呢?显然系统应该选择等待时间最短的进程对磁盘的扇区进行访问。
7.2 文件和文件系统
7.2.1 文件和文件系统的概念
文件是指一组带标识(标识即为文件名)的、在逻辑上有完整意义的信息项(构成文件内容的基本单位(单个字节, 或多个字节),各信息项之间具有顺序关系)的序列。文件其实是对磁盘的抽象。文件内容的意义由文件创建者和文件使用者解释。
文件管理系统是操作系统中实现文件统一管理的一组软件和相关数据的集合,专门负责管理和存取文件信息的软件机构欧,简称文件系统。文件系统有以下几个功能:
1)实现按名存取——实现文件从名字空间到外存地址空间的映射
2)实现文件信息的共享,并提供文件保护与保密措施
3)文件系统向用户提供给一个方便的接口
4)提供与 I/O 的统一接口
7.2.2 文件的分类
文件分类的目的是对不同文件进行管理,提高系统效率。按照不同的要求,可以将文件分为不同的类型。
按文件性质和用途分类,可将文件分为系统文件、库文件和用户文件。
按信息保存期限分类,可将文件分为临时文件、档案文件和永久文件。
按文件的保护方式分类,可将文件分为只读、读写、可执行和不保护文件。
7.3 文件的结构和组织
文件的结构是指文件的组织形式,从用户角度看到的文件组织形式称为文件的逻辑结构;从实现的角度看文件在文件存储器上的存储方式,也就是说文件的物理结构。
7.3.1 文件的逻辑结构
文件的逻辑结构可分为两大类:有结构的文件和无结构的文件。
1. 有结构的文件
有结构的文件是指由若干个相关的记录构成的文件,又被为称记录式文件。文件中的记录一般有着相同或不同数目的数据项,按记录的长度,记录式文件可分为两类:(1) 等长记录文件,指文件中所有记录的长度都是相等的。
(2) 变长记录文件,指文件中各记录的长度不相同。
2. 无结构的文件
无结构的文件又称流式文件,组成流式文件的基本信息单位是字节或字,其长度是文件中所含字节的数目,如大量的源程序和库函数等。
7.3.2 文件的物理结构
文件的物理结构指文件在外存物理存储介质上的结构,它可分为连续结构、链接结构和索引结构3种。
1. 连续结构:一个逻辑文件信息依次存放在外存的若干连续物理块中的结构称为文件的连续结构。
2. 连接结构:文件的链接结构是用非连续的物理块来存放信息,每个物理块设有一个指针指向下一个物理块。
3. 索引结构:将逻辑文件顺序地划分成等长与物理存储块相同的逻辑块,并为每个文件分别建立逻辑块号与物理块号的对照表。
7.4 文件的目录
为了便于对文件进行存取和管理,必须建立文件名与文件物理位置的对应关系。在文件系统中,这种关系称为文件目录,它是一种表格。每个文件占用一个表目称为文件的目录项,即为每个文件设置用于描述和控制文件的数据结构,记载该文件的基本信息,如文件名、文件存放的位置、文件的物理结构等。这个数据结构称为文件控制块(FCB)。常用的文件目录结构有一级目录结构、二级目录结构、多级目录结构和图形目录结构。
7.4.1 一级目录
一级目录(单级目录)是指把系统中的所有文件都建立在一个目录下,每个文件占用其中一个目录项。如图:
一级目录结构简单,但缺点是查找速度慢,不允许重名且不便于实现文件共享。
7.4.2 二级目录
二级目录由主文件目录(Master File Directory,MFD)和用户目录(User File Directory,UFD)组成的。在主文件目录中包括用户名和指向该用户目录文件的指针。用户目录由用户所有文件的目录项组成。如图:
二级目录结构提高了搜索文件的时间,较好的解决了重名问题。但是二级目录结构也存在一些问题,该结构虽然能有效地将多个用户隔离开,这种隔离在各个用户之间完全无关时是一个优点,但当多个用户之间要互相合作去共同完成一个大任务时,这种隔离便成为了一个缺点,因为这种隔离使各个用户之间不便于共享文件。
7.4.3 多级目录
在多道程序设计系统中常采用多级目录结构,这种目录结构像一棵倒置的有根树,所以也称为树形目录结构。从树根向下,每一个节点是一个目录,叶节点是文件。
采用多级目录结构的文件系统,用户要访问一个文件,必须指出文件所在的路径名,路径名可由从根目录开始到该文件的通路上的所有各级目录名拼起来得到。各目录名之间、目录名与文件名之间需要用分隔符隔开。
7.5 文件的共享
7.5.1 共享动机
文件共享是指不同用户进程使用同一文件,它不仅是不同用户完成同一任务所必须的功能,而且还可以节省大量的主存空间,减少由于文件复制而增加的访问外存的次数。
7.5.2 共享方式
文件共享方式分为静态共享和动态共享。
1. 静态共享
若不管用户是否正在使用系统,文件的连接关系都是存在的,这种共享关系成为静态共享。静态共享是使两个以上用户通过连接关系,达到共享文件的目的。用文件连接代替文件复制,不仅可以提高文件资源利用率,还可以节省文件存储器的存储空间。
2. 动态共享
动态共享是指系统中不同的用户进程,或同一用户的不同进程可并发地访问同一文件。这种共享关系,仅当用户进程存在时才可能存在,一旦用户进程消亡,共享关系也就自动消失。
7.6 文件保护
实现文件保护措施可以从两方面考虑:一是防止系统故障造成破坏;而是防止用户共享文件时可能造成的破坏。一种方法可以建立文件副本和定时转储;另一种是实现文件保密措施,包括隐藏文件目录、设置口令和对文件进行加密等方法。
7.6.1 访问类型
访问时围绕文件内容读写进行的操作。有如下几种访问类型。
1)打开(open):文件读写所进行的准备。包括给出文件路径,获得文件句柄,或文件描述符,所需文件的目录项读入到内存中。
2)关闭(close):释放文件描述符,把该文件在内存缓冲区的内容更新到外存上。
3)复制文件句柄(dup):用于子进程间文件共享,复制前后的文件句柄有相同的文件名、文件指针和访问权限。
4)读(read)、写(write)和移动文件读写指针(lseek):相同系统为每个打开文件维护一个读写指针,它是相对于文件开头的偏移地址(offset)。读写指针指向每次文件读写的开始位置,在每次读写完成后,读写指针按照读写的数据量自动后移相应的数值。
5)执行(exec):执行一个可执行文件。
6)修改文件的访问模式:提供对打开文件的控制,如文件句柄复制、读写文件句柄标志、读写文件状态标识、文件锁定控制、流的控制。
7.6.2 访问控制
访问控制是围绕文件属性控制进行的操作。
1)创建(create和open):给出文件路径,获得新文件的文件句柄。
2)删除(unlink):对于symbolic link和hard link,删除效果是不同的。
3)获得文件属性(stat和fstat):stat的参数为文件名,fstat的参数为文件句柄。
4)修改文件名(rename)。
5)修改文件属性(chowm)。
6)修改访问权限(chmod)。
7.7 存取方式和存储空间的管理
文件的存取方法是读写文件存储器上的一个物理块的方法,通常有顺序存取和随机存取两种。顺序存取是指对文件中的信息按顺序依次读写;随机存取是指对文件中的信息按任意次序随机读写。
外存具有大容量的存储空间,被多用户共享,用户执行程序经常要在磁盘上存储文件和删除文件,因此文件系统必须对磁盘空间进行管理。对外存空闲空间管理的数据结构通常称为磁盘分配表(Disk Allocation Table)。常用的空闲空间的管理方法有空闲区表、位示图、空闲块链和成组链表。
7.7.1 空闲区表
该方法将外存空间上一个连续未分配区域称为“空闲区”。操作系统为磁盘外存上所有空闲区建立一张空闲表,每个表项对应一个空闲区,空闲表中包含序号、空闲区的第一块号、空闲块的块数等信息。它适用于连续文件结构。
7.7.2 位示图
这种方法是在外存上建立一张位示图(Bitmap),记录文件存储器的使用情况。每一位对应文件存储器上的一个物理块,取值0和1分别表示空闲和占用。文件存储器上的物理块一次编号为0、1、2、...。这种方法的主要特点是位示图的大小有磁盘空间的大小(物理块总数)决定,位示图的描述能力强,适合各种物理结构。
当存储文件时,根据需要的块数在位示图中找状态为“0”的为,然后将信息存入,并将状态改为“1”。同时,根据某块信息对应的字、位可算出该块的块号,然后确定这些块在哪个柱面上,对应哪个扇区,哪个柱面。简单的算法是,假定m=[块号/字长],n={块号/字长}([]表示取整数,{}表示取余数),则由块号可计算出:
柱面号=m+1
磁头号=[n/4]+1
扇区号={n/4}+1
这些文件信息就可按照物理位置存放到磁盘上。
7.7.3 空闲块链
每个空闲物理块都有指向下一个空闲物理块的指针,所有空闲物理块构成一个链表,链表的头指针放在文件存储器的特定位置上(如管理块中)。由于不需要磁盘分配表,因而可以节省空间。每次申请空闲物理块时只需根据链表的头指针取出第一个空闲物理块,根据第一个空闲物理块的指针可找到第二个空闲物理块,依次类推即可。
7.7.4 成组链接
在UNIX系统中,将空闲块分成若干组,每100个空闲块为一组,该组空闲块总数和各空闲块块号存入下一组的第一个空闲块中。最后不满100块的那组空闲块总数和各块空闲块号记入磁盘区专用管理块的空闲块管理的数据结构。
1. 空闲盘块的组织
1)设置空闲盘块号栈。
2)文件区中的所有空闲盘块被分为若干个组,将每100个盘块作为一组。假定盘上共有10000个盘块,每块大小为1KB,其中第201—9999号盘块用于存放文件,即倒数第二组的盘块号为301—400;最后一组为201—300。
3)将每一组含有的盘块总数N和该组所有的盘块号记入其前一组的第一个盘块中,这样,由各组的第一个盘块可看成一条链。
4)将第一组的盘块总数和所有的盘块号,记入空闲盘块号栈中,作为当前可供分配的空闲盘块号。
5)最后一组只有99个盘块,其盘块号分别记入前一组的S.free(1)—S.free(99)中,而在S.free(0)中则存放“0”,作为空闲盘块链的结束标志。