linux 内存管理模块
Posted wenlee
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了linux 内存管理模块相关的知识,希望对你有一定的参考价值。
什么是MMU
MMU(Memory Management Unit)主要用来管理虚拟存储器、物理存储器的控制线路,同时也负责虚拟地址映射为物理地址,以及提供硬件机制的内存访问授权、多任务多进程操作系统。(来自百度百科,对其几个点不熟悉,因此可以只考虑加粗部分)
发展历史
注意:学习一个知识点,很重要的一步是了解其为什么而存在?它的存在是为了解决什么问题?然后,在学习的过程中带着这些问题去理解、去思考。
在许多年以前,还是使用DOS或一些古老的操作系统时,内存很小,同时,应用程序也很小,将程序存储在内存中基本能够满足需要。随着科技的发展,图形界面及一些其他更复杂的应用出现,内存已经无法存储这些应用程序了,通常的解决办法是将程序分割成很多个覆盖块,覆盖块0最先运行,运行结束之后,就调用另一个覆盖块,虽然这些操作由OS来完成,但是,需要程序员对程序进行分割,这非常不高效;因此,人们想出了一个虚拟存储器(virtual memory)的方法。虚拟存储器的基本思想是:程序、数据、堆栈的总大小可以超过内存空间的大小,操作系统将当前运行的部分保存在内存中,未使用的部分保存在磁盘中。比如一个16MB的程序和一个内存只有4MB的机器,操作系统通过选择可以决定哪部分4MB的程序内容保存在内存中,并在需要时,在内存与磁盘中交换程序代码,这样16MB的代码就可以运行在4MB的机器中了。注意:这里面包含了虚拟地址和物理地址的概念
相关概念
地址范围、虚拟地址映射成物理地址以及分页机制
- 地址范围: 指处理器能够产生的地址集合,如一个32bit的处理器ARM9,其能产生的地址集合是0x0000 0000 ~ 0xffff ffff(4G),这个地址范围也称为虚拟地址空间,其中对应的地址为虚拟地址。
- 虚拟地址与物理地址: 与虚拟地址空间和虚拟地址相对应的是物理地址空间和物理地址;物理地址空间只是虚拟地址空间的一个子集。如一台内存为256MB的32bit X86主机,其虚拟地址空间是0 ~ 0xffffffff(4GB),物理地址空间范围是0 ~ 0x0fff ffff(256M)
- 分页机制:
-
如果处理器没有MMU,或者有MMU但没有启用,CPU执行单元发出的内存地址将直接传到芯片引脚上,被内存芯片(以下称为物理内存,以便与虚拟内存区分)接收,这称为物理地址(Physical Address,以下简称PA),如下图3-1-1所示;
如果处理器启用了MMU,CPU执行单元发出的内存地址将被MMU截获,从CPU到MMU的地址称为虚拟地址(Virtual Address,以下简称VA),而MMU将这个地址翻译成另一个地址发到CPU芯片的外部地址引脚上,也就是将VA映射成PA,,如下图3-1-2。
-
大多数使用MMU的机器都采用分页机制。虚拟地址空间以页为单位进行划分,而相应的物理地址空间也被划分,其使用的单位称为页帧,页帧和页必须保持相同,因为内存与外部存储器之间的传输是以页为单位进行传输的。例如,MMU可以通过一个映射项将VA的一页0xb70010000xb7001fff映射到PA的一页0x20000x2fff,如果CPU执行单元要访问虚拟地址0xb7001008,则实际访问到的物理地址是0x2008。
-
虚拟内存的哪个页面映射到物理内存的哪个页帧是通过页表(Page Table)来描述的,页表保存在物理内存中,MMU会查找页表来确定一个VA应该映射到什么PA。
功能
执行过程
操作系统和MMU是这样配合的:
-
操作系统在初始化或分配、释放内存时会执行一些指令在物理内存中填写页表,然后用指令设置MMU,告诉MMU页表在物理内存中的什么位置。
-
设置好之后,CPU每次执行访问内存的指令都会自动引发MMU做查表和地址转换操作,地址转换操作由硬件自动完成,不需要用指令控制MMU去做。
重要:我们在程序中使用的变量和函数都有各自的地址,在程序被编译后,这些地址就成了指令中的地址,指令中的地址就成了CPU执行单元发出的内存地址,所以在启用MMU的情况下, 程序中使用的地址均是虚拟内存地址,都会引发MMU进行查表和地址转换操作。(注意理解这句话)
内存保护机制
处理器一般有用户模式(User Mode)和特权模式(privileged Mode)之分。操作系统可以在页表中设置每个页表访问权限,有些页表不可以访问,有些页表只能在特权模式下访问,有些页表在用户模式和特权模式下都可以访问,同时,访问权限又分为可读、可写和可执行三种。这样设定之后,当CPU要访问一个VA(Virtual Address)时,MMU会检查CPU当前处于用户模式还是特权模式,访问内存的目的是读数据、写数据还是取指令执行,如果与操作系统设定的权限相符,则允许访问,把VA转换成PA,否则不允许执行,产生异常(Exception)。
异常与中断:异常与中断的处理机制类似,不同的是中断由外部设备产生,而 异常由CPU内部产生的;中断产生与CPU当前执行的指令无关,而异常是由于当前执行的指令出现问题导致的
通常操作系统会将虚拟地址空间划分为用户空间和内核空间。例如x86平台的linux系统的虚拟地址空间范围是0x0000 0000 ~ 0xffff ffff,前3G的空间为用户空间,后1G的空间为内核空间。用户程序加载到用户空间,内核程序加载到内核空间,用户程序不能访问内核中的数据,也不能跳转到内核空间执行。这样可以保护内核,如果一个进程访问了非法地址,顶多就是这个进程崩溃,而不会影响到内核和系统的稳定性。在系统发生中断或异常时,不仅会跳转到中断或异常服务函数中执行,而且还会从用户模式切换到特权模式,从中断或异常服务程序跳转到内核代码中执行。总结一下:在正常情况下处理器在用户模式执行用户程序,在中断或异常情况下处理器切换到特权模式执行内核程序,处理完中断或异常之后再返回用户模式继续执行用户程序。
段错误我们已经遇到过很多次了,它是这样产生的:
- 用户程序要访问的一个VA,经MMU检查无权访问。
- MMU产生一个异常,CPU从用户模式切换到特权模式,跳转到内核代码中执行异常服务程序。
- 内核把这个异常解释为段错误,把引发异常的进程终止掉。
S3C2440/S3C2410 中的MMU
S3C2440/S3C2410 MMU概述
-
S3C2440的MMU使用页表来实现虚拟地址到物理地址的转换;页表存储在内存中,页表中的每一行对应于虚拟存储空间的一个页,该行包含了该虚拟内存页对应的物理内存页的地址、该页的方位权限和该页的缓冲特性等。这里页表中的每一行称为一个地址变换条目(entry)也称为“描述符”。描述符有:段描述符、大页描述符、小页描述符、极小页描述符——他们保存段、大页、小页或极小页的起始物理地址;粗页表描述符、细页表描述符——它们保存二级页表的物理地址。
-
页表的存储:页表存放在内存中,系统通常有一个寄存器来保存页表的基地址。在ARM中系统控制协处理器CP15的寄存器C2用来保存页表的基地址。
-
TLB:因为从虚拟地址到物理地址的变换过程是通过查询页表完成的,而页表又存储在内存中,如果每次程序执行时去读取内存中的数据获取物理地址,代价很大。而程序在执行过程中可能只对页表中的少数几个单元进行访问,根据这一特点,采用一个容量更小(通常为8~16个字)、访问速度和CPU中通用寄存器相当的存储器件来存放当前访问需要的地址变换条目。这个小容量的页表称为TLB(Translation Lookaside buffer)。
-
S3C2440/S3C2410中的页表
在S32440/S3C2410中最多会使用两级页表:以段(Section 1MB)的方式进行转换时只用到一级页表,以页(Page)的方式进行转换时用到二级页表。 -
CPU访问内存的过程:
a . 当CPU需要访问内存时,先在TLB中查询需要的地址变换条目。如果该条目不存在,CPU从位于内存中的页表中查询,并把相应的结果添加到TLB中。这样,当CPU下一次又需要该地址变换条目时,可以从TLB中直接得到,从而使地址变换的速度大大加快。
b. 当内存中的页表内容改变,或者通过修改系统控制协处理器CP15的寄存器C2使用新的页表时,TLB中的内容需要全部清除。系统控制协处理器CP15的寄存器C8用来控制清除TLB内容的相关操作。
c. MMU可以将某些地址变换条目锁定在TLB中,从而使得获取该地址变换条目的速度保持很快。在CP15中的C10用于控制TLB内容的锁定。
d. MMU 可以将整个存储空间分为最多16个域,每个域对应一定的内存区域,该区域具有相同的访问控制属性。MMU中寄存器C3用于控制与域相关的属性的配置。
e. 当存储访问失效时,MMU提供了相应的机制用于处理这种情况。在MMU中寄存器C5和寄存器C6用于支持这些机制。
禁止/使能MMU时应注意的问题(重要)
应注意如下几点:
- 在使能MMU之前,要在内存中建立页表,同时,CP15中的各相关寄存器必须完成初始化。
- 如果使用的不是平板存储模式(物理地址和虚拟地址相等),在禁止/使能MMU时,虚拟地址和物理地址的对应关系会发生改变,这时应该清除cache中的当前地址变换条目。
S3C2440/S3C2410中的MMU地址变换
ARM CPU上的地址转换过程涉及3个概念:虚拟地址(VA)、变换后的虚拟地址(MVA, modified virtrual address)、物理地址(PA)。
没启动MMU时,CPU核、cache、MMU、外设等所有部件使用的都是物理地址。
启动MMU后,CPU核对外发出虚拟地址VA;VA被转换为MVA供cache、MMU使用,在这里MVA被转换为PA,最后使用PA读写实际设备。
ARM支持的存储块大小有以下几种:
- 段(section):是大小为1M的存储块。
- 大页(Large Pages):是大小为64KB的存储块。
- 小页(Small Pages):是大小为4KB的存储块。
- 极小页(Tiny Pages):是大小为1KB的存储块。
通过配置访问控制机制,还可以将大页分成大小为16KB的子页;将小页分成大小为1KB的子页;极小页不能再细分,只能以1KB大小的整页为单位。
MMU中的域
MMU中的域指的是一些段、大页或者小页的集合。ARM支持最多16个域,每个域的访问控制特性由CP15中的寄存器C3中的两位来控制,CP15中的寄存器C3的格式如下所示:
其中每两位控制一个域的访问控制特性,其编码及对应的含义如下所示:
以上是关于linux 内存管理模块的主要内容,如果未能解决你的问题,请参考以下文章
Linux 内核 内存管理内存管理架构 ③ ( Linux 内核中的内存管理模块 | 页分配器 | 不连续页分配器 | 内存控制组 | 硬件设备内存管理 | MMU | 页表缓存 | 高速缓存 )
Linux 内核 内存管理内存管理架构 ③ ( Linux 内核中的内存管理模块 | 页分配器 | 不连续页分配器 | 内存控制组 | 硬件设备内存管理 | MMU | 页表缓存 | 高速缓存 )
Linux 内核Linux 内核特性 ( 组织形式 | 进程调度 | 内核线程 | 多平台虚拟内存管理 | 虚拟文件系统 | 内核模块机制 | 定制系统调用 | 网络模块架构 )