1.概述
文件(File)
是以硬盘为载体的存储在计算机上的信息集合,文件可以是文本文档、图片、程序等,基本访问单元可以是字节或记录,可以长期储存在硬盘中,并允许可控制的进程间共享访问,还可以被组成成更复杂的结构。
在系统运行时,计算机以进程
作为资源调度和分配的基本单位;在用户进行输入输出时,则以文件
作为基本单位。
OS为用户提供了一个文件管理系统,即OS中的分级系统(File System),以满足用户对于文件的访问、修改和保存等需求。
数据项
FS中最低级的数据组织形式。
分类:
基本数据项
:用于描述一个对象的某种属性的一个值,是数据中的最小逻辑单位。组合数据项
:由多个基本数据项组成。
记录
是一组相关的数据项的集合,用于描述一个对象在某方面的属性。
文件
是指由创建者所定义的、具有文件名的一组相关元素的集合。分为有结构文件和无结构文件两种。
在有结构的文件中,文件由若干个相似的记录构成;在无结构的文件中,文件则被视为一个字符流。
UNIX系统中,I/O设备被视为特殊文件。
2.文件的属性
名称
:文件名称是唯一的。类型
。创建者
:文件创建者的ID。所有者
:文件当前所有者的ID。位置
:指向设备和设备上文件的指针。大小
:文件当前大小(用字节、字或块表示)。保护
:对文件进行保护的访问控制信息。创建时间
:文件创建的时间。最后一次修改时间
:文件上次修改的时间。最后一次存取时间
:文件上次访问的时间。
OS通过
文件控制块(FCB)
来维护文件的元数据。
3.文件控制块(FCB)/文件目录项
TCB是用来存放控制文件需要的各种信息的数据结构,以实现“按名存取”。
FCB的有序集合称为文件目录,换言之,FCB是一个文件目录项。
基本信息
:如文件名、文件的物理位置、文件的物理结构、文件的逻辑结构等。存取控制信息
:包括文件所有者的存取权限、核准用户的存取权限和一般用户的存取权限。使用信息
:如文件的创建时间、文件的最后一次修改时间等。
一个文件目录也可以被视为一种文件,称为目录文件。
有些OS将文件描述信息从目录项中分离出来,这样做可以减少查找文件时的I/O信息量。
4.索引节点
4.1 概述
在一些OS中(如UNIX),采用了文件名和文件描述信息项分开的方法,使文件描述信息单独形成一个称为索引节点的数据结构,简称为i节点(inode)
。在文件目录中的每个目录项仅由文件名和指向该文件对应的i节点的指针构成。
4.2 分类
4.2.1 磁盘索引节点
指存放在磁盘上的索引节点,每个文件都有一个唯一的磁盘索引节点。
组成
文件类型
:包括普通文件、目录文件、特别文件。文件存取权限
:各类用户对于该文件的存取权限。文件物理地址
:每个索引节点含有13个地址项,即iaddr(0) ~ iaddr(12),它们以直接或间接的方式给出数据文件所在盘块的编号。文件长度
:指明以字节为单位的文件长度。文件链接计数
:FS在所有指向该文件的文件名的指针计数。文件存取时间
:文件最近一次被存取、被修改的时间以及索引节点被修改的时间。
目录文件是FCB的集合,一个目录中既可能有子目录,还可能有数据文件,因此目录文件存放的是子目录和数据文件的信息。
4.2.2 内存索引节点
指存放在内存中的索引节点,当文件被打开时,要将磁盘索引节点复制到内存的索引节点中去,以便后续使用。
组成
索引节点编号
:用于标识内存索引节点。状态
:指明i节点是否 被上锁或被修改。访问计数
:每当有进程访问该i节点时,计数+1
,访问结束则-1
。逻辑设备号
:文件所属FS的逻辑设备号。链接指针
:设置分别指向空闲链表和散列队列的指针。
(磁盘索引节点的属性它也有哦😘)
所能创建的最大文件数量取决于索引节点的数量。
5.文件的操作
5.1 创建文件
- 为新创建的文件分配必要的外存空间。
- 在目录中为之创建一个目录项,目录项记录了新文件名、在外存中的地址以及其他可能的信息。
5.2 写文件
将执行一个系统调用,从文件目录中检索出对应文件名的文件位置。系统还需要为该文件维护一个写指针。每当发生写操作时,便更新这个写指针。
5.3 读文件
将执行一个系统调用,从文件目录中检索出对应文件名的文件位置。系统还需要为该文件维护一个读指针。每当发生读操作时,便更新这个读指针。由于一个进程通常只对一个文件进行读或写,因此可以将读写指针合用,从而节省了空间,降低了系统复杂度。
用户进程通过read系统调用读取一个磁盘文件中的数据时:
若该文件的数据不在内存,则该进程进入睡眠等待状态(阻塞态)。
请求read系统调用将导致CPU从用户态切换核心态。
使用read系统调用并不需要文件的名称,而需要:文件描述符fd、buf缓冲区首址、传递的字节数n。
5.4 删除文件
先从文件目录中检索出对应文件的目录项,然后释放该文件所占的存储空间和对应的PCB,并删除该目录项。
5.5 重新定位文件
从文件目录中检索出某个目录项,然后将当前文件位置指针定位到此处。(该操作不涉及文件读写)
5.6 截断文件
保持文件所有属性不变,删除其文件的内容,并将其长度置0,然后是否其文件内容占据的空间。
5.7 文件的打开与关闭
打开是指通过系统调用open
根据文件名检索文件目录,然后将指明文件的属性信息从外存复制到内存打开文件表中的一个表项中去,同时将该表项的索引返回给用户。这样待用户下次向系统发出文件操作请求时,就无需再从文件目录中进行检索了,只需要同文件打开表中就能查到文件信息。
关闭是指当文件不再使用时,将调用系统调用close
来关闭它,OS将从文件打开不中删除这一表项。
通常OS会采用二级表,即整个OS表和每个进程表。
整个OS的文件打开表包含FCB的副本以及其他信息,每个进程的打开文件表将根据进程打开的文件,包含指向系统的打开表中的适当条目的指针。
通常,系统的文件打开表中会为每个表项关联一个打开计数器(Open Count)
,以记录多少进程打开了该文件。
当进程调用open
时,将在其进程的文件打开表中增加一个表项,指向系统的文件打开表的相应表项。
当进程调用close
时,count--
,当count = 0
时,则系统的文件打开表将删除相应的表项。
每个打开文件的组成:
文件指针
:对于该文件上次读写位置的记录指针。该指针对于打开该文件的某个进程是唯一的。文件打开计数
:当前文件被打开的数量,当其数量为0时,系统的文件打开表将删除对应的表项。文件磁盘位置
。访问权限
:每个进程打开都需要有一个访问模式(如创建、只读、读写、追加等),以便OS能够允许或拒绝后续的I/O请求。
打开文件的主要工作就是将该文件的FCB(文件目录项)存入内存的活跃文件目录表。
系统首次执行open系统调用打开某个文件,只会把该文件的PCB调入内存,而不会调入其内容到内存,只有读取文件内容时,才会将文件内容读入到内存。
6.文件的保护
6.1 访问类型
- 读
- 写
- 执行
- 追加
- 删除
- 列表清单
- 重命名
- 复制
- 编辑
…
6.2 访问控制
6.2.1 根据用户身份控制
为每个文件和目录增加一个访问控制列表(Access-Control List,ACL),以规定每个用户名以及所允许的访问类型。
精简的ACL采用拥有者、组和其他用户三种用户类型。
拥有者
:创建文件的用户。组
:一组需要共享文件且具有类似访问的用户。其他
:系统内的其他用户。
这样当用户进行文件访问时,若为文件的创建者,则按照拥有者所拥有的权限访问,若与创建者同组,则按照组权限访问,除此之外,只能按照其他用户的身份进行访问了。
该方式的ACL长度无法预估,且该方式可能会导致复杂的空间管理。不过使用精简的ACL可以解决这个问题。
6.2.2 根据口令控制
用户创建文件时将提供一个口令,该口令将被附在文件的FCB
上,同时告知允许共享该文件给其他用户,用户访问时需要提供相应的口令。
6.2.3 根据密码控制
创建者对文件进行加密,访问文件时需要使用密钥。
该方法保密性强,节省了存储空间,但编码译码需要花费一定的时间。
口令和密码都是为了防止文件被其他用户窃取,并没有对文件的访问类型进行限制。
目录保护的机制不同于文件保护。
对于多级目录而言,不仅需要保护目录中的文件,还需要保护子目录中的文件。
对于一个文件的访问,常由用户访问权限&文件属性共同限制。
安全性:加密保护 > 访问控制
灵活性:加密保护 < 访问控制
若加密保护只由系统实现,则将无法拓展;若访问控制不由系统实现,则系统本身的安全性将无法保证。
系统级安全管理包括注册和登录。
7.文件的逻辑结构
7.1 概述
文件的逻辑结构是从用户观点出发看到的文件的组织形式。
文件的逻辑结构与存储介质特性无关,它实际上是指在文件的内部,数据逻辑上是如何组织起来的。
文件的逻辑结构是为了方便用户而设计的。
7.2 分类
7.2.1 无结构文件/流式文件
- 无结构文件是最简单的文件组织形式。
- 无结构文件将数据按顺序组织称记录并积累、保存。
- 无结构文件是有序相关信息项的集合,以
Byte
为单位,它没有结构,因此对其记录的访问只能通过穷举搜索。 - 字符流的无结构文件管理起来比较简单,如源程序文件、目标代码文件。
7.2.2 有结构文件/记录式文件
7.2.2.1 顺序文件
文件中的记录一个接一个的排列,记录通常是定长的,可进行顺序存储或链式存储。
结构:
串结构
:记录之间的顺序与关键字无关,只与存入顺序有关。查找必须从头开始顺序进行,比较费时。顺序结构
:记录按关键字顺序排序,查找时可采用二分查找法,查找效率高。
批量操作时,顺序文件效率最高,但对单个记录进行操作时,顺序文件的性能就很差。
顺序文件占用连续的磁盘空间,最容易导致外部碎片的发生。
顺序文件相较于随机文件,其访问速度通常是最快的。
7.2.2.2 索引文件
索引文件能通过计算记录的偏移量来随机检索记录。
建立一张索引表,将主文件中的每个记录在索引表中分别设置一个表项,包含指向变长记录的指针及其记录长度,这样就将对变长记录顺序文件的检索转变为对定长记录索引文件的随机检索,从而加快了记录的检索速度。
索引表本身也是一个定长记录的顺序文件。
7.2.2.3 索引顺序文件
索引文件是顺序文件和索引文件的结合。
最简单的索引顺序文件只使用了一级索引,索引顺序文件将顺序文件中的所有记录分组,为顺序文件建立一张索引表,在索引表中为每一个组中的第一条记录建立索引项,其中含有该记录的关键字值和指向该记录的指针。
索引文件和索引顺序文件均均提高了存取速度,但是因为还需要存储索引表而增加了存储开销。
7.2.2.4 直接文件/散列文件(Hash File)
- 给定记录的键值通过散列函数将键值转换为直接决定记录的物理地址。
- 散列文件具有很高的存取速度,但是会产生冲突,即不同的键值映射到了相同的物理地址上。
- 散列文件无顺序的特性。
8.文件的物理结构
文件的物理结构是指从实现观点看到的文件在外存上的存储组织形式。
物理文件的组织方式是由OS确定的。
8.1 连续分配
8.1.1 概述
- 该方式要求每个文件在磁盘上占有一组连续的块。
- 连续分配的方式支持顺序访问和直接访问。
8.1.2 优点
- 实现简单,存取速度快。
8.1.3 缺点
- 文件长度不定,不宜进行动态增加,万一后面还有其他文件,则需要进行盘块挪动。
- 为保证文件的有序性,插入删除记录时,往往需要对相邻的记录进行物理上的挪动。
- 反复增删记录会产生外部碎片。
- 很难确定一个文件到底需要的空间大小,该方法适用于长度固定的文件。
8.2 链接分配
- 链接分配是一种离散分配的方式。
- 链接分配消除了磁盘的外部碎片,提高了磁盘的利用率,动态增删修改一个文件非常方便,而且无需实现知道文件的大小。
8.2.1 隐式链接
目录中含有文件第一块的指针和最后一块的指针。
每个文件都对应一个磁盘块的链表,磁盘块可以分布在磁盘的任何地方,除最后一个盘块外,每个盘块都含有指向文件下一个盘块的指针,这些指针对用户是透明的。
隐式链接的缺点是只适合顺序访问,随机访问效率很低。且其稳定性也是一个问题,若文件的盘块链表中的指针丢失,则会导致文件数据的丢失。通常解决方法是量将几个盘块组成
簇(cluster)
,按簇而不按块分配,可以成倍的减少查找时间,指针所占的磁盘空间比例也要小很多,但代价就是内部碎片增加了。
8.2.2 显式链接
将用于链接的各物理块的指针,从每个物理块的末尾提取出来,显式的存放在内存中的一张链表中,该表在整个磁盘中仅设置一张,称为文件分配表(File Allocation Table,FAT)
,每个表项存放链接指针,即下一个盘块号。而文件目录则只需记录每个文件的第一个盘块的盘块号即可。
FAT表在系统启动时会被读入内存,后续的检索只需在内存中进行,无需再去多次访问磁盘,从而提高了检索速度。
该方式的缺陷:FAT表将会占用较多内存。
8.3 索引分配
索引分配将每个文件的所有盘块号集中放在一起构成索引块表。索引块表是一个磁盘块地址的数组,其第i个元素指向文件的第i个物理块。
该方式的优点:支持直接访问,无外部碎片问题,缺点是由于索引块的分配,又增加了系统存储的开销。
针对于其索引块会占据存储空间的问题的解决方案:
链接方案
:一个索引块通常为一个物理块,因为它本身可直接进行读写,为了支持大文件,可以将多个索引块链接起来。多层索引
:通过第一级索引块指向第二级索引块,然后第二级索引块再指向文件的物理块,这样能够支持超大文件。混合索引
:将多种索引分配方式向结合的分配方式。(下面将单独说明)
由于索引块也存在与外存中,因此访问文件就需要两次访问外存,为了提高访问速度,可以以将索引块调入内存。
8.4 混合索引分配
为了照顾不同大小的文件,该方法将针对于不同文件采用 不同的访问方案。
对于小型文件,直接将它们的盘块地址存入FCB;对于中型文件,采用单级索引的方式,即先从FCB中找到该文件对应的索引,然后再去得到该文件的盘块地址;对于大型文件,采用多级索引的方式。
UNIX便是采用的这种方式:
直接地址
:为了提高对文件的检索速度,在索引节点中可设置10
个直接地址项,即用iaddr(0) ~ iaddr(9)
来存放直接地址(文件的物理块的块号)。一次间接地址
:对于中、大型文件,只采用直接地址是远远不够的,为此还应该再利用索引节点中的iaddr(10)
来提供一次间接地址,其实质是一级索引分配方式,一次间址块还是一个索引块,系统将该文件的物理块的块号记入其中。二次间接地址
:利用iaddr(11)
提供二次间接地址,其实质是二级索引分配,系统将在二次间址块中记入所有一次间址块的块号。
连续结构不利于拓展,链式结构不利于随机访问,索引结构既利于拓展又适合随机访问。
inode中,与单个文件长度有关的因素有:地址项的个数、文件块大小、间接地址索引的级数。