一、前置概念
实模式:直接操作物理内存。每次只能运行一个程序,不安全;最大使用内存1M,限制太大。
保护模式:虚拟地址被转换为物理地址,要有页表。
装载器:把指令和数据加载到内存运行。要满足两个条件:
- 1)可执行程序加载后占用内存空间应该是连续的。
- 2)我们需要同时加载很多个程序,并且不能让程序自己规定在内存中加载的位置。
那就是我们可以在内存里面,找到一段连续的内存空间,然后分配给装载的程序,然后把这段连续的内存空间地址,和整个程序指令里指定的内存地址做一个映射。
二、分段分页
分段分页都是操作系统发展过程中为了更好地使用内存资源。
2.1 直接映射(为物理地址)
问题:
- 1)进程地址空间不隔离。不小心程序数据被修改,导致运行异常。
- 2)内存使用效率低。内存碎片需将运行数据暂时拷贝到硬盘,再重装入内存,效率十分低下。
解决方法: 增加中间层,将虚拟地址映射为物理内存地址。
2.2 分段含义、优劣
段: 系统分配出来的连续内存空间。
分段: 找出连续物理内存和虚拟内存地址映射的方法。
优劣: 解决了程序本身不需要关系具体物理内存的问题,同时带来内存碎片的问题。
补充:
优:没内部碎片、重定位段比整个地址空间更容易;
劣:有外部碎片、很难将连续内存分配给可变大小分区、昂贵的内存管理算法。
内存交换:可解决内存不连续的问题,将内存写到硬盘,重新加载,让剩下的内存空间连续。
Linux的swap分区就是作用。但硬盘访问速度太慢,会有性能瓶颈,机器可能出现卡顿。
段表存储在线性地址空间,而页表则保存在物理地址空间。
2.3 分页
页: 切成的连续且尺寸固定的内存空间。
分页: 分段导致内存碎片和交换空间太大,为了让交换写入的数据更少,出现了内存分页。
- 和分段相比,分页把(虚拟/物理)整块内存切成一段段固定尺寸的大小内存存储单元。
缺页错误: 操作系统读取特定页,发泄数据没加载到物理内存(缓存未命中),就会触发CPU Page Fault。
三、虚拟地址和物理地址
3.1 含义
虚拟内存地址(Virtual Memory Address
):指令里用到的内存地址。
定义的虚拟地址空间是连续,使程序编写难度降低。因为每个进程都提供了一个一致的、私有的、连续完整的地址空间,让每个进程都产生了一种自己在独享主存的错觉。
物理内存地址(Physical Memory Address
):实际内存硬件里面的空间地址,它是真实的物理地址
3.2 地址转换
内存管理单元 - MMU(Memory Management Unit
):将虚拟地址转换为物理地址,借助存放在内存中的页表动态翻译虚拟地址。
页表:将虚拟内存地址映射到物理内存地址的映射表,能将虚拟内存里的页一一映射到物理内存里面。
地址变换高速缓冲/快表 - TLB(Translation lookaside buffer
):存储当前最可能被访问到的页表项,是部分页表项的一个副本,减少了因MMU导致的处理器性能下降。
页号(Directory
)和偏移量(Offset
) 可用来计算内存地址转换,步骤:
- S1:把虚拟内存地址切分成页号和偏移量的组合;
- S2:从页表里,查询出虚拟页号对应物理页号;
- S3:拿物理页号+偏移量,就得到了物理内存地址。
多级页表:
-
问题:数字范围: 0 − 2 20 0-2^{20} 0−220,一个页号是4字节(
Byte
) -
1个页表: 2 20 ∗ 4 B = 4 M 2^{20}*4B = 4M 220∗4B=4M
当内存达到4G时,页表占用内存空间太大。 -
多级页表(1-2-32-1 [
4级-1级
])时,
每1级用5个比特表示,1级 2 5 = 32 2^5=32 25=32 个条目, 32 ∗ 4 B = 128 B 32*4B=128B 32∗4B=128B
1个4级索引表
8M= 2个3级索引表
(4M+4M)=2个2级索引表
=64个1级索引表
共69个索引表,每个128字节,大概 69 ∗ 128 B ( 约 ) = 2 6 ∗ 2 7 B 9 K B 69*128B (约)= 2^6*2^7B~~9KB 69∗128B(约)=26∗27B 9KB空间。只有4MB的1/500。
四、问题
1、分段分页含义?
分段:分配连续完整的内存,然后将虚拟内存地址映射为物理内存地址的方法。
分页:分段导致外部内存碎片和交换空间太大,为了让交换写入数据更少,出现了内存分页。和分段相比,分页把(虚拟/物理)整块内存切成一段段固定尺寸的大小内存存储单元,减少了内存碎片的大小。
追问1:为什么分段?(*2)
分段引入主要扩大了内存地址,程序地址不再需要原始硬编码,程序调试更简便。
把虚拟空间的的虚拟地址空间的虚拟内存组织成一些长度可变的内存块单元。
追问2:为什么分页?(*2)
分段内存碎片太大,因此提出了分页,用大小相同的页替换大小不同的段。
- 划分颗粒度更小,然后通过映射将虚拟地址映射为物理地址,映射关系是通过页表实现的。最后将逻辑上连续线性地址转换为可不连续的物理地址,。
2、虚拟内存和物理内存(*6)理解、作用、联系?
虚拟内存地址(Virtual Memory Address
):指令里用到的内存地址。
定义的虚拟地址空间是连续,使程序编写难度降低。因为每个进程都提供了一个一致的、私有的、连续完整的地址空间,让每个进程都产生了一种自己在独享主存的错觉。
物理内存地址(Physical Memory Address
):实际在内存硬件里面的空间地址,它是真实的物理地址
追问1:什么时候进行交换?
物理内存不足时,会将最近最少频率使用的页框移出物理内存,放到存储空间(swap分区)。
追问2:不使用虚拟内存可能会出现什么问题?
- 1)进程地址空间不隔离。有Bug/恶意的程序修改其它程序的内存数据,会导致其它程序运行异常。
- 2)内存使用效率低。可能有大量的内存数据频拷贝到硬盘,释放空间给另一个程序使用,效率释放低下。
- 3)程序运行的地址不确定。当内存剩余空间满足程序要求,系统会随机分配一段连续空间,因为随机分配,所以运行地址不确定。
3、Linux内存管理及(页面置换)算法(*2)。
……
4、什么是缓存?有哪些缓存的更新算法?
……LRU……
5、malloc是怎么分配内存?
……
6、XXX语言内存分布?
……
五、参考
【段页】
1、出处: 深入探究:操作系统为什么要引入虚拟地址?
2、分段机制和分页机制
3、分段
4、怎样通俗的理解操作系统中内存管理分页和分段?
5、内存分页不就够了?为什么还要分段?还有段页式?
6、linux中为什么要有分段和分页机制
7、09 | 程序装载:“640K内存”真的不够用么?
【虚拟地址与实际地址】
1、40 | 理解内存(上):虚拟内存和内存保护是什么?
2、读懂操作系统之虚拟内存地址翻译原理分析篇(二)
3、虚拟内存的那点事儿
4、80386学习(五) 80386分页机制与虚拟内存