9、linux内存管理子系统
管理模型
右边是虚拟地址,左下角是虚拟地址到物理地址的转换。
在linux系统程序中都是用虚拟地址。虚拟地址空间是由硬件来决定的。例如32位的系统,虚拟地址空间是4G=2的32次方。0-3G是用户空间,3G-4G是内核空间。而内核空间又被分为了四个部分:直接映射区(896M),vmalloc区,永久映射区,固定映射区。
虚拟地址到物理地址的转换
上图的简述:首先在我们的cr3寄存器中,存放的是页目录的基地址,然后虚拟地址把他转换为物理地址。然后怎么去找到我们的存储单元呢?首先高10位和我们的cr3相加,就可以找到一个页目录项里的页表的基地址。页表的基地址,再加上中间的10位,就可以找到一个物理页的基地址。物理页的基地址再去加上最后12位的偏移,就可以找到这个物理页,就可以去找到这个物理存储单元了。大小通常是4K大小。
我们知道,对于4G的内存,从3G----3G+896M,称为低端内存,3G+896M----4G称为高端内存。
-
所谓直接映射区,顾名思义就是直接映射的关系。直接的关系体现在,物理内存地址和他的虚拟内存之间的大小是固定的:相差3G大小。例如,有一个虚拟地址为3G+128M,那么他的物理地址为128M。
-
Vmalloc区,他可以访问高端和低端区域,没有直接的映射关系。
-
永久映射区,固定用来访问高端内存的。
-
固定映射区,这个区域的地址与我们的特殊的寄存器建立联系的。
在linux系统中,为了避免内存的浪费,采用的是虚拟内存,所谓的虚拟内存就是当你在用户程序使用malloc函数去创建一个内存空间的时候,系统分配给你的是虚拟地址,当你真正要使用到这个物理地址的时候,会产生一个请页异常(缺页异常),此时系统才会给你分配真正的物理空间。在内核程序存在两种情况:第一是:当我们使用vmalloc函数申请内存空间的时候,也是跟用户程序一样的情况。第二是:当我们采用Kmalloc函数申请内存空间的时候,内存才会分配给你虚拟内存和物理内存映射好的内存空间。原理是:内核里有一个slab函数,他会从空闲的物理内存中,取一些物理内存放到他的池子里面。当我们使用Kmalloc的时候,就会从池中分配一些给你。
这些知识现在知识了解,等学了驱动才去深入。