From: Daniel Henrique Barboza Date: Wed, 10 Jun 2020 18:11:48 +0000 (-0300) Subject: qemu: add validations after TPM Proxy model introduction X-Git-Tag: v6.5.0-rc1~55 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=0f7e8649c787ec56f2fbcbeaebe42314ae7a8d8d;p=thirdparty%2Flibvirt.git qemu: add validations after TPM Proxy model introduction Previous patch handled the conversion of def->tpm to the array def->tpms and the XML parsing logic. This patch handles the validations needed to ensure the intended behavior. The existing qemuValidateDomainDeviceDefTPM() function was updated to guarantee that the VIR_DOMAIN_TPM_MODEL_SPAPR_PROXY model is exclusive to PPC64 guests and to the VIR_DOMAIN_TPM_TYPE_PASSTHROUGH backend. A new function called qemuDomainDefTPMsPostParse() was added to guarantee that the following combinations in the same domain are valid: - a single TPM device - a single TPM Proxy device - a single TPM + single TPM Proxy devices And these combinations in the same domain are NOT valid: - 2 or more TPM devices - 2 or more TPM Proxy devices Tested-by: Satheesh Rajendran Reviewed-by: Stefan Berger Signed-off-by: Daniel Henrique Barboza Reviewed-by: Ján Tomko Signed-off-by: Ján Tomko --- diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c index b2f0d4afda..8b2447482d 100644 --- a/src/qemu/qemu_domain.c +++ b/src/qemu/qemu_domain.c @@ -4985,6 +4985,40 @@ qemuDomainDefNumaCPUsPostParse(virDomainDefPtr def, } +static int +qemuDomainDefTPMsPostParse(virDomainDefPtr def) +{ + virDomainTPMDefPtr proxyTPM = NULL; + virDomainTPMDefPtr regularTPM = NULL; + size_t i; + + if (def->ntpms < 2) + return 0; + + for (i = 0; i < def->ntpms; i++) { + virDomainTPMDefPtr tpm = def->tpms[i]; + + if (tpm->model == VIR_DOMAIN_TPM_MODEL_SPAPR_PROXY) { + if (proxyTPM) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("only a single TPM Proxy device is supported")); + return -1; + } else { + proxyTPM = tpm; + } + } else if (regularTPM) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("only a single TPM non-proxy device is supported")); + return -1; + } else { + regularTPM = tpm; + } + } + + return 0; +} + + static int qemuDomainDefPostParseBasic(virDomainDefPtr def, void *opaque G_GNUC_UNUSED) @@ -5074,6 +5108,9 @@ qemuDomainDefPostParse(virDomainDefPtr def, if (qemuDomainDefNumaCPUsPostParse(def, qemuCaps) < 0) return -1; + if (qemuDomainDefTPMsPostParse(def) < 0) + return -1; + return 0; } diff --git a/src/qemu/qemu_validate.c b/src/qemu/qemu_validate.c index c5ca3a872f..5082a29dc7 100644 --- a/src/qemu/qemu_validate.c +++ b/src/qemu/qemu_validate.c @@ -3655,6 +3655,25 @@ qemuValidateDomainDeviceDefTPM(virDomainTPMDef *tpm, case VIR_DOMAIN_TPM_MODEL_SPAPR: flag = QEMU_CAPS_DEVICE_TPM_SPAPR; break; + case VIR_DOMAIN_TPM_MODEL_SPAPR_PROXY: + if (!ARCH_IS_PPC64(def->os.arch)) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("TPM Proxy model %s is only available for " + "PPC64 guests"), + virDomainTPMModelTypeToString(tpm->model)); + return -1; + } + + /* TPM Proxy devices have 'passthrough' backend */ + if (tpm->type != VIR_DOMAIN_TPM_TYPE_PASSTHROUGH) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("TPM Proxy model %s requires " + "'Passthrough' backend"), + virDomainTPMModelTypeToString(tpm->model)); + } + + flag = QEMU_CAPS_DEVICE_SPAPR_TPM_PROXY; + break; case VIR_DOMAIN_TPM_MODEL_LAST: default: virReportEnumRangeError(virDomainTPMModel, tpm->model);