参考
qemu的详细资料大全(入门必看!!!)
understanding qemu
QEMU 用户模式(User Mode)流程及源码分析 (一)
QEMU/KVM原理概述
2. 详解 QEMU 架构
KVM虚拟机代码揭秘——QEMU代码结构分析
qemu源码架构
Kernelgo’s KVM学习笔记
介绍
QEMU是一个类似于bochs或vmware的开源虚拟机项目,基于C/C++,主要对嵌入式开发中常用的一些处理器进行模拟,如arm、riscv等。
QEMU支持两种操作模式:
- 全系统仿真模式:在这种模式下,QEMU完整的仿真目标平台,相当于一台完整的主机,包括一个或多个处理器以及各种外围设备。此种模式可以用来运行不同的操作系统或用于调试操作系统的代码。
- 用户态仿真模式:在这种模式下,QEMU可以看作是其他架构指令代码的即时编译执行器,适合于guest机架构的代码通过系统调用的方式,使用host机的内核,并和host机使用相同的资源。
QEMU与KVM
在全系统仿真模式下,QEMU必须在Linux系统上运行,并借助KVM或XEN,利用intel或amd提供的硬件辅助虚拟化技术,使虚拟出来的机器达到接近真机的性能。
关系
QEMU与KVM的关系如图:
在物理机启动时,KVM创建/dev/kvm
设备文件。当QEMU创建虚拟机时,KVM为该虚拟机进程创建一个VM的文件描述符,当创建vCPU时,KVM为每个vCPU创建一个文件描述符,同时向用户空间提供了一系列针对特殊设备文件的ioctl系统调用。
架构
详细的架构如下:
VMX root:CPU在运行宿主机内核和宿主机上的普通进程时所处的模式。
VMX non root:CPU在运行虚拟机中的操作系统代码和用户程序时所处的模式。
QEMU的任务(图中左上)
- QEMU运行在宿主机的用户空间中。
- 创建模拟芯片组
- 创建CPU线程来表示虚拟机的CPI执行流
- 在QEMU的虚拟地址空间中分配空间作为虚拟机的物理地址
- 根据用户在命令行指定的设备为虚拟机创建对应的虚拟设备
- 在主线程中监听多种事件,如虚拟机对设备的I/O访问、虚拟设备对应宿主机上的一些I/O事件等。
虚拟机的运行(图中右上)
- 虚拟机中的一个CPU对应宿主机的一个线程,通过QEMU与KVM的合作,这些线程可直接被宿主机的操作系统调度并执行。
- 虚拟机的物理内存对应于QEMU中的虚拟内存,地址转换过程为:虚拟机的虚拟地址 -> 虚拟机的物理地址 -> (通过KVM页表)-> 宿主机物理地址。
- 虚拟机的设备通过QEMU呈现,虚拟机的操作系统启动时进行设备枚举、加载驱动。
- 虚拟机与宿主机的交互通过I/O端口或MMIO(Memory Mapped I/O)进行,交互请求由KVM截获后,分发到宿主机的QEMU进程进行处理。
KVM驱动(图中下部)
- KVM运行在宿主机的内核空间中。
- KVM通过
/dev/kvm
设备导出了一系列接口,QEMU可以通过这些接口来配置虚拟机的参数,如CPU个数、内存布局等。 - KVM需要截获虚拟机产生的虚拟机退出(VM Exit)事件进行处理。
QEMU架构
- Hypervisor(虚拟机管理程序):是一种负责创建和运行虚拟机的虚拟机监视程器,它从磁盘映像加载虚拟机的二进制机器代码,使用微代码生成器TCG将其转换为宿主机的代码,连接到虚拟或实际设备,并启动软件MMU。在集成了KVM的QEMU版本中,用KVM的Hypervisor替代了QEMU原生的Hypervisor。
- TCG(微代码生成器):QEMU将适合虚拟机架构的指令先翻译为TCG中间代码,再将中间代码翻译为宿主机架构的指令。具体来说,先把每一条虚拟机架构上的指令切分为若干条微操作,每条微操作采用一段简单的C代码来实现,运行时通过TCG,把微操作组合成一个函数加以执行,就相当于在宿主机上执行了虚拟机架构的指令。
- MMU:软件内存管理单元:处理对计算机存储地址的访问。当处理器想要访问某个地址(可以是Cache / RAM / 光盘等)时,由MMU获取该地址处的内容。
- 硬件设备:在QEMU中有两种使用设备的方式,一种是直通模式,虚拟机直接使用实际的物理设备;另一种是仿真模式,虚拟机使用由QEMU的设备驱动仿真实现的模拟设备。
- 磁盘映像:QEMU可以处理数种不同的磁盘映像格式,首选为raw或qcon2。QEMU的存储协议栈如下图,三种颜色分别代表虚拟机、QEMU、宿主机。虚拟机通过仿真硬件与QEMU交互,并将I/O执行情况的控制流和数据流交互给QEMU,再由QEMU代表虚拟机,向宿主机发起I/O请求。