session blob defined in the SEV API spec. See SEV spec LAUNCH_START section
for the session blob format.
+
+Some modern AMD processors support Secure Encrypted Virtualization with Secure
+Nested Paging enhancement, also known as SEV-SNP. :since:`Since 10.5.0` To
+enable it ``<launchSecurity type='sev-snp'>`` should be used. It shares some
+attributes and elements with ``type='sev'`` but differs in others. Example configuration:
+
+::
+
+ <domain>
+ ...
+ <launchSecurity type='sev-snp' authorKey='yes' vcek='no'>
+ <cbitpos>47</cbitpos>
+ <reducedPhysBits>1</reducedPhysBits>
+ <policy>0x00030000</policy>
+ <guestVisibleWorkarounds>...</guestVisibleWorkarounds>
+ <idBlock>...</idBlock>
+ <idAuth>...</idAuth>
+ <hostData>.../hostData>
+ </launchSecurity>
+ ...
+ </domain>
+
+The ``<launchSecurity/>`` element accepts the following attributes:
+
+``kernelHashes``
+ The optional ``kernelHashes`` attribute indicates whether the
+ hashes of the kernel, ramdisk and command line should be included
+ in the measurement done by the firmware. This is only valid if
+ using direct kernel boot.
+
+``authorKey``
+ The optional ``authorKey`` attribute indicates whether ``<idAuth/>`` element
+ contains the 'AUTHOR_KEY' field defined SEV-SNP firmware ABI.
+
+``vcek``
+ The optional ``vcek`` attribute indicates whether the guest is allowed to
+ chose between VLEK (Versioned Loaded Endorsement Key) or VCEK (Versioned
+ Chip Endorsement Key) when requesting attestation reports from firmware.
+ Set this to ``no`` to disable the use of VCEK.
+
+Aforementioned SEV-SNP firmware ABI can be found here:
+`<https://www.amd.com/system/files/TechDocs/56860.pdf>`__
+
+The ``<launchSecurity/>`` element then accepts the following child elements:
+
+``cbitpos``
+ The required ``cbitpos`` element provides the C-bit (aka encryption bit)
+ location in guest page table entry. The value of ``cbitpos`` is hypervisor
+ dependent and can be obtained through the ``sev`` element from the domain
+ capabilities.
+``reducedPhysBits``
+ The required ``reducedPhysBits`` element provides the physical address bit
+ reduction. Similar to ``cbitpos`` the value of ``reduced-phys-bit`` is
+ hypervisor dependent and can be obtained through the ``sev`` element from the
+ domain capabilities.
+``policy``
+ The required ``policy`` element provides the guest policy which must be
+ maintained by the SEV-SNP firmware. This policy is enforced by the firmware
+ and restricts what configuration and operational commands can be performed
+ on this guest by the hypervisor. The guest policy provided during guest
+ launch is bound to the guest and cannot be changed throughout the lifetime
+ of the guest. The policy is also transmitted during snapshot and migration
+ flows and enforced on the destination platform. The guest policy is a 64bit
+ unsigned number with the fields shown in table (See section `4.3 Guest
+ Policy` in aforementioned firmware ABI specification):
+
+ ====== =========================================================================================
+ Bit(s) Description
+ ====== =========================================================================================
+ 63:25 Reserved. Must be zero.
+ 24 Ciphertext hiding must be enabled when set, otherwise may be enabled or disabled.
+ 23 Running Average Power Limit (RAPL) must be disabled when set.
+ 22 Require AES 256 XTS for memory encryption when set, otherwise AES 128 XEX may be allowed.
+ 21 CXL can be populated with devices or memory when set.
+ 20 Guest can be activated only on one socket when set.
+ 19 Debugging is allowed when set.
+ 18 Association with a migration agent is allowed when set.
+ 17 Reserved. Must be set.
+ 16 SMT is allowed.
+ 15:8 The minimum ABI major version required for this guest to run.
+ 7:0 The minimum ABI minor version required for this guest to run.
+ ====== =========================================================================================
+
+ The default value is hypervisor dependant and QEMU defaults to value 0x30000
+ meaning no minimum ABI major/minor version is required and SMT is allowed.
+
+``guestVisibleWorkarounds``
+ The optional ``guestVisibleWorkarounds`` element is a 16-byte,
+ base64-encoded blob to report hypervisor-defined workarounds, corresponding
+ to the 'GOSVW' parameter of the SNP_LAUNCH_START command defined in the
+ SEV-SNP firmware ABI.
+
+``idBlock``
+ The optional ``idBlock`` element is a 96-byte, base64-encoded blob to
+ provide the 'ID Block' structure for the SNP_LAUNCH_FINISH command defined
+ in the SEV-SNP firmware ABI.
+
+``idAuth``
+ The optional ``idAuth`` element is a 4096-byte, base64-encoded blob to
+ provide the 'ID Authentication Information Structure' for the
+ SNP_LAUNCH_FINISH command defined in the SEV-SNP firmware ABI.
+
+``hostData``
+ The optional ``hostData`` element is a 32-byte, base64-encoded, user-defined
+ blob to provide to the guest, as documented for the 'HOST_DATA' parameter of
+ the SNP_LAUNCH_FINISH command in the SEV-SNP firmware ABI.
+
+
Example configs
===============
VIR_DOMAIN_LAUNCH_SECURITY_LAST,
"",
"sev",
+ "sev-snp",
"s390-pv",
);
g_free(def->data.sev.dh_cert);
g_free(def->data.sev.session);
break;
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ g_free(def->data.sev_snp.guest_visible_workarounds);
+ g_free(def->data.sev_snp.id_block);
+ g_free(def->data.sev_snp.id_auth);
+ g_free(def->data.sev_snp.host_data);
+ break;
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
case VIR_DOMAIN_LAUNCH_SECURITY_NONE:
case VIR_DOMAIN_LAUNCH_SECURITY_LAST:
}
+static int
+virDomainSEVSNPDefParseXML(virDomainSEVSNPDef *def,
+ xmlXPathContextPtr ctxt)
+{
+ if (virDomainSEVCommonDefParseXML(&def->common, ctxt) < 0)
+ return -1;
+
+ if (virXMLPropTristateBool(ctxt->node, "authorKey", VIR_XML_PROP_NONE,
+ &def->author_key) < 0)
+ return -1;
+
+ if (virXMLPropTristateBool(ctxt->node, "vcek", VIR_XML_PROP_NONE,
+ &def->vcek) < 0)
+ return -1;
+
+ if (virXPathULongLongBase("string(./policy)", ctxt, 16, &def->policy) < 0) {
+ virReportError(VIR_ERR_XML_ERROR, "%s",
+ _("failed to get launch security policy"));
+ return -1;
+ }
+
+ def->guest_visible_workarounds = virXPathString("string(./guestVisibleWorkarounds)", ctxt);
+ def->id_block = virXPathString("string(./idBlock)", ctxt);
+ def->id_auth = virXPathString("string(./idAuth)", ctxt);
+ def->host_data = virXPathString("string(./hostData)", ctxt);
+
+ return 0;
+}
+
+
static virDomainSecDef *
virDomainSecDefParseXML(xmlNodePtr lsecNode,
xmlXPathContextPtr ctxt)
if (virDomainSEVDefParseXML(&sec->data.sev, ctxt) < 0)
return NULL;
break;
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ if (virDomainSEVSNPDefParseXML(&sec->data.sev_snp, ctxt) < 0)
+ return NULL;
+ break;
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
break;
case VIR_DOMAIN_LAUNCH_SECURITY_NONE:
}
+static void
+virDomainSEVSNPDefFormat(virBuffer *attrBuf,
+ virBuffer *childBuf,
+ virDomainSEVSNPDef *def)
+{
+ virDomainSEVCommonDefFormat(attrBuf, childBuf, &def->common);
+
+ if (def->author_key != VIR_TRISTATE_BOOL_ABSENT) {
+ virBufferAsprintf(attrBuf, " authorKey='%s'",
+ virTristateBoolTypeToString(def->author_key));
+ }
+
+ if (def->vcek != VIR_TRISTATE_BOOL_ABSENT) {
+ virBufferAsprintf(attrBuf, " vcek='%s'",
+ virTristateBoolTypeToString(def->vcek));
+ }
+
+ virBufferAsprintf(childBuf, "<policy>0x%08llx</policy>\n", def->policy);
+
+ virBufferEscapeString(childBuf,
+ "<guestVisibleWorkarounds>%s</guestVisibleWorkarounds>\n",
+ def->guest_visible_workarounds);
+ virBufferEscapeString(childBuf, "<idBlock>%s</idBlock>\n", def->id_block);
+ virBufferEscapeString(childBuf, "<idAuth>%s</idAuth>\n", def->id_auth);
+ virBufferEscapeString(childBuf, "<hostData>%s</hostData>\n", def->host_data);
+}
+
+
static void
virDomainSecDefFormat(virBuffer *buf, virDomainSecDef *sec)
{
virDomainSEVDefFormat(&attrBuf, &childBuf, &sec->data.sev);
break;
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ virDomainSEVSNPDefFormat(&attrBuf, &childBuf, &sec->data.sev_snp);
+ break;
+
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
break;
typedef enum {
VIR_DOMAIN_LAUNCH_SECURITY_NONE,
VIR_DOMAIN_LAUNCH_SECURITY_SEV,
+ VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP,
VIR_DOMAIN_LAUNCH_SECURITY_PV,
VIR_DOMAIN_LAUNCH_SECURITY_LAST,
unsigned int policy;
};
+
+struct _virDomainSEVSNPDef {
+ virDomainSEVCommonDef common;
+ unsigned long long policy;
+ char *guest_visible_workarounds;
+ char *id_block;
+ char *id_auth;
+ char *host_data;
+ virTristateBool author_key;
+ virTristateBool vcek;
+};
+
+
struct _virDomainSecDef {
virDomainLaunchSecurity sectype;
union {
virDomainSEVDef sev;
+ virDomainSEVSNPDef sev_snp;
} data;
};
}
+#define CHECK_BASE64_LEN(val, elemName, exp_len) \
+{ \
+ size_t len; \
+ g_autofree unsigned char *tmp = NULL; \
+ if (val && (tmp = g_base64_decode(val, &len)) && len != exp_len) { \
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, \
+ _("Unexpected length of '%1$s', expected %2$u got %3$zu"), \
+ elemName, exp_len, len); \
+ return -1; \
+ } \
+}
+
+static int
+virDomainDefLaunchSecurityValidate(const virDomainDef *def)
+{
+ virDomainSEVSNPDef *sev_snp;
+
+ if (!def->sec)
+ return 0;
+
+ switch (def->sec->sectype) {
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ sev_snp = &def->sec->data.sev_snp;
+
+ CHECK_BASE64_LEN(sev_snp->guest_visible_workarounds, "guestVisibleWorkarounds", 16);
+ CHECK_BASE64_LEN(sev_snp->id_block, "idBlock", 96);
+ CHECK_BASE64_LEN(sev_snp->id_auth, "idAuth", 4096);
+ CHECK_BASE64_LEN(sev_snp->host_data, "hostData", 32);
+ break;
+
+ case VIR_DOMAIN_LAUNCH_SECURITY_NONE:
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_PV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_LAST:
+ }
+
+ return 0;
+}
+
+#undef CHECK_BASE64_LEN
+
static int
virDomainDefValidateInternal(const virDomainDef *def,
virDomainXMLOption *xmlopt)
if (virDomainDefValidateIOThreads(def) < 0)
return -1;
+ if (virDomainDefLaunchSecurityValidate(def) < 0)
+ return -1;
+
return 0;
}
<group>
<ref name="launchSecuritySEV"/>
</group>
+ <group>
+ <ref name="launchSecuritySEVSNP"/>
+ </group>
<group>
<attribute name="type">
<value>s390-pv</value>
</interleave>
</define>
+ <define name="launchSecuritySEVSNP">
+ <attribute name="type">
+ <value>sev-snp</value>
+ </attribute>
+ <optional>
+ <attribute name="kernelHashes">
+ <ref name="virYesNo"/>
+ </attribute>
+ </optional>
+ <optional>
+ <attribute name="authorKey">
+ <ref name="virYesNo"/>
+ </attribute>
+ </optional>
+ <optional>
+ <attribute name="vcek">
+ <ref name="virYesNo"/>
+ </attribute>
+ </optional>
+ <interleave>
+ <ref name="launchSecuritySEVCommon"/>
+ <element name="policy">
+ <ref name="hexuint"/>
+ </element>
+ <optional>
+ <element name="guestVisibleWorkarounds">
+ <data type="string"/>
+ </element>
+ </optional>
+ <optional>
+ <element name="idBlock">
+ <data type="string"/>
+ </element>
+ </optional>
+ <optional>
+ <element name="idAuth">
+ <data type="string"/>
+ </element>
+ </optional>
+ <optional>
+ <element name="hostData">
+ <data type="string"/>
+ </element>
+ </optional>
+ </interleave>
+ </define>
<!--
Enable or disable perf events for the domain. For each
of the events the following rules apply:
typedef struct _virDomainSEVDef virDomainSEVDef;
+typedef struct _virDomainSEVSNPDef virDomainSEVSNPDef;
+
typedef struct _virDomainSecDef virDomainSecDef;
typedef struct _virDomainShmemDef virDomainShmemDef;
if (vm->def->sec) {
switch (vm->def->sec->sectype) {
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
if (qemuSetupSEVCgroup(vm) < 0)
return -1;
break;
virBufferAddLit(&buf, ",memory-encryption=lsec0");
}
break;
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ break;
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
virBufferAddLit(&buf, ",confidential-guest-support=lsec0");
break;
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
return qemuBuildSEVCommandLine(vm, cmd, &sec->data.sev);
break;
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ break;
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
return qemuBuildPVCommandLine(vm, cmd);
break;
switch (vm->def->sec->sectype) {
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
if (qemuDomainGetSEVInfo(vm, params, nparams, flags) < 0)
goto cleanup;
break;
return false;
}
break;
+
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ break;
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
break;
case VIR_DOMAIN_LAUNCH_SECURITY_NONE:
switch (sec->sectype) {
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
VIR_DEBUG("Setting up launch security for SEV");
*paths = g_slist_prepend(*paths, g_strdup(QEMU_DEV_SEV));
if (vm->def->sec) {
switch (vm->def->sec->sectype) {
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
VIR_DEBUG("Updating SEV platform info");
if (qemuProcessUpdateSEVInfo(vm) < 0)
return -1;
switch (sec->sectype) {
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
return qemuProcessPrepareSEVGuestInput(vm);
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ break;
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
return 0;
case VIR_DOMAIN_LAUNCH_SECURITY_NONE:
return -1;
}
break;
+
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
+ if (!virQEMUCapsGet(qemuCaps, QEMU_CAPS_SEV_SNP_GUEST)) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("SEV SNP launch security is not supported with this QEMU binary"));
+ return -1;
+ }
+ break;
+
case VIR_DOMAIN_LAUNCH_SECURITY_PV:
if (!virQEMUCapsGet(qemuCaps, QEMU_CAPS_MACHINE_CONFIDENTAL_GUEST_SUPPORT) ||
!virQEMUCapsGet(qemuCaps, QEMU_CAPS_S390_PV_GUEST)) {
if (def->sec) {
switch (def->sec->sectype) {
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
if (virSecurityDACRestoreSEVLabel(mgr, def) < 0)
rc = -1;
break;
if (def->sec) {
switch (def->sec->sectype) {
case VIR_DOMAIN_LAUNCH_SECURITY_SEV:
+ case VIR_DOMAIN_LAUNCH_SECURITY_SEV_SNP:
if (virSecurityDACSetSEVLabel(mgr, def) < 0)
return -1;
break;
--- /dev/null
+LC_ALL=C \
+PATH=/bin \
+HOME=/var/lib/libvirt/qemu/domain--1-QEMUGuest1 \
+USER=test \
+LOGNAME=test \
+XDG_DATA_HOME=/var/lib/libvirt/qemu/domain--1-QEMUGuest1/.local/share \
+XDG_CACHE_HOME=/var/lib/libvirt/qemu/domain--1-QEMUGuest1/.cache \
+XDG_CONFIG_HOME=/var/lib/libvirt/qemu/domain--1-QEMUGuest1/.config \
+/usr/bin/qemu-system-x86_64 \
+-name guest=QEMUGuest1,debug-threads=on \
+-S \
+-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=off \
+-accel kvm \
+-cpu qemu64 \
+-m size=219136k \
+-object '{"qom-type":"memory-backend-ram","id":"pc.ram","size":224395264}' \
+-overcommit mem-lock=off \
+-smp 1,sockets=1,cores=1,threads=1 \
+-uuid c7a5fdbd-edaf-9455-926a-d65c16db1809 \
+-display none \
+-no-user-config \
+-nodefaults \
+-chardev socket,id=charmonitor,fd=1729,server=on,wait=off \
+-mon chardev=charmonitor,id=monitor,mode=control \
+-rtc base=utc \
+-no-shutdown \
+-boot strict=on \
+-device '{"driver":"piix3-usb-uhci","id":"usb","bus":"pci.0","addr":"0x1.0x2"}' \
+-blockdev '{"driver":"host_device","filename":"/dev/HostVG/QEMUGuest1","node-name":"libvirt-1-storage","read-only":false}' \
+-device '{"driver":"ide-hd","bus":"ide.0","unit":0,"drive":"libvirt-1-storage","id":"ide0-0-0","bootindex":1}' \
+-audiodev '{"id":"audio1","driver":"none"}' \
+-sandbox on,obsolete=deny,elevateprivileges=deny,spawn=deny,resourcecontrol=deny \
+-msg timestamp=on
--- /dev/null
+launch-security-sev-snp.xml
\ No newline at end of file
--- /dev/null
+<domain type='kvm'>
+ <name>QEMUGuest1</name>
+ <uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
+ <memory unit='KiB'>219100</memory>
+ <currentMemory unit='KiB'>219100</currentMemory>
+ <vcpu placement='static'>1</vcpu>
+ <os>
+ <type arch='x86_64' machine='pc'>hvm</type>
+ <boot dev='hd'/>
+ </os>
+ <cpu mode='custom' match='exact' check='none'>
+ <model fallback='forbid'>qemu64</model>
+ </cpu>
+ <clock offset='utc'/>
+ <on_poweroff>destroy</on_poweroff>
+ <on_reboot>restart</on_reboot>
+ <on_crash>destroy</on_crash>
+ <devices>
+ <emulator>/usr/bin/qemu-system-x86_64</emulator>
+ <disk type='block' device='disk'>
+ <driver name='qemu' type='raw'/>
+ <source dev='/dev/HostVG/QEMUGuest1'/>
+ <target dev='hda' bus='ide'/>
+ <address type='drive' controller='0' bus='0' target='0' unit='0'/>
+ </disk>
+ <controller type='usb' index='0' model='piix3-uhci'>
+ <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x2'/>
+ </controller>
+ <controller type='ide' index='0'>
+ <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x1'/>
+ </controller>
+ <controller type='pci' index='0' model='pci-root'/>
+ <input type='mouse' bus='ps2'/>
+ <input type='keyboard' bus='ps2'/>
+ <audio id='1' type='none'/>
+ <memballoon model='none'/>
+ </devices>
+ <launchSecurity type='sev-snp' authorKey='yes' vcek='no'>
+ <cbitpos>47</cbitpos>
+ <reducedPhysBits>1</reducedPhysBits>
+ <policy>0x00030000</policy>
+ <guestVisibleWorkarounds>bGlidmlydGxpYnZpcnRsaQ==</guestVisibleWorkarounds>
+ <idBlock>bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZp</idBlock>
+ <idAuth>bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnZpcnRsaWJ2aXJ0bA==</idAuth>
+ <hostData>bGlidmlydGxpYnZpcnRsaWJ2aXJ0bGlidmlydGxpYnY=</hostData>
+ </launchSecurity>
+</domain>
QEMU_CAPS_SEV_GUEST,
QEMU_CAPS_LAST);
+ DO_TEST_CAPS_ARCH_LATEST("launch-security-sev-snp", "x86_64");
+
DO_TEST_CAPS_ARCH_LATEST("launch-security-s390-pv", "s390x");
DO_TEST_CAPS_LATEST("vhost-user-fs-fd-memory");