linux内存管理2:内存映射和需求分页(英文名字:demand Paging,又叫:缺页中断)【转】

转自:http://blog.csdn.net/zhangxinrun/article/details/5873148

当某个程序映象开始运行时,可执行映象必须装入进程的虚拟地址空间。如果该程序用到了任何一个共享库,则共享库也必须装入进程的虚拟地址空间。实际上,Linux 并不将映象装入物理内存,相反,可执行文件只是被链接到进程的虚拟地址空间中(磁盘空间中)。随着程序的运行,被引用的程序部分会由操作系统装入物理内存。这种将映象链接到进程地址空间的方法称为“内存映射”。可执行映像.
每个进程的虚拟内存由一个 mm_struct 结构代表,我们将在下一章中详细讲述该结构。该结构中实际包含了当前执行映象的有关信息,并且包含了一组指向 vm_area_struct 结构的指针。如图 10-5 所示,每个 vm_area_struct 描述了一个虚拟内存区域的起点和终点、进程对内存的访问权限以及一个对内存的操作例程集。操作例程集是 Linux 操作该内存区域时所使用的例程集合。例如,当进程试图访问的虚拟内存当前不在物理内存当中时(通过页故障),Linux 就可以利用操作集中的一个例程执行正确的操作,在这种情况下为 nopage 操作。

图 10-5 vm_area_struct 数据结构示意图
当可执行映象映射到进程的虚拟地址空间时,将产生一组 vm_area_struct 结构来描述虚拟内存区域的起始点和终止点,每个 vm_struct 结构代表可执行映象的一部分,可能是可执行代码,也可能是初始化的变量或未初始化的数据。随着 vm_area_struct 结构的生成,这些结构所描述的虚拟内存区域上的标准操作函数也由 Linux 初始化。
某个可执行映象映射到进程虚拟内存中并开始执行时,因为只有很少一部分装入了物理内存,因此很快就会访问尚未装入物理内存的虚拟内存区域。这时,处理器将向 Linux 报告一个页故障及其对应的故障原因。
这种页故障的出现原因有两种,一是程序出现错误,例如向随机物理内存中写入数据,这种情况下,虚拟内存是无效的,Linux 将向程序发送 SIGSEGV 信号并终止程序的运行;另一种情况是,虚拟地址有效,但其所对应的页当前不在物理内存中,这时,操作系统必须从磁盘映象或交换文件中将内存装入物理内存。
那么,Linux 如何判断页故障发生时,虚拟内存地址是否是有效的呢?如前所述,Linux 利用 vm_area_struct 数据结构描述进程的虚拟内存空间,为了查找出现页故障虚拟内存相应的 vm_area_struct 结构的位置,Linux 内核同时维护一个由 vm_area_struct 结构形成的 AVL(Adelson-Velskii and Landis)树。利用 AVL 树,可快速寻找发生页故障的虚拟地址所在的内存页区域。如果搜索不到这一内存区域,则说明该虚拟地址是无效的,否则该虚拟地址是有效的。
也有可能因为进程在虚拟地址上进行的操作非法而产生页故障,例如在只读页中写入数据。这时操作系统会同样发送内存错误信号到该进程。有关页的访问控制信息(只读页、只写页、可读可写页、可执行代码页等)包含在页表项中。
对有效的虚拟地址,Linux 必须区分页所在的位置,即判断页是在交换文件中,还是在可执行映象中。为此,Linux 通过页表项中的信息区分页所在的位置。如果该页的页表项是无效的,但非空,则说明该页处于交换文件中,操作系统要从交换文件装入页(有关内存交换的内容在下一节中讲述)。否则,默认情况下,Linux 会分配一个新的物理页并建立一个有效的页表项;对于映象的内存映射来讲,则会分配新的物理页,更新页表项属性信息,并从映象中装入页。
这时,所需的页装入了物理内存,页表项也同时被更新,然后进程就可以继续执行了。这种只在必要时才将虚拟页装入物理内存的处理称为“需求分页”。
在处理页故障的过程中,因为要涉及到磁盘访问等耗时操作,因此操作系统会选择另外一个进程进入执行状态。

时间: 2024-08-02 06:18:41

linux内存管理2:内存映射和需求分页(英文名字:demand Paging,又叫:缺页中断)【转】的相关文章

Linux内存管理 (一) 内存组织

内存管理是内核最复杂同时也是最重要的一部.其特点在于非常需要处理器和内核之间的协作. 首先内存划分为结点,在内核中表示为pg_data_t,每个结点划分为内存域. 以下的所有数据结构或代码都做了不同程度的精减,一方面是为了保留相关代码,除去细枝末叶,另一方面是为了美观. 结点的数据结构为 <mmzone.h>typedef struct pglist_data { struct zone node_zones[MAX_NR_ZONES]; /*内存结点所包含的内存域数组*/ struct zo

内存管理:内存泄漏和空悬指针

********内存管理基础********************* 内存管理:针对的是实例的内存占用的管理(放在堆里面) 实例:1:由class类型构建的实例,2:闭包对象 内存管理技术:ARC:Automatic Reference Count 自动:由语言本身帮我们销毁内存,不需要你手动销毁, 比如在c中就调用dealloc() 引用:let p = Person()  p就是对Person()这个对象的一个引用 计数: let p = Person() //一个 / / let pp

java基础---JVM内存管理以及内存运行机制学习总结

自己从网上搜资料拼接了一张JVM内存图:如下图所示: 我们思考几个问题: 1.jVM是怎么运行的? 2.JVM运行时内存是怎么分配的? 3.我们写的java代码(类,对象,方法,常量,变量等等)最终存放在哪个区? VM运行时数据区域: 1.程序计数器(program Counter Register):   是一块较小的内存空间,它的作用可以看做是当前线程所执行的字节码的行号指示器.在虚拟机的概念模型里(仅是概念模型,各种虚拟机可能会通过一些更高效的 方式去实 现),字节码解释器工作时就是通过改

Kernel那些事儿之内存管理(13) --- 内核映射(下)

前面讲过,针对于内核地址空间中后面的128MB空间,Kernel提供了三种机制来映射物理内存.之前讲过了两种,即持久内核映射和临时内核映射.这两种机制的目的都是一样的:使Kernel能够访问到高端内存. 今天讲一下第三种机制:非连续内存分配,也就是vmalloc.这个机制同样可以使Kernel能够访问到高端内存,不过这不是该机制的主要目的.该机制的主要目的是:把物理上不连续的页面映射到连续的内核线性地址空间中. 非连续内存区域管理 既然是映射,肯定会涉及到三个元素:集合L,集合P,映射M. 集合

内存管理之内存池概述(转)

原文链接:http://www.xiaoyaochong.net/wordpress/index.php/2013/08/10/%E5%BC%95%E5%86%85%E5%AD%98%E7%AE%A1%E7%90%86%E4%B9%8B%E5%86%85%E5%AD%98%E6%B1%A0%E6%A6%82%E8%BF%B0/ 在我们编写代码的过程中,不可避免的要和内存打交道,在申请释放不太频繁的情况下,通常让系统进行内存管理即可.但是,直接使用系统调用malloc/free.new/delet

内存管理--检测内存

linux kernel被bootloader加载到内存后,cpu首先执行head.s中的start_of_setup函数等函数,然后跳转到main.c,main中首先执行detect_memory函数探测内存: int detect_memory(void) { int err = -1; if (detect_memory_e820() > 0) err = 0; if (!detect_memory_e801()) err = 0; if (!detect_memory_88()) err

Objective-C 【内存管理&amp;手动内存管理 综述】

------------------------------------------- 内存管理 (1)Objective-C的内存管理 栈区    存放局部变量(由于基本数据类型占用的存储空间是固定的,由系统去分配,我们不用去管,故栈区存放基本数据类型,) 堆区    存放程序运行过程中动态分配的内存空间(对象类型是程序运行过程中动态分配的,他们的大小不固定.比如说是我们Person new申请来的,存放在堆区,也是我们需要管理的) ★所以内存管理的范围是   继承了NSObject的所有对象

第九讲.内存管理初级.(内存管理的方式,引用计数机制及影响计数的各个方法,dealloc方法,内存管理的基本原则,掌握copy的实现)

一.内存管理的方式. 1.进行内存管理的原因: 1>.由于移动设备的内存极其有限,所以每个APP所占的内存也是有限制的,当app所占用的内存较多时,系统就会发出内存警告,这时需要回收一些不需要再继续使用的内存空间,比如回收一些不再使用的对象和变量等. 管理范围:任何继承NSObject的对象,对其他的基本数据类型无效. 2>.本质原因是因为对象和其他数据类型在系统中的存储空间不一样,其它局部变量主要存放于栈中,而对象存储于堆中,当代码块结束时这个代码块中涉及的所有局部变量会被回收,指向对象的指

内存管理 浅析 内存管理/内存优化技巧

内存管理 浅析 下列行为都会增加一个app的内存占用: 1.创建一个OC对象: 2.定义一个变量: 3.调用一个函数或者方法. 如果app占用内存过大,系统可能会强制关闭app,造成闪退现象,影响用户体验.如何让回收那些不再使用的对象呢?本文着重介绍OC中的内存管理. 所谓内存管理,就是对内存进行管理,涉及的操作有: 1.分配内存:比如创建一个对象,会增加内存占用: 2.清除内存:比如销毁一个对象,会减少内存占用. 内存管理的管理范围: 1.任何继承了NSObject的对象: 2.对其他非对象类