systemd-252-44

Resolves: RHEL-50103,RHEL-50651
This commit is contained in:
Lukas Nykryn 2024-08-22 16:56:09 +02:00
parent 79df79b44e
commit e17b63e7f8
6 changed files with 696 additions and 1 deletions

View File

@ -0,0 +1,152 @@
From ae92c09f0ddfea2ff6042e152eec9af86013da38 Mon Sep 17 00:00:00 2001
From: Lukas Nykryn <lnykryn@redhat.com>
Date: Thu, 22 Aug 2024 14:24:42 +0200
Subject: [PATCH] Revert "udev-builtin-net_id: use firmware_node/sun for
ID_NET_NAME_SLOT"
This reverts commit 7af151ca282d506a8e409a68b656f6d1cd2f13fb.
It seems that virtio devices always have "0" in
the firmware_node/sun. And because of that, udev will
always name the device ens0, which leads to collisions.
So let's disable it for now.
rhel-only: policy
Reverts: RHEL-50103
---
man/systemd.net-naming-scheme.xml | 5 +--
src/shared/netif-naming-scheme.h | 3 +-
src/udev/udev-builtin-net_id.c | 66 ++++---------------------------
3 files changed, 10 insertions(+), 64 deletions(-)
diff --git a/man/systemd.net-naming-scheme.xml b/man/systemd.net-naming-scheme.xml
index c9a7e1e493..83293e5636 100644
--- a/man/systemd.net-naming-scheme.xml
+++ b/man/systemd.net-naming-scheme.xml
@@ -510,10 +510,9 @@
to distinguish between devices. However, name conflict can occur if these devices are not
children of the same PCI bridge, e.g. there are multiple PCI bridges in the same slot.
</para>
-
- <para>PCI slot number is now read from <constant>firmware_node/sun</constant> sysfs file.</para>
</listitem>
</varlistentry>
+
</variablelist>
<para>By default <constant>rhel-9.0</constant> is used.</para>
@@ -667,7 +666,7 @@ ID_NET_NAME_ONBOARD_LABEL=Ethernet Port 1
</example>
<example>
- <title>PCI Ethernet card in slot with firmware index number</title>
+ <title>PCI Ethernet card in hotplug slot with firmware index number</title>
<programlisting># /sys/devices/pci0000:00/0000:00:1c.3/0000:05:00.0/net/ens1
ID_NET_NAME_MAC=enx000000000466
diff --git a/src/shared/netif-naming-scheme.h b/src/shared/netif-naming-scheme.h
index b1ac2e4320..5bc071f8db 100644
--- a/src/shared/netif-naming-scheme.h
+++ b/src/shared/netif-naming-scheme.h
@@ -42,7 +42,6 @@ typedef enum NamingSchemeFlags {
* This is disabled since rhel-9.5, as it seems not to work at least for some setups. See upstream issue #28929. */
NAMING_DEVICETREE_ALIASES = 1 << 15, /* Generate names from devicetree aliases */
NAMING_SR_IOV_R = 1 << 17, /* Use "r" suffix for SR-IOV VF representors */
- NAMING_FIRMWARE_NODE_SUN = 1 << 18, /* Use firmware_node/sun to get PCI slot number */
/* And now the masks that combine the features above */
NAMING_V238 = 0,
@@ -74,7 +73,7 @@ typedef enum NamingSchemeFlags {
NAMING_RHEL_9_2 = NAMING_RHEL_9_0,
NAMING_RHEL_9_3 = NAMING_RHEL_9_0 | NAMING_SR_IOV_R,
NAMING_RHEL_9_4 = NAMING_RHEL_9_3,
- NAMING_RHEL_9_5 = (NAMING_RHEL_9_4 & ~NAMING_BRIDGE_MULTIFUNCTION_SLOT) | NAMING_FIRMWARE_NODE_SUN,
+ NAMING_RHEL_9_5 = NAMING_RHEL_9_4 & ~NAMING_BRIDGE_MULTIFUNCTION_SLOT,
EXTRA_NET_NAMING_SCHEMES
diff --git a/src/udev/udev-builtin-net_id.c b/src/udev/udev-builtin-net_id.c
index 291fb4ba36..16c9971876 100644
--- a/src/udev/udev-builtin-net_id.c
+++ b/src/udev/udev-builtin-net_id.c
@@ -442,51 +442,6 @@ static int pci_get_hotplug_slot(sd_device *dev, uint32_t *ret) {
return -ENOENT;
}
-static int get_device_firmware_node_sun(sd_device *dev, uint32_t *ret) {
- const char *attr;
- int r;
-
- assert(dev);
- assert(ret);
-
- r = device_get_sysattr_value_filtered(dev, "firmware_node/sun", &attr);
- if (r < 0)
- return log_device_debug_errno(dev, r, "Failed to read firmware_node/sun, ignoring: %m");
-
- r = safe_atou32(attr, ret);
- if (r < 0)
- return log_device_warning_errno(dev, r, "Failed to parse firmware_node/sun '%s', ignoring: %m", attr);
-
- return 0;
-}
-
-static int pci_get_slot_from_firmware_node_sun(sd_device *dev, uint32_t *ret) {
- int r;
- sd_device *slot_dev;
-
- assert(dev);
- assert(ret);
-
- /* Try getting the ACPI _SUN for the device */
- if (get_device_firmware_node_sun(dev, ret) >= 0)
- return 0;
-
- r = sd_device_get_parent_with_subsystem_devtype(dev, "pci", NULL, &slot_dev);
- if (r < 0)
- return log_device_debug_errno(dev, r, "Failed to find pci parent, ignoring: %m");
-
- if (is_pci_bridge(slot_dev) && is_pci_multifunction(dev) <= 0)
- return log_device_debug_errno(dev, SYNTHETIC_ERRNO(ESTALE),
- "Not using slot information because the parent pcieport "
- "is a bridge and the PCI device is not multifunction.");
-
- /* Try getting the ACPI _SUN from the parent pcieport */
- if (get_device_firmware_node_sun(slot_dev, ret) >= 0)
- return 0;
-
- return -ENOENT;
-}
-
static int dev_pci_slot(sd_device *dev, const LinkInfo *info, NetNames *names) {
const char *sysname, *attr;
unsigned domain, bus, slot, func;
@@ -562,20 +517,13 @@ static int dev_pci_slot(sd_device *dev, const LinkInfo *info, NetNames *names) {
domain, bus, slot, func, strempty(info->phys_port_name), dev_port,
special_glyph(SPECIAL_GLYPH_ARROW_RIGHT), empty_to_na(names->pci_path));
- if (naming_scheme_has(NAMING_FIRMWARE_NODE_SUN))
- r = pci_get_slot_from_firmware_node_sun(names->pcidev, &hotplug_slot);
- else
- r = -1;
- /* If we don't find a slot using firmware_node/sun, fallback to hotplug_slot */
- if (r < 0) {
- r = pci_get_hotplug_slot(names->pcidev, &hotplug_slot);
- if (r < 0)
- return r;
- if (r > 0)
- /* If the hotplug slot is found through the function ID, then drop the domain from the name.
- * See comments in parse_hotplug_slot_from_function_id(). */
- domain = 0;
- }
+ r = pci_get_hotplug_slot(names->pcidev, &hotplug_slot);
+ if (r < 0)
+ return r;
+ if (r > 0)
+ /* If the hotplug slot is found through the function ID, then drop the domain from the name.
+ * See comments in parse_hotplug_slot_from_function_id(). */
+ domain = 0;
s = names->pci_slot;
l = sizeof(names->pci_slot);

View File

@ -0,0 +1,184 @@
From 704f06e7ac11b8e6887b617ae5a0d67854a98e2a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
Date: Thu, 13 Jul 2023 14:02:33 +0100
Subject: [PATCH] fundamental: share constants for confidential virt detection
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
(cherry picked from commit 129b9e3f42d6a2bd92fa7c78ab08a29d6403ddc8)
Related: RHEL-50651
---
src/basic/confidential-virt.c | 67 +----------------
.../confidential-virt-fundamental.h | 72 +++++++++++++++++++
2 files changed, 73 insertions(+), 66 deletions(-)
create mode 100644 src/fundamental/confidential-virt-fundamental.h
diff --git a/src/basic/confidential-virt.c b/src/basic/confidential-virt.c
index 746aa8c313..64067098e5 100644
--- a/src/basic/confidential-virt.c
+++ b/src/basic/confidential-virt.c
@@ -5,10 +5,10 @@
#endif
#include <errno.h>
#include <fcntl.h>
-#include <stdint.h>
#include <stdlib.h>
#include <unistd.h>
+#include "confidential-virt-fundamental.h"
#include "confidential-virt.h"
#include "fd-util.h"
#include "fileio.h"
@@ -16,71 +16,6 @@
#include "string-table.h"
#include "utf8.h"
-#define CPUID_PROCESSOR_INFO_AND_FEATURE_BITS UINT32_C(0x1)
-
-/*
- * AMD64 Architecture Programmers Manual Volume 3:
- * General-Purpose and System Instructions.
- * Chapter: E4.1 - Maximum Extended Function Number and Vendor String
- * https://www.amd.com/system/files/TechDocs/24594.pdf
- */
-#define CPUID_GET_HIGHEST_FUNCTION UINT32_C(0x80000000)
-
-/*
- * AMD64 Architecture Programmers Manual Volume 3:
- * General-Purpose and System Instructions.
- * Chapter: E4.17 - Encrypted Memory Capabilities
- * https://www.amd.com/system/files/TechDocs/24594.pdf
- */
-#define CPUID_AMD_GET_ENCRYPTED_MEMORY_CAPABILITIES UINT32_C(0x8000001f)
-
-/*
- * AMD64 Architecture Programmers Manual Volume 3:
- * General-Purpose and System Instructions.
- * Chapter: 15.34.10 - SEV_STATUS MSR
- * https://www.amd.com/system/files/TechDocs/24593.pdf
- */
-#define MSR_AMD64_SEV UINT32_C(0xc0010131)
-
-/*
- * Intel® TDX Module v1.5 Base Architecture Specification
- * Chapter: 11.2
- * https://www.intel.com/content/www/us/en/content-details/733575/intel-tdx-module-v1-5-base-architecture-specification.html
- */
-
-#define CPUID_INTEL_TDX_ENUMERATION UINT32_C(0x21)
-
-/* Requirements for Implementing the Microsoft Hypervisor Interface
- * https://learn.microsoft.com/en-us/virtualization/hyper-v-on-windows/tlfs/tlfs
- */
-#define CPUID_HYPERV_VENDOR_AND_MAX_FUNCTIONS UINT32_C(0x40000000)
-
-#define CPUID_HYPERV_FEATURES UINT32_C(0x40000003)
-
-#define CPUID_HYPERV_ISOLATION_CONFIG UINT32_C(0x4000000C)
-
-#define CPUID_HYPERV_MIN UINT32_C(0x40000005)
-#define CPUID_HYPERV_MAX UINT32_C(0x4000ffff)
-
-#define CPUID_SIG_AMD "AuthenticAMD"
-#define CPUID_SIG_INTEL "GenuineIntel"
-#define CPUID_SIG_INTEL_TDX "IntelTDX "
-#define CPUID_SIG_HYPERV "Microsoft Hv"
-
-/* ecx bit 31: set => hyperpvisor, unset => bare metal */
-#define CPUID_FEATURE_HYPERVISOR (UINT32_C(1) << 31)
-
-/* Linux include/asm-generic/hyperv-tlfs.h */
-#define CPUID_HYPERV_CPU_MANAGEMENT (UINT32_C(1) << 12) /* root partition */
-#define CPUID_HYPERV_ISOLATION (UINT32_C(1) << 22) /* confidential VM partition */
-
-#define CPUID_HYPERV_ISOLATION_TYPE_MASK UINT32_C(0xf)
-#define CPUID_HYPERV_ISOLATION_TYPE_SNP 2
-
-#define EAX_SEV (UINT32_C(1) << 1)
-#define MSR_SEV (UINT64_C(1) << 0)
-#define MSR_SEV_ES (UINT64_C(1) << 1)
-#define MSR_SEV_SNP (UINT64_C(1) << 2)
#if defined(__x86_64__)
diff --git a/src/fundamental/confidential-virt-fundamental.h b/src/fundamental/confidential-virt-fundamental.h
new file mode 100644
index 0000000000..986923e1c2
--- /dev/null
+++ b/src/fundamental/confidential-virt-fundamental.h
@@ -0,0 +1,72 @@
+/* SPDX-License-Identifier: LGPL-2.1-or-later */
+
+#include <stdint.h>
+
+/* Keep CVM detection logic in this file at feature parity with
+ * that in src/efi/boot/vmm.c */
+
+#define CPUID_PROCESSOR_INFO_AND_FEATURE_BITS UINT32_C(0x1)
+
+/*
+ * AMD64 Architecture Programmers Manual Volume 3:
+ * General-Purpose and System Instructions.
+ * Chapter: E4.1 - Maximum Extended Function Number and Vendor String
+ * https://www.amd.com/system/files/TechDocs/24594.pdf
+ */
+#define CPUID_GET_HIGHEST_FUNCTION UINT32_C(0x80000000)
+
+/*
+ * AMD64 Architecture Programmers Manual Volume 3:
+ * General-Purpose and System Instructions.
+ * Chapter: E4.17 - Encrypted Memory Capabilities
+ * https://www.amd.com/system/files/TechDocs/24594.pdf
+ */
+#define CPUID_AMD_GET_ENCRYPTED_MEMORY_CAPABILITIES UINT32_C(0x8000001f)
+
+/*
+ * AMD64 Architecture Programmers Manual Volume 3:
+ * General-Purpose and System Instructions.
+ * Chapter: 15.34.10 - SEV_STATUS MSR
+ * https://www.amd.com/system/files/TechDocs/24593.pdf
+ */
+#define MSR_AMD64_SEV UINT32_C(0xc0010131)
+
+/*
+ * Intel® TDX Module v1.5 Base Architecture Specification
+ * Chapter: 11.2
+ * https://www.intel.com/content/www/us/en/content-details/733575/intel-tdx-module-v1-5-base-architecture-specification.html
+ */
+
+#define CPUID_INTEL_TDX_ENUMERATION UINT32_C(0x21)
+
+/* Requirements for Implementing the Microsoft Hypervisor Interface
+ * https://learn.microsoft.com/en-us/virtualization/hyper-v-on-windows/tlfs/tlfs
+ */
+#define CPUID_HYPERV_VENDOR_AND_MAX_FUNCTIONS UINT32_C(0x40000000)
+
+#define CPUID_HYPERV_FEATURES UINT32_C(0x40000003)
+
+#define CPUID_HYPERV_ISOLATION_CONFIG UINT32_C(0x4000000C)
+
+#define CPUID_HYPERV_MIN UINT32_C(0x40000005)
+#define CPUID_HYPERV_MAX UINT32_C(0x4000ffff)
+
+#define CPUID_SIG_AMD "AuthenticAMD"
+#define CPUID_SIG_INTEL "GenuineIntel"
+#define CPUID_SIG_INTEL_TDX "IntelTDX "
+#define CPUID_SIG_HYPERV "Microsoft Hv"
+
+/* ecx bit 31: set => hyperpvisor, unset => bare metal */
+#define CPUID_FEATURE_HYPERVISOR (UINT32_C(1) << 31)
+
+/* Linux include/asm-generic/hyperv-tlfs.h */
+#define CPUID_HYPERV_CPU_MANAGEMENT (UINT32_C(1) << 12) /* root partition */
+#define CPUID_HYPERV_ISOLATION (UINT32_C(1) << 22) /* confidential VM partition */
+
+#define CPUID_HYPERV_ISOLATION_TYPE_MASK UINT32_C(0xf)
+#define CPUID_HYPERV_ISOLATION_TYPE_SNP 2
+
+#define EAX_SEV (UINT32_C(1) << 1)
+#define MSR_SEV (UINT64_C(1) << 0)
+#define MSR_SEV_ES (UINT64_C(1) << 1)
+#define MSR_SEV_SNP (UINT64_C(1) << 2)

View File

@ -0,0 +1,168 @@
From d8753fd5e71a4be0e99ecbbbfa052cb7bd90d717 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
Date: Fri, 7 Jul 2023 16:28:19 +0100
Subject: [PATCH] efi: add helper API for detecting confidential virtualization
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
This helper is a simplified version of detect_confidential_virtualization()
that merely returns a boolean status flag reflecting whether we are believed
to be running inside a confidential VM.
This flag can be used for turning off features that are inappropriate to
use from a CVM, but must not be used for releasing sensitive data. The
latter must only be done in response to an attestation for the environment.
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
(cherry picked from commit b354a2cafc8ea38b4551aa3e4f078f1d7aa40c7c)
Related: RHEL-50651
---
src/boot/efi/vmm.c | 117 +++++++++++++++++++++++++++++++++++++++++++++
src/boot/efi/vmm.h | 2 +
2 files changed, 119 insertions(+)
diff --git a/src/boot/efi/vmm.c b/src/boot/efi/vmm.c
index f9a59dca0a..214f8f7024 100644
--- a/src/boot/efi/vmm.c
+++ b/src/boot/efi/vmm.c
@@ -7,6 +7,7 @@
# include <cpuid.h>
#endif
+#include "confidential-virt-fundamental.h"
#include "drivers.h"
#include "efi-string.h"
#include "string-util-fundamental.h"
@@ -323,3 +324,119 @@ const char* smbios_find_oem_string(const char *name) {
return NULL;
}
+
+#if defined(__i386__) || defined(__x86_64__)
+static uint32_t cpuid_leaf(uint32_t eax, char ret_sig[static 13], bool swapped) {
+ /* zero-init as some queries explicitly require subleaf == 0 */
+ uint32_t sig[3] = {};
+
+ if (swapped)
+ __cpuid_count(eax, 0, eax, sig[0], sig[2], sig[1]);
+ else
+ __cpuid_count(eax, 0, eax, sig[0], sig[1], sig[2]);
+
+ memcpy(ret_sig, sig, sizeof(sig));
+ ret_sig[12] = 0; /* \0-terminate the string to make string comparison possible */
+
+ return eax;
+}
+
+static uint64_t msr(uint32_t index) {
+ uint64_t val;
+#ifdef __x86_64__
+ uint32_t low, high;
+ asm volatile ("rdmsr" : "=a"(low), "=d"(high) : "c"(index) : "memory");
+ val = ((uint64_t)high << 32) | low;
+#else
+ asm volatile ("rdmsr" : "=A"(val) : "c"(index) : "memory");
+#endif
+ return val;
+}
+
+static bool detect_hyperv_sev(void) {
+ uint32_t eax, ebx, ecx, edx, feat;
+ char sig[13] = {};
+
+ feat = cpuid_leaf(CPUID_HYPERV_VENDOR_AND_MAX_FUNCTIONS, sig, false);
+
+ if (feat < CPUID_HYPERV_MIN || feat > CPUID_HYPERV_MAX)
+ return false;
+
+ if (memcmp(sig, CPUID_SIG_HYPERV, sizeof(sig)) != 0)
+ return false;
+
+ __cpuid(CPUID_HYPERV_FEATURES, eax, ebx, ecx, edx);
+
+ if (ebx & CPUID_HYPERV_ISOLATION && !(ebx & CPUID_HYPERV_CPU_MANAGEMENT)) {
+ __cpuid(CPUID_HYPERV_ISOLATION_CONFIG, eax, ebx, ecx, edx);
+
+ if ((ebx & CPUID_HYPERV_ISOLATION_TYPE_MASK) == CPUID_HYPERV_ISOLATION_TYPE_SNP)
+ return true;
+ }
+
+ return false;
+}
+
+static bool detect_sev(void) {
+ uint32_t eax, ebx, ecx, edx;
+ uint64_t msrval;
+
+ __cpuid(CPUID_GET_HIGHEST_FUNCTION, eax, ebx, ecx, edx);
+
+ if (eax < CPUID_AMD_GET_ENCRYPTED_MEMORY_CAPABILITIES)
+ return false;
+
+ __cpuid(CPUID_AMD_GET_ENCRYPTED_MEMORY_CAPABILITIES, eax, ebx, ecx, edx);
+
+ /* bit 1 == CPU supports SEV feature
+ *
+ * Note, Azure blocks this CPUID leaf from its SEV-SNP
+ * guests, so we must fallback to trying some HyperV
+ * specific CPUID checks.
+ */
+ if (!(eax & EAX_SEV))
+ return detect_hyperv_sev();
+
+ msrval = msr(MSR_AMD64_SEV);
+
+ if (msrval & (MSR_SEV_SNP | MSR_SEV_ES | MSR_SEV))
+ return true;
+
+ return false;
+}
+
+static bool detect_tdx(void) {
+ uint32_t eax, ebx, ecx, edx;
+ char sig[13] = {};
+
+ __cpuid(CPUID_GET_HIGHEST_FUNCTION, eax, ebx, ecx, edx);
+
+ if (eax < CPUID_INTEL_TDX_ENUMERATION)
+ return false;
+
+ cpuid_leaf(CPUID_INTEL_TDX_ENUMERATION, sig, true);
+
+ if (memcmp(sig, CPUID_SIG_INTEL_TDX, sizeof(sig)) == 0)
+ return true;
+
+ return false;
+}
+#endif /* ! __i386__ && ! __x86_64__ */
+
+bool is_confidential_vm(void) {
+#if defined(__i386__) || defined(__x86_64__)
+ char sig[13] = {};
+
+ if (!cpuid_in_hypervisor())
+ return false;
+
+ cpuid_leaf(0, sig, true);
+
+ if (memcmp(sig, CPUID_SIG_AMD, sizeof(sig)) == 0)
+ return detect_sev();
+ if (memcmp(sig, CPUID_SIG_INTEL, sizeof(sig)) == 0)
+ return detect_tdx();
+#endif /* ! __i386__ && ! __x86_64__ */
+
+ return false;
+}
diff --git a/src/boot/efi/vmm.h b/src/boot/efi/vmm.h
index 2002f32bec..55c12039d2 100644
--- a/src/boot/efi/vmm.h
+++ b/src/boot/efi/vmm.h
@@ -9,4 +9,6 @@ EFI_STATUS vmm_open(EFI_HANDLE *ret_qemu_dev, EFI_FILE **ret_qemu_dir);
bool in_hypervisor(void);
+bool is_confidential_vm(void);
+
const char* smbios_find_oem_string(const char *name);

View File

@ -0,0 +1,58 @@
From 23d58876e6301dd33f0f039a2cacb95a340dc2ea Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
Date: Fri, 7 Jul 2023 16:30:20 +0100
Subject: [PATCH] efi: don't pull kernel cmdline from SMBIOS in a confidential
VM
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
In a confidential VM, the SMBIOS data is not trusted, as it is under the
control of the host OS/admin and not covered by attestation of the machine.
Fixes: https://github.com/systemd/systemd/issues/27604
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
(cherry picked from commit 4b1153cfcc397df5a095f2ec7e587787e8ba47ee)
Related: RHEL-50651
---
src/boot/efi/stub.c | 26 +++++++++++++++-----------
1 file changed, 15 insertions(+), 11 deletions(-)
diff --git a/src/boot/efi/stub.c b/src/boot/efi/stub.c
index 2c7c56de3e..93843f015a 100644
--- a/src/boot/efi/stub.c
+++ b/src/boot/efi/stub.c
@@ -494,17 +494,21 @@ static EFI_STATUS real_main(EFI_HANDLE image) {
log_error_status(err, "Error loading UKI-specific addons, ignoring: %m");
parameters_measured = parameters_measured < 0 ? m : (parameters_measured && m);
- const char *extra = smbios_find_oem_string("io.systemd.stub.kernel-cmdline-extra");
- if (extra) {
- _cleanup_free_ char16_t *tmp = TAKE_PTR(cmdline), *extra16 = xstr8_to_16(extra);
- cmdline = xasprintf("%ls %ls", tmp, extra16);
-
- /* SMBIOS strings are measured in PCR1, but we also want to measure them in our specific
- * PCR12, as firmware-owned PCRs are very difficult to use as they'll contain unpredictable
- * measurements that are not under control of the machine owner. */
- m = false;
- (void) tpm_log_load_options(extra16, &m);
- parameters_measured = parameters_measured < 0 ? m : (parameters_measured && m);
+ /* SMBIOS OEM Strings data is controlled by the host admin and not covered
+ * by the VM attestation, so MUST NOT be trusted when in a confidential VM */
+ if (!is_confidential_vm()) {
+ const char *extra = smbios_find_oem_string("io.systemd.stub.kernel-cmdline-extra");
+ if (extra) {
+ _cleanup_free_ char16_t *tmp = TAKE_PTR(cmdline), *extra16 = xstr8_to_16(extra);
+ cmdline = xasprintf("%ls %ls", tmp, extra16);
+
+ /* SMBIOS strings are measured in PCR1, but we also want to measure them in our specific
+ * PCR12, as firmware-owned PCRs are very difficult to use as they'll contain unpredictable
+ * measurements that are not under control of the machine owner. */
+ m = false;
+ (void) tpm_log_load_options(extra16, &m);
+ parameters_measured = parameters_measured < 0 ? m : (parameters_measured && m);
+ }
}
export_variables(loaded_image);

View File

@ -0,0 +1,121 @@
From adb6c21257cf8b077e8d55c3326549a671a70481 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
Date: Tue, 30 Jul 2024 10:51:21 +0100
Subject: [PATCH] Fix detection of TDX confidential VM on Azure platform
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The original CVM detection logic for TDX assumes that the guest can see
the standard TDX CPUID leaf. This was true in Azure when this code was
originally written, however, current Azure now blocks that leaf in the
paravisor. Instead it is required to use the same Azure specific CPUID
leaf that is used for SEV-SNP detection, which reports the VM isolation
type.
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
(cherry picked from commit 9d7be044cad1ae54e344daf8f2ec37da46faf0fd)
Related: RHEL-50651
---
src/basic/confidential-virt.c | 11 ++++++++---
src/boot/efi/vmm.c | 9 ++++++---
src/fundamental/confidential-virt-fundamental.h | 1 +
3 files changed, 15 insertions(+), 6 deletions(-)
diff --git a/src/basic/confidential-virt.c b/src/basic/confidential-virt.c
index 64067098e5..0929e0e745 100644
--- a/src/basic/confidential-virt.c
+++ b/src/basic/confidential-virt.c
@@ -77,7 +77,7 @@ static uint64_t msr(uint64_t index) {
return ret;
}
-static bool detect_hyperv_sev(void) {
+static bool detect_hyperv_cvm(uint32_t isoltype) {
uint32_t eax, ebx, ecx, edx, feat;
char sig[13] = {};
@@ -101,7 +101,7 @@ static bool detect_hyperv_sev(void) {
ebx = ecx = edx = 0;
cpuid(&eax, &ebx, &ecx, &edx);
- if ((ebx & CPUID_HYPERV_ISOLATION_TYPE_MASK) == CPUID_HYPERV_ISOLATION_TYPE_SNP)
+ if ((ebx & CPUID_HYPERV_ISOLATION_TYPE_MASK) == isoltype)
return true;
}
@@ -134,7 +134,7 @@ static ConfidentialVirtualization detect_sev(void) {
if (!(eax & EAX_SEV)) {
log_debug("No sev in CPUID, trying hyperv CPUID");
- if (detect_hyperv_sev())
+ if (detect_hyperv_cvm(CPUID_HYPERV_ISOLATION_TYPE_SNP))
return CONFIDENTIAL_VIRTUALIZATION_SEV_SNP;
log_debug("No hyperv CPUID");
@@ -172,6 +172,11 @@ static ConfidentialVirtualization detect_tdx(void) {
if (memcmp(sig, CPUID_SIG_INTEL_TDX, sizeof(sig)) == 0)
return CONFIDENTIAL_VIRTUALIZATION_TDX;
+ log_debug("No tdx in CPUID, trying hyperv CPUID");
+
+ if (detect_hyperv_cvm(CPUID_HYPERV_ISOLATION_TYPE_TDX))
+ return CONFIDENTIAL_VIRTUALIZATION_TDX;
+
return CONFIDENTIAL_VIRTUALIZATION_NONE;
}
diff --git a/src/boot/efi/vmm.c b/src/boot/efi/vmm.c
index 214f8f7024..153cafba4e 100644
--- a/src/boot/efi/vmm.c
+++ b/src/boot/efi/vmm.c
@@ -353,7 +353,7 @@ static uint64_t msr(uint32_t index) {
return val;
}
-static bool detect_hyperv_sev(void) {
+static bool detect_hyperv_cvm(uint32_t isoltype) {
uint32_t eax, ebx, ecx, edx, feat;
char sig[13] = {};
@@ -370,7 +370,7 @@ static bool detect_hyperv_sev(void) {
if (ebx & CPUID_HYPERV_ISOLATION && !(ebx & CPUID_HYPERV_CPU_MANAGEMENT)) {
__cpuid(CPUID_HYPERV_ISOLATION_CONFIG, eax, ebx, ecx, edx);
- if ((ebx & CPUID_HYPERV_ISOLATION_TYPE_MASK) == CPUID_HYPERV_ISOLATION_TYPE_SNP)
+ if ((ebx & CPUID_HYPERV_ISOLATION_TYPE_MASK) == isoltype)
return true;
}
@@ -395,7 +395,7 @@ static bool detect_sev(void) {
* specific CPUID checks.
*/
if (!(eax & EAX_SEV))
- return detect_hyperv_sev();
+ return detect_hyperv_cvm(CPUID_HYPERV_ISOLATION_TYPE_SNP);
msrval = msr(MSR_AMD64_SEV);
@@ -419,6 +419,9 @@ static bool detect_tdx(void) {
if (memcmp(sig, CPUID_SIG_INTEL_TDX, sizeof(sig)) == 0)
return true;
+ if (detect_hyperv_cvm(CPUID_HYPERV_ISOLATION_TYPE_TDX))
+ return true;
+
return false;
}
#endif /* ! __i386__ && ! __x86_64__ */
diff --git a/src/fundamental/confidential-virt-fundamental.h b/src/fundamental/confidential-virt-fundamental.h
index 986923e1c2..618b5800ea 100644
--- a/src/fundamental/confidential-virt-fundamental.h
+++ b/src/fundamental/confidential-virt-fundamental.h
@@ -65,6 +65,7 @@
#define CPUID_HYPERV_ISOLATION_TYPE_MASK UINT32_C(0xf)
#define CPUID_HYPERV_ISOLATION_TYPE_SNP 2
+#define CPUID_HYPERV_ISOLATION_TYPE_TDX 3
#define EAX_SEV (UINT32_C(1) << 1)
#define MSR_SEV (UINT64_C(1) << 0)

View File

@ -25,7 +25,7 @@
Name: systemd
Url: https://systemd.io
Version: 252
Release: 43%{?dist}
Release: 44%{?dist}
# For a breakdown of the licensing, see README
License: LGPLv2+ and MIT and GPLv2+
Summary: System and Service Manager
@ -1125,6 +1125,11 @@ Patch1033: 1033-udev-add-conf-virt-constant-for-confidential-virtual.patch
Patch1034: 1034-confidential-virt-split-caching-of-CVM-detection-int.patch
Patch1035: 1035-confidential-virt-add-detection-for-s390x-target.patch
Patch1036: 1036-man-systemd-detect-virt-list-known-CVM-technologies.patch
Patch1037: 1037-Revert-udev-builtin-net_id-use-firmware_node-sun-for.patch
Patch1038: 1038-fundamental-share-constants-for-confidential-virt-de.patch
Patch1039: 1039-efi-add-helper-API-for-detecting-confidential-virtua.patch
Patch1040: 1040-efi-don-t-pull-kernel-cmdline-from-SMBIOS-in-a-confi.patch
Patch1041: 1041-Fix-detection-of-TDX-confidential-VM-on-Azure-platfo.patch
# Downstream-only patches (90009999)
@ -2007,6 +2012,13 @@ systemd-hwdb update &>/dev/null || :
%{_prefix}/lib/dracut/modules.d/70rhel-net-naming-sysattrs/*
%changelog
* Thu Aug 22 2024 systemd maintenance team <systemd-maint@redhat.com> - 252-44
- Revert "udev-builtin-net_id: use firmware_node/sun for ID_NET_NAME_SLOT" (RHEL-50103)
- fundamental: share constants for confidential virt detection (RHEL-50651)
- efi: add helper API for detecting confidential virtualization (RHEL-50651)
- efi: don't pull kernel cmdline from SMBIOS in a confidential VM (RHEL-50651)
- Fix detection of TDX confidential VM on Azure platform (RHEL-50651)
* Thu Aug 22 2024 systemd maintenance team <systemd-maint@redhat.com> - 252-43
- udev-builtin-net_id: skip non-directory entry earlier (RHEL-50103)
- udev-builtin-net_id: return earlier when hotplug slot is not found (RHEL-50103)