本文来自:http://www.ywnds.com/?p=5856前端
云计算如今已经很是成熟了,而虚拟化是构建云计算基础架构不可或缺的关键技术之一。 云计算的云端系统, 其实质上就是一个大型的分布式系统。 虚拟化经过在一个物理平台上虚拟出更多的虚拟平台, 而其中的每个虚拟平台则能够做为独立的终端加入云端的分布式系统。 比起直接使用物理平台, 虚拟化在资源的有效利用、 动态调配和高可靠性方面有着巨大的优点。 利用虚拟化, 企业没必要抛弃现有的基础架构便可构建全新的信息基础架构,从而更加充分地利用原有的IT投资。后端
虚拟化是一个广义的术语,是指计算元件在虚拟的基础上而不是真实的基础上运行,是一个为了简化管理、优化资源的解决方案。缓存
在X86平台虚拟化技术中,新引入的虚拟化层一般称为虚拟机监控器(Virtual MachineMonitor, VMM), 也叫作Hypervisor。 虚拟机监控器运行的环境,也就是真实的物理平台,称之为宿主机。而虚拟出来的平台一般称为客户机,里面运行的系统对应地也称为客户机操做系统,以下图:安全
1974年,Popek和Goldberg在一篇论文中定义了“经典虚拟化(Classical virtualization)”的基本需求,他们认为,一款真正意义上的VMM至少要符合三个方面的标准:服务器
虚拟化技术有不少种实现方式, 好比软件虚拟化和硬件虚拟化, 再好比半虚拟化和全虚拟化。 下面将针对每种实现方式作一个简单的介绍。网络
1、软件虚拟化和硬件虚拟化架构
1)虚拟化—软件方案分布式
纯软件虚拟化, 顾名思义, 就是用纯软件的方法在现有的物理平台上(每每并不支持硬件虚拟化) 实现对物理平台访问的截获和模拟。常见的软件虚拟机例如QEMU,它是经过纯软件来仿真X86平台处理器的取指、解码和执行,客户机的指令并不在物理平台上直接执行。因为全部的指令都是软件模拟的,所以性能每每比较差,可是能够在同一平台上模拟不一样架构平台的虚拟机。ide
VMWare的软件虚拟化则使用了动态二进制翻译(BT)的技术,与QEMU这种模拟的方式不一样,BT是一种加速虚拟化的方案之一,另外一种常见的虚拟化加速方案就是硬件辅助虚拟化技术。BT就是在虚拟机监控机可控制的范围内,容许客户机的指令在物理平台上直接运行。可是,客户机指令在运行前会被虚拟机监控机扫描,其中突破虚拟机监控机限制的指令会被动态替换为能够在物理平台上直接运行的安全指令,或者替换为对虚拟机监控器的软件调用。这样作的好处是比纯软件模拟性能有大幅的提高(模拟其根本就是经过一个软件作出一个假的,能够是不存在的;而虚拟是把这个设备经过某种切割或其余方式虚拟出去提供必定程度的服务), 可是也同时失去了跨平台虚拟化的能力。性能
有了BT技术后,Guest的用户空间运行在CPU ring 3上,而Guest的内核空间运行在了CPU ring 1上,Host的内核空间运行在CPU ring 0上。BT就监控在CPU ring 1上,随时将Guest内核的调用给转换为特权指令调用。固然CPU ring 1并无被使用,BT这种技术让虚拟化性能获得了大大的提高。可是BT有一个大大的缺点就是没法跨平台,使用QEMU这种模拟器无论底层硬件是什么,能模拟各类CPU架构平台,如PowerPC、ARM等;可是BT却没法作到这点,BT强烈依赖底层架构,好比底层是X86的那么只能建立X86 CPU的虚拟机。
在纯软件虚拟化解决方案中,VMM在软件套件中的位置是传统意义上操做系统所处的位置,而操做系统的位置是传统意义上应用程序所处的位置, 这种转换必然会增长系统的复杂性。软件堆栈的复杂性增长意味着,这些环境难于管理,于是会加大确保系统可靠性和安全性的困难。
2) 虚拟化—硬件方案
硬件辅助虚拟化(HVM),简而言之,就是物理平台自己提供了对特殊指令的截获和重定向的硬件支持,甚至,新的硬件会提供额外的资源来帮助软件实现对关键硬件资源的虚拟化,从而提高性能。能够理解为CPU额外增长了一个ring -1环专门提供给虚拟机运行的。以X86平台的虚拟化为例,支持虚拟技术的X86 CPU带有特别优化过的指令集来控制虚拟过程,经过这些指令集,VMM会很容易将客户机置于一种受限制的模式下运行,一旦客户机试图访问物理资源,硬件会暂停客户机的运行,将控制权交回给VMM处理。VMM还能够利用硬件的虚拟化加强机制,将客户机在受限模式下对一些特定资源的访问,彻底由硬件重定向到VMM指定的虚拟资源,整个过程不须要暂停客户机的运行和VMM软件的参与。
因为虚拟化硬件可提供全新的架构,支持操做系统直接在上面运行,无需进行二进制转换,减小了相关的性能开销,极大简化了VMM 设计,进而使VMM可以按通用标准进行编写, 性能更增强大。
须要说明的是, 硬件虚拟化技术是一套解决方案。完整的状况须要CPU、主板芯片组、BIOS和软件的支持,例如VMM软件或者某些操做系统自己。即便只是CPU支持虚拟化技术,在配合VMM软件的状况下,也会比彻底不支持虚拟化技术的系统有更好的性能。鉴于虚拟化的巨大需求和硬件虚拟化产品的广阔前景,Intel一直都在努力完善和增强本身的硬件虚拟化产品线。自2005年底,Intel便开始在其处理器产品线中推广应用Intel Virtualization Technology(IntelVT)虚拟化技术,发布了具备IntelVT虚拟化技术的一系列处理器产品,包括桌面的Pentium和Core系列,还有服务器的Xeon至强和Itanium安腾。Intel一直保持在每一代新的处理器架构中优化硬件虚拟化的性能和增长新的虚拟化技术。如今市面上,从桌面的Core i3/5/7,到服务器端的E3/5/7/9,几乎所有都支持Intel VT技术。能够说, 在不远的未来, Intel VT极可能会成为全部Intel处理器的标准配置。固然AMD的CPU也都支持虚拟化技术。
总结
硬件辅助虚拟化貌似比BT技术更好,若是BT技术可以让虚拟机性能达到物理机80%的性能的话,那么硬件辅助虚拟化(HVM)就可以让虚拟机性能达到物理机85%左右。固然这中间的转换仍是须要的,只不过是由硬件直接完成了,仅此而已。
2、全虚拟化和半虚拟化
Full-virtualization(全虚拟化)
全虚拟化为客户机提供了完整的虚拟X86平台, 包括处理器、 内存和外设, 支持运行任何理论上可在真实物理平台上运行的操做系统, 为虚拟机的配置提供了最大程度的灵活性。不须要对客户机操做系统作任何修改便可正常运行任何非虚拟化环境中已存在基于X86平台的操做系统和软件,这也是全虚拟化无可比拟的优点。
在全虚拟化状况下,虚拟机并不知道本身运行在虚拟化环境下,是无感知的,安装使用时跟在物理机上没有什么区别。可是这种彻底虚拟化中间须要软件作支撑的,须要软件去模拟提供全部的硬件资源,至少是这个CPU的特权指令须要用软件去模拟的,由于你要让各Guest并不知道本身运行在虚拟环境中,那么你就必需要提供一个带有特权指令的CPU。
在虚拟化环境中,一般虚拟跟模拟是两个概念,VMWare的动态二进制翻译技术(BT)是虚拟的而QEMU软件技术是模拟的。最大的区别在于,模拟经过软件实现时须要模拟CPU ring 0-3,也就是须要转换CPU ring 0-3全部的指令,而虚拟只须要转换CPU ring 0特权指令便可。
固然无论上面说到的BT技术仍是QEMU仍是硬件辅助虚拟化技术都属于彻底虚拟化技术,都是须要指令转换的,都是须要复杂的步骤才能完成的,若是咱们可以精简这其中的步骤那么虚拟机的性能必定会有提高的。那么怎么精简呢?这就是下面说的半虚拟化技术。另外,在全虚拟化模式下:
CPU若是不支持硬件虚拟化技术:那么全部指令都是经过VMM虚拟的,经过VMM内的BT动态翻译技术把虚拟机要运行的特权指令转换为物理指令集,而后到CPU上运行。
CPU若是支持硬件虚拟化技术:VMM运行ring -1,而GuestOS运行在ring 0。
Para-virtualization(半虚拟化)
软件虚拟化能够在缺少硬件虚拟化支持的平台上彻底经过VMM软件来实现对各个虚拟机的监控,以保证它们之间彼此独立和隔离。 可是付出的代价是软件复杂度的增长,和性能上的损失。减轻这种负担的一种方法就是,改动客户操做系统,使它知道本身运行在虚拟环境下,可以与虚拟机监控机协同工做。这种方法就叫半虚拟化(para-virtualization)。虚拟机内核明确知道本身是运行在虚拟化之上的,对于硬件资源的使用再也不须要BT而是本身向VMM申请使用,如对于内存或CPU的使用是直接向VMM申请使用,直接调用而非翻译。就算对于I/O设备的使用它也能够经过Hyper Call(Hypervisor提供的系统调用)直接能够跟硬件打交道,减小了中间的翻译步骤天然性能就行了,听说这种半虚拟化方式可以让虚拟化达到物理机90%的性能。本质上,半虚拟化弱化了对虚拟机特殊指令的被动截获要求,将其转化成客户机操做系统的主动通知。可是,半虚拟化须要修改客户机操做系统的源代码来实现主动通知。
Xen是开源准虚拟化技术的一个例子,操做系统做为虚拟服务器在Xen Hypervisor上运行以前,它必须在内核层面进行某些改变。所以,Xen适用于BSD、Linux、Solaris及其余开源操做系统,但不适合对像Windows这些专有的操做系统进行虚拟化处理,由于它们不
公开源代码,因此没法修改其内核。
总结
因为硬件辅助虚拟化的出现,使得彻底虚拟化在性能上也获得了提高。而且相比半虚拟化而言,彻底虚拟化使用上更加简化,虚拟过程对于Guest而言是透明的。因此彻底虚拟化更加符合市场需求,好比后面说的KVM虚拟机。
说完虚拟化技术中最重要的CPU相关技术外,下面再来讲说计算机五大部件中的第二大部件存储器,内存虚拟化技术。
首先咱们知道内存自己就相似于虚拟化技术,其经过虚拟地址对外提供服务,全部的进程都觉得本身可使用全部的物理内存。以下图提供了在非虚拟化中和虚拟化中寻址方式。
No Virtualation
在非虚拟化中,系统把物理地址经过虚拟地址的方式(一个个页框)提供出去给进程使用,每一个进程都觉得本身可使用全部的物理内存。原本在CPU上有个称为MMU(memory management unit)的东西,任什么时候候当某个进行想要访问数据本身的线性地址中的某段数据的时候,就是虚拟地址。这个进程就会传给CPU一个地址,并须要读取数据,可是CPU知道这个地址是没法真正访问到数据的,因而CPU要经过MMU将这段地址转换为对应物理地址的访问,从而这段数据就能访问到了。通常进程所获得的内存地址空间是一个连续的虚拟地址空间,而在真正的物理内存存储时通常都不会是连续的地址空间。
In Virtualation
为了实现内存虚拟化,让客户机使用一个隔离的、从零开始且具备连续的内存空间,像KVM虚拟机引入一层新的地址空间,即客户机物理地址空间 (Guest Physical Address, GPA),这个地址空间并非真正的物理地址空间,它只是宿主机虚拟地址空间在客户机地址空间的一个映射。对客户机来讲,客户机物理地址空间都是从零开始的连续地址空间,但对于宿主机来讲,客户机的物理地址空间并不必定是连续的,客户机物理地址空间有可能映射在若干个不连续的宿主机地址区间。
从上图咱们看出,在虚拟化环境中,因为虚拟机物理地址不能直接用于宿主机物理MMU进行寻址,因此须要把虚拟机物理地址转换成宿主机虚拟地址 (Host Virtual Address, HVA)。运行在硬件之上的Hypervisor首先会对物理内存进行虚拟地址 (Host Virtual Address, HVA)转换,而后还须要对转换后的虚拟地址内存空间进行再次虚拟,而后输出给上层虚拟机使用,而在虚拟机中一样又要进行GVA转换到GPA操做。显然经过这种映射方式,虚拟机的每次内存访问都须要Hypervisor介入,并由软件进行屡次地址转换,其效率是很是低的。
所以,为了提升GVA到HPA转换的效率,目前有两种实现方式来进行客户机虚拟地址到宿主机物理地址之间的直接转换。其一是基于纯软件的实现方式,也即经过影子页表(Shadow Page Table)来实现客户虚拟地址到宿主机物理地址之间的直接转换(KVM虚拟机是支持的)。其二是基于硬件辅助MMU对虚拟化的支持,来实现二者之间的转换。
其中Shadow Page Table(影子页表),其实现很是复杂,由于每个虚拟机都须要有一个Shadow Page Table。而且这种状况会出现一种很是恶劣的结果,那就是TLB(Translation Lookaside Buffer,传输后备缓冲器)很难命中,尤为是由多个虚拟主机时,由于TLB中缓存的是GVA到GPA的转换关系,因此每一次虚拟主机切换都须要清空TLB,否则主机之间就会发生数据读取错误(由于各主机间都是GVA到GPA)。传输后备缓冲器是一个内存管理单元用于改进虚拟地址到物理地址转换后结果的缓存,而这种问题也会致使虚拟机性能低下。
此外,Intel的EPT(Extent Page Table) 技术和AMD的NPT(Nest Page Table) 技术都对内存虚拟化提供了硬件支持。这两种技术原理相似,都是在硬件层面上实现客户机虚拟地址到宿主机物理地址之间的转换。称为Virtualation MMU。当有了这种MMU虚拟化技术后,对于虚拟机进程来讲仍是一样把GVA经过内部MMU转换为GPA,并不须要改变什么,保留了彻底虚拟化的好处。可是同时会自动把GVA经过Virtualation MMU技术转换为真正的物理地址(HPA)。很明显减小了由GPA到HPA的过程,提高虚拟机性能。
而且CPU厂商还提供了TLB硬件虚拟化技术,之前的TLB只是标记GVA到GPA的对应关系,就这两个字段,如今被扩充为了三个字段,增长了一个主机字段,而且由GVA到GPA以及对应变成了GVA到HPA的对应关系。明确说明这是哪一个虚拟机它的GVA到HPA的映射结果。
总结
由此看出内存虚拟化,若是没有硬件作支撑,那么只能使用Shadow Page Table(影子页表),也就意味着TLB须要不断地进行清空。而有了内存虚拟机技术后,虚拟机的性能在某种程度上也获得了大大地提高。
从处理器的角度看,外设是经过一组I/O资源(端口I/O或者是MMIO)来进行访问的,因此设备的相关虚拟化被称为I/O虚拟化,如:
1)外存设备:硬盘、光盘、U盘。
2)网络设备:网卡。
3)显示设备:VGA(显卡)。
4)键盘鼠标:PS/二、USB。
还有一些如串口设备、COM口等等设备统称IO设备,所谓IO虚拟化就是提供这些设备的支持,其思想就是VMM截获客户操做系统对设备的访问请求,而后经过软件的方式来模拟真实设备的效果。基于设备类型的多样化,I/O虚拟化的方式和特色纷繁复杂,咱们挑一些经常使用IO设备说一说。
但通常IO虚拟化的方式有如下三种,以下图:
第一种:模拟I/O设备
彻底使用软件来模拟,这是最简单但性能最低的方式,对于IO设备来讲模拟和彻底虚拟化没有太大意义上的区别。VMM给Guest OS模拟出一个IO设备以及设备驱动,Guest OS要想使用IO设备须要调内核而后经过驱动访问到VMM模拟的IO设备,而后到达VMM模拟设备区域。VMM模拟了这么多设备以及VMM之上运行了那么多主机,因此VMM也提供了一个I/O Stack(多个队列)用来调度这些IO设备请求到真正的物理IO设备之上。通过多个步骤才完成一次请求。
举例:Qemu、VMware Workstation
第二种:半虚拟化
半虚拟化比模拟性能要高,其经过系统调用直接使用I/O设备,跟CPU半虚拟化差很少,虚拟化明确知道本身使用的IO设备是虚拟出来的而非模拟。VMM给Guest OS提供了特定的驱动程序,在半虚拟化IO中咱们也称为“前端IO驱动”;跟模拟I/O设备工做模式不一样的是,Guest OS本身自己的IO设备不须要处理IO请求了,当Guest OS有IO请求时经过自身驱动直接发给VMM进行处理,而在VMM这部分的设备处理咱们称之为“后端IO驱动”。
举例:Xen、virtio
第三种:I/O透传技术
I/O透传技术(I/O through)比模拟和半虚拟化性能都好,几乎进阶于硬件设备,Guest OS直接使用物理I/O设备,操做起来比较麻烦。其思想就是提供多个物理I/O设备,如硬盘提供多块,网卡提供多个,而后规划好宿主机运行Guest OS的数量,经过协调VMM来达到每一个Guest OS对应一个物理设备。另外,要想使用I/O透传技术,不光提供多个I/O设备还须要主板上的I/O桥提供支持透传功能才能够,通常Intel提供的这种技术叫VT-d,是一种基于北桥芯片的硬件辅助虚拟化技术,主要功能是由来提升I/O灵活性、可靠性和性能的。
为何I/O透传还须要主板支持呢?每一个虚拟机直接使用一个网卡不就能够了吗?主要是由于在咱们传统的X86服务器架构上,全部的IO设备一般有一个共享或集中式的DMA(直接内存访问),DMA是一种加速IO设备访问的方式。因为是集中式的,因此在VMM上管理多块网卡时其实使用的仍是同一个DMA,若是让第一个Guest OS直接使用了第一块网卡,第二个Guest OS直接使用第二块网卡,但使用的DMA仍是同一个,而DMA是没法区分哪一个Guest OS使用的是哪块网卡,这就变的麻烦了。而像Intel的VT-d就是用来处理这些问题的,以及处理各主机中断。
举例:Intel VT-d
对应具体设备是如何实现?
1)硬盘如何虚拟化?
虚拟化技术中,CPU能够按时间切割,内存能够按空间切割,那么磁盘设备呢?也能够按照空间来切割,把硬盘划分红一个一个的区域。可是好像没有这么用的,通常磁盘虚拟化的方式就是经过模拟的技术来实现。
2)网卡如何虚拟化?
网卡的虚拟化方式通常使用模拟、半虚拟化、IO透传技术都行,其实现方式根据VMM的不一样有所不一样,通常的VMM都会提供全部的方式。
3)显卡如何虚拟化?
显卡虚拟化一般使用的方式叫frame buffer(帧缓存机制),经过frame buffer给每一个虚拟机一个独立的窗口来实现。固然其实对于显示设备的虚拟化是比较麻烦的,因此一般在虚拟化环境中咱们的显示设备性能都不会很好的,固然安装个Windows显示仍是没有问题的,但不适用图形处理类的服务。
4)键盘鼠标如何虚拟化?
咱们在虚拟机中使用键盘鼠标一般都是经过模拟的方式实现的,经过焦点捕获将模拟的设备跟当前设备创建关联关系,好比你使用Vmware workstation时把鼠标点进哪一个虚拟机后,至关于被此虚拟机捕获了,全部的操做都是针对此虚拟机了。
总结
简单描述了CPU虚拟化、内存虚拟化、IO虚拟化的实现方式。其一,咱们大概知道了如何选择虚拟化主机性能会最大化,CPU支持硬件辅助虚拟化技术,如Intel的VT;内存支持硬件辅助虚拟化技术,如Virtualization mmu和TLB;IO支持硬件辅助虚拟化技术,如Intel的VT-d。固然光有硬件的支持还不是太够,在使用虚拟化时要可以充分利用到这些硬件才行。
Type-I:直接运行在操做系统之上的虚拟化,模式以下图:
如:Vmware workstations、Kvm等。
Type-II:直接运行在硬件之上的(提供各类硬件驱动),模式以下图:
如:Vmware EXSI、Xen等。
可是Xen有点特别,虽然也是直接安装在硬件之上,提供Hypervisor,可是只负责CPU、内存、中断,不提供I/O驱动,须要额外安装一个虚拟机再安装一个Linux系统用来管理I/O设备,以下图:
Type-III:其余类型
固然,除了上面提到的基于操做系统或直接基于硬件的虚拟化外,还有以下常见的类型。
容器虚拟化
基于内核的虚拟化,全部的虚拟机都是一个独立的容器,但共同运行硬件之上,使用着同一个内核。优势就是速度快,部署容易,缺点就是相互间的资源相互隔离比较麻烦,但如今市场也都有了相对成熟的解决方案。如,现在大火的Docker,网上都有人说Docker具备取代虚拟化的势头。
模拟器虚拟化
经过模拟器模拟全部的硬件,如QEMU,KVM就是使用QEMU。
库虚拟化
经过在操做系统之上模拟出不一样系统的库,如Linux上运行Wine就能够支持Windows上的软件运行,Windows上运行Cywin就能够支持Linux上的软件运行。由于如今操做系统都是遵循POSIX标准,因此各自提供的库接口都是同一个标准,只须要在对应的平台上运行一个能够提供对方库的软件,而后在此软件之上运行针对对方系统编译好的软件便可。为何要运行针对对方平台编译好的软件,由于虽然库统一了,可是各自的ABI(应用二进制接口)接口仍是不一样的。
首先咱们知道X86处理器有4个特权级别,Ring 0~Ring 3,只有运行在Ring 0 ~ 2级时,处理器才能够访问特权资源或执行特权指令,运行在Ring 0级时,处理器能够运行全部的特权指令。X86平台上的操做系统通常只使用Ring 0和Ring 3这两个级别,其中,操做系统内核运行在Ring 0级,也被称为内核空间指令,用户进程运行在Ring 3级,也被称为用户空间指令。
特权级压缩(ring compression)
为了知足上面所述的需求,VMM自身必须运行在Ring 0级,同时为了不Guest OS控制系统资源,Guest OS不得不下降自身的运行级别而运行于Ring 3(Ring 一、2 不使用)。
此外,VMM使用分页或段限制的方式保护物理内存的访问,可是64位模式下段限制不起做用,而分页又不区分Ring 0,1,2。为了统一和简化VMM的设计,Guest OS只能和用户进程同样运行在Ring 3。VMM必须监视Guest OS对GDT、IDT等特权资源的设置,防止Guest OS运行在Ring 0级,同时又要保护降级后的Guest OS不受Guest进程的主动攻击或无心破坏。
特权级别名(Ring Alias)
设计上的缘由,操做系统假设本身运行于ring 0,然而虚拟化环境中的Guest OS实际上运行于Ring 1或Ring 3,由此,VMM必须保证各Guest OS不能得知其正运行于虚拟机中这一事实,以避免其打破前面的“等价执行”标准。例如,x86处理器的特权级别存放在CS代码段寄存器内,Guest OS却可使用非特权PUSH指令将CS寄存器压栈,而后POP出来检查该值;又如,Guest OS在低特权级别时读取特权寄存器GDT、LDT、IDT和TR时并不发生异常。这些行为都不一样于Guest OS的正常指望。
地址空间压缩(Address Space Compression)
地址空间压缩是指VMM必须在Guest OS的地址空间中保留一段供本身使用,这是x86虚拟化技术面临的另外一个挑战。VMM能够彻底运行于自有的地址空间,也能够部分地运行于Guest OS的地址空间。前一种方式,需在VMM模式与Guest OS模式之间切换,这会带来较大的开销;此外,尽管运行于本身的地址空间,VMM仍须要在Guest OS的地址空间保留出一部分来保存控制结构,如IDT和GDT。不管是哪种方式,VMM必须保证本身用到地址空间不会受到Guest OS的访问或修改。
非特权敏感指令
x86使用的敏感指令并不彻底隶属于特权指令集,VMM将没法正确捕获此类指令并做出处理。例如,非特权指令SMSW在寄存器中存储的机器状态就可以被Guest OS所读取,这违反了经典虚拟化理论的要求。
静默特权失败(Silent Privilege Failures)
x86的某些特权指令在失败时并不返回错误,所以,其错误将没法被VMM捕获,这将致使其违反经典虚拟化信条中的“等价执行”法则。
中断虚拟化(Interrupt Virtualization)
虚拟化环境中,屏蔽中断及非屏蔽中断的管理都应该由VMM进行;然而,GuestOS对特权资源的每次访问都会触发处理器异常,这必然会频繁屏蔽或启用中断,若是这些请求均由VMM处理,势必会极大影响总体系统性能。