linux的物理内存与线性地址空间布局--1

在支持 MMU 32 位处理器平台上, Linux 系统中的物理存储空间和虚拟存储空间的地址范围分别都是从 0x00000000 0xFFFFFFFF ,共 4GB ,但物理存储空间与虚拟存储空间布局 完全不同。 Linux 运行在虚拟存储空间,并负责把系统中实际存在的远小于 4GB 的物理内存根据不同需求映射到整个 4GB 的虚拟存储空间中。

n 物理存储空间布局

Linux 的物理存储空间布局与处理器相关,详细情况可以从处理器用户手册的存储空间分布表( memory map )相关章节中查到,我 们这里只列出嵌入式处理器平台 Linux 物理内存空间的一般布局,如图 18-4 所示。



18-4  Linux 物理内存空间一般布局示意图

说明:

1 )最大 node n 不能大于 MAX_NUMNODES-1

2 MAX_NUMNODES 表示系统支持的最多 node 数。在 ARM 系统中, Sharp 芯片最多支持 16 nodes ,其他芯片最多支持 4 nodes

3 numnodes 是当前系统中实际的内存 node 数。

4 )在不支持 CONFIG_DISCONTIGMEM 选项的系统中,只有一个内存 node

5 )最大 bank m 不能大于 NR_BANKS-1

6 NR_BANKS 表示系统中支持的最大内存 bank 数,一般等于处理器的 RAM 片选数。在 ARM 系统中, Sharp 芯片最多支持 16 banks ,其他芯片最多支持 8 banks

7 mem_init() 函数会将所有节点的页帧位码表所占空间、孔洞页描述符空间及空闲内存页都释放掉

n 虚拟存储空间布局

在支持 MMU 的系统中,当系统做完硬件初始化后就使能 MMU 功能,这样整个系统就运行在虚拟存储空间中,实现虚拟存储空间到物理存储空间映射功能的是处理器的 MMU ,而虚拟存储空间与 5 路存储空间的映射关系则是由 Linux 内核来管理的。 32 位系统中物理存储空间占 4GB 空间,虚拟存储空间同样占 4GB 空间, Linux 把物理空间中实际存在的远远小于 4GB 的内存空间映射到整个 4GB 虚拟存储空间中除映射 I/O 空间之外的全部空间,所以虚拟内存空 间远远大于物理内存空间,这就说同一块物理内存可能映射到多处虚拟内存地址空间上,这正是 Linux 内存管理职责所在。图 18-5 列出了 Linux 内核中虚拟内存空间的一般布局(其实 I/O 空间也在其中,通常占用高端内存空间,在此未标出)。



18-5  Linux 系统虚拟内存空间一般布局示意图

说明:

1 )线性地址空间:是指 Linux 系统中从 0x00000000 0xFFFFFFFF 整个 4GB 虚拟存储空间。

2 )内核空间:内核空间表示运行在处理器最高级别的超级用户模式( supervisor mode )下的代码或数据,内核空间占用从 0xC0000000 0xFFFFFFFF 1GB 线性地址空间,内核线性地 址空间由所有进程共享,但只有运行在内核态的进程才能访问,用户进程可以通过系统调用切换到内核态访问内核空间,进程运行在内核态时所产生的地址都属于内 核空间。

3 )用户空间:用户空间占用从 0x00000000 0xBFFFFFFF 3GB 的线性地址空间,每个进程都有一个独立的 3GB 用户空间,所以用户空间由每 个进程独有,但是内核线程没有用户空间,因为它不产生用户空间地址。另外子进程共享(继承)父进程的用户空间只是使用与父进程相同的用户线性地址到物理内 存地址的映射关系,而不是共享父进程用户空间。运行在用户态和内核态的进程都可以访问用户空间。

4 )内核逻辑地址空间:是指从 PAGE_OFFSET(3G) high_memory(物理内存的大小,最大896 ) 之间的线性地址空间,是系统物理内存映射区,它映射了全部或部分(如果系统包含高端内存) 物理内存。内核逻辑地址空间与图 18-4 中的系统 RAM 内存物理地址空间是一一对应的(包括内存孔洞也是一一对应的),内核逻辑地址空间中的地址与 RAM 内存 物理地址空间中对应的地址只差一个固定偏移量(3G) ,如果 RAM 内存物理地址空间从 0x00000000 地址编址,那么这个偏移量就是 PAGE_OFFSET

5 )低端内存:内核逻辑地址空间所映射物理内存就是 低端内存(实际物理内存的大小,但是小于896) ,低端内存在 Linux 线性地址空间中始终有永久的一一对应的内核逻辑地址,系统初始化过程中将低端内存永久映 射到了内核逻辑地址空间,为低端内存建立了虚拟映射页表。低端内存内物理内存的物理地址与线性地址之间的转换可以通过 __pa(x) __va(x) 两个宏来进行,#define __pa (x ) ((unsigned long)(x )-PAGE_OFFSET) __pa(x) 将内核逻辑地址空间的地址 x 转换成对应的物理地址,相当于 __virt_to_phys((unsigned long)(x)) __va(x) 则相反,把低端物理 内存空间的地址转换成对应的内核逻辑地址,相当于 ((void *)__phys_to_virt((unsigned long)(x)))

6 )高端内存:低端内存地址之上的物理内存是高端内 存(物理内存896之上) ,高端内存在 Linux 线性地址空间中没有没有固定的一一对应的内核逻辑地址,系统初始化过程中不会为这些内存建 立映射页表将其固定映射到 Linux 线性地址空间,而是需要使用高端内存的时候才为分配的高端物理内存建立映射页表,使其能够 被内核使用,否则不能被使用。高端内存的物理地址于现行地址之间的转换不能使用上面的 __pa(x) __va(x) 宏。

7 )高端内存概念的由来:如上所述, Linux 4GB 的线性地址空间划分成两部分,从 0x00000000 0xBFFFFFFF 3GB 空间作为用户空间由用户进程独占,这部分线性地址空间并没有固定映射到物理内存空间上; 从 0xC0000000 0xFFFFFFFF 的第 4GB 线性地址空间作为内核空间,在嵌入式系统中,这部分线性地址空间除了映射物理内存空间之 外还要映射处理器内部外设寄存器空间等 I/O 空间。 0xC0000000~ high_memory 之间的内 核逻辑地址空间专用来固定映射系统中的物理内存,也就是说 0xC0000000~ high_memory 之间空间 大小与系统的物理内存空间大小是相同的(当然在配置了 CONFIG_DISCONTIGMEMD 选项的非连续内存系统中,内核逻辑地址空间和物理内存空间一样可能存在内存孔洞), 如果系统中的物理内存容量远小于 1GB ,那么内核现行地址空间中内核逻辑地址空间之上的 high_memory~0xFFFFFFFF 之间还有足够的空间来固定映射一些 I/O 空间。可是,如果系统中的物理内存容量(包括内存孔洞)大于 1GB ,那么就没有足够的内核线性 地址空间来固定映射系统全部物理内存以及一些 I/O 空间了,为了解决这个问题,在 x86 处理器平台设置了一个经验值: 896MB ,就是说,如果系统中的物理内存(包括内存孔洞)大于 896MB ,那么将前 896MB 物理内存固定映射到内 核逻辑地址空间 0xC0000000~0xC0000000+896MB =high_memory )上,而 896MB 之后的物理内存则不建立到内核线性地址空间的固定映射,这部分内存就叫高端物理内存。此 时内核线性地址空间 high_memory~0xFFFFFFFF 之间的 128MB 空间就称为高端内存线性地址空间,用来映射高端物理内存和 I/O 空间 896MB x86 处理器平台的经验值,留了 128MB 线性地址空间来映射高端内存以及 I/O 地址空间,我们在嵌入式系统中可以根据具体情况修改这个阈值,比如, MIPS 中将这个值设置为 0x20000000B 512MB ),那么只有当系统中 的物理内存空间容量大于 0x20000000B 时,内核才需要配置 CONFIG_HIGHMEM 选项,使能内核对高端内存的分配和映射功能。什么情况需要划分出高端物理内存以及高端物 理内存阈值的设置原则见上面的内存页区( zone )概念说明。

8 )高端线性地址空间:从 high_memory 0xFFFFFFFF 之间的线性地址空间属于高端线性地址空间,其中 VMALLOC_START~VMALLOC_END 之间线性地址被 vmalloc() 函数用来分配物理上不连续但线性地址空间连续的高端物理内存,或者被 vmap() 函数用来映射高端或 低端物理内存,或者由 ioremap() 函数来重新映射 I/O 物理空间。 PKMAP_BASE 开始的 LAST_PKMAP (一般等于 1024 )页线性地址空间被 kmap() 函数用来永久映射高端物理内存。 FIXADDR_START 开始的 KM_TYPE_NR*NR_CPUS 页线性地址空间被 kmap_atomic() 函数用来临时映射高端物理内存,其他未用高端线性地址空间可以用来在系统初始化期间永久 映射 I/O 地址空间。

Linux 2.6.10 内核中的 ARM 处理器平台部分没有对高端内存的支持,图 18-6 和图 18-7 分别列出了 SA1100 IXP4XX 处理器平台的 Linux 线性地址空间布局。

转自[http://blog.csdn.net/w_s_xin/archive/2009/12/21/5050656.aspx]

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值