145 lines
4.7 KiB
Diff
145 lines
4.7 KiB
Diff
From d228f2ad7fb96be3ec1fa3256ee0404cf7e2b094 Mon Sep 17 00:00:00 2001
|
|
From: Paolo Bonzini <pbonzini@redhat.com>
|
|
Date: Fri, 18 Jul 2025 18:03:48 +0200
|
|
Subject: [PATCH 075/115] i386/tdx: Add supported CPUID bits related to TD
|
|
Attributes
|
|
|
|
RH-Author: Paolo Bonzini <pbonzini@redhat.com>
|
|
RH-MergeRequest: 391: TDX support, including attestation and device assignment
|
|
RH-Jira: RHEL-15710 RHEL-20798 RHEL-49728
|
|
RH-Acked-by: Yash Mankad <None>
|
|
RH-Acked-by: Peter Xu <peterx@redhat.com>
|
|
RH-Acked-by: David Hildenbrand <david@redhat.com>
|
|
RH-Commit: [75/115] 095f42329711d2cb7f147856ebf2775a522fd8e3 (bonzini/rhel-qemu-kvm)
|
|
|
|
For TDX, some CPUID feature bit is configured via TD attributes. They
|
|
are not covered by tdx_caps.cpuid (which only contians the directly
|
|
configurable CPUID bits), but they are actually supported when the
|
|
related attributre bit is supported.
|
|
|
|
Note, LASS and KeyLocker are not supported by KVM for TDX, nor does
|
|
QEMU support it (see TDX_SUPPORTED_TD_ATTRS). They are defined in
|
|
tdx_attrs_maps[] for the completeness of the existing TD Attribute
|
|
bits that are related with CPUID features.
|
|
|
|
Signed-off-by: Xiaoyao Li <xiaoyao.li@intel.com>
|
|
Link: https://lore.kernel.org/r/20250508150002.689633-47-xiaoyao.li@intel.com
|
|
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
|
|
(cherry picked from commit 31df29c532a9ef473c6efd497950a620099bf1da)
|
|
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
|
|
---
|
|
target/i386/cpu.h | 4 +++
|
|
target/i386/kvm/tdx.c | 60 +++++++++++++++++++++++++++++++++++++++++++
|
|
2 files changed, 64 insertions(+)
|
|
|
|
diff --git a/target/i386/cpu.h b/target/i386/cpu.h
|
|
index 529f24df00..e02cb75619 100644
|
|
--- a/target/i386/cpu.h
|
|
+++ b/target/i386/cpu.h
|
|
@@ -903,6 +903,8 @@ uint64_t x86_cpu_get_supported_feature_word(X86CPU *cpu, FeatureWord w);
|
|
#define CPUID_7_0_ECX_LA57 (1U << 16)
|
|
/* Read Processor ID */
|
|
#define CPUID_7_0_ECX_RDPID (1U << 22)
|
|
+/* KeyLocker */
|
|
+#define CPUID_7_0_ECX_KeyLocker (1U << 23)
|
|
/* Bus Lock Debug Exception */
|
|
#define CPUID_7_0_ECX_BUS_LOCK_DETECT (1U << 24)
|
|
/* Cache Line Demote Instruction */
|
|
@@ -963,6 +965,8 @@ uint64_t x86_cpu_get_supported_feature_word(X86CPU *cpu, FeatureWord w);
|
|
#define CPUID_7_1_EAX_AVX_VNNI (1U << 4)
|
|
/* AVX512 BFloat16 Instruction */
|
|
#define CPUID_7_1_EAX_AVX512_BF16 (1U << 5)
|
|
+/* Linear address space separation */
|
|
+#define CPUID_7_1_EAX_LASS (1U << 6)
|
|
/* CMPCCXADD Instructions */
|
|
#define CPUID_7_1_EAX_CMPCCXADD (1U << 7)
|
|
/* Fast Zero REP MOVS */
|
|
diff --git a/target/i386/kvm/tdx.c b/target/i386/kvm/tdx.c
|
|
index 6fa30c3ec4..60dd239c05 100644
|
|
--- a/target/i386/kvm/tdx.c
|
|
+++ b/target/i386/kvm/tdx.c
|
|
@@ -458,6 +458,34 @@ KvmCpuidInfo tdx_fixed1_bits = {
|
|
},
|
|
};
|
|
|
|
+typedef struct TdxAttrsMap {
|
|
+ uint32_t attr_index;
|
|
+ uint32_t cpuid_leaf;
|
|
+ uint32_t cpuid_subleaf;
|
|
+ int cpuid_reg;
|
|
+ uint32_t feat_mask;
|
|
+} TdxAttrsMap;
|
|
+
|
|
+static TdxAttrsMap tdx_attrs_maps[] = {
|
|
+ {.attr_index = 27,
|
|
+ .cpuid_leaf = 7,
|
|
+ .cpuid_subleaf = 1,
|
|
+ .cpuid_reg = R_EAX,
|
|
+ .feat_mask = CPUID_7_1_EAX_LASS,},
|
|
+
|
|
+ {.attr_index = 30,
|
|
+ .cpuid_leaf = 7,
|
|
+ .cpuid_subleaf = 0,
|
|
+ .cpuid_reg = R_ECX,
|
|
+ .feat_mask = CPUID_7_0_ECX_PKS,},
|
|
+
|
|
+ {.attr_index = 31,
|
|
+ .cpuid_leaf = 7,
|
|
+ .cpuid_subleaf = 0,
|
|
+ .cpuid_reg = R_ECX,
|
|
+ .feat_mask = CPUID_7_0_ECX_KeyLocker,},
|
|
+};
|
|
+
|
|
static struct kvm_cpuid_entry2 *find_in_supported_entry(uint32_t function,
|
|
uint32_t index)
|
|
{
|
|
@@ -494,6 +522,37 @@ static void tdx_add_supported_cpuid_by_fixed1_bits(void)
|
|
}
|
|
}
|
|
|
|
+static void tdx_add_supported_cpuid_by_attrs(void)
|
|
+{
|
|
+ struct kvm_cpuid_entry2 *e;
|
|
+ TdxAttrsMap *map;
|
|
+ int i;
|
|
+
|
|
+ for (i = 0; i < ARRAY_SIZE(tdx_attrs_maps); i++) {
|
|
+ map = &tdx_attrs_maps[i];
|
|
+ if (!((1ULL << map->attr_index) & tdx_caps->supported_attrs)) {
|
|
+ continue;
|
|
+ }
|
|
+
|
|
+ e = find_in_supported_entry(map->cpuid_leaf, map->cpuid_subleaf);
|
|
+
|
|
+ switch(map->cpuid_reg) {
|
|
+ case R_EAX:
|
|
+ e->eax |= map->feat_mask;
|
|
+ break;
|
|
+ case R_EBX:
|
|
+ e->ebx |= map->feat_mask;
|
|
+ break;
|
|
+ case R_ECX:
|
|
+ e->ecx |= map->feat_mask;
|
|
+ break;
|
|
+ case R_EDX:
|
|
+ e->edx |= map->feat_mask;
|
|
+ break;
|
|
+ }
|
|
+ }
|
|
+}
|
|
+
|
|
static void tdx_setup_supported_cpuid(void)
|
|
{
|
|
if (tdx_supported_cpuid) {
|
|
@@ -508,6 +567,7 @@ static void tdx_setup_supported_cpuid(void)
|
|
tdx_supported_cpuid->nent = tdx_caps->cpuid.nent;
|
|
|
|
tdx_add_supported_cpuid_by_fixed1_bits();
|
|
+ tdx_add_supported_cpuid_by_attrs();
|
|
}
|
|
|
|
static int tdx_kvm_init(ConfidentialGuestSupport *cgs, Error **errp)
|
|
--
|
|
2.50.1
|
|
|