2019-01-13 CSAPP 第九章

9.虚拟存储器

为了更加有效地管理存储器且少出错,现代系统提供了对主存的抽象概念,叫做虚拟存储器(VM)。

虚拟存储器是硬件异常,硬件地址翻译,主存,磁盘文件和内核软件的完美交互。

为每个进程提供一个大的,一致的和 私有的地址空间。

提供了3个重要能力。

将主存看成磁盘地址空间的高速缓存。

只保留了活动区域,并根据需要在磁盘和主存间来回传送数据,高效使用主存。

为每个进程提供一致的地址空间

简化存储器管理

保护了每个进程的地址空间不被其他进程破坏。

程序员为什么要理解它?

虚拟存储器是中心的。

遍布在计算机系统所有层次,硬件异常,汇编器,连接器,加载器,共享对象,文件和进程中扮演重要角色。

虚拟存储器是强大的。

可以创建和销毁存储器片(chunk)

将存储器片映射到磁盘文件的某个部分。

其他进程共享存储器。

例子

能读写存储器位置来修改磁盘文件内容。

加载文件到存储器不需要显式的拷贝。

虚拟存储器是危险的

引用变量,间接引用指正,调用malloc动态分配程序,就会和虚拟存储器交互。

如果使用不当,将遇到复杂危险的与存储器有关的错误。

例子

一个带有错误指针的程序可以立即崩溃于段错误或者保护错误。

运行完成,却不产生正确结果。

本章从两个角度分析。

虚拟存储器如何工作。

应用程序如何使用和管理虚拟存储器。

9.1 物理与虚拟寻址

物理地址(Physical Address,PA):计算机系统的主存被组织为M个连续的字节大小的单元组成的数组。每个字节的地址叫物理地址.

CPU访问存储器的最自然的方式使用物理地址,这种方式称为物理寻址。

- 早期的PC,数字信号处理器,嵌入式微控制器以及Cray超级计算机使用物理寻址。

现代处理器使用的是虚拟寻址(virtual addressing)的寻址形式。

CPU通过生成一个虚拟地址(Virtual address,VA)来访问主存。

将虚拟地址转换为物理地址叫做地址翻译(address translation)。

地址翻译也需要CPU硬件和操作系统之间的紧密结合。

CPU芯片上有叫做存储器管理单元(Memory Management Unit,MMU)的专用硬件。

利用存储在主存中的查询表来动态翻译虚拟地址。

查询表由操作系统管理。

9.2 地址空间

地址空间(address space)是一个非负整数地址的有序集合。

如果地址空间中整数是连续的,我们说它是线性地址空间(linear address space)。

为了简化讨论,我们总是假设使用线性地址空间。

在一个带虚拟存储器的系统中,CPU从一个有N=2^n个地址的地址空间中生成虚拟地址,这个地址空间称为虚拟地址空间(virtual address space)。

一个地址空间大小是由表示最大地址所需要的位数来描述的。

如N=2^n个地址的虚拟地址空间叫做n位地址空间。

现在操作系统支持32位或64位。

一个系统还有物理地址空间,它与系统中物理存储器的M=2^m(假设为2的幂)个字节相对应。

地址空间的概念很重要,因为它区分了数据对象(字节)和 它们的属性(地址)。

每个字节(数据对象)一般有多个 独立的地址(属性)。每个地址都选自不同的地址空间。

比如一般来说。

字节 有一个在虚拟地址空间的虚拟地址。

还有一个在物理地址空间的 物理地址。

两个地址都能访问到这个字节。

类似现实世界的门牌号, 和经纬度。

9.3 虚拟存储器作为缓存的工具

感悟

在讲述这一小章之前,必须交代一下我对虚拟存储器概念的存疑。

原本我以为虚拟存储器=虚拟内存。

以下是虚拟内存的定义

虚拟内存是计算机系统内存管理的一种技术。它使得应用程序认为它拥有连续的可用的内存(一个连续完整的地址空间),而实际上,它通常是被分隔成多个物理内存碎片,还有部分暂时存储在外部磁盘存储器上,在需要时进行数据交换

而在下面的定义我们可以看到CSAPP中认为虚拟存储器是存放在磁盘上的。

在此,我们姑且当做两者是不同的东西,以后有更深刻的理解,再思考。

虚拟存储器(VM)被组织为一个存放在磁盘上的N个连续字节大小的单元组成的数组。

每个字节都有一个唯一的虚拟地址,这个虚拟地址作为到数组的索引。

磁盘上数组的内容被缓存到主存中。

同存储器层次结构其他缓存一样,磁盘上的数据被分割称块。

这些块作为磁盘和主存之间的传输单元。

虚拟页(Virtual Page,VP)就是这个块

每个虚拟页大小为P=2^p字节。

物理存储器被分割为物理页,大小也为P字节

也被称为页帧(page frame)

任何时候,虚拟页的集合都被分为3个不相交的子集。

未分配的:VM系统还未分配(或者创建)的页。未分配的块没有任何数据与之相关联。

不占用磁盘空间

通过malloc来分配

缓存的:当前缓存在物理存储器的已分配页。

未缓存的:没有缓存在物理页面存储器中的已分配页。

9.3.1 DRAM缓存的组织结构

DRAM表示虚拟存储器系统的缓存,在主存中缓存虚拟页,有两个特点。

DRAM缓存不命中处罚十分严重。

因为磁盘比DRAM慢100000多倍。

访问一字节开销

:从一个磁盘的一个扇区读取第一个字节的时间开销要比从该扇区中读连续的字节慢大约100000倍

DRAM缓存的组织结构由这种巨大的不命中开销驱动。因此有以下特点。

(有些地方不是特别懂,之后看完第六章应该会好点)

虚拟页往往很大。

4KB~2MB

访问一字节开销的原因才要这么大。

DRAM缓存是全相联

也就是: 任何虚拟页都能放在任何物理页中。

原因在于大的不命中惩罚

更精密的替换算法

替换错了虚拟页的惩罚很高。

DRAM缓存总是写回

因为对磁盘的访问时间很长

而不用直写

9.3.2 页表

判断命中和替换又多种软硬件联合提供。

操作系统软件,MMU中的地址翻译硬件和页表(page table)。

页表是存放在物理存储器的数据结构。

页表将虚拟页映射到物理页。

地址翻译硬件将虚拟地址转换为物理地址都会读取页表。

操作系统负责维护页表的内容,以及磁盘及DRAM之间来回传送页。

页表就是一个页表条目(Page Table Entry,PTE)的数组.

虚拟地址空间 中每个页在页表的固定偏移量处都有一个PTE.

每个PTE由一个有效位和n位地址字段。

有效位表明虚拟页是否被缓存。

如果有效位存在,那么地址字段指向对应的物理存储器。

如果有效位不存在。

地址字段要么为NULL

要么指向虚拟页在磁盘所在的位置。

9.3.3 页命中

一个页命中的过程。

一个虚拟地址转换为物理地址的过程。

9.3.4 缺页

在虚拟存储器的习惯说法中,DRAM缓存不命中称为缺页。

处理过程如下:

读取虚拟地址所指向的PT。

读取PTE有效位,发现未被缓存,触发缺页异常。

调用缺页异常处理程序

选择牺牲页。

如果牺牲页发生了改变,将其拷贝回磁盘(因为是写回)

需要读取的页代替了牺牲页的位置。

结果:牺牲也不被缓存,需要读取的页被缓存。

中断结束,重新执行最开始的指令。

在DRAM中读取成功。

虚拟存储器是20世纪60年代发明的,因此即使与SRAM缓存使用了不同的术语。

块被称为页。

磁盘和DRAM之间传送页的活动叫做交换(swapping)或者页面调度(paging)。

有不命中发生时,才换入页面,这种策略叫做按需页面调度(demand paging)。

现代系统基本都是用这个。

9.3.5 分配页面

比如某个页面所指向地址为NULL,将这个地址指向磁盘某处,那么这就叫分配页面。

此时虚拟页从未分配状态 变为 未缓存。

9.3.6 又是局部性拯救了我们

虚拟存储器工作的相当好,主要归功于老朋友局部性(locality)

尽管从头到尾的活动页面数量大于物理存储器大小。

但是在局部内,程序往往在一个较小的活动页面集合工作

这个集合叫做工作集(working set)或者叫常驻集(resident set)

初始载入开销比较大。

程序有良好的时间局部性,虚拟存储器都工作的相当好。

如果程序实在很烂,或者物理空间很小,工作集大于物理存储器大小。这种状态叫颠簸(thrashing).

这时,页面不断换进换出。性能十分低。

统计缺页次数

可以利用Unix的getrusage函数检测缺页数量。

9.4 虚拟存储器作为存储器的管理工具

实际上,操作系统为每个进程提供一个独立的页表。

因此,VM简化了链接和加载,代码和数据共享,以及应用程序的存储器分配。

简化链接

独立的空间地址意味着每个进程的存储器映像使用相同的格式。

文本节总是从0x08048000(32位)处或0x400000(64位)处开始。

然后是数据,bss节,栈。

一致性极大简化了链接器的设计和实现。

简化加载

加载器可以从不实际拷贝任何数据从磁盘到存储器。

基本都是虚拟存储系统完成。

将一组连续的虚拟页映射到任意一个文件中的任意位置的表示法称作存储器映射。Unix提供一个称为mmap的系统调用,允许程序自己做存储器映射。在9.8详细讲解。

简化共享

独立地址空间为操作系统提供了一个管理用户进程和操作系统自身之间的一致共享机制.

例子

操作相同的操作系统内核代码

C标准库的printf.

因此操作系统需要将不同进程的适当的虚拟页映射到相同的物理页面。

多个进程共享这部分代码的一个拷贝。

而不是每个进程都要加载单独的内核和C标准库的拷贝。

简化存储器分配.

即虚拟页连续(虚拟页还是单独的),物理页可以不连续。使得分配更加容易。

9.5 虚拟存储器作为存储器保护的工具

任何现代操作系统必须为操作系统提供手段来控制对 存储器系统的访问。

不应该允许用户进程修改它的只读文本段。

不允许它读或修改任何内核的代码和数据结构

不允许读写其他进程的私有存储器。

不允许修改共享的虚拟页,除非所有共享者显示允许这么做(通过调用明确的进程间通信)

方式:在PTE上添加一些格外的许可位来控制访问。

SUP:是否只有在内核模式下才能访问?

READ:读权限。

WRITE:写权限。

如果指令违反了许可条件,触发一般保护性异常,然后交给异常处理程序,Shell一般会报告为段错误(segmentaion fault)。

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,185评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,445评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 157,684评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,564评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,681评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,874评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,025评论 3 408
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,761评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,217评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,545评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,694评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,351评论 4 332
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,988评论 3 315
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,778评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,007评论 1 266
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,427评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,580评论 2 349

推荐阅读更多精彩内容