Computer Operation System
安徽师范大学——计算机与信息学院———— 作者(授课教师): 周文
存储器的多层结构 对于通用计算机而言,存储层次至少应具有三级:
最高层为CPU寄存器,中间为主存,最底层是辅存。
在较高档的计算机中,还可以根据具体的功能细分为寄存器、高速缓存、主存储器、磁盘缓存、固定磁盘、可移动存储介质等6层。如图4-1所示。
可执行存储器
I/O设备
实现。主存储器
可执行存储器
。 寄存器
高速缓存
磁盘缓存
用户程序要在系统中运行,必须先将它装入内存,然后再将其转变为一个可以执行的程序,通常都要经过以下几个步骤:
(1) 编译,由编译程序(Compiler)对用户源程序进行编译,形成若干个目标模块(Object Module);
(2) 链接,由链接程序(Linker)将编译后形成的一组目标模块以及它们所需要的库函数链接在一起,形成一个完整的装入模块(Load Module);
(3) 装入,由装入程序(Loader)将装入模块装入内存
图4-2示出了这样的三步过程。本节将扼要阐述程序(含数据)的链接和装入过程。
绝对装入方式(Absolute Loading Mode)
目标代码
。 可重定位装入方式(Relocation Loading Mode)
绝对装入方式只能将目标模块装入到内存中事先指定的位置,这只适用于单道程序环境。
而在多道程序环境下,编译程序不可能预知经编译后所得到的目标模块应放在内存的何处。
因此,对于用户程序编译所形成的若干个目标模块,它们的起始地址通常都是从0开始的,程序中的其它地址也都是相对于起始地址计算的。
动态运行时的装入方式(Dynamic Run-time Loading)
静态链接(Static Linking)方式
在程序运行之前,先将各目标模块及它们所需的库函数链接成一个完整的装配模块,以后不再拆开。
在图4-4(a)中示出了经过编译后所得到的三个目标模块A、B、C,它们的长度分别为L、M和N。在模块A中有一条语句CALL B,用于调用模块B。在模块B中有一条语句CALL C,用于调用模块C。B和C都属于外部调用符号,在将这几个目标模块装配成一个装入模块时,须解决以下两个问题:
(1) 对相对地址进行修改。
(2) 变换外部调用符号。
装入时动态链接(Load-time Dynamic Linking)
将用户源程序编译后所得到的一组目标模块,在装入内存时,采用边装入边链接的链接方式。
即在装入一个目标模块时,若发生一个外部模块调用事件,将引起装入程序去找出相应的外部目标模块,并将它装入内存,还要按照图4-4所示的方式修改目标模块中的相对地址。装入时动态链接方式有以下优点:
(1) 便于修改和更新。
(2) 便于实现对目标模块的共享。
运行时动态链接(Run-time Dynamic Linking)
OS
使用,它通常是放在内存的低址部分。单一连续分配方式
。划分分区的方法
可用下述两种方法将内存的用户空间划分为若干个固定大小的分区:
(1) 分区大小相等(指所有的内存分区大小相等)。
(2) 分区大小不等。
内存分配
为了便于内存分配,通常将分区按其大小进行排队,并为之建立一张分区使用表,其中各表项包括每个分区的起始地址、大小及状态(是否已分配),如图4-5所示。
动态分区分配中的数据结构
常用的数据结构有以下两种形式:
① 空闲分区表,在系统中设置一张空闲分区表,用于记录每个空闲分区的情况。每个空闲分区占一个表目,表目中包括分区号、分区大小和分区始址等数据项,如图4-6所示。
② 空闲分区链。为了实现对空闲分区的分配和链接,在每个分区的起始部分设置一些用于控制分区分配的信息,以及用于链接各分区所用的前向指针,在分区尾部则设置一后向指针。通过前、后向链接指针,可将所有的空闲分区链接成一个双向链,如图4-7所示。
动态分区分配算法
分区分配操作
1) 分配内存
系统应利用某种分配算法,从空闲分区链(表)中找到所需大小的分区。
设请求的分区大小为u.size
,表中每个空闲分区的大小可表示为m.size
。
2) 回收内存
当进程运行完毕释放内存时,系统根据回收区的首址,从空闲区链(表)中找到相应的插入点,此时可能出现以下四种情况之一:
(1) 回收区与插入点的前一个空闲分区F1相邻接,见图4-9(a)。此时应将回收区与插入点的前一分区合并,不必为回收分区分配新表项,而只需修改其前一分区F1的大小。
(2) 回收分区与插入点的后一空闲分区F2相邻接,见图4-9(b)。此时也可将两分区合并,形成新的空闲分区,但用回收区的首址作为新空闲区的首址,大小为两者之和。
(3) 回收区同时与插入点的前、后两个分区邻接,见图4-9(c)。此时将三个分区合并,使用的表项和的首址,取消的表项,大小为三者之和。
(4) 回收区既不与邻接,又不与邻接。这时应为回收区单独建立一个新表项,填写回收区的首址和大小,并根据其首址插入到空闲链中的适当位置。图4-10示出了内存回收时的流程。
首次适应(first fit,FF)算法
空闲分区链
为例来说明采用FF算法时的分配情况。FF算法
要求空闲分区链以地址递增的次序链接。循环首次适应(next fit,NF)算法
最佳适应(best fit,BF)算法
最坏适应(worst fit,WF)算法
快速适应(quick fit)算法
伙伴系统(buddy system)
该算法规定,无论已分配分区或空闲分区,其大小均为2的次幂(k为整数,)。
通常是整个可分配内存的大小(也就是最大分区的大小)。假设系统的可利用空间容量为 个字节,则系统开始运行时,整个内存区是一个大小为的空闲分区。
在系统运行过程中,由于不断地划分,将会形成若干个不连续的空闲分区,将这些空闲分区按分区的大小进行分类。对于具有相同大小的所有空闲分区,单独设立一个空闲分区双向链表,这样,不同大小的空闲分区形成了个空闲分区链表。
在伙伴系统中,对于一个大小为,地址为的内存块,其伙伴块的地址则用表示,其通式为:
哈希算法
紧凑
连续分配方式的一个重要特点是,一个系统或用户程序必须被装入一片连续的内存空间中。
当一台计算机运行了一段时间后,它的内存空间将会被分割成许多小的分区,而缺乏大的空闲空间。
即使这些分散的许多小分区的容量总和大于要装入的程序,但由于这些分区不相邻接,也无法把该程序装入内存。
动态重定位
在2.1节中所介绍的动态运行时装入的方式中,作业装入内存后的所有地址仍然都是相对(逻辑)地址。
将相对地址转换为绝对(物理)地址的工作被推迟到程序指令要真正执行时进行。为使地址的转换不会影响到指令的执行速度,必须有硬件地址变换机构的支持,即须在系统中增设一个重定位寄存器,用它来存放程序(数据)在内存中的起始地址。
程序在执行时,真正访问的内存地址是相对地址与重定位寄存器中的地址相加
而形成的。
动态重定位分区分配算法
动态重定位分区分配算法与动态分区分配算法基本上相同,差别仅在于:
在这种分配算法中,增加了紧凑的功能。通常,当该算法不能找到一个足够大的空闲分区以满足用户需求时,如果所有的小的空闲分区的容量总和大于用户的要求,这时便须对内存进行“紧凑
”,将经“紧凑”后所得到的大空闲分区分配给用户。如果所有的小的空闲分区的容量总和仍小于用户的要求,则返回分配失败信息。
对换技术也称为交换技术
,最早用于麻省理工学院的单用户分时系统CTSS
中。
由于当时计算机的内存都非常小,为了使该系统能分时运行多个用户程序而引入了对换技术。系统把所有的用户作业存放在磁盘上,每次只能调入一个作业进入内存,当该作业的一个时间片用完时,将它调至外存的后备队列上等待,再从后备队列上将另一个作业调入内存。
对换的引入
对换的类型
对换空间管理的主要目标
在具有对换功能的OS中,通常把磁盘空间分为文件区
和对换区
两部分。
1) 对文件区管理的主要目标
2) 对对换空间管理的主要目标
对换区空闲盘块管理中的数据结构
对换区的首址及其大小
,分别用盘块号和盘块数表示。对换空间的分配与回收
首次适应算法
、循环首次适应算法
或最佳适应算法
等。进程的换出
对换进程在实现进程换出时,是将内存中的某些进程调出至对换区,以便腾出内存空间。
换出过程可分为以下两步:
(1) 选择被换出的进程。
(2) 进程换出过程。
进程的换入
(1) 分页存储管理方式。
(2) 分段存储管理方式。
(3) 段页式存储管理方式。
页面和物理块
(1)页面。
(2)页面大小。
地址结构
分页地址中的地址结构如下:
对某特定机器,其地址结构是一定的。若给定一个逻辑地址空间中的地址为A,页面的大小为L,则页号P
和页内地址d
可按下式求得:
页表
在分页系统中,允许将进程的各个页离散地存储在内存的任一物理块中,为保证进程仍然能够正确地运行,即能在内存中找到每个页面所对应的物理块,系统又为每个进程建立了一张页面映像表,简称页表
。
基本的地址变换机构
进程在运行期间,需要对程序和数据的地址进行变换,即将用户地址空间中的逻辑地址变换为内存空间中的物理地址,由于它执行的频率非常高,每条指令的地址都需要进行变换,因此需要采用硬件来实现。
页表功能是由一组专门的寄存器来实现的。一个页表项用一个寄存器。
具有快表的地址变换机构
由于页表是存放在内存中的,这使CPU在每存取一个数据时,都要两次访问内存。
因此,采用这种方式将使计算机的处理速度降低近。可见,以此高昂代价来换取存储器空间利用率的提高,是得不偿失的。
从进程发出指定逻辑地址的访问请求,经过地址变换,到在内存中找到对应的实际物理地址单元并取出数据,所需要花费的总时间,称为内存的有效访问时间(Effective Access Time,EAT
)。
假设访问一次内存的时间为t,在基本分页存储管理方式中,有效访问时间分为第一次访问内存时间(即查找页表对应的页表项所耗费的时间t)与第二次访问内存时间(即将页表项中的物理块号与页内地址拼接成实际物理地址所耗费的时间t)之和:
在引入快表的分页存储管理方式中,通过快表查询,可以直接得到逻辑页所对应的物理块号,由此拼接形成实际物理地址,减少了一次内存访问,缩短了进程访问内存的有效时间。
但是,由于快表的容量限制,不可能将一个进程的整个页表全部装入快表,所以在快表中查找到所需表项存在着命中率的问题。
所谓命中率,是指使用快表并在其中成功查找到所需页面的表项的比率。这样,在引入快表的分页存储管理方式中,有效访问时间的计算公式即为:
上式中,表示查找快表所需要的时间,表示命中率,表示访问一次内存所需要的时间。
可见,引入快表后的内存有效访问时间分为查找到逻辑页对应的页表项的平均时间,以及对应实际物理地址的内存访问时间。
假设对快表的访问时间为20 ns(纳秒),对内存的访问时间t为100 ns,则下表中列出了不同的命中率与有效访问时间的关系:
两级页表(Two-Level Page Table)
针对难于找到大的连续的内存空间来存放页表的问题,可利用将页表进行分页的方法,使每个页面的大小与内存物理块的大小相同,并为它们进行编号,即依次为0# 页、1# 页,…,n# 页
,然后离散地将各个页面分别存放在不同的物理块中。
同样,也要为离散分配的页表再建立一张页表,称为外层页表(Outer Page Table)
,在每个页表项中记录了页表页面的物理块号。
为了方便实现地址变换,在地址变换机构中,同样需要增设一个外层页表寄存器,用于存放外层页表的始址,并利用逻辑地址中的外层页号作为外层页表的索引,从中找到指定页表分页的始址。
再利用作为指定页表分页的索引,找到指定的页表项,其中含有该页在内存的物理块号,用该块号P和页内地址d即可构成访问的内存物理地址。
图4-18示出了两级页表时的地址变换机构。
多级页表
对于32位的机器,采用两级页表结构是合适的,但对于64位的机器,采用两级页表是否仍然合适,须做以下简单分析。
212 B
,那么还剩下52
位,假定仍按物理块的大小(212位
)来划分页表,则将余下的42
位用于外层页号。此时在外层页表中可能有4096 G
个页表项,要占用16 384 GB
的连续内存空间。 反置页表的引入
地址变换
固定分区分配
。 方便编程
通常,用户把自己的作业按照逻辑关系划分为若干个段,每个段都从0开始编址,并有自己的名字和长度。
因此,程序员们都迫切地需要访问的逻辑地址是由段名(段号)和段内偏移量(段内地址)决定的,这不仅可以方便程序员编程,也可使程序非常直观,更具可读性。
例如,下述的两条指令便使用段名和段内地址:
信息共享
信息保护
动态增长
动态链接
分段
在分段存储管理方式中,作业的地址空间被划分为若干个段,每个段定义了一组逻辑信息。
例如,有主程序段MAIN、子程序段X、数据段D及栈段S等,如图4-19所示。
分段地址中的地址具有如下结构:
段表
在前面所介绍的动态分区分配方式中,系统为整个进程分配一个连续的内存空间。
而在分段式存储管理系统中,则是为每个分段分配一个连续的分区。进程中的各个段,可以离散地装入内存中不同的分区中。
为保证程序能正常运行,就必须能从物理内存中找出每个逻辑段所对应的位置。
地址变换机构
为了实现进程从逻辑地址到物理地址的变换功能,在系统中设置了段表寄存器,用于存放段表始址和段表长度TL
。在进行地址变换时,系统将逻辑地址中的段号
与段表长度TL
进行比较。
若S>TL
,表示段号太大,是访问越界,于是产生越界中断信号。若未越界,则根据段表的始址和该段的段号,计算出该段对应段表项的位置,从中读出该段在内存的起始地址。
然后,再检查段内地址d是否超过该段的段长SL
。若超过,即d>SL
,同样发出越界中断信号。若未越界,则将该段的基址d与段内地址相加
,即可得到要访问的内存物理地址。
图4-20示出了分段系统的地址变换过程。
分页和分段的主要区别
(1) 页是信息的物理单位。
(2) 页的大小固定且由系统决定。
(3) 分页的用户程序地址空间是一维的。
分页系统中对程序和数据的共享
在分页系统中,虽然也能实现对程序和数据的共享,但远不如分段系统来得方便。
我们通过一个例子来说明这个问题。
分段系统中程序和数据的共享
在分段系统中,由于是以段为基本单位的,不管该段有多大,我们都只需为该段设置一个段表项,因此使实现共享变得非常容易。
我们仍以共享editor为例,此时只需在(每个)进程1和进程2的段表中,为文本编辑程序设置一个段表项,让段表项中的基址(80)指向editor程序在内存的起始地址。
图4-22是分段系统中共享editor的示意图。
页式与段式存储器比较
页式 | 段式 |
---|---|
分页由操作系统为内存管理划分 | 分段由用户设计划分,有完整的意义 |
页是信息的物理单位 | 段是信息的逻辑单位 |
页一般不能共享 | 便于段的共享,执行时按需动态链接装入 |
页面大小相同,不能够动态增长 | 段长不等,可动态增长 |
一维地址空间 | 二维地址空间,段名、段内地址 |
往往需要多次缺页中断才能够将所需信息完整调入内存 | 管理形式上像页式,但概念不一样 |
基本原理
段页式系统的基本原理是分段和分页原理的结合,即先将用户程序分成若干个段,再把每个段分成若干个页,并为每一个段赋予一个段名。
图4-23(a)示出了一个作业地址空间的结构。
该作业有三个段:主程序段、子程序段和数据段;页面大小为 4 KB。
在段页式系统中,其地址结构由段号、段内页号及页内地址三部分所组成,如图4-23(b)所示。
在段页式系统中,为了实现从逻辑地址到物理地址的变换,系统中需要同时配置段表和页表。
段表的内容与分段系统略有不同,它不再是内存始址和段长,而是页表始址和页表长度。
图4-24示出了利用段表和页表进行从用户地址空间到物理(内存)空间的映射。
地址变换过程
在段页式系统中,为了便于实现地址变换,须配置一个段表寄存器,其中存放段表始址
和段长TL
。进行地址变换时,首先利用段号S
,将它与段长TL
进行比较。
若S < TL
,表示未越界,于是利用段表始址和段号来求出该段所对应的段表项在段表中的位置,从中得到该段的页表始址,并利用逻辑地址中的段内页号P
来获得对应页的页表项位置,从中读出该页所在的物理块号b,再利用块号b和页内地址来构成物理地址。
图4-25示出了段页式系统中的地址变换机构。
设某虚拟存储器的用户编程空间共有32
个页面,每页大小为1KB
,内存为16KB,若某时刻一用户页表中已调入内存,页面的页号和物理卡号对照表如下图所示,则逻辑地址为0A5CH
所对应的物理地址是什么?当逻辑地址变为1A5CH
时,会发生什么情况?
页号 | 物理块号 |
---|---|
0 | 5 |
1 | 10 |
2 | 4 |
3 | 7 |
答案
逻辑地址0A5CH所对应的的二进制形式是:,由于页面大小为1KB
,即10位
,所以逻辑地址的后10表示页内地址,前6位表示该逻辑地址对应的页号为2,查询页表可知,得到物理块号为4,即物理块号的物理地址为0001 0000 0000 0000,块内偏移地址为
同理,对应的二进制形式是
某段表内容如下表所示,若有一逻辑地址,则该逻辑地址对应的实际物理地址为什么?
答案
答案
J1:212KB | J2:417KB | J3:112KB | J4:426KB |
若一个由8个页面,每页由1024个字节组成的逻辑空间,把它装入到有32个物理块的存储器中,则逻辑地址和物理地址分别需要多少位来表示?
答案
由于页面数为8,故需要3位二进制表示,每页1024
个字节,说明页内地址需要10位二进制来表示,32个物理块,需要5位来二进制来表示。
13
位二进制表示。15
位二进制表示。
本节结束 2019年10月5日