[SRU][N:linux-intel][PATCH 1/2] UBUNTU: SAUCE: KVM: TDX: Use guest physical address to configure EPT level and GPAW

Thibault Ferrante thibault.ferrante at canonical.com
Thu Feb 20 11:09:11 UTC 2025


From: Xiaoyao Li <xiaoyao.li at intel.com>

BugLink: https://bugs.launchpad.net/bugs/2098952

KVM reports guest physical address in CPUID.0x800000008.EAX[23:16],
which is similar to TDX's GPAW. Use this field as the interface for
userspace to configure the GPAW and EPT level for TDs.

Note,

1. only value 48 and 52 are supported. 52 means GPAW-52 and EPT level
   5, and 48 means GPAW-48 and EPT level 4.
2. value 48, i.e., GPAW-48 is always supported. value 52 is only
   supported when the platform supports 5 level EPT.

Current TDX module doesn't support max_gpa configuration. However
current implementation relies on max_gpa to configure  EPT level and
GPAW. Hack KVM to make it work.

Signed-off-by: Xiaoyao Li <xiaoyao.li at intel.com>
Signed-off-by: Rick Edgecombe <rick.p.edgecombe at intel.com>
(backported from https://lore.kernel.org/all/20240812224820.34826-23-rick.p.edgecombe@intel.com/)
[thibf: setup_kvm_tdx_caps doesn't exist in current tree, skip this part]
Signed-off-by: Thibault Ferrante <thibault.ferrante at canonical.com>
---
 arch/x86/kvm/vmx/tdx.c | 26 +++++++++++++-------------
 1 file changed, 13 insertions(+), 13 deletions(-)

diff --git a/arch/x86/kvm/vmx/tdx.c b/arch/x86/kvm/vmx/tdx.c
index a1d3ae09091c..85700fb90665 100644
--- a/arch/x86/kvm/vmx/tdx.c
+++ b/arch/x86/kvm/vmx/tdx.c
@@ -2345,23 +2345,21 @@ static int setup_tdparams_eptp_controls(struct kvm_cpuid2 *cpuid,
 					struct td_params *td_params)
 {
 	const struct kvm_cpuid_entry2 *entry;
-	int max_pa = 36;
+	int guest_pa;
 
 	entry = kvm_find_cpuid_entry2(cpuid->entries, cpuid->nent, 0x80000008, 0);
-	if (entry)
-		max_pa = entry->eax & 0xff;
+	if (!entry)
+		return -EINVAL;
+	guest_pa = (entry->eax >> 16) & 0xff;
 
-	td_params->eptp_controls = VMX_EPTP_MT_WB;
-	/*
-	 * No CPU supports 4-level && max_pa > 48.
-	 * "5-level paging and 5-level EPT" section 4.1 4-level EPT
-	 * "4-level EPT is limited to translating 48-bit guest-physical
-	 *  addresses."
-	 * cpu_has_vmx_ept_5levels() check is just in case.
-	 */
-	if (!cpu_has_vmx_ept_5levels() && max_pa > 48)
+	if (guest_pa != 48 && guest_pa != 52)
 		return -EINVAL;
-	if (cpu_has_vmx_ept_5levels() && max_pa > 48) {
+
+	if (guest_pa == 52 && !cpu_has_vmx_ept_5levels())
+		return -EINVAL;
+
+	td_params->eptp_controls = VMX_EPTP_MT_WB;
+	if (guest_pa == 52) {
 		td_params->eptp_controls |= VMX_EPTP_PWL_5;
 		td_params->exec_controls |= TDX_EXEC_CONTROL_MAX_GPAW;
 	} else {
@@ -2406,6 +2404,8 @@ static void setup_tdparams_cpuids(struct kvm *kvm, struct kvm_cpuid2 *cpuid,
 		value->ecx = entry->ecx & c->ecx;
 		value->edx = entry->edx & c->edx;
 
+		if (c->leaf == 0x80000008)
+			value->eax &= 0xff00ffff;
 		/* Remember the setting to check for KVM_SET_CPUID2. */
 		kvm_tdx->cpuid[kvm_tdx->cpuid_nent] = *entry;
 		kvm_tdx->cpuid_nent++;
-- 
2.43.0




More information about the kernel-team mailing list