libvirt/QEMU 驱动 / CPU 亲和性

把可运行 CPU 集合传递给虚拟机线程

libvirt 将 vCPU 允许使用的宿主 CPU 集合表示为位图,并转换为运行时亲和性配置。

v10.10.0调度与资源分配核验 2026-10-08
相关概念

工程问题#

一条绑定规则可能包含多个 CPU;接口需要紧凑传输、检查空集,并区分立即生效与保存为持久配置。

实际实现#

qemuDomainPinVcpuFlags 把 cpumap 转为 virBitmap。运行态对在线 vCPU 设置线程亲和性,若存在 cpuset 控制器则先配置 cpuset;持久态保存 vCPU 的 cpumask,两条路径可由 flags 同时请求。

处理流程#

  1. 把字节数组转换为 CPU 位图
  2. 校验 vCPU 与非空集合
  3. 按 flags 更新运行态或持久配置
  4. 把允许集合传递给对应线程

源码片段#

固定版本 · 原文摘录
src/qemu/qemu_driver.cv10.10.0 · L4402–L4421
查看原文件
4402    if (!(pcpumap = virBitmapNewData(cpumap, maplen)))4403        goto endjob;44044405    if (virBitmapIsAllClear(pcpumap)) {4406        virReportError(VIR_ERR_INVALID_ARG, "%s",4407                       _("Empty cpu list for pinning"));4408        goto endjob;4409    }44104411    if (def &&4412        qemuDomainPinVcpuLive(vm, def, vcpu, driver, pcpumap) < 0)4413        goto endjob;44144415    if (persistentDef) {4416        virBitmapFree(vcpuinfo->cpumask);4417        vcpuinfo->cpumask = g_steal_pointer(&pcpumap);44184419        ret = virDomainDefSave(persistentDef, driver->xmlopt, cfg->configDir);4420        goto endjob;4421    }
qemuDomainPinVcpuFlags

cpumap 从接口字节数组转成 virBitmap,空集合会报错;live 与 persistent 两条路径共用这份集合。运行态交给 qemuDomainPinVcpuLive,持久态接管位图并保存配置,因此该 API 不保证一定立即修改线程亲和性。

收益与取舍#

工程分析

带来的收益

  • 每个 CPU 仅占一个集合成员位
  • 成员判断和集合表达直观

付出的代价

  • 工程分析:空间取决于最大 CPU 编号
  • 集合只表达允许范围,不表达优先级或权重

可比较的选择

CPU 编号列表极稀疏集合可能更省空间,但成员操作与接口转换需要额外处理。

版本与适用范围#

对应 QEMU 驱动的 vCPU pinning;CPU 亲和性不自动保证独占 CPU,也不能替代 NUMA 内存策略。

参考来源#

源码、官方文档与原始论文
01
libvirt · qemuDomainPinVcpuFlags / qemuDomainPinVcpuLive

src/qemu/qemu_driver.c · qemuDomainPinVcpuFlags / qemuDomainPinVcpuLive

源码v10.10.0

相关实现与比较#

2 个相关案例
QEMU·块设备增量备份v9.2.0

QEMU dirty bitmap 为磁盘区间记录是否被写入,使增量备份能够只复制发生变化的范围。

附源码片段 · 存储与数据放置
11 个匹配案例