`
liuguxing
  • 浏览: 94910 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论

进程地址空间与虚拟存储空间的理解

 
阅读更多
【转自】http://blog.csdn.net/do2jiang/archive/2009/10/17/4690967.aspx

[笔记]
程序编译后文件包含进程空间信息,执行的时候并不是完全载入内存,是按分页访问到哪个页面才载入虚拟内存地址映射到得物理内存地址空间。

在进入正题前先来谈谈操作系统内存管理机制的发展历程,了解这些有利于我们更好的理解目前操作系统的内存管理机制。

一 早期的内存分配机制

在早期的计算机中,要运行一个程序,会把这些程序全都装入内存,程序都是直接运行在内存上的,也就是说程序中访问的内存地址都是实际的物理内存地址。当计算机同时运行多个程序时,必须保证这些程序用到的内存总量要小于计算机实际物理内存的大小。那当程序同时运行多个程序时,操作系统是如何为这些程序分配内存的呢?下面通过实例来说明当时的内存分配方法:

某台计算机总的内存大小是 128M ,现在同时运行两个程序 A 和 B , A 需占用内存 10M , B 需占用内存 110 。计算机在给程序分配内存时会采取这样的方法:先将内存中的前 10M 分配给程序 A ,接着再从内存中剩余的 118M 中划分出 110M 分配给程序 B 。这种分配方法可以保证程序 A 和程序 B 都能运行,但是这种简单的内存分配策略问题很多。


图一 早期的内存分配方法

问题 1 :进程地址空间不隔离。由于程序都是直接访问物理内存,所以恶意程序可以随意修改别的进程的内存数据,以达到破坏的目的。有些非恶意的,但是有 bug 的程序也可能不小心修改了其它程序的内存数据,就会导致其它程序的运行出现异常。这种情况对用户来说是无法容忍的,因为用户希望使用计算机的时候,其中一个任务失败了,至少不能影响其它的任务。

问题 2 :内存使用效率低。在 A 和 B 都运行的情况下,如果用户又运行了程序 C ,而程序 C 需要 20M 大小的内存才能运行,而此时系统只剩下 8M 的空间可供使用,所以此时系统必须在已运行的程序中选择一个将该程序的数据暂时拷贝到硬盘上,释放出部分空间来供程序 C 使用,然后再将程序 C 的数据全部装入内存中运行。可以想象得到,在这个过程中,有大量的数据在装入装出,导致效率十分低下。

问题 3 :程序运行的地址不确定。当内存中的剩余空间可以满足程序 C 的要求后,操作系统会在剩余空间中随机分配一段连续的 20M 大小的空间给程序 C 使用,因为是随机分配的,所以程序运行的地址是不确定的。

二 分段

为了解决上述问题,人们想到了一种变通的方法,就是增加一个中间层,利用一种间接的地址访问方法访问物理内存。按照这种方法,程序中访问的内存地址不再是实际的物理内存地址,而是一个虚拟地址,然后由操作系统将这个虚拟地址映射到适当的物理内存地址上。这样,只要操作系统处理好虚拟地址到物理内存地址的映射,就可以保证不同的程序最终访问的内存地址位于不同的区域,彼此没有重叠,就可以达到内存地址空间隔离的效果。

当创建一个进程时,操作系统会为该进程分配一个 4GB 大小的虚拟 进程地址空间。之所以是 4GB ,是因为在 32 位的操作系统中,一个指针长度是 4 字节,而 4 字节指针的寻址能力是从 0x00000000~0xFFFFFFFF ,最大值 0xFFFFFFFF 表示的即为 4GB 大小的容量。与虚拟地址空间相对的,还有一个物理地址空间,这个地址空间对应的是真实的物理内存。如果你的计算机上安装了 512M 大小的内存,那么这个物理地址空间表示的范围是 0x00000000~0x1FFFFFFF 。当操作系统做虚拟地址到物理地址映射时,只能映射到这一范围,操作系统也只会映射到这一范围。当进程创建时,每个进程都会有一个自己的 4GB 虚拟地址空间。要注意的是这个 4GB 的地址空间是“虚拟”的,并不是真实存在的,而且每个进程只能访问自己虚拟地址空间中的数据,无法访问别的进程中的数据,通过这种方法实现了进程间的地址隔离。那是不是这 4GB 的虚拟地址空间应用程序可以随意使用呢?很遗憾,在 Windows 系统下,这个虚拟地址空间被分成了 4 部分: NULL 指针区、用户区、 64KB 禁入区、内核区。应用程序能使用的只是用户区而已,大约 2GB 左右 ( 最大可以调整到 3GB) 。内核区为 2GB ,内核区保存的是系统线程调度、内存管理、设备驱动等数据,这部分数据供所有的进程共享,但应用程序是不能直接访问的。

人们之所以要创建一个虚拟地址空间,目的是为了解决进程地址空间隔离的问题。但程序要想执行,必须运行在真实的内存上,所以,必须在虚拟地址与物理地址间建立一种映射关系。这样,通过映射机制,当程序访问虚拟地址空间上的某个地址值时,就相当于访问了物理地址空间中的另一个值。人们想到了一种分段 (Sagmentation) 的方法,它的思想是在虚拟地址空间和物理地址空间之间做一一映射。比如说虚拟地址空间中某个 10M 大小的空间映射到物理地址空间中某个 10M 大小的空间。这种思想理解起来并不难,操作系统保证不同进程的地址空间被映射到物理地址空间中不同的区域上,这样每个进程最终访问到的

物理地址空间都是彼此分开的。通过这种方式,就实现了进程间的地址隔离。还是以实例说明,假设有两个进程 A 和 B ,进程 A 所需内存大小为 10M ,其虚拟地址空间分布在 0x00000000 到 0x00A00000 ,进程 B 所需内存为 100M ,其虚拟地址空间分布为 0x00000000 到 0x06400000 。那么按照分段的映射方法,进程 A 在物理内存上映射区域为 0x00100000 到 0x00B00000 ,,进程 B 在物理内存上映射区域为 0x00C00000 到 0x07000000 。于是进程 A 和进程 B 分别被映射到了不同的内存区间,彼此互不重叠,实现了地址隔离。从应用程序的角度看来,进程 A 的地址空间就是分布在 0x00000000 到 0x00A00000 ,在做开发时,开发人员只需访问这段区间上的地址即可。应用程序并不关心进程 A 究竟被映射到物理内存的那块区域上了,所以程序的运行地址也就是相当于说是确定的了。




图二 分段方式的内存映射方法



这种分段的映射方法虽然解决了上述中的问题一和问题三,但并没能解决问题二,即内存的使用效率问题。在分段的映射方法中,每次换入换出内存的都是整个程序,这样会造成大量的磁盘访问操作,导致效率低下。所以这种映射方法还是稍显粗糙,粒度比较大。实际上,程序的运行有局部性特点,在某个时间段内,程序只是访问程序的一小部分数据,也就是说,程序的大部分数据在一个时间段内都不会被用到。基于这种情况,人们想到了粒度更小的内存分割和映射方法,这种方法就是分页 (Paging) 。

三 分页

分页的基本方法是,将地址空间分成许多的页。每页的大小由 CPU 决定,然后由操作系统选择页的大小。目前 Inter 系列的CPU 支持 4KB 或 4MB 的页大小,而 PC 上目前都选择使用 4KB 。按这种选择, 4GB 虚拟地址空间共可以分成 1048576 个页, 512M 的物理内存可以分为 131072 个页。显然虚拟空间的页数要比物理空间的页数多得多。

在分段的方法中,每次程序运行时总是把程序全部装入内存,而分页的方法则有所不同。分页的思想是程序运行时用到哪页就为哪页分配内存,没用到的页暂时保留在硬盘上。当用到这些页时再在物理地址空间中为这些页分配内存,然后建立虚拟地址空间中的页和刚分配的物理内存页间的映射。

下面通过介绍一个可执行文件的装载过程来说明分页机制的实现方法。一个可执行文件 (PE 文件 ) 其实就是一些编译链接好的数据和指令的集合,它也会被分成很多页,在 PE 文件执行的过程中,它往内存中装载的单位就是页。当一个 PE 文件被执行时,操作系统会先为该程序创建一个 4GB 的进程虚拟地址空间。前面介绍过,虚拟地址空间只是一个中间层而已,它的功能是利用一种映射机制将虚拟地址空间映射到物理地址空间,所以,创建 4GB 虚拟地址空间其实并不是要真的创建空间,只是要创建那种映射机制所需要的数据结构而已,这种数据结构就是页目和页表。

当创建完虚拟地址空间所需要的数据结构后,进程开始读取 PE 文件的第一页。在 PE 文件的第一页包含了 PE 文件头和段表等信息,进程根据文件头和段表等信息,将 PE 文件中所有的段一一映射到虚拟地址空间中相应的页 (PE 文件中的段的长度都是页长的整数倍 ) 。这时 PE 文件的真正指令和数据还没有被装入内存中,操作系统只是根据 PE 文件的头部等信息建立了 PE 文件和进程虚拟地址空间中页的映射关系而已。当 CPU 要访问程序中用到的某个虚拟地址时,当 CPU 发现该地址并没有相相关联的物理地址时, CPU 认为该虚拟地址所在的页面是个空页面, CPU 会认为这是个页错误 (Page Fault) , CPU 也就知道了操作系统还未给该 PE 页面分配内存, CPU 会将控制权交还给操作系统。操作系统于是为该 PE 页面在物理空间中分配一个页面,然后再将这个物理页面与虚拟空间中的虚拟页面映射起来,然后将控制权再还给进程,进程从刚才发生页错误的位置重新开始执行。由于此时已为 PE 文件的那个页面分配了内存,所以就不会发生页错误了。随着程序的执行,页错误会不断地产生,操作系统也会为进程分配相应的物理页面来满足进程执行的需求。

分页方法的核心思想就是当可执行文件执行到第 x 页时,就为第 x 页分配一个内存页 y ,然后再将这个内存页添加到进程虚拟地址空间的映射表中 , 这个映射表就相当于一个 y=f(x) 函数。应用程序通过这个映射表就可以访问到 x 页关联的 y 页了。

总结:

32 位的CPU 的寻址空间是4G , 所以虚拟内存的最大值为4G , 而windows 操作系统把这4G 分成2 部分, 即2G 的用户空间和2G 的系统空间, 系统空间是各个进程所共享的, 他存放的是操作系统及一些内核对象等, 而用户空间是分配给各个进程使用的, 用户空间包括用: 程序代码和数据, 堆, 共享库, 栈。
分享到:
评论

相关推荐

    Linux中的物理和虚拟存储空间布局

    1. **线性地址空间**:从0x00000000到0xFFFFFFFF的4GB虚拟存储空间。 2. **内核空间**:占用从0xC0000000到0xFFFFFFFF的1GB线性地址空间,这部分空间仅可由运行在内核态下的代码或数据访问。内核空间由所有进程共享...

    Linux进程地址空间分析

    在Linux操作系统中,每个进程都有其独特的地址空间,这是一个虚拟化的内存区域,使得每个进程都可以独立地访问内存,而不会相互干扰。这个地址空间的组织和管理是操作系统核心的重要组成部分,它涉及到进程间的隔离...

    深入理解linux内核(3)第9章.进程地址空间

    进程地址空间"这一章节,将带你深入探讨Linux内核如何组织和管理进程的虚拟地址空间,这是理解Linux系统性能和调试关键问题的基础。 首先,我们需要了解的是,每个进程都有其独立的地址空间,这是进程隔离的一个...

    虚拟存储器 操作系统 模拟分页式虚拟存储管理中硬件的地址转换和缺页中断

    通过本实验帮助同学理解在分页式存储管理中怎样实现虚拟存储管理。 三. 实验题目 第—题:模拟分页式存储管理中硬件的地址转换和产生缺页中断。 第二题:用先进先出(FIFO) 运行环境:Microsoft Visual Studio 2005

    Linux中的物理和虚拟存储空间布局.doc

    在Linux操作系统中,物理存储空间和虚拟存储空间的布局对于理解和优化系统性能至关重要。以下是关于这两个方面的详细说明: 首先,让我们关注物理存储空间布局。在32位处理器上,无论是物理还是虚拟空间,地址范围...

    SY3_检测进程的虚拟地址空间_

    总的来说,理解和检测进程的虚拟地址空间是操作系统和系统编程中的重要技能。掌握这一技能可以帮助开发者更好地管理内存,提高程序的稳定性和安全性。在实际操作中,需要注意遵循系统的安全策略,确保不会侵犯其他...

    操作系统 实验 模拟分页式虚拟存储管理中硬件的地址转换和缺页中断

    在本实验中,我们将深入探讨操作系统中的分页式虚拟存储管理,包括硬件的地址转换机制和缺页中断的处理,以及如何应用先进先出(FIFO)页面调度算法来解决这些问题。此外,我们还将实践构建一个简单的文件系统,以便...

    银行家算法和进程虚拟地址空间分布实验

    ### 银行家算法与进程虚拟地址空间分布实验知识点解析 #### 一、银行家算法 银行家算法是一种避免死锁的算法,主要用于操作系统中的资源管理。它通过模拟银行家处理贷款请求的方式来决定是否应该将资源分配给请求...

    操作系统---虚拟存储区和内存工作区

    虚拟存储系统通过将物理内存与硬盘上的交换空间结合,创建了一个逻辑上比实际物理内存大得多的地址空间,即虚拟存储区。每个进程都有自己独立的虚拟地址空间,使得多个进程可以并发运行,而不会相互干扰。 虚拟...

    深入理解linux内核中文第三版-第九章 进程地址空间

    在Linux操作系统中,进程地址空间是每个进程独立的虚拟内存区域,它决定了进程可以访问哪些内存地址,并且是如何组织这些地址的。《深入理解Linux内核中文第三版》的第九章详细介绍了这一核心概念,帮助读者理解...

    计算机操作系统实验_源码_模拟请求分页虚拟存储管理中的硬件地址变换过程.pdf

    本实验的主要目的是通过模拟请求分页虚拟存储管理中的硬件地址变换过程,来加深对请求分页虚拟存储器管理中的地址变换的理解,并熟练使用所学知识完成地址转换过程。 在实验中,我们首先需要了解请求分页虚拟存储...

    页式虚拟存储管理中地址转换和缺页中断的模拟 操作系统课程设计

    在操作系统领域,页式虚拟存储管理是一种常见的内存管理策略,它通过将进程的逻辑地址空间划分为固定大小的页,并在物理内存中分配相应的页框,实现程序的按需加载和动态调度。在这个课程设计中,我们将深入探讨页式...

    模拟分页式虚拟存储管理(操作系统)

    ### 模拟分页式虚拟存储管理:操作系统层面的关键知识点 ...通过上述实验设计与实践,学习者能够深入理解分页式虚拟存储管理的内部机制,掌握关键概念和技术细节,为进一步研究高级内存管理策略奠定坚实的基础。

    物理地址逻辑地址虚拟地址的概念

    因此,称物理地址“与地址总线相对应”更为准确。尽管如此,在大多数情况下,将物理地址视为直接映射到物理内存上的地址也是可以接受的简化方式。 #### 二、虚拟地址(Virtual Address) 虚拟地址是对整个内存的一种...

    117-演示文稿-虚拟存储思想.pdf

    理解虚拟存储思想需要首先明确逻辑空间与物理空间的区分。逻辑空间指的是程序运行时所使用的地址空间,它是由程序中的地址构成的抽象概念。而物理空间则是实际存在于计算机硬件中的内存。虚拟存储的关键点在于,逻辑...

    Linux的进程地址空间研究.pdf

    内核模式下的内存管理受到限制,内核只能直接寻址1GB的物理内存,前896MB与物理地址线性映射,而超过896MB的高内存则通过最后128MB的线性地址空间映射,采用固定映射和非连续存储区管理技术。Linux 2.6的内存管理...

    Linux操作系统课程指导:Ch15ProcessAddressSpace(进程地址空间).pptx

    1. **平坦地址空间**:每个进程都有自己的平坦地址空间,这意味着在不同进程中,相同地址可能存储不同的数据。这种设计使得进程间的数据隔离得以实现。 2. **共享地址空间**:通过线程或特定机制,进程可以共享地址...

    物理地址逻辑地址虚拟地址的概念.doc

    虚拟内存使得每个进程都可以拥有比实际物理内存更大的地址空间,并且允许不同的进程使用相同的虚拟地址,因为它们会被转换为不同的物理地址。 逻辑地址(Logical Address)在Intel架构中是基于早期的段式内存管理的...

    模拟页式虚拟存储管理中缺页中断先进先出淘汰算法.rar_存储管理_模拟 存储 分配 管理_虚拟 页式 管理_虚拟存储_虚拟存储管

    页式虚拟存储管理是一种常见的技术,它将进程的地址空间划分为固定大小的页,并在需要时将页从磁盘上的虚拟存储器交换到内存中。本篇我们将深入探讨标题和描述中提到的"模拟页式虚拟存储管理中缺页中断先进先出...

Global site tag (gtag.js) - Google Analytics