文章目录
- 1.为什么要有逻辑地址?
- 2.逻辑地址如何与物理地址映射?
- 3.分页中的时间与空间的优化
- 4.程序内部的内存管理——分段
- 5.CPU的缓存cache如何起作用?
1.为什么要有逻辑地址?
- 逻辑地址:是直接在程序中看到的内存地址
- 逻辑内存也叫虚拟内存
- 硬件可用的地址是变化的, 比如增加减少内存条,程序的地址是写死的
- 因为程序无法知道可用的逻辑地址,所以必须要作出映射
2.逻辑地址如何与物理地址映射?
- 一种简单的思路:固定偏移量映射,eg如下图
缺点:
(1)以程序1为例,一个程序所使用的内存是无法计算的,右边程序没有使用的物理内存称之为内碎片
(2)程序1运行完毕后,释放内存,接着运行程序3,因为程序3的地址是0-201,它无法使用0-200的地址,长期以往,该块内存一直被闲置,,那么这块内存称之为外碎片
- 所以将逻辑内存分为页
(1)页表:左边代表逻辑内存中的页,右边代表物理内存中的帧
页表还存储的信息:当前条目是否可用,当前页的读写权限,当前帧是否是脏的等; - 每个进程都有自己的页表
每个进程的帧号不一样,就保证了不同进程之间是隔离的 - 小知识
(1)内存的一个地址里面住的是一个字节Byte的数据;
(2)32位的OS物理地址有2^32个,因而只能使用4GB的内存
(3)任何一个32位的程序可操作的逻辑地址是2^32个,即4GB;(每个32位的程序都天真的以为自己拥有4GB的内存)
(4)上面势必会造成多个程序使用内存总和大于物理内存,此时会借助磁盘,将并不着急使用的内存先存到磁盘,PT对应的帧号只显示磁盘
如下图,大部门页映射到帧中,小部门页映射到磁盘中 - 内存映射的过程
eg问题:
机器:32bit,256MB内存,页大小为4KB
程序:32bit程序
逻辑地址0x000011a3如何映射到物理地址?
分析:
(1)4K=12bit,就是2^12,所以偏移量是12bit,所以,页号就是32-12=20bit;
逻辑地址32bit=20bit页号+12bit偏移
(2)256MB=28bit,就是2^28,偏移量是12bit,所以帧号就是28-12=16bit
物理地址28bit=16bit帧号+12bit偏移
对于0x0000011a3而言,1a3代表12bit的偏移地址,000001代表20bit的页号 - (3)在页表PT(Page Table)中查找,00001对应的帧号是00f3(16bit转16进制数),在帧内寻找偏移量1a3的地址,最终找到内存;
如果对应的帧号是磁盘,会发生什么?
会发生缺页中断或缺页异常,会触发程序进入内核态,内核会到磁盘中找到对应的数据,然后会将其加载到物理内存的帧中,然后把加载好的帧号填写到PT表的帧号那一栏中,重新进行寻址。
若帧已经加载满了,会有页替换算法(只需知道能选出要逐出的页帧就行了),将最少使用的帧逐出到磁盘(所以linux下的该部分又称之为:swapping),把当前的数据放入到物理的帧中。
如下图是:逻辑地址映射到物理地址的过程 - 分页小结
(1)分页使得每个程序都有很大的逻辑地址空间,通过映射磁盘和高效的置换算法,使得内存“无限大”
(2)分页使不同的进程的内存隔离,保证了安全
(3)分页降低了内存碎片问题
(4)但是上述分页过程中,需要两次(第一次是从页表中获取帧号,第二次:拿着帧号到内存中再查一遍)读内存时间上有待优化,页表占用空间较大,空间上也有待优化
3.分页中的时间与空间的优化
- 时间优化:
(1)将最常访问的几个(一般是8-128个左右)页表项存到访问速度更快的硬件中,一般是MMU内存管理单元(一般情况,MMU属于CPU),该页表的名称是TLB(Translation Lookaside Buffer),可以称其为快表;
(2)先寻址先查TLB,然后miss后,再查PT。
快表命中率很高,因为一个事实:程序最常访问的页没几个 - 空间优化:
多级页表可以缩小页表占用的空间
4.程序内部的内存管理——分段
- 堆区,栈区就是段,段错误啥的。。。
- 现在我们所说的段,已经不再是最初的会影响内存管理的段了,而是更多的是程序层面的逻辑上的段
- eg:如图C语言的分段情况:对虚拟地址分的段
(1)最高的地址空间是留给Kernel Space内核的
(2)Text段:存储程序本身的二进制字节码;
Data段:存储程序中的静态的变量
Heap段:是从低往高增长的
Stact栈区:是从高往低增长的
Libraries:是函数库的区域,eg:linux的so文件,windows的dll动态链接库。进程之间是可以共享函数库的,就是进程间通信的共享内存的通信方式。
补充:(3)malloc若申请>128K的内存,会调用mmap,在堆和栈之间区域申请内存码。和这里的lib区其实是相同的位置的,因为他们都是页映射磁盘。 (mmap就是文件映射内存的系统调用)。 - 共享内存极其常见,eg:windows下选择文件的那个对话框
- 分段和分页的关系
(1)分段和分页结合的方式是:
每个段有很多页,页表中存储端号和页号唯一映射物理帧号
(2)但是段页结合的模式只在x86 Intel cpu等少数上还支持,更新的x86-64架构都不再支持段页结合了。
但是仍然保留了段的概念,只是程序层面便于计算,并不会影响分页式内存管理 - eg:两个程序分别映射到物理内存中
(1)内核区域是各个程序所共享的,所有2个程序都映射到了Kernel内核区域
(2)各自有各自的栈区,Libraries库区可能是多个进程所共享的
5.CPU的缓存cache如何起作用?
- 计算机的存储器结构大致是: CPU寄存器 —缓存cache–存储器(内存)–磁盘存储(硬盘)。从左到又速度从快变慢,存储大小由小变大。
- 所以cache做的事情是把内存里面常用的存储数据存在自己这里供CPU读取,因为cache的访问延迟远远小于内存, 所以访问这部分存在cache里的数据就会比直接去访问内存快的多,大概快一个量级。
- 至于为什么不用CPU直接读取,第一CPU的寄存器容量非常小,是Kb级别的,你让他去访问,内存,一次就这点,得多久才能把一个QQ那么大的程序运行了。第二是CPU访问内存,速度瓶颈自然在内存这里,那CPU当然访问cache更快了,而且现在的cache分L1 L2 L3这几层,从左到又速度从快变慢,存储大小由小变大。
参考: