虚拟机的迁移是指把一台VM上的OS迁移到另外一台VM,两个VM可以run在不同的物理机上。
包括:Offline Migration和Live Migration。这里讲讲比较常用的Live Migration(热迁移)。
在热迁移过程中,Guest OS完全无感,其运行的任务,在快速迁移过后能继续运行。
首先,对于Guest OS从一个VM迁移到其他VM,涉及到对register配置,dirty cache,runtime context等数据的迁移。
如下图Guest OS1从VM1到VM2迁移过程:先由qemu monitor发起live migration,PC1的QEMU进程执行precopy,对源Guest OS的register,dirty cache bitmap,runtime context进行备份,创建传输channel,包括RDMA, tcp socket(网络),unix socket(进程间),exec stdin/stdout(进程间),fd(虚拟文件)等类型。迁移过程中 dirty page bitmap由QEMU copy,send,recv,restore,SRC和DST的QEMU进程间负责交互。
- KVM ram live migration
qemu接收HMP CMD:hmp_migrate, 如下图左上角的调用流程是基于tcp socket的migrate发送过程,创建migation_thread, 在SRC端发起precopy,层层调用到kvm KVG_GET_DIRTY_LOG,进入kernel mode之后,会调用vmx_flush_log_dirty,发生VM_ENTRY进入Guest OS mode,在Guest OS里log sync相关cache dirty page,cpu state等,下一次VM_EXIT会把该dirty log拷贝到user space供qemu 进程进行migration。(这里针对 intel VT-X技术)。
在intel cpu 中支持PML(Page Modification Logging )模块用于记录dirty page。
PML介绍
https://www.intel.com/content/www/us/en/processors/page-modification-logging-vmm-white-paper.htmlVMX dirty loging相关ops如下,位于linux/arch/x86/kvm/vmx/vmx.c
- Device ram live migration
这里提下virtio-net & vhost的live migration中的rx log 迁移
首先,virtio & vhost是一种半虚拟化技术,分为f'ront-end, back-end,Guest OS 安装front-end
driver virtio-net,Host OS 安装back-end driver vhost-net。qemu维护通信channel vring。
如下:
+---------+------+--------+----------+--+
| +------+ +----------+ |
| user | | | | |
| space | | | guest | |
| | | | | |
| | qemu | | +-+------+ |
| | | | | virtio | |
| | | | | driver | |
| +------+ +-+---++---+ |
| | |
| | |
| v |
| |
+-+-----+---+-+----+------+----+--+-----+
| |tap | | vhost-net.ko| | kvm.ko |
| +---^-+ +------+----^-+ +----+---+
| |-------| kernel |-----------| |
+---------------------------------------+
- DIRTY LOG space MMAP & ioeventd init
QEMU的vhost初始化部分层层调用主要完成:用户态log space映射到内核态;设置好VRING_KICK的eventfd,后续可用于QEMU和HOST OS的相互通知,eventfd好处是免除类似ioctl系统调用时用户态和内核态的切换。通过ioctl VHOST_SET_LOG_BASE可配置kernel mode下的logbase,通过ioctl VHOST_SET_VRING_KICK可配置kick eventfd。(kick每次收发package 会发生)。
- rx dirty log记录过程
在上面配置完EVENTFD之后,Guest OS安装的virtio-net(virtio 前端),通过写ioeventfd mem region(也就是预先配置好的memory区域用于ioeventfd映射),发起rx请求,在调用到kernel mode handle_rx_kick,这时候会发生记录vhost_log_write并更新eventfd的region区域。
- dirty log MEMORY REGION标记
由QEMU HMP migration命令发起迁移,在precopy阶段获取到之前 mmap过的LOG_BASE开始的内容,标记为dirty-page,后续在迁移过程中会拷贝该page。