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

news/2024/7/20 13:02:09 标签: 内存管理, 操作系统, 数据结构与算法

转自: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 会分配一个新的物理页并建立一个有效的页表项;对于映象的内存映射来讲,则会分配新的物理页,更新页表项属性信息,并从映象中装入页。
这时,所需的页装入了物理内存,页表项也同时被更新,然后进程就可以继续执行了。这种只在必要时才将虚拟页装入物理内存的处理称为“需求分页”。
在处理页故障的过程中,因为要涉及到磁盘访问等耗时操作,因此操作系统会选择另外一个进程进入执行状态。

【作者】 张昺华
【出处】 http://www.cnblogs.com/sky-heaven/
【博客园】 http://www.cnblogs.com/sky-heaven/
【新浪博客】 http://blog.sina.com.cn/u/2049150530
【知乎】 http://www.zhihu.com/people/zhang-bing-hua
【我的作品---旋转倒立摆】 http://v.youku.com/v_show/id_XODM5NDAzNjQw.html?spm=a2hzp.8253869.0.0&from=y1.7-2
【我的作品---自平衡自动循迹车】 http://v.youku.com/v_show/id_XODM5MzYyNTIw.html?spm=a2hzp.8253869.0.0&from=y1.7-2
【新浪微博】 张昺华--sky
【twitter】 @sky2030_
【facebook】 张昺华 zhangbinghua
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利.

http://www.niftyadmin.cn/n/1667387.html

相关文章

ARM汇编指令集汇总

作者:毛茏玮 / Saint 掘金:juejin.im/user/5aa1f8… 微博:weibo.com/5458277467/… GitHub :github.com/saint-000 今天Saint给大家分享一下对汇编指令代码的汇总。 一.汇编数据处理指令 1.数据传送指令 【MOV指令】&a…

大家知道为什么要加 final 关键字了

原文链接:www.jianshu.com/p/acc8d9a67d0c 在开发过程中,由于习惯的原因,我们可能对某种编程语言的一些特性习以为常,特别是只用一种语言作为日常开发的情况。但是当你使用超过一种语言进行开发的时候就会发现,虽然都…

VS Code 插件 主题 快捷键

VS Code 插件 主题 快捷键 window 下的操作,自己亲自测试 快捷键 打开终端命令行:ctrl 打开命令面板:ctrl shift p 在这里直接输入一些命令,比如输入snippet,选择打开用户代码片段,选中你要编辑的语言…

Vue项目el-input 不能输入的解决办法

目录 一、背景 二、解决办法 1、方法1:标签嵌套太深 2、方法2:使用了 template 作为 el-input 的父标签 3、方法3:v-model 一、背景 输入框动态填充值,但是填充后不能编辑了, 就像是被禁止了一样, 就很无语...查了下资料, v-model填写了, 也没有templete标签嵌套最终方法一即可…

【Mysql】常用DDL语句

修改列的默认值: alter table t_goods alter column enable set default N; 转载于:https://www.cnblogs.com/njlittlecat/p/9854630.html

POJ NOI0113-01 数制转换(PKU2710)

问题链接:POJ NOI0113-01 数制转换。 原题出处:PKU2710 数制转换。 总时间限制:1000ms内存限制: 65536kB描述求任意两个不同进制非负整数的转换(2进制~16进制),所给整数在long所能表达的范围之内。 不同进制…

你知道一个比SpringBoo快44倍的Java框架嘛?

最近栈长看到一个框架,官方号称可以比 Spring Boot 快 44 倍,居然这么牛逼,有这么神奇吗?今天带大家来认识一下。 这个框架名叫:light-4j。 官网简介:A fast, lightweight and more productive microservi…

装箱问题--C++实现

题目描述 一个工厂制造的产品形状都是长方体,它们的高度都是h,长和宽都相等,一共有六个型号,他们的长宽分别为1*1, 2*2, 3*3, 4*4, 5*5, 6*6。这些产品通常使用一个 6*6*h 的长方体包裹包装然后邮寄给客户。因为邮费很贵&#xf…