5. 内存虚拟化

  • 1. 概述
  • 2. 影子页表
  • 3. VT-x支持
    • 3.1. EPT
    • 3.2. VPID
  • 4. Intel EPT
    • 4.1. EPT原理
      • 4.1.1. GVA->HPA地址转换过程
    • 4.2. EPT的硬件支持
      • 4.2.1. VM-Execution控制域的Enable EPT字段
      • 4.2.2. VM-Execution控制域的Extended page table pointer字段
      • 4.2.3. TLB、INVEPT指令和VPID
      • 4.2.4. VM-Exit信息域的EPT Violation相关字段
    • 4.3. EPT的软件使用
  • 5. VPID
    • 5.1. 传统TLB
    • 5.2. TLB项的VPID标识不同虚拟处理器的不同TLB
    • 5.3. VPID的软件使用
  • 6. Linux系统检查
    • 6.1. /proc/cpuinfo
    • 6.2. sysfs文件系统
  • 7. AMD NPT

1. 概述

内存虚拟化的主要任务是实现地址空间的虚拟化.

由于引入了客户机物理地址空间内存虚拟化通过两次地址转换来支持地址空间的虚拟机, 即 客户机虚拟地址GVA客户机物理地址GPA宿主机物理地址HPA的转换.

其中,

  • GVA→GPA的转换是由客户机软件决定, 通常是客户机OS通过VMCS中客户机状态域CR3指向的页表来指定;

  • GPA→HPA的转换是由VMM决定, VMM在将物理内存分配给客户机时就确定了GPA→HPA的转换, VMM通常会用内部数据结构来记录这个关系. VMM 为每个虚拟机动态地维护了一张客户机物理地址宿主机物理地址映射表。

2. 影子页表

传统的IA32架构只支持一次地址转换, 即通过CR3指定的页表实现"虚拟地址"→"物理地址"的转换.

这和内存虚拟化所要求的两次地址转换产生矛盾.

可通过将两次转换合并成一次转换解决, 即VMM根据GVA→GPA→HPA的映射关系, 计算出GVA→HPA的映射关系, 并将其写入"影子页表".

影子页表的作用:

5. 内存虚拟化_第1张图片

这样的软件方法尽管可以, 但缺点也很明显.

  • 首先是实现非常复杂, 例如要考虑 各种页表同步情况!!! 等, 这样导致开发、调试和维护比较困难. 可参考Xen/KVM中影子页表的实现.
  • 另外, 开销也很大, 因为要为 每个客户机进程对应的页表!!! 都要维护一个"影子页表".

具体可以看 第4章 基于软件的完全虚拟化

3. VT-x支持

3.1. EPT

为解决这个问题, VT-x提供了Extend Page Table(EPT)技术, 直接在硬件支持GVA→GPA→HPA的两次地址转换, 降低内存虚拟化的难度, 提高内存虚拟化性能.

3.2. VPID

此外, 为进一步提高TLB的使用效率, VT-x还引入了Virtual Processor ID(VPID)功能, 进一步增强内存虚拟化性能.

4. Intel EPT

4.1. EPT原理

在原有客户机页表!!!客户机虚拟地址!!!客户机物理地址!!!映射 (CR3页表地址映射!!!GVA→GPA!!!) 基础上, EPT还引入了 EPT页表(GPA→HPA!!!) 来实现 客户机物理地址宿主机物理地址的另一次映射.

这样, GVA→GPA→HPA两次地址转换!!! 都由 CPU硬件自动完成!!!.

图5-13描述了EPT基本原理.

5. 内存虚拟化_第2张图片

客户机运行时,客户机页表基地址被载入物理CR3,而EPT页表基地址VMCS中获取。

4.1.1. GVA->HPA地址转换过程

  1. 处于non-root模式CPU加载guest进程的gCR3;
  2. gCR3是GPA,cpu需要通过查询EPT页表来实现GPA->HPA
  3. 如果没有,CPU触发EPT Violation, 由VMM截获处理
  4. 假设客户机m级页表宿主机EPTn级,在TLB均miss的最坏情况下,会产生m*n次内存访问,完成一次客户机的地址翻译

5. 内存虚拟化_第3张图片

这里假设客户机页表!!!EPT页表!!!都是4级页表, CPU完成一次地址转换的基本过程如下.

CPU首先查找Guest CR3指向的L4页表. 由于Guest CR3给的是GPA(!!!客户机物理地址, 不是客户机逻辑地址, 也不是宿主机物理地址!!!), 因此CPU需要通过EPT页表!!!来实现Guest CR3 GPA→HPA的转换!!!: CPU首先会查看硬件的EPT TLB(因为CR3是GPA!!!所以查找的是EPT的TLB!!!), 如果没有对应的转换, CPU会进一步查找EPT页表, 如果还没有, CPU则抛出EPT Violation异常VMM来处理.

获取L4页表物理地址(!!!HPA!!!)后, CPU根据GVA!!!L4页表项内容, 获取L3页表项的GPA!!!. 如果L4页表中GVA对应的表项显示为"缺页", 那么CPU产生Page Fault, 直接交给Guest Kernel!!!处理. 注意, 这里不会产生VM-Exi!!!t. 获得L3页表项的GPA后, CPU同样要通过查询EPT页表!!!来实现L3 GPA→HPA的转换, 过程和上面一样.

同样, CPU依次查找L2、L1页表, 最后获得GVA对应的GPA, 然后通过查询EPT页表获得HPA.

上图可以看出, CPU需要5次!!!查询EPT页表(CR3、L3页表地址、L2页表地址、L1页表地址和最终GPA查询EPT页表!!!), 每次查询!!!都需要4次内存访问(!!!每级页表都是一次内存访问!!!), 最坏共20次内存访问. EPT硬件通过增大EPT TLB来尽量减少内存访问.

一个GPAHPA的转换过程如下图.

5. 内存虚拟化_第4张图片

5. 内存虚拟化_第5张图片

客户机物理地址GPA宿主机物理地址HPA转换的过程中,由于缺页、写权限不足等原因也会导致客户机退出,产生 EPT 异常

注意: 上面的EPT TLB是用来缓存客户机的GPA转换成宿主机的HPA; 而在这之前, 客户机的GVA转成GPA是可以使用原始TLB???

4.2. EPT的硬件支持

4.2.1. VM-Execution控制域的Enable EPT字段

为了支持EPT, VT-x规范在VMCS的"VM-Execution控制域"中提供了Enable EPT字段. 如果在VM-Entry的时候该位被置, CPU会使用EPT功能进行两次转换.

4.2.2. VM-Execution控制域的Extended page table pointer字段

EPT页表的基地址是由VMCS"VM-Execution控制域"的Extended page table pointer字段来执行的, 它包含了EPT页表的宿主机物理地址HPA!!!.

EPT是一个多级页表, 每级页表表项格式是相同!!! 的, 如表5-8

5. 内存虚拟化_第6张图片

EPT页表转换过程和CR3页表转换是类似的. 图5-14展现了CPU使用EPT页表进行地址转换的过程.

5. 内存虚拟化_第7张图片

EPT通过EPT页表SP字段!!!支持大小为2MB或1GB的超级页. 图5-15给出2MB超级页的地址转换过程. 和上图不同在于, 当CPU发现SP字段为1时, 就停止继续向下遍历页表, 而是直接转换了.

5. 内存虚拟化_第8张图片

4.2.3. TLB、INVEPT指令和VPID

EPT同样会使用TLB缓冲来加速页表的查找过程. 因此, VT-x还提供了一条新指令INVEPT, 可使EPT的TLB项失效. 这样, 当EPT页表有更新时, CPU可以执行INVEPT使旧的TLB失效, 使CPU使用新的EPT表项.

VPID下面讲到

4.2.4. VM-Exit信息域的EPT Violation相关字段

和CR3页表会导致Page Fault一样, 使用EPT后, 如果CPU在遍历EPT页表进行GPA→HPA转换时, 也会发生异常.

⓵ GPA的地址位数大于GAW.

⓶ 客户机试图读一个不可读的页(R=0).

⓷ 客户机试图写一个不可写的页(W=0)

⓸ 客户机试图执行一个不可执行的页(X=0)

发生异常, CPU会产生VM-Exit!!!, 退出原因是EPT Violation!!!. VMCS的"VM-Exit信息域"还包括如下信息.

  • VM-Exit physical-address information: 引起EPT Violalation的GPA
  • VM-Exit linear-address information: 引起EPT Violation的GVA
  • Qualification: 引起EPT Violation的原因, 如由于读或写引起等.

4.3. EPT的软件使用

使用EPT, VMM需要做如下事情.

  • 首先需要在VMCS中将EPT功能打开, 这个只需要写VMCS相应字段即可.

  • 其次需要设置好EPT的页表. EPT页表反应了GPA→HPA的映射关系. 由于是VMM负责给虚拟机分配物理内存!!!, 因此, VMM拥有足够信息建立EPT页表. 此外, 如果VMM给虚拟机分配的物理内存足够连续的话, VMM可以在EPT页表尽量使用超级页, 这样有利于提高TLB的性能.

  • 当CPU开始使用EPT时, VMM还需要处理EPT Violation.

通常, EPT Violation的来源如下几种.

⓵ 客户机访问MMIO地址!!!. 这时, VMM需要将请求转给I/O虚拟化模块!!!.

EPT页表的动态创建. 有些VMM采用懒惰方法, 一开始EPT页表为空, 第一次使用发生EPT Violation时再建立映射.

由此, EPT相对"影子页表", 大大简化了.

  • 而且, 由于客户机内存的Page Fault不用发生VM-Exit, 也大大减少VM-Exit个数, 提高了性能.
  • 此外, EPT只需要维护一张EPT页表, 不像"影子页表"那样需要为每个客户机进程的页表维护一张影子页表, 也减少了内存的开销.

5. VPID

5.1. 传统TLB

TLB页表项的缓存. TLB需要和页表一起工作才有效. 因此, 当页表发生切换时, TLB原有内容也就失效了, CPU需要使用INVLPG指令使其所有项失效, 这样才不会影响之后页表的工作. 例如, 进程切换时, 通过切换CR3切换进程地址空间, 使前一个进程的TLB项全部失效.

类似, 每次VM-EntryVM-Exit时, CPU会强制TLB内容全部失效, 以避免VMM以及不同虚拟机虚拟处理器之间TLB项的混用, 因为硬件无法区分!!!一个TLB项属于VMM还是特定虚拟机的虚拟处理器.

5.2. TLB项的VPID标识不同虚拟处理器的不同TLB

VPID是一种硬件级的对TLB资源管理的优化. 通过在硬件上每个TLB项增加一个标志, 来标识不同的虚拟处理器地址空间, 从而区分开VMM以及不同虚拟机的不同虚拟处理器的TLB. 即, 硬件具备了区分不同的TLB项属于不同虚拟处理器地址空间(对应不同的虚拟处理器)的能力.

这样,

  • 硬件可以避免每次VM-EntryVM-Exit时, 使全部TLB失效!!!, 提高VM切换效率.
  • 并且, 由于这些继续存在的TLB, 硬件也避免了VM切换后的一些不必要页表遍历, 减少内存访问, 提高了VMM以及虚拟机运行速度.

VT-x通过在VMCS中增加两个域来支持VPID.

  • 一个是VMCS中的Enable VPID域, 当该域被置上, VT-x硬件会开启VPID功能.
  • 第二个是VMCS中的VPID域, 标识该VMCS对应的TLB. VMM本身也需要一个VPID, VT-x规定虚拟处理器标志0被指定为用于VMM自身.

注意: VPID是和VCPU对应的, 不是和虚拟机本身

5. 内存虚拟化_第9张图片

5.3. VPID的软件使用

因此, 软件上使用VPID很简单, 两件事.

  • 首先为VMCS分配一个VPID, 只要是非0的且和其它VMCS的VPID不同即可;
  • 其次是VMCS中Enable VPID置位.

6. Linux系统检查

6.1. /proc/cpuinfo

对于内存虚拟化EPT以及vpid的支持查询

[root@kvm-host ~]# grep -E “ept|vpid” /proc/cpuinfo 

6.2. sysfs文件系统

宿主机中,可以根据sysfs文件系统kvm_intel模块当前参数值来确定KVM是否打开EPT和VPID特性。

在默认情况下,如果硬件支持了EPT、VPID,则kvm_intel模块加载默认开启EPT和VPID特性,这样KVM会默认使用它们。

[root@kvm-host ~]# cat /sys/module/kvm_intel/parameters/ept
Y
[root@kvm-host ~]# cat /sys/module/kvm_intel/parameters/vpid
Y

在加载kvm_intel模块时,可以通过设置eptvpid参数的值来打开或关闭EPT和VPID

当然,如果kvm_intel模块已经处于加载状态,则需要先卸载这个模块,在重新加载之时加入所需的参数设置。当然,一般不要手动关闭EPT和VPID功能,否则会导致客户机中内存访问的性能下降。

[root@kvm-host ~]# modprobe kvm_intel ept=0,vpid=0 
[root@kvm-host ~]# rmmod kvm_intel
[root@kvm-host ~]# modprobe kvm_intel ept=1,vpid=1

7. AMD NPT

AMD NPT(Nested Page Table,嵌套页表)是AMD提供的内存虚拟化支持技术。 如图 2-9 所示,传统的分页技术下的地址转换是直接将线性地址空间上的线性地址转换为物理地址空间上的物理地址。CR3寄存器中存储着页表的物理基地址。  图2-9 传统分页技术下的地址转换:

5. 内存虚拟化_第10张图片

嵌套分页技术的原理如图2-10所示。

1)客户机和宿主机都有自己的CR3寄存器,分别记为gCR3(guest CR3)和nCR3(nested CR3)。真正的CR3由VMM所控制和使用。

2)gPT(guest Page Table,客户机页表)负责将客户机线性地址转换为客户机物理地址。客户机页表存在于客户机物理内存中,并由gCR3索引。

3)nPT(nested Page Table,嵌套页表)负责将客户机物理地址转换为系统物理地址。嵌套页表存在于系统物理内存中,并由nCR3索引。

4)最常用到的客户机线性地址到系统物理地址的映射关系在TLB中缓存。

5)gCR3和客户机页表中存放的都是客户机物理地址,所以,在访问客户机页表前需要将客户机物理地址转换为系统物理地址。  图2-10 嵌套分页技术下的地址转换:

5. 内存虚拟化_第11张图片

你可能感兴趣的:(5. 内存虚拟化)