玩转男子学院本书能为计算机工程师、学术研究人员、研究生新生,及经验丰富的从业人员提供一个关于虚拟内存(VM, Virtual Memory)的衔接性概述(end-to-end overview)。我们首先从基本概念的简要回顾开始,随后讨论目前关于虚拟内存最先进的硬软件支持,以及这一领域中的新兴研究动向。
所涵盖的主题将横跨处理器微架构(processor microarchitecture)、内存系统(memory system)、操作系统(OS, operating system)设计和内存分配(memory allocation)。我们也将展示,虚拟内存该如何通过细致的硬软件实现有效地实现[1],并讨论了这一领域中新问题的有关研究方向。
虚拟内存作为计算机科学的经典抽象概念,是计算机革命(computing revolution)的支柱之一。它可以实现硬件上的灵活性、软件上的可执行性、以及总体上更好的安全性,这里仅列举其强大优势中的一小部分。如今,近乎所有的用户级程序(user-level program)都会想当然地认为,它们已经从(关于硬件、操作系统、设备驱动程序和系统库的)物理内存管理负担中解脱出来了。
尽管虚拟内存从仓库级数据中心(warehouse-scale datacentel)到嵌入式物联网(IoT, Internet of Things)设备系统无处不在,但如今,虚拟内存的开销已成为了一个关键性能瓶颈。
通常为单CPU甚至单核设计的虚拟内存架构都难以被拓展至今天的系统上,而这些系统如今正在越来越多地包含外来的硬件加速器(如GPU、FPGA或DSP),以及新兴的内存基数(如非易失性内存),并且运行着的工作负载(如虚拟化或者“大数据”应用)也在日益增长。
所以,许多虚拟内存的基本抽象和实现方法正在被扩充、扩展甚至完全重建,以确保虚拟内存在未来几年内仍然有效并可行。
这本书详细介绍了虚拟内存(VM)的软硬件支持中的最新技术。我们首先从虚拟机的基础知识简要回顾开始,随后跳转到近年来于学术界和工业界星期的虚拟机领域中的最新进展。
本书的核心在于去全面评述(surveying)这一空间中的亮点(highlight)和结论。我们还会强调地描述一些重要的开放性问题,这些问题可能会在未来几年主导该研究领域。我们希望本书能够成为读者在工作中,用于选择并处理问题的实用指南。
第2章总结了VM抽象(VM abstraction)的基础知识,其中描述了一个典型虚拟地址空间的布局与管理,从基本的内存布局和权限位到共享内存和线章概述了一个典型的,基于分页(paging)的现代虚拟机子系统实现。对那些不太熟悉这些材料的人来说,这几章可以作为复习。读者也可能发现,有关如(synonyms)和(homonyms)这样的主题中的细节复习,会非常有用。不过,更有经验的读者也可以选择跳过这些章节。
第6章涵盖了VM的(非)一致性和高并行虚拟机实现同步化中的挑战。这些章节重视的是,现代虚拟机子系统设计空间是如何在有趣的新方向上继续发展的,以跟上当今应用不断增长的工作集(work set)。
然后从这里开始,本书便转向了该领域中一些更具前瞻性的线章介绍了一些能让虚拟内存适应各种异构体系结构或者内存技术的办法。第8章介绍了一些关于虚拟机系统硬件改进的最新研究,第9章介绍了软硬件的协同设计。到了这里,我们期望读者已经能够深入研究文献,为快速变化的虚拟机世界做好探索的准备,甚至在未来做出贡献了。
我们假定读者已具有一些合适的背景知识。在计算机体系结构方面,我们假定读者对一些如流水线、超标量、乱序执行、缓存(cache)以及缓存一致性等这样基本概念具有一定了解。在操作系统方面,我们假定读者对执行的进程,线程模型、用于支持这些执行模型的内核(kernel)结构、以及内存管理和文件系统等基础知识具有基本的了解。
任何规模的现代计算机系统——数据中心、台式机、平板电脑、可穿戴设备、甚至嵌入式——都在依赖虚拟内存(VM, virtual memory),以为用户提供一个干净且实用的编程模型。读者应该知道,VM就是:关于给定机器上的,实际可用存储资源的理想抽象。
程序在访问内存时只会使用虚拟地址(virtual address),而处理器和操作系统则会协同将这些虚拟地址转换为物理地址(physical address),以指向数据的实际物理位置(图1.1)。
尽管已假定大多读者至少对虚拟机的基础已经有了一定了解,但我们还是觉得从虚拟机的一些优势好处开始回顾仍是重要的。这些优势能促使我们继续去扩充和扩展虚拟机,以应对架构异构性、“大数据”以及虚拟化(virtualization)等挑战。像这样的,我们应该牢记在心,以作为今天该领域所有新研究和开发的目标。
VM抽象能允许我们“不受限制”地运行代码以控制整个内存范围,而不必考虑系统中同时并发运行的任何其它程序。而这又能反过来允许程序员编写具有更高可移植性更高的代码,可运行在具有完全不同的物理资源集的机器上,或者是单个机器上随动态使用不断变化的物理资源。实际上,用户级进程(user-level process)甚至没办法去确定背后实际所使用的物理地址。
没有VM的话,程序员就必须去面对物理内存空间中的低层次复杂性,这些空间由几个RAM芯片、硬盘和固态驱动等组成。一旦RAM的容量或者任何配置发生了改变,程序员就需要去重写以及重新编译他们的代码。
VM还能提供保护(protection)和隔离(isolation),它可以防止bug、恶意代码或设备去接触那些,它们不应该访问的其它程序空间。
没有VM(或其它类似抽象[112])的话,也将不会有这种内存保护,从而程序能够覆盖并损坏其它程序的内存映像(memory image),安全性将受到严重损害。
此外,VM还能允许程序以一种能够优雅扩展的方式去低度申请(under subscribe)(使用的内存比分配的内存少)或者过度申请(over subscribe)(分配的内存比实际可用的内存多)以提高效率,而不是简单地崩溃(crash)系统。事实上,甚至没必要去要求虚拟和物理地址空间要有相同的大小(size)。
在所有的这些方式下,除我们将讨论的一些例外情况之外,每个程序都能够去忽略物理实现中的细节,或者共享系统中的其它程序。
VM子系统还会负责一些其它重要的内存管理任务。首先,内存经常会被分配(allocate)以及释放(deallocate),因此VM子系统必须要以能满足分配请求的方式去处理可用资源。简单的实现(implementation)会导致诸如碎片化(fragmentation)之类的问题,在碎片化的情况下,地址空间中内存区域的低效排序将会导致无法访问或者浪费资源。
VM还必须去优雅地处理内存被过度申请(over subscribed)的情况。通常是将某些内存区域(memory region)交换(swap)到后备存储(backing store)(如磁盘驱动器)中来实现的。所增加的磁盘访问延迟通常会对性能造成极大影响,但通过智能的VM子系统实现,也能够降低其中的一些开销。
最后,在最近出现的一些情境中,内存有时还需要从一个物理地址迁移到另一个物理地址上。这可通过将内存从一个插槽移到另一个插槽上来实现,或者从一个物理存储器移动到另一个物理存储器(如DRAM到非易失性内存)、从一个设备到另一个设备(如,CPU到GPU)、甚至只是对一个物理内存块中的内存区域进行碎片整理。
在应用了VM的架构(architecture)中,VM子系统的性能对整个的系统性能是至关重要的。在典型的一个程序中,内存访问通常会占指令数的三分之一左右。除非系统采用的是带虚拟索引(virtual indexed)和虚拟标记(virtually tagged)的缓存(cache),否则每个加载(load)和存储(store)操作都将经过VM子系统。
为此,要让VM变得实用,我们必须以一种高效的方式实现地址转换(address translation),既不消耗过多的硬软件资源,也不消耗过多能量。
然而,虚拟机的优势如今正在受到威胁。如上所述性能方面的课题,就是虚拟机在当代研究领域中一直保持着高价值的原因。
程序工作集(work set)正在变得越来越大,为此过去曾能有效用于VM硬件结构的实现,和OS的算法也正在努力跟上。这导致了人们对超级页面(super page)和TLB预取等功能重新提起了兴趣,这些功能机制能够帮助VM子系统跟上工作负载。
除此之外,随着诸如GPU和DSP等加速器(accelerator)的集成,并与传统CPU用户代码共享虚拟地址空间,计算机系统的架构正在变得越来越异构。
上述趋势正在推动许多有趣的新研究与开发,以使得虚拟机抽象能够在未来有效地扩展到更大、更广的环境中。其中就包括了许多引人入胜的新技术研究:包括在存储器间、存储器和设备间迁移页面的技术,可扩展的TLB同步算法,以及允许设备与CPU共享同一虚拟地址空间的IOMMUs。
现代虚拟机的研究问题可大体分为两类,一类是一直在探索的传统意义上的领域,另一类则是由于硬件的新趋势而导致变得重要的领域。
传统主题中,关于TLB结构、大小、组织、分配和替换策略的课题都在变得越来越重要,因为工作负载的数据量在不断增加。自然地,数据越大,硬件缓存结构(如TLB和MMU缓存)的压力也就越大,从而引发了这些课题。我们会在第3~5章探讨这些主题。
除功能和性能问题外,正确性(correctness)也仍是一个重要课题。VM是一个复杂的接口,需要正确的软硬件协调合作(cooperation)。尽管经历了几十年的积极研究,现实世界中的VM实现仍常在硬件和操作系统层出现错误[5, 80, 94]。
硬件加速器和新内存技术的出现也带来了新的硬软件VM管理层,而这增加了本就极具挑战的验证难度。因此,允许对VM正确性进行规范的形式化推理工具与方法,在未来会非常重要,我们在第6章研究了这些困难的正确性问题。
最后,新兴的计算趋势也带来了更新、更基本的问题。例如,随着系统能够容纳越来越多地内存,我们必须回答一个这样的基本问题:虚拟机最初是在内存不足时构思出来的,那么我们现在继续使用它的理由是什么呢?以及如果是这样的话,它的哪些部分会在未来最有用,又该如何设计以获得更好的性能?
要回答这些问题,我们又需要反过来讨论分页(paging)与分段(segmentation)的优劣势、适当的页面大小、接口间的策略以及新兴的芯片层叠(die-stack)技术、与非易失性内存间的页面迁移机制与策略,还有对新兴硬件加速器(不只是GPU)的正确VM支持。我们会在第7~9章探讨这些非常适时的问题。
在本书最后的第10章,我们对该领域未来几年的发展进行了简要的展望,并且提供了一些想法,可能帮助研究人员、工程师和开发人员找到他们感兴趣深入并作出贡献的方向。
此句原文:We show how efficient virtual memory implementations hinge on careful hardware and software cooperation。
我们一般会将“memory”翻译为“内存”,但实际上“内存”不一定为“内”。“memory”本身(在计算机领域)的含义应当是“存储器”可指寄存器文件、片内缓存、片外缓存、磁盘硬盘等任何带存储功能的器件。但为了方便,或者说读起来更连贯,本文中许多地方还是会将“memory”翻译为“内存”,请注意这不一定意味着它要处于什么东西的“内部”。我甚至还看到某些地方说“内存(Memory)....,也称内存储器和主存储器”,非常具有迷惑性。我们知道,主存储器(Main Memory)又是另一个术语了。初学者也可能会对这些翻译感到迷惑,因此我在这里做出一定解释。
这里将demand翻译为了立即,这里它与lazy是一个相对的概念(或者说反义词)。关于“惰性(lazy)”,可以查到比较多搜索结果的关键词是“惰性求值(lazy evaluation)”,其也用到了“惰性(lazy)”的思想。
Consistency”译为“连贯性”,意思是执行的先后顺序是一致的(特别要注意的是,这里“先后顺序”这一概念定义有一定的自由空间,比如可以定义为时间上事件发生的先后顺序,也可定义为程序语义上的先后因果顺序)。可以理解为时间上的的一致。“Coherence”译为“一致性”,意思是数据(在不同地方)的多个副本(在某一致性模型下)是一致,或者说是相同的。可以理解为空间上的一致。 似乎很多地方把“Consistency”和“Coherence”都翻译成了“一致性”,但这两个术语是存在区别的,请注意区分!目前关于这两个术语的中文翻译较为混乱,具体说明请见“”中的译注。
这里“TLB合并(TLB coalescing)”所“合并”的是TLB中的TLB项。
|