ARTICLE DETAIL

资讯详情

深耕网站SEO优化与搜索引擎排名提升的一线实战洞察。

[virtio](九):virtio 设备迁移状态

[virtio](九):virtio 设备迁移状态 第八篇讨论了 vhost-user。本篇看 virtio 与 live migration迁移一台 VM 时virtio 设备要保存什么状态为什么只复制 guest RAM 不够vhost backend 又如何让迁移变得更复杂1. 迁移为什么涉及 virtioLive migration 不只是复制 guest RAM。一台正在运行的虚拟机还包含设备状态。对于 virtio 设备来说这些状态包括device statusnegotiated featuresconfig spacequeue stateavail/used ring indexpending interruptin-flight requestdevice-specific statebackend state如果这些状态没有正确保存和恢复target 上的 guest driver 可能看到一个不一致的设备。后果可能是I/O 请求丢失I/O 请求重复完成driver 等不到中断queue index 错乱设备被 guest 认为故障文件系统或网络状态异常2. virtio 迁移的目标迁移目标不是让 target 上的设备重新初始化。而是让 guest 觉得设备只是暂停了一小段时间。迁移前Guest driver owns virtqueue state QEMU device model owns device state backend may own in-flight I/O state迁移后Guest driver continues from same queue state Target QEMU restores same device state Target backend resumes compatible data plane所以迁移保存的是 guest 可见语义而不是 source host 的所有内部实现细节。3. virtio common state所有 virtio 设备都有一些 common state。典型包括device status negotiated feature bits queue enable state queue size queue addresses last_avail_idx used_idx or shadow state interrupt status config generation这些状态决定 guest driver 和 device model 对设备进度的共同理解。例如Guest 认为 queue 已经提交到 avail idx 100 QEMU 恢复后却认为只处理到 80这种不一致会导致请求重复处理或卡住。4. device-specific state不同 virtio 设备还有自己的状态。virtio-blk 可能涉及pending block requestswrite cache statedevice configurationrequest throttling stateblock backend relationvirtio-net 可能涉及MAC addresslink statusoffload configurationmultiqueue statecontrol queue statepending packetsRX/TX queue statevirtio-balloon 可能涉及balloon sizereported pagesfree page hinting state这些状态不是 virtio core 能完全理解的需要具体设备自己参与 migration。5. queue state 为什么关键virtqueue 是 guest 和 device 之间的共享进度条。迁移时最关键的是两边对 queue index 的理解必须一致。简化模型Guest avail ring: guest 已提交到哪里 Device last_avail_idx: device 已经消费到哪里 Used ring: device 已经完成到哪里如果 target 恢复后last_avail_idx错了可能出现两种问题太小: 重复处理已经处理过的 descriptor 太大: 跳过还没处理的 descriptor所以 queue state 是迁移状态中的核心。6. in-flight request迁移最难处理的是 in-flight request。所谓 in-flight就是请求已经离开 virtqueue正在 backend 中处理但还没有向 guest 完成。例如Guest submits block write | v QEMU sends request to host storage backend | | migration starts before completion v request is in-flight此时不能简单丢掉请求。也不能在 source 和 target 上重复执行。QEMU 需要让设备进入可迁移状态例如等待请求完成暂停数据面记录 in-flight descriptor与 backend 协调 inflight state在 target 上恢复或重新提交具体策略取决于设备和 backend 能力。7. pending interrupt迁移不能丢中断。比如一个 virtio 请求已经完成used ring 已经写了但 guest 还没处理中断。状态是used ring updated interrupt pending Guest has not handled completion yet如果迁移后 pending interrupt 丢失guest 可能永远不知道请求完成。如果重复注入也可能导致 guest 额外进入 handler但通常 driver 会检查 used ring 状态。因此迁移需要保存和恢复中断 pending 语义。8. vhost 让迁移更复杂基础 QEMU virtio 设备中QEMU 掌握 device model 和 queue 处理状态。使用 vhost 后数据面状态部分在 vhost backend 中。例如 vhost-netQEMU: virtio control plane, migration orchestration vhost backend: vring processing, in-flight packets, eventfds迁移时 QEMU 需要协调 backendstop or pause backend | v collect vring/backend state | v serialize QEMU virtio state | v restore target backend | v resume queues如果 backend 不支持迁移所需状态迁移可能受限或需要特殊处理。9. vhost-user 的迁移挑战vhost-user 比 vhost-kernel 更复杂因为 backend 是独立用户态进程。迁移时需要考虑source backend 如何暂停backend 是否能导出状态target backend 如何启动vhost-user socket 如何重连shared memory 如何重新映射inflight descriptors 如何转移backend feature 是否兼容如果 backend 是 DPDK 应用或用户态交换机还要考虑外部网络状态和连接关系。所以 vhost-user 的高性能来自灵活的数据面但迁移需要更强的协议和工程约束。10. target 上恢复什么Target QEMU 恢复 virtio device 时需要重建的是 guest 可见状态。例如VirtIODevice common state VirtQueue state Device-specific state Backend connection Interrupt routing Eventfd / irqfd setup注意target 不需要复制 source 的所有内部指针或线程状态。它需要恢复的是 guest 继续运行所依赖的协议状态。这和 KVM migration 中通常不迁移 source stage-2 page table 类似。迁移 guest 可见状态target 重建 host 本地实现细节。11. 迁移版本兼容QEMU 迁移还涉及版本兼容。Source 和 target QEMU 可能不是完全相同版本。设备迁移状态需要稳定的格式和兼容策略。可能的问题包括新版本增加了设备字段feature bits 不一致target 不支持 source 使用的 featurebackend 能力不同machine type 兼容性不同这就是为什么生产环境通常要求 source 和 target 使用兼容 machine type、CPU model、设备配置和 QEMU 版本策略。12. 调试迁移问题的方向virtio 迁移问题常见表现迁移后磁盘 I/O hang 迁移后网络中断 迁移后 virtio driver reset device 迁移后 packet loss 增加 迁移后 guest dmesg 出现 virtqueue error 迁移阶段 downtime 异常变长排查方向queue index 是否一致pending interrupt 是否恢复backend 是否正确暂停和恢复in-flight request 是否处理negotiated features 是否一致target 设备配置是否与 source 相同QEMU migration log 是否有设备状态错误13. 源码阅读入口本篇可以看hw/virtio/virtio.chw/virtio/vhost.chw/virtio/vhost-user.chw/block/virtio-blk.chw/net/virtio-net.cmigration/include/migration/阅读问题VirtIODevicecommon state 如何保存queue state 如何进入 migration streamdevice-specific migration fields 在哪里定义virtio-net 保存了哪些额外状态virtio-blk 如何处理 pending requestvhost backend 在迁移前如何暂停target 上如何重新启用 queue 和 eventfd14. 本篇小结virtio 迁移的核心是让 target 上的 guest driver 和 device model 对设备状态保持同一个理解。除了 guest RAM迁移还要保存 virtio common state、queue state、device-specific state、pending interrupt 和 backend/in-flight 状态。使用 vhost 或 vhost-user 后数据面状态不再只在 QEMU 中迁移需要额外协调 backend。可以把本篇压缩成一句话virtio migration 迁移的不是 QEMU 内部实现本身而是 guest 可见的设备协议状态只要 queue、feature、config、completion 和 backend 状态一致guest 才能在 target 上无感继续运行。15. 下一篇预告trace、调试与故障定位下一篇作为本系列收束讨论如何观察 virtio 路径。会讨论QEMU traceguest dmesg 和 sysfseventfd/ioctl 观察vhost 路径确认virtqueue 卡死如何定位迁移后设备异常如何排查下一篇的问题可以写成当 virtio 设备不工作或性能异常时应该从 guest、QEMU、vhost、backend 哪一层开始看
返回列表