第十章 虚拟内存
更新日期:2005-6-20
在第九章,我们讨论了计算机系统所采用的各种内存管理策略。这些策略都有一个共同的目标:在内存中同时保留多个进程。然而,这些策略往往需要在进程执行之前把整个进程拷入内存。
而利用虚拟内存技术,不用把整个进程完全载入内存就可以执行。(Virtual memory is a technique that allows the execution of processes that may not be completely in memory.)这种机制的一个主要优点是程序可以比物理内存更大。更进一步讲,虚拟内存技术把主内存抽象到一个极大的一致的存储队列中,将用户所见的逻辑内存和实际的物理内存分离开来。这种技术使程序员免受内存容量的限制。虚拟内存技术也允许进程很容易的共享文件和地址空间,并提供了高效的创建进程的机制。
然而,虚拟内存技术的实现并不容易,使用不当则会显著降低性能。在本章,我们将以请求分页的形式讨论虚拟内存技术并考察它的复杂度和代价。
10.1 背景知识
在第九章所描述的内存管理算法是必需的,这是因为:指令必须要处于物理内存中才可以被执行。为了满足这个需求,第一个方法是把整个逻辑地址空间放置到物理内存中。Overlays和动态载入可以减轻这种限制的负担,但是它们都需要特别的预处理和程序员的额外工作。这种限制似乎是必需的和合理的,但是非常不幸,因为它把程序的大小限制在物理内存的大小范围内。
实际上,对实际程序的检测表明,在许多情况下不会需要整个程序。例如:
l 程序中通常有一些处理不寻常的错误的代码。因为这些错误很少发生,实际上这些代码几乎从来都不会执行。
l 被分配到数组、列表和表的内存往往多于实际所需。一个数组可能会声明100个数组项,即使很少会用到多于10个。一个汇编语言符号表可能会拥有3,000个符号的空间,虽然平均每个程序不会多过200个符号。
l 一个程序的某些选项和特性很少会用到。例如,美国政府用于平衡预算的程序只是最近才用到。
即使在需要整个程序的情况下,也不会同时用其全部(这种情况如overlays)。
在内存中部分的执行程序有如下几个优点:
l 程序不再受可用物理内存容量的限制。程序员将面对一个极大的虚拟地址空间,简化了程序设计任务。
l 因为每个用户程序占用的物理内存更少了,所以可以同时运行更多的程序,相应提高了CPU利用率和吞吐率,不过没有增加响应时间和周转时间。
l 用户程序的载入和交换所需的I/O操作更少,所以每个用户程序都可以运行的更快。
这样,不需要把程序完整的载入内存即可执行,对系统和用户都有利。
虚拟内存(virtual memory)把逻辑内存从物理内存中分离出来。这种分离为程序员提供了一个远大于有效内存的虚拟内存(图10.1)。(This separation allows an extremely large virtual memory to be provided for programmers when only a smaller physical memory is available (Figure 10.1).)虚拟内存简化了程序设计,因为程序员不再需要担心可用物理内存的数量或者是把代码放置到overlay中;她可以集中精力于程序设计。一旦系统支持虚拟内存,几乎都不再使用overlays了。
图10.1 虚拟内存大于物理内存
除了把逻辑内存从物理内存中分离之外,虚拟内存也允许多个不同的进程共享文件和内存(9.4.5节)。页面共享更进一步允许在进程创建期间提高性能。
通常用请求页式(demand paging)来实现虚拟内存。也可以用分段系统实现。多种系统提供了段页机制,其中对段进行了分页。这样,用户看到的是段,但是操作系统可以利用请求页式来实现。也可以用请求段式(demand segmentation)来实现虚拟内存。Burroughs的计算机系统采用了请求段式。IBM OS/2操作系统也采用请求段式。然而,因为段的大小是不同的,所以段置换(segment replacement)算法比页置换(page replacement)算法更为复杂。在本书中我们不会讨论请求分段;请参考文献注记获取相应的资料。