ICode9

精准搜索请尝试: 精确搜索
首页 > 系统相关> 文章详细

二十五、linux内存映射

2022-01-24 14:01:39  阅读:165  来源: 互联网

标签:映射 虚拟地址 物理地址 内存 linux 进程 虚拟内存


一、物理地址空间是什么

  理解虚拟地址空间还得从物理地址空间开始说起。我们知道内存就像一个数组,每个存储单元被分配了一个地址,这个地址就是物理地址,所有物理地址构成的集合就是物理地址空间。物理地址也就是真实的地址,对应真实的那个内存条。

如果CPU使用物理地址向内存寻址的话,就是下面这样,这条指令中的地址就是数据真实存放的地址。

 

 

二、虚拟地址空间是什么

引入虚拟地址之后,对于每一个进程,操作系统提供一种假象,让每个进程感觉自己拥有一个巨大的连续的内存可以使用,这个虚拟的空间甚至还可以比内存的容量还大。这个“假象”就是虚拟地址空间。虚拟地址是面向每个进程的,只是一个“假象”罢了。

此时CPU使用虚拟地址向内存寻址,通过专用的内存管理单元(MMU)硬件把虚拟地址转换为真实的物理地址(地址翻译),操作系统负责把虚拟地址和物理地址的映射关系维护在页表之中。

 

 

指令中的地址不是数据真实存放的地址.

三、程序和进程

  当我们写完代码,编译,链接并且生成可执行文件后,得到的这个东西就是一系列二进制代码的集合,我们管这东西叫做程序,存储在磁盘上。只有当我们执行这个文件后,程序才会被操作系统读入内存运行,但是注意系统并不会把程序全部读入内存,我们把正在运行的程序叫做进程。

从进程的视角来看,我的数据和代码被存放在一个连续的空间之中,每个区域分别有着不同的功能。典型的如存放代码的区域和存放数据的区域。

                              

然而我们知道,这只是个假象。代码和数据中的地址都是一个虚拟地址,还需要经过地址翻译才能得到真正的物理地址。

四、分页、页表和缺页异常

  虚拟地址和物理地址的映射关系是以“页”为单位的。分页就是把整个虚拟内存和物理内存分割成大小固定的块,以一个页作为映射的最小单位。运行时,CPU请求一个虚拟地址,虚拟地址又被翻译为物理地址,从而确定数据在内存中的哪个位置。下面的页表中记录了这个进程虚拟内存每个页的映射关系。

当CPU寻址的时候,这个映射会有三种可能。

  • 未分配:虚拟地址所在的那一页并未被分配,代表没有数据和他们关联,这部分也不会占用内存。
  • 未缓存:虚拟地址所在的那一页被分配了,但并不在内存中。
  • 已缓存:虚拟地址所在的那一页就在内存中。

  当访问一个未缓存的区域时,系统将产生缺页中断,然后进程被阻塞,等待操作系统将缺失的那一页从磁盘复制到内存。当复制完成后,CPU继续执行导致缺页中断的那条指令,此时就会正常执行了。这种仅在需要的时候将页面拷贝到内存的策略叫做按需调度页面。 可以想象当程序被装入内存的时候,开始时仅有有很小的一部分内容被放入内存。程序在运行中不断缺页,不断的把需要的部分拷贝进内存。
从上面的图中还可以看出,虚拟内存实际上就是磁盘的缓存。系统通过缺页中断的机制,小心的维护着每个进程的虚拟地址假象。

五、虚拟内存的应用

在Linux中,将一片虚拟内存和一个磁盘上的对象关联起来,并用磁盘上的对象初始化这片虚拟内存,这个机制就叫做内存映射。

1、化简资源的共享

当我们使用共享库的函数时时,例如printf(),没有必要为每个进程拷贝一本代码,这样太浪费内存了。我们只需要让每个进程的一块虚拟内存映射到相同的对象上就可以了。

假如进程1和进程2想要共享同一个文件。其中文件A已经被映射到进程2(文件被缓存在内存中),进程2还是通过缺页中断载入的文件A。

此时进程1也打开文件A,由于文件的名字在系统中是唯一的,操作系统清楚文件A已经被缓存在内存之中。因此系统将进程1的虚拟内存映射到相同内存之中,完成文件的共享。

2、零拷贝技术的一种实现

对于linux中最常用的I/O函数 read() 来说,文件先会被系统复制到内核空间的缓冲区,然后再复制到用户空间。读一个文件需要复制两次显然不是我们希望的,尤其是读大文件的时候, sad...

通过内存映射,我们可以绕过内核缓冲,直接将文件A映射到虚拟内存,这里一共就发生一次拷贝,nice~

六、总结
虚拟内存无时无刻都在为我们工作,而且我们不需要任何干涉就能自动地工作。虚拟内存可以看成对磁盘的一个缓存,它通过缺页中断触发操作系统处理访问未缓存块的问题。虚拟内存可以应用在处理共享对象、减少I/O开销问题中。

标签:映射,虚拟地址,物理地址,内存,linux,进程,虚拟内存
来源: https://www.cnblogs.com/yuanqiangfei/p/15839104.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有