文章目录
- 计算机存储体系介绍
- 虚拟存储器
- 内存管理单元与页式存储管理
- CPU发起一次访存的全过程
一、计算机存储体系介绍
从计算机的组成角度来看,计算机的存储分为,寄存器-高速缓存-主存储器(泛指内存)-本地存储(磁盘)-外部存储(光盘、云盘等),由下到上,运行速度越来越快,存储空间越来越小,费用越来越高(如图1)。而对于使用者来着,我们肯定希望能用最少的成本,尽可能用最快、空间最大的存储设备。因此,就引出了操作系统层次性存储体系,根据局部性原理(时间局部性&&空间局部性)和对应的汰换算法,将最常用的信息存储在上层的存储设备,按照一定的策略更新上层存储设备的内容。
时间局部性:程序中某个(内存对象)数据被访问,近期很可能会被再次访问。
空间局部性:程序中某个(内存对象)数据被访问,与其相邻的(内存对象)数据近期很可能也会被访问。
(图1)
进程是操作系统进行资源分配调度的最小单元,一个进程具有操作系统分配给它的一块逻辑上连续的虚拟内存空间。我们编写的程序,运行后就作为一个进程受操作系统的管理和调度,其相关的变量,函数库,开辟的空间都在这个进程的内存中,所以一个进程可使用的内存大小,就成了影响这个进程执行效率,可用性重要因素。但是我们应该给这个进程分配多少内存才合适呢?假如过大,则进程宿主机可以同时运行的进程数就受到限制,也容易造成内存空间的浪费;假如过小,则内存空间不满足进程需求,造成进程运行不稳定。所以,合理的分配和高效的利用内存,就成了对操作系统的核心诉求之一。
二、虚拟存储器
对于计算机本身来说,内存就是真实的硬件存储设备的容量,即内存条。在操作系统的角度上,对这部分容量用物理内存这个名词来定义。对物理内存会有一个布局,以一个数组的方式(如图2)。数组的每一项都被叫做一个物理内存地址,这个物理内存地址对应着真实的物理内存,且物理内存地址是连续的, 假如要取一段内存空间,则可以根据初始物理内存地址附加上一个偏移量来得到。
(图2)
进程在运行的不同时间,不同状态所需要的内存空间大小是变化的,所以操作系统只能按照进程所需内存的最大值来分配,这样就难免造成了内存浪费。假如给多个进程分配同一块内存空间,就又难免造成了内存访问冲突的问题,使得进程效率低下。针对这些问题,操作系统使用虚拟存储器来解决上述问题。
虚拟存储便是在物理真实存储的基础上,构建一套逻辑的存储空间以供进程使用,由操作系统对虚拟存储和物理存储之间构建映射关系,管理真实的物理内存分配,以达到提高利用率的效果。进程从这个虚拟存储空间的内存地址获取数据,操作系统将这个虚拟地址转变成实际的物理地址,从真实的物理内存上加载数据。这样子,对于每个进程来讲,它自己独享了一块连续的存储空间,也无需考虑访问冲突这件事。另外,在物理内存空间不足时,操作系统还会虚拟化磁盘空间作为虚拟存储空间(如图3)。
(图3)
三、内存管理单元与页式存储管理
操作系统应该如何去映射和管理虚拟存储和物理真实存储的关系呢?这其中就要用到内存管理单元和页表进行虚拟内存的管理,接下来对它们逐一介绍。
- 内存管理单元(MMU):虚拟内存管理的核心硬件,用来管理虚拟内存地址到物理内存地址的映射。操作系统通过页,页表,页表条目来管理虚拟内存, 而页作为管理内存的基本单位。
- 页:管理内存的基本单位;操作系统将内存划分固定大小的块,通常大小为4KB、8KB;基于物理内存的块叫做物理页,而基于虚拟内存的块叫做虚拟页。每个进程自己的虚拟地址空间,被分为若干页。
- 页表:页的集合,即基于页的一个数组,用于管理虚拟内存和物理内存之间的映射关系,每个进程有自己的页表。这个数组中的每一个元素为一个页表条目(Page Table Entry 简称PTE)
- 页表条目:页表中的单个条目,每个页表项对应一个虚拟页,且保存了虚拟页到物理页的映射信息(和一些其他的权限、状态信息,如是在内存还是磁盘的标识位,该页是否允许读写操作,该页是否是用户/内核态都能访问等)。页、页表条目、页表之间的关系如(图4);PTE内部构造如(图5)。
(图4)
(图5)
四、CPU发起一次访存的全过程
前文说过,内存管理单元(MMU)是虚拟内存管理的核心硬件,用来管理虚拟内存地址到物理内存地址的映射。进程要访问一个内存地址时,CPU将虚拟地址给到MMU,MMU去页表中查询虚拟地址对应的物理地址;因为页表本身也需要空间存储,假如MMU每次都去主存中查找页表会拖慢整次存储访问的速度,所以操作系统会在高速缓存区中维护了一个TLB(Translation Lookaside Buffer),TLB中保存了部分虚拟页到物理页的映射,MMU查询页表时会优先访问TLB,TLB未命中虚拟地址的页号时,才会去主存的进程页表中查询。整个访存过程如(图6)所示。
-
进程A要访问某个变量,CPU生成访存指令,访问的虚拟地址为 0xABCDEF01
-
MMU 查询TLB,查看虚拟地址0xABCDEF01是否对应物理地址,假如有,直接使用TLB记录的物理地址
-
MMU查询页表,从页表中查询虚页号对应的物理页号
-
根据物理页号和虚拟地址偏移量,找到组合找到对应物理地址
-
将本次查询页表的虚页号实页号映射关系更新至TLB
以上便是操作系统对进程内存管理的一些基本概念,有了这些基础概念做铺垫后,一起探讨下go runtime是如何管理进程内存的。