存储管理
northboat 3/7/2024 OperatingSystem
存储管理概述
通过维护两个寄存器对物理地址进行查找和保护
- 基地址寄存器,又叫重定位寄存器
- 界地址寄存器
一个系统只维护一个重定位寄存器(因为同时只运行一个进程,多了没用)
产生内部碎片 | 产生外部碎片 |
---|---|
固定分区分配 | 动态分区分配 |
分页式存储 | 分段式存储 |
请求分页式存储 | 请求分段式存储 |
存在外部碎片的分配方式通过紧凑技术(拼接技术)来合并较小的连续的碎片,希望能得以利用
存储空间的最大值
- 实际最大值:内存加外存的总空间
- 理论最大值:与地址寄存器的位数有关,如 32 位,则最大值为 2^32 B
注意,逻辑地址的寻址(即对内存的访问)是以字节为单位(基地址+偏移地址),而内存的分配是以内存块为单位,二者要分清
连续存储
就是内存管理
程序的链接、装入
- 程序在链接时形成逻辑地址
- 在装入时对逻辑地址进行转换,为物理地址(由硬件完成)
静态装入:在编程阶段就把物理地址规定好
地址重定位
- 静态地址重定位:一次性装入时定位
- 动态地址重定位:边执行边定位
固定分区分配:对内存进行固定分区,如将一整块内存均分为 100 份,每个分区只装入一道作业
- 显然,这样会产生内部碎片(即分区内部无法利用的区域),而不会产生外部碎片(整块内存都被分区,无残留)
动态分区分配:根据作业所需内存为其分配内存,同样是每个分区装一道作业,这样会产生外部碎片(有残留的未形成分区的内存)
动态分区分配算法
- 首次适应 FF:地址升序
- 邻近适应 NF:地址升序,循环队列,继承指针位置遍历
- 最差适应 WF:空闲区大小降序排列
- 最优适应 BF:空闲区大小升序排列(产生最多的内部碎片)
离散存储
分页
- 每个进程都有其对应的一张页表
- 页表的始地址存储在寄存器中
页面大小的制定:进程平均大小、页表长度(无论如何制定,每个页面的大小都是一样的)
分段
- 程序如何分段在编程时决定
- 每个进程都有其对应的一张段表
段页式
- 采用分段的方式存储逻辑地址,采用分页来存储物理地址
- 每个程序对应一个段表,每个分段对应一张页表
这里涉及到一些关于页表项、多级页表、页表大小的计算题:如一个页表项占 2B,一页 8KB,虚拟地址 48 位,实地址 36 位
可以获得的信息有
- 一页可存 4KB/8B = 2^9 个页表项
- 页内偏移地址为 8KB = 2^12,需要 12 位
- 虚拟地址 48 位,去掉页内偏移的 12 位,共可给 2^36 个页编号
- 要存储这 2^36 个页,需要 2^36 个页表项,由于一个进程一张页表(这张页表必须能够囊括所有的页),又因为一张表可存 2^9 个项,有 (2^9)^4 = 2^36,故需要 4 级页表来进行存储
一定要注意题目中的隐藏信息,如
- 通过页面大小得知偏移地址位数
- 通过虚拟地址位数、偏移地址位数得知最大页面容量
- 通过页面大小、页表项大小得知一个页面可存储的页表项数
在考虑页面调用时,一定使用的是虚拟地址位数,而不是实地址(已经扩充过了,肯定要用啊,不然扩了不管等于没扩)
虚拟存储
用于扩充内存容量
- 请求分页式
- 请求分段式
遵循程序的局部性原理(对程序的不均匀访问)
页面置换算法
- 先进先出:FIFO
- 最近最久未使用:LRU
- 最近未使用:NRU
内存分配策略
- 静态分配局部置换:对于每道作业,页框大小不变,自己调度自己的
- 动态分配全局置换:页框大小任意,缺页时即从物理块队列中取出并分配(容易盲目给进程分配内存块,从而降低多道程序并发能力)
- 动态分配局部置换:页框可变,但相对固定,当缺页时从自己的页框中进行调度,当频繁缺页时系统给其分配更多物理块
一定是不存在静态分配全局置换的,都静态分配固定了页框,还全局分配个集贸
注意页面的置换 ≠ 调页
- 页置换:指页面一进一出,将页面 1 调入空闲的页框,这不叫页置换
- 调页:指将页面从磁盘调入内存,这包含页置换
抖动与 Belady 现象
- 所有的页面置换算法都无法避免抖动:即频繁页面调度的现象
- 只有 FIFO 存在 Belady 现象:即增大所分配页框大小,其页面调度次数不降反升的现象