diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c index fc46a380f6..9edb4ca4d4 100644 --- a/src/qemu/qemu_capabilities.c +++ b/src/qemu/qemu_capabilities.c @@ -1570,6 +1570,25 @@ virQEMUCapsHostCPUDataClear(virQEMUCapsHostCPUDataPtr cpuData) } +static int +virQEMUCapsSEVInfoCopy(virSEVCapabilityPtr *dst, + virSEVCapabilityPtr src) +{ + VIR_AUTOPTR(virSEVCapability) tmp = NULL; + + if (VIR_ALLOC(tmp) < 0 || + VIR_STRDUP(tmp->pdh, src->pdh) < 0 || + VIR_STRDUP(tmp->cert_chain, src->cert_chain) < 0) + return -1; + + tmp->cbitpos = src->cbitpos; + tmp->reduced_phys_bits = src->reduced_phys_bits; + + VIR_STEAL_PTR(*dst, tmp); + return 0; +} + + virQEMUCapsPtr virQEMUCapsNewCopy(virQEMUCapsPtr qemuCaps) { virQEMUCapsPtr ret = virQEMUCapsNew(); @@ -1632,6 +1651,11 @@ virQEMUCapsPtr virQEMUCapsNewCopy(virQEMUCapsPtr qemuCaps) for (i = 0; i < qemuCaps->ngicCapabilities; i++) ret->gicCapabilities[i] = qemuCaps->gicCapabilities[i]; + if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_SEV_GUEST) && + virQEMUCapsSEVInfoCopy(&ret->sevCapabilities, + qemuCaps->sevCapabilities) < 0) + goto error; + return ret; error: @@ -3344,6 +3368,58 @@ virQEMUCapsCachePrivFree(void *privData) } +static int +virQEMUCapsParseSEVInfo(virQEMUCapsPtr qemuCaps, xmlXPathContextPtr ctxt) +{ + VIR_AUTOPTR(virSEVCapability) sev = NULL; + + if (!virQEMUCapsGet(qemuCaps, QEMU_CAPS_SEV_GUEST)) + return 0; + + if (virXPathBoolean("boolean(./sev)", ctxt) == 0) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("missing SEV platform data in QEMU " + "capabilities cache")); + return -1; + } + + if (VIR_ALLOC(sev) < 0) + return -1; + + if (virXPathUInt("string(./sev/cbitpos)", ctxt, &sev->cbitpos) < 0) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("missing or malformed SEV cbitpos information " + "in QEMU capabilities cache")); + return -1; + } + + if (virXPathUInt("string(./sev/reducedPhysBits)", ctxt, + &sev->reduced_phys_bits) < 0) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("missing or malformed SEV reducedPhysBits information " + "in QEMU capabilities cache")); + return -1; + } + + if (!(sev->pdh = virXPathString("string(./sev/pdh)", ctxt))) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("missing SEV pdh information " + "in QEMU capabilities cache")); + return -1; + } + + if (!(sev->cert_chain = virXPathString("string(./sev/certChain)", ctxt))) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("missing SEV certChain information " + "in QEMU capabilities cache")); + return -1; + } + + VIR_STEAL_PTR(qemuCaps->sevCapabilities, sev); + return 0; +} + + /* * Parsing a doc that looks like * @@ -3592,6 +3668,9 @@ virQEMUCapsLoadCache(virArch hostArch, } VIR_FREE(nodes); + if (virQEMUCapsParseSEVInfo(qemuCaps, ctxt) < 0) + goto cleanup; + virQEMUCapsInitHostCPUModel(qemuCaps, hostArch, VIR_DOMAIN_VIRT_KVM); virQEMUCapsInitHostCPUModel(qemuCaps, hostArch, VIR_DOMAIN_VIRT_QEMU); @@ -3709,6 +3788,24 @@ virQEMUCapsFormatCPUModels(virQEMUCapsPtr qemuCaps, } +static void +virQEMUCapsFormatSEVInfo(virQEMUCapsPtr qemuCaps, virBufferPtr buf) +{ + virSEVCapabilityPtr sev = virQEMUCapsGetSEVCapabilities(qemuCaps); + + virBufferAddLit(buf, "\n"); + virBufferAdjustIndent(buf, 2); + virBufferAsprintf(buf, "%u\n", sev->cbitpos); + virBufferAsprintf(buf, "%u\n", + sev->reduced_phys_bits); + virBufferEscapeString(buf, "%s\n", sev->pdh); + virBufferEscapeString(buf, "%s\n", + sev->cert_chain); + virBufferAdjustIndent(buf, -2); + virBufferAddLit(buf, "\n"); +} + + char * virQEMUCapsFormatCache(virQEMUCapsPtr qemuCaps) { @@ -3790,6 +3887,9 @@ virQEMUCapsFormatCache(virQEMUCapsPtr qemuCaps) emulated ? "yes" : "no"); } + if (qemuCaps->sevCapabilities) + virQEMUCapsFormatSEVInfo(qemuCaps, &buf); + virBufferAdjustIndent(&buf, -2); virBufferAddLit(&buf, "\n"); diff --git a/tests/domaincapsschemadata/qemu_2.12.0.x86_64.xml b/tests/domaincapsschemadata/qemu_2.12.0.x86_64.xml index 7a1be4c093..a8d6a4d629 100644 --- a/tests/domaincapsschemadata/qemu_2.12.0.x86_64.xml +++ b/tests/domaincapsschemadata/qemu_2.12.0.x86_64.xml @@ -142,6 +142,9 @@ - + + 47 + 1 + diff --git a/tests/qemucapabilitiesdata/caps_2.12.0.x86_64.xml b/tests/qemucapabilitiesdata/caps_2.12.0.x86_64.xml index d34d762ca8..d134e5632d 100644 --- a/tests/qemucapabilitiesdata/caps_2.12.0.x86_64.xml +++ b/tests/qemucapabilitiesdata/caps_2.12.0.x86_64.xml @@ -1253,4 +1253,10 @@ + + 47 + 1 + AQAAAAAOAAAAQAAAAAOAAAAQAAAAAOAAAAQAAAAAOAAAAQAAAAAOAAAAQAAAAAOAAA + AQAAAAAOAAAAQAAAAAOAAAAQAAAAAOAAAAQAAAAAOAAAAQAAAAAOAAA +