虚拟化简介
虚拟化是将计算机的各种实体资源(CPU、内存、存储、网络等)进行抽象后呈现出来,即是将一台物理计算机分割成多台计算机,实现在一台计算机上运行多台虚拟机,每台虚拟机可运行不同的操作系统,可包含不同的虚拟硬件,并且它们在相互独立的空间内运行而互不影响。
block-beta
columns 5
block:L:2
columns 4
app1["应用程序"] app2["应用程序"] ... app3["应用程序"]
host1["物理机操作系统"]:4
cpu1["CPU"] mem1["内存"] io1["IO设备"] network1["网络"]
end
blockArrowId<["虚拟化"]>(right):1
block:R:2
columns 4
block:RLL:1
columns 1
app5["应用程序"]
guest1["虚拟机操作系统"]
end
block:RLR:1
columns 1
app6["应用程序"]
guest2["虚拟机操作系统"]
end
block:RR:2
columns 2
app7["应用程序"] app8["应用程序"]
guest3["虚拟机操作系统"]:2
end
hypervisor["虚拟化层"]:4
host2["物理机操作系统"]:4
cpu2["CPU"] mem2["内存"] io2["IO设备"] network2["网络"]
end
在虚拟化软件层次结构中引入了虚拟化层,这个通常称为虚拟机监控器(Virtual Machine Manager,VMM)。虚拟机监控器运行的环境就是物理机,也称为宿主机。虚拟出来的平台通常称为客户机。
虚拟机使用软件的方法重新定义划分计算机资源,有如下优势:
隔离:虽然虚拟机可共享一台物理机,但它们之间完全隔离,它们就是完全不同的物理计算机。
可靠:虚拟服务器独立于硬件进行工作,灾难恢复更容易实现,当一台虚拟服务器故障,可短时间内迁移恢复到另一台虚拟服务器上。
成本:当物理机资源较少时,也可通过虚拟化实现使用更多服务器才能做的事情。
便于管理:通过虚拟机集群管理系统,一个管理员可管理更多服务器。
KVM/QEMU
KVM/QEMU 简介
2008 年,KVM 被 RedHat 收购,成为红帽开源项目的一员。KVM 全称 Kernel-based Virtual Machine,即基于内核的虚拟机,是一个 x86 平台上的全虚拟化解决方案。它是 Linux 内核的一个可加载模块,包括核心虚拟化模块 kvm.ko,以及特定 CPU 的模块 kvm-inet.ko 或 kvm-amd.ko,其实现需要宿主机的 CPU 支持硬件虚拟化 。
KVM 可运行多个虚拟机,无论是未经修改的 Linux 镜像还是 Windows 镜像。每个虚拟机都有私有的虚拟化硬件如:网卡、磁盘、显卡驱动等。
从 Linux 内核版本 2.6.20 开始,KVM 核心组件被包含在 Linux 内核中。从 QEMU 版本 1.3 开始,KVM 用户空间组件被包含其中。
在 x86 平台下 CPU 的硬件虚拟化技术有 Intel 的 VT-X 和 AMD 的 AMD-V。
KVM 的特征请查看官网,传送门
注意 :BIOS 需要开启虚拟化支持,VMware 的虚拟机需要开启虚拟化支持。
Linux 内核加载了 KVM 模块后,就可以使用 KVM 模块实现虚拟机的内存分配、虚拟 CPU 的读写及管理虚拟 CPU 的运行。但是仅有 KVM 模块远远不够,因为用户无法直接控制内核模块,所以还需要一个用户空间的工具。这个用户空间的工具就是开源虚拟化软件 QEMU,使用它来模拟 PC 硬件的用户空间组件、I/O 设备及提供访问外设的途径。
%%{init: {
'theme': 'base',
'themeVariables': {
'background': '#ffffff',
'primaryColor': '#F0F4FF',
'primaryBorderColor': '#4A6CF7',
'primaryTextColor': '#1E293B',
'lineColor': '#94A3B8',
'secondaryColor': '#FEF3C7',
'tertiaryColor': '#F0FDF4',
'fontFamily': 'system-ui, -apple-system, "PingFang SC", sans-serif',
'fontSize': '14px',
'edgeLabelBackground': '#ffffff',
'nodeBorder': '2px'
}
}}%%
block-beta
columns 5
%% ===== 第一行:客户模式 =====
title1["👤 客户模式 (Guest Mode)"]:1
block:group1:4
columns 1
user1["👨💻 用户模式<br><small>用户态进程</small>"]
kernel1["⚙️ 内核模式<br><small>内核态进程</small>"]
end
%% ===== 第二行:Linux 用户模式 =====
title2["🐧 Linux 用户模式"]:1
block:group2:4
columns 1
qemu["📦 QEMU"]
libkvm["🔧 libkvm"]
ioctl["📤 ioctl"]
devkvm["📂 /dev/kvm"]
end
%% ===== 第三行:Linux 内核模式 =====
title3["⚡ Linux 内核模式"]:1
block:group3:4
columns 1
vmm["🖥️ VMM(Linux 内核 KVM Driver)"]
end
%% ===== 样式定义(使用 classDef) =====
classDef titleMode fill:#E3F2FD,stroke:#42A5F5,stroke-width:2px,color:#0D47A1,font-weight:bold,font-size:15px;
classDef titleLinux fill:#FFF3E0,stroke:#FB8C00,stroke-width:2px,color:#E65100,font-weight:bold,font-size:15px;
classDef titleKernel fill:#F3E5F5,stroke:#8E24AA,stroke-width:2px,color:#4A148C,font-weight:bold,font-size:15px;
classDef guestMode fill:#BBDEFB,stroke:#1E88E5,stroke-width:1.5px,color:#0D47A1;
classDef linuxUser fill:#C8E6C9,stroke:#388E3C,stroke-width:1.5px,color:#1B5E20;
classDef linuxKernel fill:#FCE4EC,stroke:#D81B60,stroke-width:2px,stroke-dasharray:4 4,color:#880E4F,font-weight:bold;
classDef vmm fill:#FFE0B2,stroke:#F57C00,stroke-width:2px,color:#E65100,font-weight:bold;
%% ===== 应用样式 =====
class title1 titleMode;
class title2 titleLinux;
class title3 titleKernel;
class user1,kernel1 guestMode;
class qemu,libkvm,ioctl,devkvm linuxUser;
class vmm vmm;
QEMU 利用 KVM 提供的应用程序接口,通过 ioctl 系统调用创建和运行虚拟机。KVM Driver 使得整个 Linux 成为一个虚拟机监控器。并且在原有的 Linux 两种执行模式(内核模式和用户模式)的基础上新增了客户模式,客户模式拥有自己的内核模式和用户模式。
在虚拟机运行下,三种模式的分工如下:
客户模式:执行非 I/O 操作。虚拟机运行在客户模式下。
内核模式:实现到客户模式的切换,处理因为 I/O 或者其他指令所引起的从客户模式退出。KVM Driver 工作在内核模式下。
用户模式:代表客户机执行 I/O 指令。QEMU 运行在用户模式下。
QEMU 与 KVM 的区别与联系
上一节已经明确 KVM 仅仅是一个内核模块,它可以模拟虚拟机的 CPU 和内存,但是我们还需要 I/O 设备,这些 I/O 设备就是通过 QEMU 这个用户空间模拟器来模拟的。QEMU 本身是一套通用开源的机器仿真器和虚拟程序,它有两种使用方式。
全系统仿真(单独使用)
这种方式对宿主机硬件没有要求,也不需要宿主机 CPU 支持虚拟化,QEMU 为虚拟机操作系统模拟整套硬件环境,虚拟机操作系统感觉不到自己运行在模拟的硬件环境中。这种纯软件模拟效率很低,它可模拟出各种硬件设备。
用户空间仿真(配合 KVM 等)
这种方式与内核模块 KVM 配合完成硬件环境的模拟。在 QEMU 1.3 之前,它有一个专门的分支版本 qemu-kvm 作为 KVM 的用户空间程序,qemu-kvm 通过 ioctl 调用 /dev/kvm 这个接口与 KVM 交互,这样 KVM 在内核空间模拟虚拟机 CPU,qemu-kvm 负责模拟虚拟机 I/O 设备。在 QEMU 1.3 以后的版本中,qemu-kvm 分支代码已经合并到 QEMU 的 master 分支中。在编译 QEMU 时开启 --enable-kvm 选项,就能够使 QEMU 支持 KVM。
libvirt
libvirt 简介
通过 QEMU 命令来管理虚拟机非常麻烦,RedHat 发布了一个开源项目 libvirt,它是为了更加方便的管理各种虚拟化引擎而设计的。libvirt 作为中间适配层,让底层虚拟化引擎对上层用户空间的管理工具做到完全透明,因为 libvirt 屏蔽了底层各种虚拟化的细节,为上层管理工具提供了一个统一的接口。
block-beta
columns 6
block1["virsh"]
block2["virt-manager"]
block3["virt-viewer"]
block4["Openstack"]
block5["CloudStack"]
block6["etc."]
space:6
space:2 block7["Libvirt\n(Libvirt API)\n(Libvirt Daemon)"]:2 space:2
space:6
block:group1:1
columns 2
xen["Xen"]:2
space:2
guest1["guest1"] guest2["guest2"]
end
block:group2:1
columns 2
kvmqemu["Kvm/Qemu"]:2
space:2
guest3["guest1"] guest4["guest2"]
end
block:group3:1
columns 2
vmware["VMWare"]:2
space:2
guest5["guest1"] guest6["guest2"]
end
block:group4:1
columns 2
virtualbox["VirtualBox"]:2
space:2
guest7["guest1"] guest8["guest2"]
end
block:group5:1
columns 2
etc["etc."]:2
space:2
guest9["guest1"] guest10["guest2"]
end
block1 --> block7
block2 --> block7
block3 --> block7
block4 --> block7
block5 --> block7
block6 --> block7
block7-->group1
block7-->group2
block7-->group3
block7-->group4
block7-->group5
xen-->guest1
xen-->guest2
kvmqemu-->guest3
kvmqemu-->guest4
vmware-->guest5
vmware-->guest6
virtualbox-->guest7
virtualbox-->guest8
etc-->guest9
etc-->guest10
libvirt 通过相同的方式管理不同的虚拟化引擎,支持虚拟机的创建、启动、关闭、暂停、睡眠、迁移、删除,以及对虚拟机 CPU、内存、磁盘、网卡等多种设备的热添加。libvirt 还支持通过远程连接的方式管理虚拟机。