They require special handling since they are dependent on the basic tlbflush feature itself and therefore are not handled automatically as part of virDomainHyperv enum, just like the stimer-direct feature. Resolves: https://issues.redhat.com/browse/RHEL-7122 Signed-off-by: Martin Kletzander <mkletzan@xxxxxxxxxx> --- src/qemu/qemu_command.c | 6 +++++ src/qemu/qemu_process.c | 24 +++++++++++++++++++ .../qemuxmlconfdata/hyperv.x86_64-latest.args | 2 +- tests/qemuxmlconfdata/hyperv.xml | 5 +++- 4 files changed, 35 insertions(+), 2 deletions(-) diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index dcb9c4934ec6..1f28de619432 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -6350,6 +6350,12 @@ qemuBuildCpuCommandLine(virCommand *cmd, if ((i == VIR_DOMAIN_HYPERV_STIMER) && (def->hyperv_stimer_direct == VIR_TRISTATE_SWITCH_ON)) virBufferAsprintf(&buf, ",%s=on", VIR_CPU_x86_HV_STIMER_DIRECT); + if (i == VIR_DOMAIN_HYPERV_TLBFLUSH) { + if (def->hyperv_tlbflush_direct == VIR_TRISTATE_SWITCH_ON) + virBufferAsprintf(&buf, ",%s=on", VIR_CPU_x86_HV_TLBFLUSH_DIRECT); + if (def->hyperv_tlbflush_extended == VIR_TRISTATE_SWITCH_ON) + virBufferAsprintf(&buf, ",%s=on", VIR_CPU_x86_HV_TLBFLUSH_EXT); + } break; case VIR_DOMAIN_HYPERV_SPINLOCKS: diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c index ba581cf05af9..ea8da5828cb7 100644 --- a/src/qemu/qemu_process.c +++ b/src/qemu/qemu_process.c @@ -4281,6 +4281,30 @@ qemuProcessVerifyHypervFeatures(virDomainDef *def, "direct"); return -1; } + if (i == VIR_DOMAIN_HYPERV_TLBFLUSH) { + if (def->hyperv_tlbflush_direct == VIR_TRISTATE_SWITCH_ON) { + rc = virCPUDataCheckFeature(cpu, VIR_CPU_x86_HV_TLBFLUSH_DIRECT); + if (rc < 0) + return -1; + if (rc == 0) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("host doesn't support hyperv tlbflush '%1$s' feature"), + "direct"); + return -1; + } + } + if (def->hyperv_tlbflush_extended == VIR_TRISTATE_SWITCH_ON) { + rc = virCPUDataCheckFeature(cpu, VIR_CPU_x86_HV_TLBFLUSH_EXT); + if (rc < 0) + return -1; + if (rc == 0) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("host doesn't support hyperv tlbflush '%1$s' feature"), + "extended"); + return -1; + } + } + } continue; } diff --git a/tests/qemuxmlconfdata/hyperv.x86_64-latest.args b/tests/qemuxmlconfdata/hyperv.x86_64-latest.args index 2aafafb340a6..5a32b80e717f 100644 --- a/tests/qemuxmlconfdata/hyperv.x86_64-latest.args +++ b/tests/qemuxmlconfdata/hyperv.x86_64-latest.args @@ -12,7 +12,7 @@ XDG_CONFIG_HOME=/var/lib/libvirt/qemu/domain--1-QEMUGuest1/.config \ -object '{"qom-type":"secret","id":"masterKey0","format":"raw","file":"/var/lib/libvirt/qemu/domain--1-QEMUGuest1/master-key.aes"}' \ -machine pc,usb=off,dump-guest-core=off,memory-backend=pc.ram,acpi=on \ -accel tcg \ --cpu 'qemu64,hv-relaxed=on,hv-vapic=on,hv-spinlocks=0x2fff,hv-vpindex=on,hv-runtime=on,hv-synic=on,hv-stimer=on,hv-reset=on,hv-vendor-id=KVM Hv,hv-frequencies=on,hv-reenlightenment=on,hv-tlbflush=on,hv-ipi=on,hv-evmcs=on,hv-avic=on,hv-emsr-bitmap=on,hv-xmm-input=on' \ +-cpu 'qemu64,hv-relaxed=on,hv-vapic=on,hv-spinlocks=0x2fff,hv-vpindex=on,hv-runtime=on,hv-synic=on,hv-stimer=on,hv-reset=on,hv-vendor-id=KVM Hv,hv-frequencies=on,hv-reenlightenment=on,hv-tlbflush=on,hv-tlbflush-direct=on,hv-tlbflush-ext=on,hv-ipi=on,hv-evmcs=on,hv-avic=on,hv-emsr-bitmap=on,hv-xmm-input=on' \ -m size=219136k \ -object '{"qom-type":"memory-backend-ram","id":"pc.ram","size":224395264}' \ -overcommit mem-lock=off \ diff --git a/tests/qemuxmlconfdata/hyperv.xml b/tests/qemuxmlconfdata/hyperv.xml index a1e3cbbdf842..8c323f657851 100644 --- a/tests/qemuxmlconfdata/hyperv.xml +++ b/tests/qemuxmlconfdata/hyperv.xml @@ -22,7 +22,10 @@ <vendor_id state='on' value='KVM Hv'/> <frequencies state='on'/> <reenlightenment state='on'/> - <tlbflush state='on'/> + <tlbflush state='on'> + <direct state='on'/> + <extended state='on'/> + </tlbflush> <ipi state='on'/> <evmcs state='on'/> <avic state='on'/> -- 2.47.1